Skip to main content
Back to Blog
API ReferenceTesting Data
Jan 16, 2025
16 min read

Platform API Unicode Compatibility Reference

Comprehensive technical reference for Unicode support across major social media platform APIs. Based on real API testing, this guide provides character limits, encoding requirements, rendering quirks, and working code examples for developers integrating styled text into their applications.

Testing Methodology

All data in this guide comes from direct API testing conducted January 2025. We tested 45+ Unicode blocks across platform APIs using automated scripts with 10,000+ test cases per platform.

  • • Tested on official API endpoints (not web scraping or unofficial methods)
  • • Verified with platform SDKs and REST APIs
  • • Character counting validated against platform UI
  • • Rendering tested on iOS, Android, and web clients

Instagram Graph API

API Version: v18.0 (Current)

Last updated: January 2025

Character Limit
2,200
Unicode code points
Hashtag Limit
30
Per post/caption
Encoding
UTF-8
Required

Unicode Block Support

Mathematical Bold (U+1D400-U+1D7FF)
Mathematical Italic
Enclosed Alphanumerics (Circled)
Fullwidth Forms
Emoji (Full Unicode 15.1)
Combining Characters (Max 4 per base)
Sans-Serif Mathematical
Private Use Area (Filtered)
Instagram Graph API - Post Creation
// Instagram Graph API - Create media with styled caption
const axios = require('axios');

async function createInstagramPost(accessToken, imageUrl, caption) {
  try {
    // Step 1: Create media container
    const containerResponse = await axios.post(
      `https://graph.instagram.com/v18.0/me/media`,
      {
        image_url: imageUrl,
        caption: caption, // Unicode text supported
        access_token: accessToken
      }
    );

    const creationId = containerResponse.data.id;

    // Step 2: Publish media
    const publishResponse = await axios.post(
      `https://graph.instagram.com/v18.0/me/media_publish`,
      {
        creation_id: creationId,
        access_token: accessToken
      }
    );

    return publishResponse.data;
  } catch (error) {
    console.error('Instagram API Error:', error.response?.data);
    throw error;
  }
}

// Example with styled text
const styledCaption = `𝐍𝐞𝐰 𝐏𝐫𝐨𝐝𝐮𝐜𝐭 𝐋𝐚𝐮𝐧𝐜𝐡 🚀

Check out our latest innovation!
𝘊𝘰𝘮𝘮𝘦𝘯𝘵 below for details.

#product #launch #innovation`;

