From 4503c217eb5f172e52cd6050f1af18157937d3b9 Mon Sep 17 00:00:00 2001 From: mirivlad Date: Mon, 30 Mar 2026 10:36:02 +0800 Subject: [PATCH] =?UTF-8?q?Feat:=20=D0=A3=D0=BD=D0=B8=D0=B2=D0=B5=D1=80?= =?UTF-8?q?=D1=81=D0=B0=D0=BB=D1=8C=D0=BD=D1=8B=D0=B9=20=D0=BA=D0=BE=D0=BC?= =?UTF-8?q?=D0=BF=D0=BE=D0=BD=D0=B5=D0=BD=D1=82=20Searchable=20Select?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ✅ TomSelect библиотека (15KB vs 100KB у Select2) ✅ Blade компонент x-searchable-select ✅ API endpoint /api/organizations/search ✅ Поиск по названию и ИНН ✅ AJAX загрузка данных ✅ Используется в create.blade.php для групп ✅ Модульная архитектура - можно использовать для других полей Co-authored-by: Qwen-Coder --- .../Controllers/Admin/GroupUserController.php | 4 +- .../Api/OrganizationSearchController.php | 30 ++++++++++ resources/views/admin/groups/create.blade.php | 17 +++--- .../components/searchable-select.blade.php | 55 +++++++++++++++++++ routes/web.php | 4 ++ 5 files changed, 100 insertions(+), 10 deletions(-) create mode 100755 app/Http/Controllers/Api/OrganizationSearchController.php create mode 100644 resources/views/components/searchable-select.blade.php diff --git a/app/Http/Controllers/Admin/GroupUserController.php b/app/Http/Controllers/Admin/GroupUserController.php index 74b7bb9..16385b5 100755 --- a/app/Http/Controllers/Admin/GroupUserController.php +++ b/app/Http/Controllers/Admin/GroupUserController.php @@ -47,9 +47,7 @@ class GroupUserController extends Controller { Gate::authorize('create', Group::class); - $organizations = Organization::pluck('name', 'id'); - - return view('admin.groups.create', compact('organizations')); + return view('admin.groups.create'); } public function store(Request $request) diff --git a/app/Http/Controllers/Api/OrganizationSearchController.php b/app/Http/Controllers/Api/OrganizationSearchController.php new file mode 100755 index 0000000..e466f13 --- /dev/null +++ b/app/Http/Controllers/Api/OrganizationSearchController.php @@ -0,0 +1,30 @@ +get('q', ''); + + $organizations = Organization::query() + ->where('name', 'like', "%{$query}%") + ->orWhere('inn', 'like', "%{$query}%") + ->orderBy('name') + ->limit(50) + ->get() + ->map(function($org) { + return [ + 'id' => $org->id, + 'text' => $org->name . ($org->inn ? " (ИНН: {$org->inn})" : ''), + ]; + }); + + return response()->json($organizations); + } +} diff --git a/resources/views/admin/groups/create.blade.php b/resources/views/admin/groups/create.blade.php index 89ab528..c73b1b6 100755 --- a/resources/views/admin/groups/create.blade.php +++ b/resources/views/admin/groups/create.blade.php @@ -30,13 +30,13 @@
@@ -90,3 +90,6 @@ document.addEventListener('DOMContentLoaded', function() { }); @endsection + +@push('scripts') +@endpush diff --git a/resources/views/components/searchable-select.blade.php b/resources/views/components/searchable-select.blade.php new file mode 100644 index 0000000..c9fd532 --- /dev/null +++ b/resources/views/components/searchable-select.blade.php @@ -0,0 +1,55 @@ +@props(['name', 'url', 'placeholder' => 'Начните вводить...', 'value' => null, 'required' => false]) + + + + +@push('scripts') + + + +@endpush diff --git a/routes/web.php b/routes/web.php index cb3254b..021c4fe 100644 --- a/routes/web.php +++ b/routes/web.php @@ -11,6 +11,7 @@ use App\Http\Controllers\Admin\TestController; use App\Http\Controllers\Admin\QuestionController; use App\Http\Controllers\Admin\CourseAssignmentController; use App\Http\Controllers\Admin\GroupUserController; +use App\Http\Controllers\Api\OrganizationSearchController; use App\Http\Controllers\DashboardController; use Illuminate\Support\Facades\Route; @@ -53,4 +54,7 @@ Route::middleware('auth')->group(function () { Route::post('/users/{user}/groups/add', [GroupUserController::class, 'addUser'])->name('groups.users.add'); Route::delete('/groups/{group}/users/{user}/remove', [GroupUserController::class, 'removeUser'])->name('groups.users.remove'); }); + + // API для поиска + Route::get('/api/organizations/search', OrganizationSearchController::class)->name('api.organizations.search'); });