# Admin → MNG 마이그레이션 계획 > 📌 **Admin 시스템 관리 메뉴 11개를 MNG로 마이그레이션** **작성일**: 2025-11-21 **상태**: Phase 4 준비 중 --- ## 📋 마이그레이션 개요 ### 목표 Admin(Filament v4)의 시스템 관리 메뉴 11개를 MNG(Plain Laravel)로 이식하여 수정 용이한 관리자 패널 구축 ### 핵심 전략 ``` ┌─────────────────────────────────────────┐ │ Blade 화면 (Web Routes) │ │ - 화면만 담당, 데이터 처리 없음 │ │ ↓ HTMX 호출 (hx-get, hx-post 등) │ │ ↓ │ │ API Routes (/api/admin/*) │ │ - 실제 데이터 CRUD 처리 │ │ - HTMX 요청 시 HTML 반환 │ │ - 일반 요청 시 JSON 반환 │ │ ↓ │ │ API Controller → Service → Model │ │ ↓ │ │ MySQL (admin/api와 DB 공유) │ └─────────────────────────────────────────┘ ``` ### 기술 스택 - **프론트엔드**: Blade + HTMX + DaisyUI + Tailwind CSS - **백엔드**: Laravel 12 + PHP 8.4 + Sanctum - **인터랙션**: HTMX (Alpine.js 제거) --- ## 🎯 마이그레이션 대상 (11개 메뉴) ### Admin 시스템 관리 메뉴 분석 | # | 메뉴명 | Resource 파일 | 모델 | 복잡도 | 우선순위 | |---|--------|--------------|------|--------|---------| | 1 | 테넌트 | `TenantResource.php` | `Tenant` | ⭐⭐ | 1 | | 2 | 사용자 | `UserResource.php` | `User` | ⭐⭐⭐ | 2 | | 3 | 메뉴 | `MenuResource.php` | `Menu` | ⭐⭐ | 3 | | 4 | 역할 | `RoleResource.php` | `Role` | ⭐⭐ | 4 | | 5 | 부서 | `DepartmentResource.php` | `Department` | ⭐⭐ | 5 | | 6 | 권한 | `PermissionResource.php` | `Permission` | ⭐⭐ | 6 | | 7 | 역할 권한 관리 | `RolePermissionsResource.php` | - | ⭐⭐⭐ | 7 | | 8 | 부서 권한 관리 | `DepartmentPermissionsResource.php` | - | ⭐⭐⭐ | 8 | | 9 | 개인 권한 관리 | `UserPermissionsResource.php` | - | ⭐⭐⭐ | 9 | | 10 | 권한 분석 | `PermissionAnalysisResource.php` | - | ⭐⭐⭐⭐ | 10 | | 11 | 삭제된 데이터 백업 | `ArchivedRecordResource.php` | `ArchivedRecord` | ⭐⭐⭐ | 11 | **복잡도:** - ⭐ 단순 CRUD - ⭐⭐ CRUD + 관계 - ⭐⭐⭐ CRUD + 복잡한 관계 + 커스텀 UI - ⭐⭐⭐⭐ 읽기 전용 + 복잡한 쿼리 + 매트릭스 UI --- ## 🏗️ 라우트 구조 ### Web Routes (Blade 화면만) ```php // routes/web.php Route::middleware(['auth:sanctum'])->group(function () { // 테넌트 관리 Route::get('/tenants', [TenantController::class, 'index'])->name('tenants.index'); Route::get('/tenants/create', [TenantController::class, 'create'])->name('tenants.create'); Route::get('/tenants/{tenant}/edit', [TenantController::class, 'edit'])->name('tenants.edit'); // 사용자 관리 Route::get('/users', [UserController::class, 'index'])->name('users.index'); Route::get('/users/create', [UserController::class, 'create'])->name('users.create'); Route::get('/users/{user}/edit', [UserController::class, 'edit'])->name('users.edit'); // ... 나머지 메뉴 }); ``` ### API Routes (실제 데이터 처리) ```php // routes/api.php Route::middleware(['auth:sanctum'])->prefix('admin')->group(function () { // 테넌트 API Route::apiResource('tenants', Api\Admin\TenantController::class); // 사용자 API Route::apiResource('users', Api\Admin\UserController::class); // 권한 관리 API (Custom) Route::prefix('permissions')->group(function () { Route::get('/role/{role}', [Api\Admin\RolePermissionController::class, 'show']); Route::post('/role/{role}', [Api\Admin\RolePermissionController::class, 'update']); Route::get('/department/{department}', [Api\Admin\DepartmentPermissionController::class, 'show']); Route::post('/department/{department}', [Api\Admin\DepartmentPermissionController::class, 'update']); Route::get('/user/{user}', [Api\Admin\UserPermissionController::class, 'show']); Route::post('/user/{user}', [Api\Admin\UserPermissionController::class, 'update']); Route::get('/analysis', [Api\Admin\PermissionAnalysisController::class, 'index']); }); // ... 나머지 메뉴 }); ``` --- ## 📐 표준 개발 프로세스 ### 1. 모델 복사 (Admin → MNG) ```bash # 1. 모델 복사 cp admin/app/Models/Tenants/Tenant.php mng/app/Models/Tenant.php cp admin/app/Models/Members/User.php mng/app/Models/User.php # ... # 2. Filament 코드 제거 # - form(), table(), getNavigationLabel() 등 제거 # - 순수 Eloquent 관계만 유지 # 3. Traits 복사 cp admin/app/Traits/BelongsToTenant.php mng/app/Traits/ cp admin/app/Traits/ModelTrait.php mng/app/Traits/ ``` ### 2. Service Layer 생성 ```php // mng/app/Services/TenantService.php namespace App\Services; use App\Models\Tenant; use Illuminate\Pagination\LengthAwarePaginator; class TenantService { /** * 테넌트 목록 조회 (검색, 필터, 페이징) */ public function getTenants(array $filters = []): LengthAwarePaginator { $query = Tenant::query(); // 검색 if (!empty($filters['search'])) { $query->where('company_name', 'like', "%{$filters['search']}%"); } // 상태 필터 if (!empty($filters['status'])) { $query->where('tenant_st_code', $filters['status']); } return $query->paginate(20); } /** * 테넌트 생성 */ public function createTenant(array $data): Tenant { return Tenant::create($data); } // update(), delete() ... } ``` ### 3. API Controller 생성 ```php // mng/app/Http/Controllers/Api/Admin/TenantController.php namespace App\Http\Controllers\Api\Admin; use App\Http\Controllers\Controller; use App\Http\Requests\Tenant\StoreTenantRequest; use App\Services\TenantService; use Illuminate\Http\JsonResponse; use Illuminate\Http\Request; class TenantController extends Controller { public function __construct( private TenantService $tenantService ) {} /** * 테넌트 목록 (API) * GET /api/admin/tenants */ public function index(Request $request): JsonResponse { $tenants = $this->tenantService->getTenants($request->all()); // HTMX 요청 시 HTML 반환 if ($request->header('HX-Request')) { return response()->view('tenants.partials.table', compact('tenants')); } // 일반 요청 시 JSON 반환 return response()->json([ 'success' => true, 'data' => $tenants->items(), 'meta' => [ 'current_page' => $tenants->currentPage(), 'total' => $tenants->total(), ], ]); } /** * 테넌트 생성 (API) * POST /api/admin/tenants */ public function store(StoreTenantRequest $request): JsonResponse { $tenant = $this->tenantService->createTenant($request->validated()); return response()->json([ 'success' => true, 'data' => $tenant, 'message' => 'tenants.created', ], 201); } // update(), destroy() ... } ``` ### 4. Web Controller 생성 (Blade 화면만) ```php // mng/app/Http/Controllers/TenantController.php namespace App\Http\Controllers; class TenantController extends Controller { /** * 테넌트 목록 화면 * GET /tenants */ public function index() { return view('tenants.index'); } /** * 테넌트 생성 화면 * GET /tenants/create */ public function create() { return view('tenants.create'); } /** * 테넌트 수정 화면 * GET /tenants/{tenant}/edit */ public function edit($id) { return view('tenants.edit', compact('id')); } } ``` ### 5. Blade 뷰 생성 (HTMX 호출) ```blade {{-- resources/views/tenants/index.blade.php --}} @extends('layouts.app') @section('content')
@endsection ``` ### 6. 부분 템플릿 생성 (HTMX 응답) ```blade {{-- resources/views/tenants/partials/table.blade.php --}}| ID | 회사명 | 이메일 | 상태 | 작업 |
|---|---|---|---|---|
| {{ $tenant->id }} | {{ $tenant->company_name }} | {{ $tenant->email }} | {{ $tenant->tenant_st_code }} | 수정 |