findOneBy(['uuid' => $uuid]); } /** @return Clinic[] */ public function findByDoctor(Doctor $doctor): array { return $this->createQueryBuilder('c') ->innerJoin('c.doctors', 'd') ->where('d.id = :doctorId') ->setParameter('doctorId', $doctor->getId()) ->getQuery() ->getResult(); } public function findByUser(User $user): ?Clinic { return $this->findOneBy(['user' => $user]); } public function findWithFilters(array $filters): array { $page = max(1, (int) ($filters['page'] ?? 1)); $limit = min(50, max(1, (int) ($filters['limit'] ?? 10))); $sort = strtoupper($filters['sort'] ?? 'DESC') === 'ASC' ? 'ASC' : 'DESC'; $qb = $this->createQueryBuilder('c') ->leftJoin('c.specialties', 's') ->distinct(); // City/province live on the clinic's address (DoctorAddress.clinicId), // not on the clinic itself. DoctorAddress has no Doctrine relation to // Clinic, so join on the scalar clinicId with a WITH condition. if (!empty($filters['city']) || !empty($filters['state'])) { $qb->join(DoctorAddress::class, 'addr', Join::WITH, 'addr.clinicId = c.id'); if (!empty($filters['city'])) { $qb->andWhere('IDENTITY(addr.city) = :city')->setParameter('city', (int) $filters['city']); } if (!empty($filters['state'])) { $qb->andWhere('IDENTITY(addr.province) = :state')->setParameter('state', (int) $filters['state']); } } if (!empty($filters['specialty'])) { $qb->andWhere('s.id = :specialty')->setParameter('specialty', (int) $filters['specialty']); } $qb->orderBy('c.id', $sort); $total = (new Paginator($qb))->count(); $results = $qb->setFirstResult(($page - 1) * $limit) ->setMaxResults($limit) ->getQuery() ->getResult(); return [ 'items' => $results, 'total' => $total, 'page' => $page, 'limit' => $limit, 'totalPages' => (int) ceil($total / $limit), ]; } /** * City/province names for each clinic, taken from the clinic's address * (DoctorAddress.clinicId). Returns [clinicId => ['city' => ?string, 'state' => ?string]]. * * @param int[] $clinicIds * @return array */ public function findAddressLocations(array $clinicIds): array { if ($clinicIds === []) { return []; } $rows = $this->getEntityManager()->createQueryBuilder() ->select('addr.clinicId AS clinic_id', 'cityCat.name AS city', 'provinceCat.name AS state') ->from(DoctorAddress::class, 'addr') ->leftJoin('addr.city', 'cityCat') ->leftJoin('addr.province', 'provinceCat') ->where('addr.clinicId IN (:ids)') ->setParameter('ids', $clinicIds) ->getQuery() ->getResult(); $map = []; foreach ($rows as $row) { $id = (int) $row['clinic_id']; if (!isset($map[$id])) { $map[$id] = ['city' => $row['city'], 'state' => $row['state']]; } } return $map; } public function save(Clinic $clinic, bool $flush = true): void { $this->getEntityManager()->persist($clinic); if ($flush) { $this->getEntityManager()->flush(); } } public function remove(Clinic $clinic, bool $flush = true): void { $this->getEntityManager()->remove($clinic); if ($flush) { $this->getEntityManager()->flush(); } } }