phone number standards
phone number standards
Estonia Phone Number Format: +372 Code, Validation & Examples
Complete guide to Estonia phone numbers (+372): format examples, mobile vs landline validation, E.164 standard implementation, and developer best practices for Estonian numbering.
Estonia Phone Numbers: Format, Area Code & Validation Guide
Complete guide to Estonian phone numbers (+372), covering format specifications, mobile and landline examples, validation patterns, and implementation best practices for developers. Estonia's advanced digital infrastructure and closed numbering plan (no area codes) make it essential to understand the streamlined +372 system for seamless integration with Estonian digital services.
Quick Reference
- Country: Estonia
- Country Code: +372
- International Prefix: 00 (dialed before the country code when calling internationally from Estonia)
- National Prefix: None
Example Numbers:
- Geographic (landline): +372 6XX XXXX (7 digits)
- Mobile: +372 5XXX XXXX (7-8 digits)
- Toll-free: +372 8002 XXX
- Premium rate: +372 900 XXXX
Understanding the Estonian Numbering System
Estonia's numbering system supports a digital-first society through:
- Advanced Digital Services Integration: Estonia ranks 9th among 27 EU member states in the Digital Economy and Society Index (DESI) 2022, enabling seamless integration with e-government platforms, e-residency services, online voting, and digital contract signing using ID cards.
- E-government Initiatives: Over 93.7% internet penetration rate (as of early 2024) supports comprehensive digital public services where phone numbers serve as authentication identifiers.
- Mobile-First Communication Approach: Estonia had 1.92 million active cellular mobile connections in early 2024, equating to 145.7% of the total population – reflecting widespread use of multiple connections for personal and work purposes.
- Cross-border Digital Services within the EU: Aligns with EU standards for telecommunications interoperability, with cross-border data exchange agreements in place (notably with Finland for population data and commercial registers).
Estonia Phone Number Format Specifications
General Structure
Estonian phone numbers follow a closed numbering plan (implemented May 1, 2003). Geographic area codes are absent and all calls within Estonia are local:
- Country Code: +372 (always use the '+' prefix for international compatibility)
- Service Identifier: The first digit after the country code indicates the service type:
3: Geographic (fixed-line) - ranges include 32x, 33x, 35x, 38x, 39x, 43x-48x5: Mobile - covers 5xx (7 digits) and 5xxx (8 digits)6: VoIP and other non-geographic numbers - ranges 60x-68x8: Toll-free and mobile - 8000-8009 for freephone, 81xx-87xx for mobile9: Premium rate - 900 xxxx format
- Subscriber Number: The remaining digits form the subscriber's unique number.
Format Examples by Service Type
Estonia uses ITU E.164 standard for international numbering. Total number length in E.164 format (including country code +372) is 10-15 digits depending on service type.
| Service Type | Format Example | Number Length (without country code) | E.164 Total Length |
|---|---|---|---|
| Geographic | +372 6XX XXXX | 7 digits | 11 digits |
| Mobile (7-digit) | +372 5XX XXXX | 7 digits | 11 digits |
| Mobile (8-digit) | +372 5XXX XXXX | 8 digits | 12 digits |
| VoIP | +372 6XX XXXX | 7-8 digits | 11-12 digits |
| Toll-free | +372 8002 XXX | 7 digits (8002-8009 prefixes) | 11 digits |
| Premium Rate | +372 900 XXXX | 7 digits | 11 digits |
| M2M | +372 8XXX... | Up to 12 digits | Up to 16 digits |
How to Validate Estonia Phone Numbers (+372)
Prerequisites
Before implementing Estonian phone number handling, ensure you:
- Understand the closed numbering plan – no trunk codes or area codes are used; all domestic calls use 7-8 digit numbers directly
- Support E.164 format – store and process numbers using the international standard (+372XXXXXXXX)
- Account for number portability – numbers are portable between locations and operators since the 2003 numbering reform
- Handle variable lengths – mobile numbers can be 7 or 8 digits; M2M numbers extend up to 12 digits
Validation Patterns and Code Examples
Use regular expressions for robust validation:
const patterns = {
// Geographic: 3xx xxxx (7 digits), ranges: 32x, 33x, 35x, 38x, 39x, 43x-48x, 60x-68x, 71x-79x, 88x
geographic: /^(\+372)?([3][2358]|[34][3-8]|[67][0-8]|[7][1-9]|88)\d{5}$/,
// Mobile: 5xx xxxx (7 digits) or 5xxx xxxx (8 digits), also 81xx-87xx ranges
mobile: /^(\+372)?(5\d{6,7}|8[1-7]\d{6})$/,
// VoIP: 6xx xxxx (7-8 digits)
voip: /^(\+372)?6\d{6,7}$/,
// Toll-free: 8000-8009 ranges with 4 additional digits
tollFree: /^(\+372)?800[0-9]\d{3}$/,
// Premium rate: 900 xxxx
premium: /^(\+372)?900\d{4}$/,
// Emergency and special numbers
emergency: /^112$/,
shortCode: /^1\d{2,3}$/ // 3-4 digit short codes like 1247, 1343
};
function validateEstonianNumber(number, type = 'mobile') {
// Normalize: remove spaces, hyphens, parentheses
let normalized = number.replace(/[\s\-\(\)]/g, '');
// Handle different input formats
if (normalized.startsWith('00372')) {
normalized = '+372' + normalized.substring(5);
} else if (normalized.startsWith('372') && !normalized.startsWith('+')) {
normalized = '+372' + normalized.substring(3);
} else if (!normalized.startsWith('+') && normalized.length >= 7) {
// Assume domestic format, prepend +372
normalized = '+372' + normalized;
}
// Validate against pattern
if (!patterns[type]) {
throw new Error(`Unknown number type: ${type}`);
}
const isValid = patterns[type].test(normalized);
// Return both validation result and normalized number
return {
valid: isValid,
normalized: isValid ? normalized : null,
type: type
};
}
// Example usage with different input formats
console.log(validateEstonianNumber('5123 4567', 'mobile')); // { valid: true, normalized: '+3725123467' }
console.log(validateEstonianNumber('+372 51234567', 'mobile')); // { valid: true, normalized: '+37251234567' }
console.log(validateEstonianNumber('003725123 4567', 'mobile')); // { valid: true, normalized: '+3725123467' }Common Pitfalls:
- Variable mobile number length: Mobile numbers have either 7 or 8 digits (5xx xxxx vs 5xxx xxxx). Your regex must accommodate both
- Multiple mobile prefixes: Mobile services use both
5xxand8[1-7]xranges – don't limit validation to only5xx - Country code handling: Users may input numbers with +372, 00372, 372, or no prefix. Normalize before validation
- Special numbers exclusion: Emergency (112) and short codes (116, 1247, 1343) should be handled separately and not validated as regular numbers
Best Practices
Storage Format:
Always store numbers in E.164 format (+372XXXXXXXX). This ensures international compatibility and simplifies processing.
// Example: Storing in database
function storePhoneNumber(rawNumber, userId) {
const validation = validateEstonianNumber(rawNumber);
if (!validation.valid) {
throw new Error('Invalid Estonian phone number');
}
// Store in E.164 format
return db.users.update({
id: userId,
phone: validation.normalized, // E.g., '+3725123467'
phone_verified: false,
updated_at: new Date()
});
}Display Format:
Format numbers for readability based on the user's context:
function formatPhoneDisplay(e164Number, context = 'domestic') {
if (!e164Number.startsWith('+372')) return e164Number;
const digits = e164Number.substring(4); // Remove +372
if (context === 'domestic') {
// Estonian users: "5123 4567" or "51 234 567"
if (digits.length === 7) {
return `${digits.substring(0, 3)} ${digits.substring(3)}`;
} else if (digits.length === 8) {
return `${digits.substring(0, 4)} ${digits.substring(4)}`;
}
}
// International context: full E.164
return e164Number;
}Database Schema Considerations:
- Use
VARCHAR(16)to accommodate E.164 format (max 15 digits + plus sign). - Index phone numbers for lookup performance:
CREATE INDEX idx_phone ON users(phone); - Consider adding a
phone_country_codecolumn if supporting multiple countries for faster filtering. - Store verification status separately:
phone_verified BOOLEAN DEFAULT FALSE.
Network Infrastructure and Coverage
Estonia boasts a world-class telecommunications infrastructure, with substantial recent investment in 5G deployment:
- Extensive 4G/5G Coverage: 4G/LTE covers over 99% of the population across all three major operators (Telia, Elisa, Tele2). 5G deployment accelerated following spectrum auctions in 2022-2023 (700 MHz, 3.5 GHz, and 26 GHz bands).
- High Data Throughput: Average mobile download speeds exceed 58.6 Mbps (Telia) to 30+ Mbps (other operators) nationwide, with urban areas seeing 100+ Mbps on 5G networks.
- Excellent Network Reliability: Network uptime approaches 99.9% in population centers, supported by comprehensive infrastructure sharing arrangements.
Major Operators and Market Share
According to TTJA 2024 data:
| Operator | Market Share (Subscribers) | Coverage Notes |
|---|---|---|
| Telia Estonia | 44% | Largest network, extensive 5G in Tallinn (150+ base stations), best overall coverage |
| Elisa Estonia | 32% | Claims 70% population 5G coverage, competitive pricing for families |
| Tele2 Estonia | 24% | Budget operator, coverage approximately 50% of Telia/Elisa, first mmWave 26GHz 5G base station (2023) |
All three operators provide fixed and mobile services, with Telia and Elisa also offering substantial fiber broadband infrastructure.
Advanced Considerations
Number Portability
Number portability allows users to switch operators while keeping their number. TTJA regulations mandate:
Timeline:
- Mobile numbers: 3-25 working days (average: 3-6 working days)
- Landline numbers: 3-39 working days (includes technical facility identification)
Process:
- Customer submits request to new operator (receiving operator) or terminates with current operator
- Receiving operator initiates portability verification via Number Reservation Database (NBA)
- Former operator confirms portability date
- Number transfers on confirmed date
- Process is free of charge for customers
Important Notes:
- Customers can suspend the portability request until the former operator confirms the transfer date.
- A conditional 30-day termination window applies if initiated with the current operator.
- Numbers are portable between locations and operators under Estonia's closed numbering plan.
Implementation Consideration:
Currently, there is no publicly documented API for real-time portability checks from TTJA. Operators manage portability through the NBA system. For applications requiring current operator identification, consider:
- Maintain an operator prefix lookup table (updated quarterly from TTJA data)
- Cache known number-to-operator mappings
- Handle portability as an eventual consistency issue (numbers may take 3-6 days to fully port)
Error Handling
Implement comprehensive error handling for Estonian phone numbers:
class EstonianPhoneError extends Error {
constructor(code, message, details = {}) {
super(message);
this.code = code;
this.details = details;
}
}
function validateWithErrors(number) {
// Check for special numbers first
const cleaned = number.replace(/\D/g, '');
if (cleaned === '112') {
throw new EstonianPhoneError(
'SPECIAL_NUMBER',
'Emergency number 112 cannot be used for registration',
{ isEmergency: true }
);
}
if (/^1\d{2,3}$/.test(cleaned)) {
throw new EstonianPhoneError(
'SHORT_CODE',
'Short codes (116, 1247, 1343, etc.) are not valid for user registration',
{ isShortCode: true }
);
}
// Validate length
if (cleaned.length < 7 || cleaned.length > 15) {
throw new EstonianPhoneError(
'INVALID_LENGTH',
`Phone number must be 7-15 digits, got ${cleaned.length}`,
{ length: cleaned.length }
);
}
// Validate service prefix
const validation = validateEstonianNumber(number);
if (!validation.valid) {
throw new EstonianPhoneError(
'INVALID_FORMAT',
'Number does not match Estonian numbering plan',
{ input: number }
);
}
return validation.normalized;
}
// Network error handling with retry
async function sendSMSWithRetry(phone, message, maxRetries = 3) {
let lastError;
for (let attempt = 1; attempt <= maxRetries; attempt++) {
try {
return await smsProvider.send(phone, message);
} catch (error) {
lastError = error;
if (error.code === 'INVALID_NUMBER') {
throw error; // Don't retry invalid numbers
}
if (attempt < maxRetries) {
await new Promise(resolve => setTimeout(resolve, 1000 * attempt));
}
}
}
throw new EstonianPhoneError(
'NETWORK_ERROR',
`Failed to send SMS after ${maxRetries} attempts`,
{ originalError: lastError }
);
}Special Numbers to Handle:
- Emergency: 112 (European emergency number)
- Short codes: 116 (Harmonized European Short Codes), 1247 (State helpline), 1343 (Electric circuit breakdown), 1524 (Rescue service info)
- International freephone: 8000 xxxx, 8001 xxxx ranges
GDPR Compliance
Estonia is an EU member state. When handling Estonian phone numbers, ensure GDPR compliance:
Data Minimization:
// Only collect what you need
const userSchema = {
phone: String, // Required for authentication
phone_verified: Boolean, // Required for security
// Don't store: call logs, SMS content, carrier info (unless necessary)
};Purpose Limitation:
- Document why you collect phone numbers (e.g., "two-factor authentication")
- Don't use for marketing without separate consent
- Delete when purpose is fulfilled
Storage Security:
// Encrypt at rest
const crypto = require('crypto');
function encryptPhone(phone, key) {
const iv = crypto.randomBytes(16);
const cipher = crypto.createCipheriv('aes-256-gcm', key, iv);
const encrypted = Buffer.concat([cipher.update(phone, 'utf8'), cipher.final()]);
const tag = cipher.getAuthTag();
return { encrypted: encrypted.toString('hex'), iv: iv.toString('hex'), tag: tag.toString('hex') };
}
// Encrypt in transit (use HTTPS/TLS)
app.use((req, res, next) => {
if (!req.secure && process.env.NODE_ENV === 'production') {
return res.redirect('https://' + req.headers.host + req.url);
}
next();
});User Consent:
// Explicit opt-in for phone collection
const consentForm = {
phone_consent: {
granted: true,
purpose: 'Two-factor authentication',
timestamp: new Date().toISOString(),
ip_address: req.ip
}
};
// Allow users to withdraw consent and delete data
app.post('/api/delete-phone', authenticateUser, async (req, res) => {
await db.users.update({ id: req.user.id, phone: null, phone_verified: false });
await db.audit.log({ user: req.user.id, action: 'PHONE_DELETED', timestamp: new Date() });
res.json({ success: true });
});Data Retention:
- Define retention periods: e.g., "Phone numbers retained while account is active + 30 days post-deletion"
- Implement automated deletion: schedule jobs to purge phone data per retention policy
- Maintain audit logs of deletions for compliance verification
Integration Best Practices
Normalization Function:
function normalizeEstonianPhone(input) {
if (!input) return null;
// Remove all non-digit characters except +
let cleaned = input.replace(/[^\d+]/g, '');
// Handle different prefixes
if (cleaned.startsWith('+372')) {
return cleaned;
} else if (cleaned.startsWith('00372')) {
return '+372' + cleaned.substring(5);
} else if (cleaned.startsWith('372')) {
return '+372' + cleaned.substring(3);
} else if (/^\d{7,8}$/.test(cleaned)) {
// Assume domestic Estonian number
return '+372' + cleaned;
}
return null; // Invalid format
}Webhook Implementation:
For real-time phone verification status updates:
app.post('/webhooks/sms-provider', express.json(), (req, res) => {
const { phone, status, timestamp } = req.body;
// Verify webhook signature
const signature = req.headers['x-webhook-signature'];
if (!verifyWebhookSignature(req.body, signature)) {
return res.status(401).json({ error: 'Invalid signature' });
}
// Update verification status
db.users.update({
phone: normalizeEstonianPhone(phone),
phone_verified: status === 'verified',
phone_verified_at: new Date(timestamp)
});
res.json({ received: true });
});Testing Strategies:
- Unit tests: Validate all number format variations (with/without country code, spaces, hyphens)
- Integration tests: Test against real Estonian numbers from each operator
- Use test numbers: Coordinate with SMS providers for test phone numbers that don't send actual SMS
- Recommended tools: libphonenumber (Google's library supports Estonian numbers)
// Example test suite
describe('Estonian Phone Validation', () => {
test('validates 7-digit mobile', () => {
expect(validateEstonianNumber('5123456', 'mobile').valid).toBe(true);
});
test('validates 8-digit mobile', () => {
expect(validateEstonianNumber('51234567', 'mobile').valid).toBe(true);
});
test('normalizes various input formats', () => {
const inputs = ['+372 5123 4567', '00372 51234567', '372 5123 4567', '5123 4567'];
inputs.forEach(input => {
const result = normalizeEstonianPhone(input);
expect(result).toMatch(/^\+3725\d{7,8}$/);
});
});
test('rejects emergency numbers', () => {
expect(() => validateWithErrors('112')).toThrow('SPECIAL_NUMBER');
});
});Regular Updates:
Stay informed about changes to Estonian numbering regulations:
- Monitor TTJA website for numbering plan updates
- Review official Estonian Numbering Plan documentation (ITU database) annually
- Subscribe to TTJA newsletters for regulatory changes
Related Resources
For comprehensive guidance on international phone standards and SMS best practices, explore these related guides:
- E.164 Phone Number Format Guide - International standard for phone number formatting, essential for multi-country SMS implementation
- Albania SMS Guide - Learn about SMS delivery in another Baltic region with similar EU regulatory standards
- East Timor SMS Pricing - Compare international SMS costs and delivery considerations
Additional Resources
-
Estonian Telecommunications Regulatory Authority (TTJA): https://www.ttja.ee/en
-
Official Numbering Plan: ITU Estonia Numbering Plan (E.164)
-
Major Operator Resources:
- Telia Estonia - Market leader, 44% market share
- Elisa Estonia - 32% market share, extensive 5G
- Tele2 Estonia - Budget operator, 24% market share
-
Developer Tools:
- libphonenumber - Google's international phone number library with Estonia support
- E.164 Format Guide - International standard documentation
-
Regulatory & Compliance:
- GDPR Official Text - EU data protection regulation
- Estonia Digital Services - E-governance and digital infrastructure information