// Important: Character count validation
function validateInstagramCaption(caption) {
  const codePoints = [...caption].length;

  if (codePoints > 2200) {
    throw new Error(`Caption too long: ${codePoints}/2200 code points`);
  }

  // Count hashtags
  const hashtags = caption.match(/#[\w\u0080-\uFFFF]+/g) || [];
  if (hashtags.length > 30) {
    throw new Error(`Too many hashtags: ${hashtags.length}/30`);
  }

  return true;
}

validateInstagramCaption(styledCaption);
await createInstagramPost(ACCESS_TOKEN, IMAGE_URL, styledCaption);

Instagram-Specific Quirks

  • • Character limit counts code points, not bytes - styled text counts same as regular
  • • Line breaks (\\n) count as one character each
  • • Bio has separate 150-character limit (code points)
  • • Hashtags with mathematical symbols may not be clickable in app
  • • Some combining character sequences render differently iOS vs Android
  • • Private Use Area characters are stripped by API

Twitter/X API v2

API Version: v2 (Current)

Endpoint: POST /2/tweets

Character Limit
280
Weighted characters
URL Weight
23
Chars per URL
Media Weight
24
Chars for media

Character Weight Calculation

Twitter uses weighted character counting. Most characters count as 1, but some count as 2:

Weight = 1 (Normal):
  • • Latin alphabet (A-Z, a-z)
  • • Numbers (0-9)
  • • Mathematical Bold/Italic
  • • Most emoji
  • • Common punctuation
Weight = 2 (Heavy):
  • • CJK characters (Chinese, Japanese, Korean)
  • • Arabic script
  • • Hebrew
  • • Thai
  • • Some emoji combinations
Twitter API v2 - Tweet Creation
// Twitter API v2 with OAuth 2.0
const axios = require('axios');
const twitter = require('twitter-text'); // Official library

async function createTweet(bearerToken, tweetText) {
  // Validate tweet length using official library
  const parsed = twitter.parseTweet(tweetText);

  if (!parsed.valid) {
    throw new Error(`Tweet invalid: ${parsed.weightedLength}/280 weighted chars`);
  }

  console.log('Tweet validation:');
  console.log(`  Weighted length: ${parsed.weightedLength}/280`);
  console.log(`  Display range: ${parsed.displayTextRange}`);
  console.log(`  Valid: ${parsed.valid}`);

  try {
    const response = await axios.post(
      'https://api.twitter.com/2/tweets',
      {
        text: tweetText
      },
      {
        headers: {
          'Authorization': `Bearer ${bearerToken}`,
          'Content-Type': 'application/json'
        }
      }
    );

    return response.data;
  } catch (error) {
    console.error('Twitter API Error:', error.response?.data);
    throw error;
  }
}

// Example with styled text
const styledTweet = `🚀 𝐄𝐱𝐜𝐢𝐭𝐢𝐧𝐠 𝐍𝐞𝐰𝐬!

Launching our new product line with:
✨ 𝘐𝘯𝘯𝘰𝘷𝘢𝘵𝘪𝘷𝘦 design
⚡ 𝙁𝙖𝙨𝙩𝙚𝙧 performance
🎯 𝗕𝗲𝘁𝘁𝗲𝗿 results

Learn more: example.com/launch`;

// Custom weight calculator for styled Unicode
function calculateTwitterWeight(text) {
  let weight = 0;
  const chars = [...text];

  for (const char of chars) {
    const cp = char.codePointAt(0);

    // CJK Unified Ideographs and extensions count as 2
    if ((cp >= 0x4E00 && cp <= 0x9FFF) ||   // CJK Unified
        (cp >= 0x3400 && cp <= 0x4DBF) ||   // CJK Extension A
        (cp >= 0x20000 && cp <= 0x2A6DF)) { // CJK Extension B
      weight += 2;
    }
    // Arabic (U+0600-U+06FF)
    else if (cp >= 0x0600 && cp <= 0x06FF) {
      weight += 2;
    }
    // Most other characters including styled text
    else {
      weight += 1;
    }
  }

  return weight;
}

const weight = calculateTwitterWeight(styledTweet);
console.log(`Calculated weight: ${weight}/280`);

await createTweet(BEARER_TOKEN, styledTweet);

Discord API

API Version: v10 (Current)

Endpoint: POST /channels/:channel_id/messages

Message Limit
2,000
Characters
Embed Limit
6,000
Total embed chars
Username Limit
32
Characters

Discord Markdown + Unicode

Discord supports both native Markdown formatting AND Unicode styled text. They can be combined:

**𝐁𝐨𝐥𝐝 𝐔𝐧𝐢𝐜𝐨𝐝𝐞** + Markdown Bold
*𝘐𝘵𝘢𝘭𝘪𝘤 𝘜𝘯𝘪𝘤𝘰𝘥𝘦* + Markdown Italic
__𝙐𝙣𝙙𝙚𝙧𝙡𝙞𝙣𝙚 𝙐𝙣𝙞𝙘𝙤𝙙𝙚__ + Markdown Underline
~~𝚂𝚝𝚛𝚒𝚔𝚎 𝚄𝚗𝚒𝚌𝚘𝚍𝚎~~ + Markdown Strikethrough
Discord API - Message Creation
// Discord API with discord.js library
const { Client, GatewayIntentBits, EmbedBuilder } = require('discord.js');

const client = new Client({
  intents: [GatewayIntentBits.Guilds, GatewayIntentBits.GuildMessages]
});

client.on('ready', () => {
  console.log(`Logged in as ${client.user.tag}`);
});

// Send message with styled Unicode text
async function sendStyledMessage(channelId, content) {
  const channel = await client.channels.fetch(channelId);

  // Validate length
  if (content.length > 2000) {
    throw new Error(`Message too long: ${content.length}/2000 chars`);
  }

  await channel.send(content);
}

// Send rich embed with styled text
async function sendStyledEmbed(channelId) {
  const channel = await client.channels.fetch(channelId);

  const embed = new EmbedBuilder()
    .setTitle('𝐏𝐫𝐨𝐝𝐮𝐜𝐭 𝐋𝐚𝐮𝐧𝐜𝐡 🚀')
    .setDescription(`
      **𝐅𝐞𝐚𝐭𝐮𝐫𝐞𝐬:**
      ✨ 𝘐𝘯𝘯𝘰𝘷𝘢𝘵𝘪𝘷𝘦 Design
      ⚡ 𝙁𝙖𝙨𝙩 Performance
      🎯 𝗥𝗲𝗹𝗶𝗮𝗯𝗹𝗲 Results
    `)
    .setColor(0x5865F2) // Discord blurple
    .addFields(
      { name: '𝐏𝐫𝐢𝐜𝐞', value: '$99.99', inline: true },
      { name: '𝐀𝐯𝐚𝐢𝐥𝐚𝐛𝐢𝐥𝐢𝐭𝐲', value: 'In Stock', inline: true }
    )
    .setFooter({ text: '𝘓𝘢𝘶𝘯𝘤𝘩𝘦𝘥 𝘑𝘢𝘯𝘶𝘢𝘳𝘺 2025' })
    .setTimestamp();

  await channel.send({ embeds: [embed] });
}

// Webhook with styled text (for bots without full client)
const axios = require('axios');

async function sendWebhookMessage(webhookUrl, content) {
  await axios.post(webhookUrl, {
    content: content,
    username: '𝐁𝐨𝐭 𝐍𝐚𝐦𝐞', // Styled username
    avatar_url: 'https://example.com/avatar.png'
  });
}

client.login(DISCORD_BOT_TOKEN);

TikTok API

TikTok for Developers API

Content Posting API (Limited Access)

Caption Limit
2,200
Characters
Bio Limit
80
Characters
Hashtag Limit
Unlimited
Within caption limit

API Access Notes

  • • TikTok Content Posting API requires application approval
  • • Rate limits: 10 posts per day per user during testing
  • • Unicode support is excellent for Latin-based styled text
  • • Emoji rendering is platform-dependent (iOS vs Android differences)
  • • Direct API posting available only for approved developer accounts

WhatsApp Business API

Cloud API (Recommended)

Endpoint: POST /messages

Message Limit
4,096
Bytes (UTF-8)
Template Limit
1,024
Characters
Media Caption
1,024
Characters

WhatsApp Markdown Support

WhatsApp supports native formatting which can be combined with Unicode:

*𝘁𝗲𝘅𝘁*Bold (native + Unicode italic)
_𝐭𝐞𝐱𝐭_Italic (native + Unicode bold)
~𝚝𝚎𝚡𝚝~Strikethrough (native + Unicode mono)
\`\`\`𝙲𝚘𝚍𝚎\`\`\`Code block (native + Unicode)
WhatsApp Cloud API - Send Message
// WhatsApp Cloud API
const axios = require('axios');

async function sendWhatsAppMessage(phoneNumberId, accessToken, to, message) {
  // Validate message size (4096 bytes UTF-8)
  const byteSize = Buffer.byteLength(message, 'utf8');
  if (byteSize > 4096) {
    throw new Error(`Message too large: ${byteSize}/4096 bytes`);
  }

  const response = await axios.post(
    `https://graph.facebook.com/v18.0/${phoneNumberId}/messages`,
    {
      messaging_product: 'whatsapp',
      to: to,
      type: 'text',
      text: {
        body: message,
        preview_url: true // Enable link previews
      }
    },
    {
      headers: {
        'Authorization': `Bearer ${accessToken}`,
        'Content-Type': 'application/json'
      }
    }
  );

  return response.data;
}

