# افزودن فیلد شبکه‌های اجتماعی به Doctor

## پروژه

`clinicpro` (Backend) — این تغییر پیش‌نیاز پرامپت همتا در frontend است: `nobat724_front/.claude/prompt/doctor-seo-schema-knowledge-panel.md`. آن پرامپت برای Knowledge Panel گوگل به `sameAs` در JSON-LD نیاز دارد که باید از همین فیلد جدید پر شود.

## زمینه

برای فعال‌سازی Knowledge Panel گوگل برای صفحه‌ی هر پزشک (هدف نهایی در `nobat724_front`)، schema.org نیاز به آرایه‌ی `sameAs` دارد که لینک پروفایل‌های شبکه‌های اجتماعی پزشک (اینستاگرام، تلگرام، آپارات، یوتیوب، لینکدین) را به گوگل معرفی می‌کند. بررسی `src/Doctor/Entity/Doctor.php` و `docs/api/doctor.md` نشان داد این داده هیچ‌جا در API موجود نیست — نه در پاسخ `GET /api/v1/doctor/{uuid}` و نه در فرم ادمین (`assets/admin/pages/DoctorFormPage.tsx`).

نکته‌ی مهم: برخلاف انتظار اولیه، `DoctorAddress` (`src/Doctor/Entity/DoctorAddress.php`) از قبل `latitude`/`longitude` دارد و در `toArray()` به‌صورت `map: { latitude, longitude }` برمی‌گرداند — یعنی GeoCoordinates برای LocalBusiness schema نیازی به تغییر backend ندارد. فقط شبکه‌های اجتماعی پزشک باقی می‌ماند.

## مشکل / هدف

به `Doctor` entity یک فیلد JSON برای ذخیره‌ی لینک شبکه‌های اجتماعی (اینستاگرام، تلگرام، آپارات، یوتیوب، لینکدین، توییتر/X) اضافه شود، در پاسخ API برگردانده شود، و در فرم ادمین برای ویرایش در دسترس باشد.

## فایل‌های مرتبط

| فایل | نقش |
|------|-----|
| `src/Doctor/Entity/Doctor.php` | باید فیلد `socialMedia` (JSON nullable) اضافه شود |
| `src/Doctor/Controller/DoctorController.php` | پاسخ `GET /api/v1/doctor/{uuid}` باید `social_media` را برگرداند؛ متد update باید آن را بپذیرد |
| `migrations/` | migration جدید برای ستون `social_media` روی جدول `doctors` |
| `assets/admin/pages/DoctorFormPage.tsx` | فیلدهای ورودی لینک‌های اجتماعی به فرم اضافه شود |
| `assets/admin/types/index.ts` | type پزشک باید `socialMedia` را شامل شود |
| `docs/api/doctor.md` | باید فیلد جدید مستند شود |

## وضعیت فعلی

`src/Doctor/Entity/Doctor.php` فیلدهای پایه دارد (نام، تخصص، آدرس‌ها) اما هیچ فیلد JSON برای داده‌ی نیمه‌ساخت‌یافته ندارد. الگوی مشابه را می‌توان از `DoctorAddress::toArray()` که `map` را به‌صورت nested object برمی‌گرداند الگو گرفت:

```php
// src/Doctor/Entity/DoctorAddress.php — الگوی موجود برای nested object در toArray()
'map'        => [
    'latitude'  => $this->latitude !== null ? (string) $this->latitude : null,
    'longitude' => $this->longitude !== null ? (string) $this->longitude : null,
],
```

## وظایف

### ۱. افزودن فیلد `socialMedia` به `Doctor` entity

```php
// src/Doctor/Entity/Doctor.php
#[ORM\Column(name: 'social_media', type: 'json', nullable: true)]
private ?array $socialMedia = null;

public function getSocialMedia(): ?array { return $this->socialMedia; }
public function setSocialMedia(?array $v): self { $this->socialMedia = $v; $this->touch(); return $this; }
```

ساختار JSON ذخیره‌شده:

```json
{
  "instagram": "https://instagram.com/dr.example",
  "telegram": "https://t.me/dr_example",
  "aparat": "https://aparat.com/dr.example",
  "youtube": "https://youtube.com/@dr.example",
  "linkedin": "https://linkedin.com/in/dr-example"
}
```

هر کلید nullable است — پزشک ممکن است فقط بعضی شبکه‌ها را داشته باشد. کلیدهای خالی/null باید در پاسخ API هم `null` بمانند (نه حذف شوند) تا frontend به‌سادگی چک کند.

### ۲. Migration

```bash
ddev exec php bin/console doctrine:migrations:diff --no-interaction
ddev exec php bin/console doctrine:migrations:migrate --no-interaction
```

### ۳. بازگرداندن فیلد در پاسخ API

در `src/Doctor/Controller/DoctorController.php`، هرجا `toArray()`-مانند برای پزشک ساخته می‌شود (GET تکی، GET لیست)، کلید `social_media` اضافه شود:

```php
'social_media' => $doctor->getSocialMedia(),
```

و در متد update، فیلد جدید از request body خوانده و validate شود (فقط باید URL معتبر یا null باشد برای هر کلید — از `InputValidator` یا یک Assert ساده استفاده کن، الگوی موجود validation در همان کنترلر را دنبال کن).

### ۴. فرم ادمین

در `assets/admin/pages/DoctorFormPage.tsx`، یک بخش جدید «شبکه‌های اجتماعی» با ۵ فیلد متنی (اینستاگرام، تلگرام، آپارات، یوتیوب، لینکدین) اضافه شود. الگوی `Field()` موجود در همین فایل (خط ۵۲) را برای ساخت input استفاده کن. مقدار اولیه از `doctor.socialMedia` پر شود، در submit به همان شکل JSON ارسال شود.

در `assets/admin/types/index.ts`، interface پزشک باید شامل شود:

```ts
socialMedia?: {
  instagram?: string | null;
  telegram?: string | null;
  aparat?: string | null;
  youtube?: string | null;
  linkedin?: string | null;
} | null;
```

## نکات مهم

- این فیلد باید **nullable** کامل باشد — پزشکانی که شبکه اجتماعی ندارند نباید خطا بگیرند.
- مقادیر باید URL کامل (با `https://`) ذخیره شوند، نه فقط username — frontend مستقیماً این مقدار را در `sameAs` آرایه‌ی JSON-LD قرار می‌دهد بدون پردازش اضافی.
- بعد از این تغییر، `docs/api/doctor.md` را طبق قانون پروژه (به‌روزرسانی مستندات هم‌زمان با تغییر API) ویرایش کن — هم در نمونه‌ی JSON پاسخ `GET /api/v1/doctor/{uuid}` و هم در بخش فیلدهای قابل ویرایش.
- migration را قبل از merge باید روی دیتابیس dev واقعی تست کنی (`ddev exec php bin/console doctrine:migrations:migrate --no-interaction`).
