Files
sam-api/app/Services/TenantOptionGroupService.php
hskwon 43e4c507a7 fix : 결과 전달시 두번 래핑되는 부분 수정
- 컨트롤러와 서비스에서 각각 래핑 후 결과 전달됨으로 이중 래핑되고 있음
  -> 서비스에서 래핑하는 부분을 컨트롤러로 옮겨서 컨트롤러에서만 한번 래핑하는 걸로 수정
2025-08-19 12:41:17 +09:00

186 lines
5.6 KiB
PHP

<?php
namespace App\Services;
use App\Helpers\ApiResponse;
use Illuminate\Support\Facades\Validator;
use Illuminate\Validation\Rule;
use App\Models\Tenants\TenantOptionGroup;
use App\Models\Tenants\TenantOptionValue;
use App\Models\Tenants\TenantFieldSetting;
class TenantOptionGroupService
{
/** 활성 테넌트 ID */
protected static function tenantId(): ?int
{
return app('tenant_id');
}
/**
* [GET] 옵션 그룹 목록 (페이징)
* params: page?, per_page?/size?, q?
*/
public static function index(array $params = [])
{
$tenantId = self::tenantId();
if (!$tenantId) {
return ['error' => '활성 테넌트가 없습니다.', 'code' => 400];
}
$per = (int)($params['per_page'] ?? $params['size'] ?? 20);
$page = isset($params['page']) ? (int)$params['page'] : null;
$q = TenantOptionGroup::where('tenant_id', $tenantId)->orderBy('group_key');
if (!empty($params['q'])) {
$kw = $params['q'];
$q->where(function ($w) use ($kw) {
$w->where('group_key', 'like', "%{$kw}%")
->orWhere('name', 'like', "%{$kw}%");
});
}
$data = $q->paginate($per, ['*'], 'page', $page);
return $data;
}
/**
* [POST] 옵션 그룹 생성
*/
public static function store(array $params = [])
{
$tenantId = self::tenantId();
if (!$tenantId) {
return ['error' => '활성 테넌트가 없습니다.', 'code' => 400];
}
$v = Validator::make($params, [
'group_key' => [
'required','string','max:64','alpha_dash',
Rule::unique('tenant_option_groups', 'group_key')
->where(fn ($q) => $q->where('tenant_id', $tenantId)),
],
'name' => ['required','string','max:100'],
'description' => ['nullable','string','max:255'],
]);
if ($v->fails()) {
return ['error' => $v->errors()->first(), 'code' => 422];
}
$data = $v->validated();
$data['tenant_id'] = $tenantId;
$item = TenantOptionGroup::create($data);
return $item->toArray();
}
/**
* [GET] 옵션 그룹 단건 조회
*/
public static function show(int $id)
{
$tenantId = self::tenantId();
if (!$tenantId) {
return ['error' => '활성 테넌트가 없습니다.', 'code' => 400];
}
if (!$id) {
return ['error' => 'id가 올바르지 않습니다.', 'code' => 422];
}
$item = TenantOptionGroup::where('tenant_id', $tenantId)->find($id);
if (!$item) {
return ['error' => '옵션 그룹을 찾을 수 없습니다.', 'code' => 404];
}
return $item->toArray();
}
/**
* [PATCH] 옵션 그룹 수정
*/
public static function update(int $id, array $params = [])
{
$tenantId = self::tenantId();
if (!$tenantId) {
return ['error' => '활성 테넌트가 없습니다.', 'code' => 400];
}
if (!$id) {
return ['error' => 'id가 올바르지 않습니다.', 'code' => 422];
}
$item = TenantOptionGroup::where('tenant_id', $tenantId)->find($id);
if (!$item) {
return ['error' => '옵션 그룹을 찾을 수 없습니다.', 'code' => 404];
}
$v = Validator::make($params, [
'group_key' => [
'sometimes','string','max:64','alpha_dash',
Rule::unique('tenant_option_groups', 'group_key')
->where(fn ($q) => $q->where('tenant_id', $tenantId))
->ignore($item->id),
],
'name' => ['sometimes','string','max:100'],
'description' => ['nullable','string','max:255'],
]);
if ($v->fails()) {
return ['error' => $v->errors()->first(), 'code' => 422];
}
$data = $v->validated();
if (empty($data)) {
return ['error' => '수정할 항목이 없습니다.', 'code' => 422];
}
$item->fill($data)->save();
return $item->toArray();
}
/**
* [DELETE] 옵션 그룹 삭제
* - 참조 무결성 검사:
* 1) tenant_option_values에 값이 남아있으면 삭제 불가
* 2) tenant_field_settings.option_group_id에서 참조 중이면 삭제 불가
*/
public static function destroy(int $id)
{
$tenantId = self::tenantId();
if (!$tenantId) {
return ['error' => '활성 테넌트가 없습니다.', 'code' => 400];
}
if (!$id) {
return ['error' => 'id가 올바르지 않습니다.', 'code' => 422];
}
$item = TenantOptionGroup::where('tenant_id', $tenantId)->find($id);
if (!$item) {
return ['error' => '옵션 그룹을 찾을 수 없습니다.', 'code' => 404];
}
// 1) 옵션 값 존재 여부
$hasValues = TenantOptionValue::where('group_id', $item->id)->exists();
if ($hasValues) {
return ['error' => '해당 그룹에 옵션 값이 존재하여 삭제할 수 없습니다.', 'code' => 409];
}
// 2) 필드 설정에서 참조 여부
$isReferenced = TenantFieldSetting::where('tenant_id', $tenantId)
->where('option_group_id', $item->id)
->exists();
if ($isReferenced) {
return ['error' => '필드 설정에서 참조 중인 그룹은 삭제할 수 없습니다.', 'code' => 409];
}
$item->delete();
return ['deleted' => true];
}
}