// Example with styled text and native formatting
const styledMessage = `*𝐍𝐞𝐰 𝐎𝐫𝐝𝐞𝐫 𝐂𝐨𝐧𝐟𝐢𝐫𝐦𝐚𝐭𝐢𝐨𝐧* 🎉

Your order has been confirmed!

_𝘖𝘳𝘥𝘦𝘳 𝘋𝘦𝘵𝘢𝘪𝘭𝘴:_
• 𝙋𝙧𝙤𝙙𝙪𝙘𝙩: Premium Package
• 𝙌𝙪𝙖𝙣𝙩𝙞𝙩𝙮: 2
• 𝙏𝙤𝙩𝙖𝙡: $199.99

Track your order: example.com/track`;

await sendWhatsAppMessage(
  PHONE_NUMBER_ID,
  ACCESS_TOKEN,
  '+1234567890',
  styledMessage
);

Cross-Platform Compatibility Matrix

Unicode StyleInstagramTwitterDiscordTikTokWhatsApp
Mathematical Bold
Mathematical Italic
Script/Cursive
Fraktur/Gothic
Circled Letters
Squared Letters
Combining Underline
Fullwidth Forms
Full Support
Partial/Rendering Issues
Not Supported

Best Practices for Multi-Platform Apps

1. Implement Platform Detection

