| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546 |
- <?php
- declare(strict_types=1);
- namespace app\miniapi\support;
- /** Shared telephone format policy. Format validation does not verify ownership or reachability. */
- final class PhoneNumber
- {
- public static function normalize(string $phone): string
- {
- $phone = trim($phone);
- if (!preg_match('/^\+?(?:[0-9 -]|\([0-9]+\))+$/D', $phone)) {
- throw new \InvalidArgumentException('联系电话格式无效');
- }
- $normalized = str_replace([' ', '-', '(', ')'], '', $phone);
- $pattern = str_starts_with($normalized, '+') ? '/^\+[1-9][0-9]{6,14}$/D' : '/^[0-9]{7,15}$/D';
- if (!preg_match($pattern, $normalized) || preg_match('/^0+$/D', $normalized)) {
- throw new \InvalidArgumentException('联系电话须包含7至15位数字');
- }
- return $normalized;
- }
- public static function mask(string $phone): string
- {
- if (trim($phone) === '') {
- return '';
- }
- try {
- $normalized = self::normalize($phone);
- } catch (\InvalidArgumentException) {
- // Historical unrecognized values must never fall back to plaintext.
- return '****';
- }
- $prefix = str_starts_with($normalized, '+') ? '+' : '';
- $digits = ltrim($normalized, '+');
- $length = strlen($digits);
- $visibleStart = $length >= 10 ? 3 : 2;
- $visibleEnd = $length >= 10 ? 4 : 2;
- return $prefix . substr($digits, 0, $visibleStart)
- . str_repeat('*', $length - $visibleStart - $visibleEnd)
- . substr($digits, -$visibleEnd);
- }
- }
|