feat:동기화 페이지에 글로벌/테넌트 필터 추가
- 환경 탭 앞에 글로벌/테넌트 토글 버튼 추가 - 글로벌: tenant_id가 NULL인 코드/카테고리만 표시 - 테넌트: 현재 선택된 테넌트의 데이터만 표시 - Push/Pull API에 type 파라미터 추가 Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -50,9 +50,10 @@ public function index(Request $request): View|Response
|
||||
|
||||
$environments = $this->getEnvironments();
|
||||
$selectedEnv = $request->get('env', 'dev');
|
||||
$selectedType = $request->get('type', 'global'); // global or tenant
|
||||
|
||||
// 로컬 카테고리 조회
|
||||
$localCategories = $this->getCategoryList();
|
||||
// 로컬 카테고리 조회 (타입 필터 적용)
|
||||
$localCategories = $this->getCategoryList($selectedType);
|
||||
|
||||
// 원격 카테고리 조회
|
||||
$remoteCategories = [];
|
||||
@@ -60,7 +61,7 @@ public function index(Request $request): View|Response
|
||||
|
||||
if (! empty($environments[$selectedEnv]['url'])) {
|
||||
try {
|
||||
$remoteCategories = $this->fetchRemoteCategories($environments[$selectedEnv]);
|
||||
$remoteCategories = $this->fetchRemoteCategories($environments[$selectedEnv], $selectedType);
|
||||
} catch (\Exception $e) {
|
||||
$remoteError = $e->getMessage();
|
||||
}
|
||||
@@ -72,6 +73,7 @@ public function index(Request $request): View|Response
|
||||
return view('categories.sync', [
|
||||
'environments' => $environments,
|
||||
'selectedEnv' => $selectedEnv,
|
||||
'selectedType' => $selectedType,
|
||||
'localCategories' => $localCategories,
|
||||
'remoteCategories' => $remoteCategories,
|
||||
'remoteError' => $remoteError,
|
||||
@@ -92,7 +94,8 @@ public function export(Request $request): JsonResponse
|
||||
return response()->json(['error' => 'Unauthorized'], 401);
|
||||
}
|
||||
|
||||
$categories = $this->getCategoryList();
|
||||
$type = $request->get('type', 'all'); // global, tenant, or all
|
||||
$categories = $this->getCategoryList($type);
|
||||
|
||||
return response()->json([
|
||||
'success' => true,
|
||||
@@ -216,6 +219,7 @@ public function push(Request $request): JsonResponse
|
||||
{
|
||||
$validated = $request->validate([
|
||||
'env' => 'required|string|in:dev,prod',
|
||||
'type' => 'required|string|in:global,tenant',
|
||||
'category_keys' => 'required|array|min:1',
|
||||
'category_keys.*' => 'string',
|
||||
]);
|
||||
@@ -227,8 +231,8 @@ public function push(Request $request): JsonResponse
|
||||
return response()->json(['error' => '환경 설정이 없습니다.'], 400);
|
||||
}
|
||||
|
||||
// 선택된 카테고리 조회
|
||||
$localCategories = $this->getCategoryList();
|
||||
// 선택된 카테고리 조회 (타입 필터 적용)
|
||||
$localCategories = $this->getCategoryList($validated['type']);
|
||||
$selectedCategories = array_filter($localCategories, function ($cat) use ($validated) {
|
||||
$key = $this->makeCategoryKey($cat);
|
||||
return in_array($key, $validated['category_keys']);
|
||||
@@ -271,6 +275,7 @@ public function pull(Request $request): JsonResponse
|
||||
{
|
||||
$validated = $request->validate([
|
||||
'env' => 'required|string|in:dev,prod',
|
||||
'type' => 'required|string|in:global,tenant',
|
||||
'category_keys' => 'required|array|min:1',
|
||||
'category_keys.*' => 'string',
|
||||
]);
|
||||
@@ -282,9 +287,9 @@ public function pull(Request $request): JsonResponse
|
||||
return response()->json(['error' => '환경 설정이 없습니다.'], 400);
|
||||
}
|
||||
|
||||
// 원격 카테고리 조회
|
||||
// 원격 카테고리 조회 (타입 필터 적용)
|
||||
try {
|
||||
$remoteCategories = $this->fetchRemoteCategories($env);
|
||||
$remoteCategories = $this->fetchRemoteCategories($env, $validated['type']);
|
||||
} catch (\Exception $e) {
|
||||
return response()->json(['error' => $e->getMessage()], 500);
|
||||
}
|
||||
@@ -378,65 +383,70 @@ public function pull(Request $request): JsonResponse
|
||||
}
|
||||
|
||||
/**
|
||||
* 카테고리 목록 조회 (글로벌 + 테넌트)
|
||||
* 카테고리 목록 조회
|
||||
* @param string $type 'global', 'tenant', or 'all'
|
||||
*/
|
||||
private function getCategoryList(): array
|
||||
private function getCategoryList(string $type = 'all'): array
|
||||
{
|
||||
$tenantId = $this->getTenantId();
|
||||
$categories = [];
|
||||
|
||||
// 글로벌 카테고리
|
||||
$globalCategories = GlobalCategory::whereNull('deleted_at')
|
||||
->orderBy('code_group')
|
||||
->orderBy('sort_order')
|
||||
->get();
|
||||
if ($type === 'global' || $type === 'all') {
|
||||
$globalCategories = GlobalCategory::whereNull('deleted_at')
|
||||
->orderBy('code_group')
|
||||
->orderBy('sort_order')
|
||||
->get();
|
||||
|
||||
foreach ($globalCategories as $cat) {
|
||||
$parentCode = null;
|
||||
if ($cat->parent_id) {
|
||||
$parent = GlobalCategory::find($cat->parent_id);
|
||||
$parentCode = $parent?->code;
|
||||
foreach ($globalCategories as $cat) {
|
||||
$parentCode = null;
|
||||
if ($cat->parent_id) {
|
||||
$parent = GlobalCategory::find($cat->parent_id);
|
||||
$parentCode = $parent?->code;
|
||||
}
|
||||
|
||||
$categories[] = [
|
||||
'is_global' => true,
|
||||
'tenant_id' => null,
|
||||
'code_group' => $cat->code_group,
|
||||
'code' => $cat->code,
|
||||
'name' => $cat->name,
|
||||
'parent_code' => $parentCode,
|
||||
'sort_order' => $cat->sort_order,
|
||||
'description' => $cat->description,
|
||||
'is_active' => $cat->is_active,
|
||||
];
|
||||
}
|
||||
|
||||
$categories[] = [
|
||||
'is_global' => true,
|
||||
'tenant_id' => null,
|
||||
'code_group' => $cat->code_group,
|
||||
'code' => $cat->code,
|
||||
'name' => $cat->name,
|
||||
'parent_code' => $parentCode,
|
||||
'sort_order' => $cat->sort_order,
|
||||
'description' => $cat->description,
|
||||
'is_active' => $cat->is_active,
|
||||
];
|
||||
}
|
||||
|
||||
// 테넌트 카테고리
|
||||
$tenantCategories = Category::withoutGlobalScopes()
|
||||
->where('tenant_id', $tenantId)
|
||||
->whereNull('deleted_at')
|
||||
->orderBy('code_group')
|
||||
->orderBy('sort_order')
|
||||
->get();
|
||||
if ($type === 'tenant' || $type === 'all') {
|
||||
$tenantCategories = Category::withoutGlobalScopes()
|
||||
->where('tenant_id', $tenantId)
|
||||
->whereNull('deleted_at')
|
||||
->orderBy('code_group')
|
||||
->orderBy('sort_order')
|
||||
->get();
|
||||
|
||||
foreach ($tenantCategories as $cat) {
|
||||
$parentCode = null;
|
||||
if ($cat->parent_id) {
|
||||
$parent = Category::withoutGlobalScopes()->find($cat->parent_id);
|
||||
$parentCode = $parent?->code;
|
||||
foreach ($tenantCategories as $cat) {
|
||||
$parentCode = null;
|
||||
if ($cat->parent_id) {
|
||||
$parent = Category::withoutGlobalScopes()->find($cat->parent_id);
|
||||
$parentCode = $parent?->code;
|
||||
}
|
||||
|
||||
$categories[] = [
|
||||
'is_global' => false,
|
||||
'tenant_id' => $cat->tenant_id,
|
||||
'code_group' => $cat->code_group,
|
||||
'code' => $cat->code,
|
||||
'name' => $cat->name,
|
||||
'parent_code' => $parentCode,
|
||||
'sort_order' => $cat->sort_order,
|
||||
'description' => $cat->description,
|
||||
'is_active' => $cat->is_active,
|
||||
];
|
||||
}
|
||||
|
||||
$categories[] = [
|
||||
'is_global' => false,
|
||||
'tenant_id' => $cat->tenant_id,
|
||||
'code_group' => $cat->code_group,
|
||||
'code' => $cat->code,
|
||||
'name' => $cat->name,
|
||||
'parent_code' => $parentCode,
|
||||
'sort_order' => $cat->sort_order,
|
||||
'description' => $cat->description,
|
||||
'is_active' => $cat->is_active,
|
||||
];
|
||||
}
|
||||
|
||||
return $categories;
|
||||
@@ -445,12 +455,14 @@ private function getCategoryList(): array
|
||||
/**
|
||||
* 원격 카테고리 조회
|
||||
*/
|
||||
private function fetchRemoteCategories(array $env): array
|
||||
private function fetchRemoteCategories(array $env, string $type = 'all'): array
|
||||
{
|
||||
$response = Http::withHeaders([
|
||||
'X-Menu-Sync-Key' => $env['api_key'],
|
||||
'Accept' => 'application/json',
|
||||
])->timeout(10)->get(rtrim($env['url'], '/') . '/category-sync/export');
|
||||
])->timeout(10)->get(rtrim($env['url'], '/') . '/category-sync/export', [
|
||||
'type' => $type,
|
||||
]);
|
||||
|
||||
if (! $response->successful()) {
|
||||
throw new \Exception('API 오류: HTTP ' . $response->status());
|
||||
|
||||
Reference in New Issue
Block a user