upsert($item); } $this->seedMarketingTemplates(); $this->seedServiceLifecycleTemplates(); $this->createMarketingIfMissing([...self::ipRevocationTemplate(), 'marketing' => false]); } public function seedMarketingTemplates(): void { foreach (MarketingTemplates::all() as $item) { $this->createMarketingIfMissing($item); } } public function seedServiceLifecycleTemplates(): void { foreach (ServiceLifecycleTemplates::all() as $item) { $this->createMarketingIfMissing([...$item, 'marketing' => false]); } } public function seedScenarioIfMissing(string $scenario): void { if (Template::query()->where('key', $scenario)->orWhere('scenario', $scenario)->exists()) { return; } foreach (self::templates() as $item) { if ($item['scenario'] === $scenario) { $this->upsert($item); } } } public function reseedScenario(string $scenario): void { foreach (self::templates() as $item) { if ($item['scenario'] === $scenario) { $this->upsert($item); } } } private function createMarketingIfMissing(array $item): void { $template = Template::firstOrNew(['name' => $item['name']]); if ($template->exists) { return; } $template->fill([ 'type_id' => 0, 'format' => 'html', 'subject' => SubjectFormat::for($item['name']) ?? $item['subject'], 'message' => $item['message'] ?? EmailTemplateShell::page($item['body']), 'status' => 1, ]); if (($item['marketing'] ?? true) === false) { $template->metadata = [...(array) $template->metadata, 'marketing' => false]; } $template->syncVariables($item['variables']); $template->save(); } public function markNonMarketing(): void { $items = [ ...array_map(fn (array $item) => [...$item, 'marketing' => false], ServiceLifecycleTemplates::all()), ...MarketingTemplates::all(), [...self::ipRevocationTemplate(), 'marketing' => false], ]; foreach ($items as $item) { if (($item['marketing'] ?? true) !== false) { continue; } $template = Template::whereNull('key')->whereNull('scenario')->where('name', $item['name'])->first(); if ($template && ! array_key_exists('marketing', (array) $template->metadata)) { $template->forceFill(['metadata' => [...(array) $template->metadata, 'marketing' => false]])->save(); } } } /** * @return array}> */ public static function templates(): array { $layout = [ 'scenario' => 'layout', 'name' => 'Bố cục Header/Footer (mặc định)', 'subject' => '', 'message' => EmailTemplateShell::page('{{$content}}'), ]; $scenarios = array_map( fn (array $item) => [...$item, 'subject' => SubjectFormat::for($item['scenario']) ?? $item['subject'], 'message' => EmailTemplateShell::page($item['body'])], [ ...AccountTemplates::all(), ...ServiceTemplates::all(), ...IpTemplates::all(), ...BillingTemplates::all(), ...AdminTemplates::all(), ], ); return [$layout, ...$scenarios]; } /** * @return array */ public static function legacyTemplates(): array { return array_map( fn (array $item) => [...$item, 'subject' => SubjectFormat::for($item['scenario']) ?? $item['subject'], 'message' => EmailTemplateShell::page($item['body'])], LegacyTemplates::all(), ); } /** * Template mẫu thông báo danh sách tài nguyên IP đã thu hồi. * * @return array{name: string, subject: string, message: string, variables: array{}} */ private static function ipRevocationTemplate(): array { $subject = 'V/v: Thế Giới Số gửi thông tin Thu hồi IP — {{service_name}} — {{customer_name}}'; $message = <<<'HTML'
  
Thế Giới Số
THÔNG BÁO THU HỒI TÀI NGUYÊN IP
   
{{notification_date}}

Kính gửi Quý Khách hàng {{customer_name}},

Thế Giới Số trân trọng thông báo thông tin thu hồi tài nguyên IP theo yêu cầu vận hành/dịch vụ.

Thông tin IP● Đã thu hồi
STTIP AddressDịch vụNgày thu hồi
1{{ip_address}}{{service_name}}{{revocation_date}}
Thế Giới Số xin chân thành cảm ơn Quý Khách hàng đã tin tưởng và đồng hành cùng chúng tôi trong thời gian qua.
Khi có nhu cầu sử dụng lại dịch vụ hoặc cấp mới tài nguyên IP,
Quý Khách hàng vui lòng liên hệ Thế Giới Số qua các kênh hỗ trợ sau.
Rất mong tiếp tục được phục vụ Quý Khách hàng trong thời gian tới.
Trân trọng,
BỘ PHẬN KỸ THUẬT
THẾ GIỚI SỐ
CÔNG TY CỔ PHẦN GIẢI PHÁP CÔNG NGHỆ THẾ GIỚI SỐ
✆ Tel: (028) 7309 7379  |  ✉ Support@tgs.com.vn
🥇 Thế Giới Số 🥇 - Premium HOSTING • CLOUD • SERVER & WEBSITE | 15+ năm Phụng Sự 🚀
HTML; return [ 'name' => 'Thông báo thu hồi tài nguyên IP', 'subject' => $subject, 'message' => $message, 'variables' => [ ['key' => 'customer_name', 'label' => 'Tên khách hàng', 'example' => 'CÔNG TY TNHH KHÁCH HÀNG MẪU'], ['key' => 'service_name', 'label' => 'Tên dịch vụ', 'example' => 'Dịch vụ IP'], ['key' => 'notification_date', 'label' => 'Ngày lập thông báo', 'example' => 'TP. Hồ Chí Minh, ngày 15 tháng 10 năm 2026'], ['key' => 'ip_address', 'label' => 'Địa chỉ IP', 'example' => '192.0.2.1'], ['key' => 'revocation_date', 'label' => 'Ngày thu hồi', 'example' => '15/10/2026'], ], ]; } private function upsert(array $item): void { $scenario = $item['scenario']; $template = Template::query() ->where(fn ($q) => $q->where('key', $scenario)->orWhere('scenario', $scenario)) ->orderByRaw('`key` = ? desc', [$scenario]) ->orderBy('id') ->first() ?? new Template(['type_id' => 0, 'status' => 1]); $template->fill([ 'key' => $scenario, 'scenario' => $scenario, 'name' => $item['name'], 'subject' => $item['subject'], 'message' => $item['message'], 'format' => 'html', ]); $template->metadata = [ ...($template->metadata ?? []), 'variables' => $this->variables($template, $item['types'] ?? []), ]; $template->save(); } /** * @param array $typeOverrides * @return array */ private function variables(Template $template, array $typeOverrides): array { $existing = $template->variables(); return collect(MailPlaceholders::extract($template->subject, $template->message)) ->map(function (string $key) use ($existing, $typeOverrides) { [$label, $type, $example] = TemplateVariables::DEFINITIONS[$key] ?? [$key, 'string', '']; return [ 'key' => $key, 'label' => $existing[$key]['label'] ?? $label, 'type' => $typeOverrides[$key] ?? $type, 'example' => $existing[$key]['example'] ?? $example, ]; }) ->values() ->all(); } }