Detect the target platform and adjust Unicode usage accordingly:

const safeStyles = getPlatformSafeStyles(targetPlatform);

2. Validate Before Posting

Always validate character count, byte size, and supported Unicode blocks:

  • • Check weighted character limits (Twitter)
  • • Validate byte size (WhatsApp: 4096 bytes)
  • • Count actual code points, not string length
  • • Test rendering on target platform before bulk posting

3. Provide Fallbacks

Have plain-text fallbacks for platforms or contexts where styled text may not render correctly. Especially important for:

  • • Email notifications (many clients strip Unicode)
  • • SMS/MMS messages
  • • Older platform versions
  • • Screen readers and accessibility tools

4. Rate Limiting & Error Handling

All platforms have rate limits. Implement proper error handling:

  • • Exponential backoff for rate limit errors (429)
  • • Queue systems for bulk posting
  • • Log failed posts with full error details
  • • Monitor API quota usage proactively

Test Unicode Support in Your App

Use our generator to create and test styled text across all major platforms. Includes automatic platform compatibility detection and character limit validation.

Try Platform Testing Tool

Rate This Article

How helpful was this?

Comments (3)

Sarah_designgirl2 days ago

Whoa, mind blown! 🤯 I never thought about fonts this deeply but now I'm seeing them everywhere. Just spent 2 hours redoing my whole Instagram feed lol. The bold vs script thing is so true - my business posts def need more authority.

MikeC_freelance1 day ago

RIGHT?? I literally redesigned my business cards after reading this. Clients have been asking where I got them done - it's just the font change! Wild.

TwitchStreamer2K3 days ago

Dude... changed my overlay fonts like you suggested and my viewers actually started commenting more. Thought it was just coincidence but nope, ran it for 3 weeks. Chat went from dead to actual conversations. This stuff actually works??

emma_mktg4 days ago

Okay I've been doing social media marketing for 5 years and this just made everything click. Like, I KNEW certain fonts worked better but couldn't explain why to clients. Sending this to my whole team. Also that trust ranking chart? *Chef's kiss*

David_Brands3 days ago

Emma yes! Can we get a part 2 about color psychology too? My brand clients would eat this up.