← CodeClarityLab Home
Browse by Category
+ added · updated 7d
← Back to glossary

MySQL String Types: VARCHAR vs TEXT vs CHAR

database Beginner

Also Known As

VARCHAR vs TEXT MySQL CHAR VARCHAR TEXT MySQL string column types

TL;DR

CHAR is fixed-length, VARCHAR is variable-length up to 65,535 bytes, TEXT variants store large content — each with different indexing and storage behaviour.

Explanation

CHAR(n) pads shorter values with spaces — slightly faster for fixed-length data. VARCHAR(n) stores actual length + 1-2 bytes overhead. TEXT (64KB), MEDIUMTEXT (16MB), LONGTEXT (4GB) store large content off the main row page — cannot be fully indexed without a prefix length and cannot have DEFAULT values. VARCHAR up to 767 bytes (InnoDB row format default) supports full-column indexing. For utf8mb4, the index limit is 191 characters on older InnoDB row formats.

Common Misconception

TEXT and VARCHAR are interchangeable. TEXT cannot have a DEFAULT value, cannot be fully indexed, and stores data off the main row page — impacting row fetch performance.

Why It Matters

Using TEXT for short columns like email prevents full-column indexes and default values. Using CHAR(255) for variable names pads every row to 255 bytes — wasting storage on every row.

Common Mistakes

  • Using TEXT for email, name, or slug columns — no DEFAULT, no full-column index.
  • Using CHAR(255) for variable-length data — pads every row regardless of actual content length.
  • Forgetting that utf8mb4 VARCHAR(255) requires 255×4=1020 bytes — exceeds the 767-byte InnoDB index limit on older row formats.

Avoid When

  • Avoid TEXT for columns that need DEFAULT values or full-column unique indexes.
  • Avoid CHAR for variable-length content — every row is padded to the declared length.

When To Use

  • Use VARCHAR(255) as the default for most string columns — fully indexable and flexible.
  • Use TEXT/MEDIUMTEXT/LONGTEXT for article bodies, descriptions, or any content over 1KB.
  • Use CHAR for truly fixed-length values: country codes (CHAR(2)), currency codes (CHAR(3)), UUIDs (CHAR(36)).

Code Examples

✗ Vulnerable
-- TEXT for short fields: no DEFAULT, no full index
email TEXT NOT NULL,
-- CHAR(100) wastes 100 bytes even for 'Bob'
name CHAR(100) NOT NULL
✓ Fixed
CREATE TABLE users (
    id           INT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
    email        VARCHAR(255) NOT NULL UNIQUE,
    country_code CHAR(2)      NOT NULL DEFAULT 'GB',
    bio          TEXT,
    slug         VARCHAR(100) NOT NULL UNIQUE
) ENGINE=InnoDB CHARSET=utf8mb4 ROW_FORMAT=DYNAMIC;

Added 31 Mar 2026
Views 16
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings F 0 pings S 0 pings S 0 pings M 1 ping T 0 pings W 0 pings T 0 pings F 0 pings S 2 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 1 ping T 0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S
No pings yet today
No pings yesterday
Google 5 Perplexity 4 Unknown AI 2 ChatGPT 1 Ahrefs 1
crawler 11 crawler_json 2
DEV INTEL Tools & Severity
⚙ Fix effort: Low
⚡ Quick Fix
Use VARCHAR(255) for most string columns, TEXT for large content, CHAR only for truly fixed-length values like country codes
📦 Applies To
web cli
🔗 Prerequisites
🔍 Detection Hints
TEXT column with UNIQUE or DEFAULT, or CHAR on variable-length fields
Auto-detectable: ✓ Yes semgrep
⚠ Related Problems
🤖 AI Agent
Confidence: High False Positives: Low ✓ Auto-fixable Fix: Low Context: Line

✓ schema.org compliant