*/ public function counts(string $organizationId): array { $counts = []; Block::query()->where('organization_id', $organizationId)->get(['data'])->each(function (Block $block) use (&$counts) { foreach ($this->assetIds($block->data) as $id) { $counts[$id] = ($counts[$id] ?? 0) + 1; } }); Course::query()->where('organization_id', $organizationId)->whereNotNull('cover_asset_id')->pluck('cover_asset_id')->each(function (string $id) use (&$counts) { $counts[$id] = ($counts[$id] ?? 0) + 1; }); foreach (['review_threads', 'review_replies'] as $table) { DB::table($table)->where('organization_id', $organizationId)->whereNotNull('attachment_asset_ids')->pluck('attachment_asset_ids')->each(function ($value) use (&$counts) { foreach (json_decode($value, true) ?? [] as $id) { $counts[$id] = ($counts[$id] ?? 0) + 1; } }); } return $counts; } /** @param array|list $value @return list */ public function assetIds(array $value): array { $ids = []; foreach ($value as $key => $item) { if (is_string($key) && ($key === 'assetId' || str_ends_with($key, 'AssetId')) && is_string($item) && $item !== '') { $ids[] = $item; } elseif (is_array($item)) { array_push($ids, ...$this->assetIds($item)); } } return array_values(array_unique($ids)); } public function detach(string $organizationId, string $assetId): void { $publishedVersionIds = CourseVersion::query() ->where('organization_id', $organizationId) ->where('status', CourseVersionStatus::Published) ->pluck('id') ->map(fn ($id): string => (string) $id) ->all(); $blocks = Block::query()->where('organization_id', $organizationId)->get(); foreach ($blocks as $block) { if (in_array($assetId, $this->assetIds($block->data), true) && in_array((string) $block->course_version_id, $publishedVersionIds, true)) { throw ValidationException::withMessages(['asset' => ['این فایل در نسخه منتشرشده استفاده شده و تا زمان ایجاد نسخه قابل‌ویرایش قابل حذف نیست.']]); } } foreach ($blocks as $block) { if (! in_array($assetId, $this->assetIds($block->data), true)) { continue; } $block->update(['data' => $this->withoutAsset($block->data, $assetId), 'revision' => $block->revision + 1]); } Course::query()->where('organization_id', $organizationId)->where('cover_asset_id', $assetId)->update(['cover_asset_id' => null]); foreach (['review_threads', 'review_replies'] as $table) { DB::table($table)->where('organization_id', $organizationId)->whereNotNull('attachment_asset_ids')->get(['id', 'attachment_asset_ids'])->each(function ($row) use ($table, $assetId): void { $ids = array_values(array_filter(json_decode($row->attachment_asset_ids, true) ?? [], fn ($id) => $id !== $assetId)); DB::table($table)->where('id', $row->id)->update(['attachment_asset_ids' => json_encode($ids), 'updated_at' => now()]); }); } } /** @param array|list $value @return array|list */ private function withoutAsset(array $value, string $assetId): array { if (array_is_list($value)) { return array_values(array_map( fn ($item) => is_array($item) ? $this->withoutAsset($item, $assetId) : $item, array_filter($value, fn ($item): bool => ! (is_array($item) && ($item['assetId'] ?? null) === $assetId)), )); } foreach ($value as $key => $item) { if (is_string($key) && ($key === 'assetId' || str_ends_with($key, 'AssetId')) && $item === $assetId) { $value[$key] = null; } elseif (is_array($item)) { $value[$key] = $this->withoutAsset($item, $assetId); } } return $value; } }