Commit 82a9544dc9e201666cc245fce63bb786c74eddd7

Authored by Андрей Ларионов
1 parent bb2fb443df

Связи моделей, группы и сообщения системы

Showing 23 changed files with 672 additions and 19 deletions Side-by-side Diff

app/Http/Controllers/Admin/GroupsController.php
... ... @@ -0,0 +1,72 @@
  1 +<?php
  2 +
  3 +namespace App\Http\Controllers\Admin;
  4 +
  5 +use App\Http\Controllers\Controller;
  6 +use App\Models\Group_user;
  7 +use Illuminate\Http\Request;
  8 +use Illuminate\Support\Facades\Auth;
  9 +use Illuminate\Support\Facades\Validator;
  10 +
  11 +class GroupsController extends Controller
  12 +{
  13 + // индексная страница
  14 + public function index() {
  15 + $groups = Group_user::query()->paginate(15);
  16 + return view('admin.groups.index', compact('groups'));
  17 + }
  18 +
  19 + // форма добавления группы
  20 + public function add() {
  21 + $editor = Auth::user()->id;
  22 + return view('admin.groups.add', compact('editor'));
  23 + }
  24 +
  25 + // форма сохранения добавленной группы
  26 + public function store(Request $request) {
  27 + $rules = [
  28 + 'name_group' => 'required|min:3',
  29 + ];
  30 + $messages = [
  31 + 'required' => 'Укажите обязательное поле',
  32 + ];
  33 + $validator = Validator::make($request->all(), $rules, $messages);
  34 +
  35 + if ($validator->fails()) {
  36 + return redirect()->route('admin.add-group')
  37 + ->withErrors($validator);
  38 + } else {
  39 + Group_user::create($request->all());
  40 + return redirect()->route('admin.groups')
  41 + ->with('success', 'Данные были успешно сохранены');
  42 + }
  43 + return redirect()->route('admin.groups');
  44 + }
  45 +
  46 + // форма редактирования группы
  47 + public function edit(Group_user $group, Request $request) {
  48 + $editor = Auth::user()->id;
  49 + return view('admin.groups.edit', compact('editor', 'group'));
  50 + }
  51 +
  52 + // форма сохранения редактированной группы
  53 + public function update(Group_user $group, Request $request) {
  54 + $rules = [
  55 + 'name_group' => 'required|min:3',
  56 + ];
  57 + $messages = [
  58 + 'required' => 'Укажите обязательное поле',
  59 + ];
  60 + $validator = Validator::make($request->all(), $rules, $messages);
  61 +
  62 + if ($validator->fails()) {
  63 + return redirect()->route('admin.edit-group', ['group' => $group->id])
  64 + ->withErrors($validator);
  65 + } else {
  66 + $group->update($request->all());
  67 + return redirect()->route('admin.groups')
  68 + ->with('success', 'Данные были успешно сохранены');
  69 + }
  70 + return redirect()->route('admin.groups');
  71 + }
  72 +}
app/Http/Controllers/Admin/MsgAnswersController.php
... ... @@ -0,0 +1,16 @@
  1 +<?php
  2 +
  3 +namespace App\Http\Controllers\Admin;
  4 +
  5 +use App\Http\Controllers\Controller;
  6 +use App\Models\Message;
  7 +use Illuminate\Http\Request;
  8 +
  9 +class MsgAnswersController extends Controller
  10 +{
  11 + public function messages() {
  12 + $Msgs = Message::query()->orderByDesc('created_at')->paginate(25);
  13 +
  14 + return view('admin.messages', compact('Msgs'));
  15 + }
  16 +}
app/Models/Ad_employer.php
... ... @@ -11,8 +11,25 @@ class Ad_employer extends Model
11 11  
12 12 /*
13 13 * Связь таблицы employers с таблицей ad_employers
  14 + многие-к-одному
14 15 */
15 16 public function employer() {
16 17 return $this->belongsTo(Employer::class, 'employer_id');
17 18 }
  19 +
  20 + /*
  21 + * Связь модели Вакансии (Ad_employer) с моделью Должности (Job_title)
  22 + многие-ко-многим
  23 + */
  24 + public function jobs() {
  25 + return $this->belongsToMany(Job_title::class, 'ad_jobs');
  26 + }
  27 +
  28 + /*
  29 + * Связь модели Вакансия (Ad_employers) с моделью Отклик на Вакансию (Ad_response)
  30 + один-ко-многим
  31 + */
  32 + public function response() {
  33 + return $this->hasMany(ad_response::class);
  34 + }
18 35 }
app/Models/Employer.php
... ... @@ -30,4 +30,12 @@ class Employer extends Model
30 30 return $this->belongsTo(User::class, 'user_id');
31 31 }
32 32  
  33 + /*
  34 + * Связь Работодателя с вакансиями
  35 + */
  36 + public function ads() {
  37 + return $this->hasMany(Ad_employer::class);
  38 + }
  39 +
  40 +
33 41 }
app/Models/Group_user.php
... ... @@ -8,4 +8,26 @@ use Illuminate\Database\Eloquent\Model;
8 8 class Group_user extends Model
9 9 {
10 10 use HasFactory;
  11 +
  12 + protected $fillable = [
  13 + 'name_group',
  14 + 'user_id',
  15 + ];
  16 +
  17 + /*
  18 + * Связь Модели Группы (Group_user) с Модели Юзеры (User)
  19 + многие-к-одному
  20 + */
  21 + public function user() {
  22 + return $this->belongsTo(User::class, 'user_id');
  23 + }
  24 +
  25 + /*
  26 + * Связь модели Группы (Group_user) с Моделью Юзеры (User) - участники группы
  27 + многие-ко-многим
  28 + */
  29 + public function ingroup() {
  30 + return $this->belongsToMany(User::class, 'group_works');
  31 + }
  32 +
11 33 }
app/Models/Job_title.php
... ... @@ -8,4 +8,11 @@ use Illuminate\Database\Eloquent\Model;
8 8 class Job_title extends Model
9 9 {
10 10 use HasFactory;
  11 +
  12 + /*
  13 + * Связь модели Вакансии (Ad_employer) с моделью Должности (Job_title)
  14 + */
  15 + public function Ads() {
  16 + return $this->belongsToMany(Ad_employer::class, 'ad_jobs');
  17 + }
11 18 }
app/Models/Message.php
... ... @@ -8,4 +8,25 @@ use Illuminate\Database\Eloquent\Model;
8 8 class Message extends Model
9 9 {
10 10 use HasFactory;
  11 +
  12 + /*
  13 + * Связь таблицы Message с таблицей User (Отправитель)
  14 + */
  15 + public function user_from() {
  16 + return $this->belongsTo(User::class, 'user_id');
  17 + }
  18 +
  19 + /*
  20 + * Связь таблицы Message с таблицей User (Получатель)
  21 + */
  22 + public function user_to() {
  23 + return $this->belongsTo(User::class, 'to_user_id');
  24 + }
  25 +
  26 + /*
  27 + * Связь модели Сообщения (Message) с моделью Отклик на Вакансию (Ad_response)
  28 + */
  29 + public function response() {
  30 + return $this->hasMany(ad_response::class);
  31 + }
11 32 }
app/Models/ad_response.php
... ... @@ -8,4 +8,26 @@ use Illuminate\Database\Eloquent\Model;
8 8 class ad_response extends Model
9 9 {
10 10 use HasFactory;
  11 +
  12 + /*
  13 + * Связь таблицы Отклик на вакансию (ad_response) с таблицей Вакансия (ad_employer)
  14 + */
  15 + public function ad_employer() {
  16 + return $this->belongsTo(Ad_employer::class, 'ad_employer_id');
  17 + }
  18 +
  19 + /*
  20 + * Связь таблицы Отклик на вакансию (ad_response) с таблицей Должность (job_title)
  21 + */
  22 + public function job_title() {
  23 + return $this->belongsTo(Job_title::class, 'job_title_id');
  24 + }
  25 +
  26 + /*
  27 + * Связь таблицы Отклик на вакансию (ad_response) с таблицей Сообщение (messages)
  28 + */
  29 + public function message() {
  30 + return $this->belongsTo(Message::class, 'message_id');
  31 + }
  32 +
11 33 }
... ... @@ -14,7 +14,8 @@
14 14 "laravel/framework": "^9.19",
15 15 "laravel/sanctum": "^3.0",
16 16 "laravel/tinker": "^2.7",
17   - "laravel/ui": "^4.2"
  17 + "laravel/ui": "^4.2",
  18 + "ext-http": "*"
18 19 },
19 20 "require-dev": {
20 21 "fakerphp/faker": "^1.9.1",
database/migrations/2023_05_16_092746_alter_ad_jobs_table.php
... ... @@ -15,8 +15,6 @@ return new class extends Migration
15 15 {
16 16 Schema::create('ad_jobs', function (Blueprint $table) {
17 17 $table->id();
18   - $table->bigInteger('ad_employer_id')->nullable(false);
19   - $table->bigInteger('job_title_id')->nullable(false);
20 18 $table->timestamps();
21 19 });
22 20 }
database/migrations/2023_09_01_135734_create_dop_info_table.php
... ... @@ -15,8 +15,6 @@ return new class extends Migration
15 15 {
16 16 Schema::create('dop_info', function (Blueprint $table) {
17 17 $table->id();
18   - $table->bigInteger('worker_id')->nullable(false);
19   - $table->bigInteger('infoblok_id')->nullable(false);
20 18 $table->text('text')->nullable();
21 19 $table->timestamps();
22 20 });
database/migrations/2023_09_06_090200_alter_dop_info_table.php
... ... @@ -0,0 +1,46 @@
  1 +<?php
  2 +
  3 +use Illuminate\Database\Migrations\Migration;
  4 +use Illuminate\Database\Schema\Blueprint;
  5 +use Illuminate\Support\Facades\Schema;
  6 +
  7 +return new class extends Migration
  8 +{
  9 + /**
  10 + * Run the migrations.
  11 + *
  12 + * @return void
  13 + */
  14 + public function up()
  15 + {
  16 + Schema::table('dop_info', function (Blueprint $table) {
  17 +
  18 + $table->unsignedBigInteger('infoblok_id')->nullable();
  19 + //внешний ключ, ссылается на поле id таблицы infobloks
  20 + $table->foreign('infoblok_id', 'key_infoblok_id')
  21 + ->references('id')
  22 + ->on('infobloks')
  23 + ->onDelete('cascade');
  24 +
  25 + $table->unsignedBigInteger('worker_id')->nullable();
  26 + //внешний ключ, ссылается на поле id таблицы workers
  27 + $table->foreign('worker_id', 'key_worker_id')
  28 + ->references('id')
  29 + ->on('workers')
  30 + ->onDelete('cascade');
  31 + });
  32 + }
  33 +
  34 + /**
  35 + * Reverse the migrations.
  36 + *
  37 + * @return void
  38 + */
  39 + public function down()
  40 + {
  41 + Schema::table('dop_info', function (Blueprint $table) {
  42 + $table->dropIndex(['key_infoblok_id']);
  43 + $table->dropIndex(['key_worker_id']);
  44 + });
  45 + }
  46 +};
database/migrations/2023_09_06_090312_alter_ad_jobs_table.php
... ... @@ -0,0 +1,47 @@
  1 +<?php
  2 +
  3 +use Illuminate\Database\Migrations\Migration;
  4 +use Illuminate\Database\Schema\Blueprint;
  5 +use Illuminate\Support\Facades\Schema;
  6 +
  7 +return new class extends Migration
  8 +{
  9 + /**
  10 + * Run the migrations.
  11 + *
  12 + * @return void
  13 + */
  14 + public function up()
  15 + {
  16 + Schema::table('ad_jobs', function (Blueprint $table) {
  17 + $table->unsignedBigInteger('ad_employer_id')->nullable();
  18 + //внешний ключ, ссылается на поле id таблицы ad_employers
  19 + $table->foreign('ad_employer_id', 'key_ad_employer_id')
  20 + ->references('id')
  21 + ->on('ad_employers')
  22 + ->onDelete('cascade');
  23 +
  24 + $table->unsignedBigInteger('job_title_id')->nullable();
  25 + //внешний ключ, ссылается на поле id таблицы job_titles
  26 + $table->foreign('job_title_id', 'key_job_title_id')
  27 + ->references('id')
  28 + ->on('job_titles')
  29 + ->onDelete('cascade');
  30 + });
  31 + }
  32 +
  33 + /**
  34 + * Reverse the migrations.
  35 + *
  36 + * @return void
  37 + */
  38 + public function down()
  39 + {
  40 + Schema::table('ad_jobs', function (Blueprint $table) {
  41 + $table->dropIndex(['key_ad_employer_id']);
  42 + $table->dropIndex(['key_job_title_id']);
  43 + $table->dropColumn('job_title_id');
  44 + $table->dropColumn('ad_employer_id');
  45 + });
  46 + }
  47 +};
database/migrations/2023_09_06_100450_alter_ad_employers_table.php
... ... @@ -0,0 +1,32 @@
  1 +<?php
  2 +
  3 +use Illuminate\Database\Migrations\Migration;
  4 +use Illuminate\Database\Schema\Blueprint;
  5 +use Illuminate\Support\Facades\Schema;
  6 +
  7 +return new class extends Migration
  8 +{
  9 + /**
  10 + * Run the migrations.
  11 + *
  12 + * @return void
  13 + */
  14 + public function up()
  15 + {
  16 + Schema::table('ad_employers', function (Blueprint $table) {
  17 + $table->string('name', 255)->nullable();
  18 + });
  19 + }
  20 +
  21 + /**
  22 + * Reverse the migrations.
  23 + *
  24 + * @return void
  25 + */
  26 + public function down()
  27 + {
  28 + Schema::table('ad_employers', function (Blueprint $table) {
  29 + $table->dropColumn('name');
  30 + });
  31 + }
  32 +};
resources/views/admin/ad_employers/index.blade.php
1   -@extends('layout.admin', ['title' => 'Админка - Работодатели'])
  1 +@extends('layout.admin', ['title' => 'Админка - Вакансии'])
2 2  
3 3 @section('script')
4 4 @endsection
5 5  
6 6 @section('search')
7   - <div class="absolute inset-y-0 flex items-center pl-2">
  7 + <!--<div class="absolute inset-y-0 flex items-center pl-2">
8 8 <svg
9 9 class="w-4 h-4"
10 10 aria-hidden="true"
... ... @@ -23,13 +23,13 @@
23 23 class="w-full pl-8 pr-2 text-sm text-gray-700 placeholder-gray-600 bg-gray-100 border-0 rounded-md dark:placeholder-gray-500 dark:focus:shadow-outline-gray dark:focus:placeholder-gray-600 dark:bg-gray-700 dark:text-gray-200 focus:placeholder-gray-500 focus:bg-white focus:border-purple-300 focus:outline-none focus:shadow-outline-purple form-input"
24 24 style="width: 400px"
25 25 type="text"
26   - placeholder="Искать..."
  26 + placeholder="Искать компанию или вакансию"
27 27 aria-label="Search"
28 28 /></div>
29 29 <div style="float: left">
30   - <button type="submit" class="px-3 py-1 rounded-md focus:outline-none focus:shadow-outline-purple">Искать</button>
  30 + <button type="submit" class="px-3 py-1 rounded-md focus:outline-none focus:shadow-outline-purple">Поиск</button>
31 31 </div>
32   - </form>
  32 + </form>-->
33 33 @endsection
34 34  
35 35 @section('content')
... ... @@ -41,9 +41,11 @@
41 41 class="text-xs font-semibold tracking-wide text-left text-gray-500 uppercase border-b dark:border-gray-700 bg-gray-50 dark:text-gray-400 dark:bg-gray-800"
42 42 >
43 43 <th class="px-4 py-3">№</th>
  44 + <th class="px-4 py-3">Название объявления</th>
44 45 <th class="px-4 py-3">Название компании</th>
45 46 <th class="px-4 py-3">Вакансии</th>
46 47 <th class="px-4 py-3">Город</th>
  48 + <th class="px-4 py-3">З/п</th>
47 49 <th class="px-4 py-3">Дата</th>
48 50 </tr>
49 51 </thead>
... ... @@ -54,17 +56,27 @@
54 56 {{$ad->id}}
55 57 </td>
56 58 <td class="px-4 py-3">
57   - {{$ad->employers->name_company}}
  59 + {{$ad->name}}
  60 + </td>
  61 + <td class="px-4 py-3">
  62 + {{$ad->employer->name_company}}
58 63 </td>
59 64 <td class="px-4 py-3">
60 65 <div class="flex items-center text-sm">
  66 + @if ($ad->jobs->count())
61 67 <div>
62   -
63   - <p class="font-semibold"></p>
64   - <p class="text-xs text-gray-600 dark:text-gray-400">
65   - </p>
66   -
  68 + <?php $i = 0;?>
  69 + @foreach ($ad->jobs as $title)
  70 + <?php if ($i==0) {?>
  71 + <p class="font-semibold">{{$title->name}}</p>
  72 + <?php } else {?>
  73 + <p class="font-semibold">/ {{$title->name}}</p>
  74 + <?php }
  75 + $i++;
  76 + ?>
  77 + @endforeach
67 78 </div>
  79 + @endif
68 80 </div>
69 81  
70 82 </td>
... ... @@ -72,6 +84,9 @@
72 84 {{ $ad->city }}
73 85 </td>
74 86 <td class="px-4 py-3 text-sm">
  87 + {{ $ad->salary }}
  88 + </td>
  89 + <td class="px-4 py-3 text-sm">
75 90 {{ $ad->created_at }}
76 91 </td>
77 92 </tr>
... ... @@ -81,7 +96,7 @@
81 96 </div>
82 97  
83 98 <div class="grid px-4 py-3 text-xs font-semibold tracking-wide text-gray-500 uppercase border-t dark:border-gray-700 bg-gray-50 sm:grid-cols-9 dark:text-gray-400 dark:bg-gray-800">
84   - <?=$ad->appends($_GET)->links('admin.pagginate'); ?>
  99 + <?=$ad_employers->appends($_GET)->links('admin.pagginate'); ?>
85 100 </div>
86 101 </div>
87 102 @endsection
resources/views/admin/groups/add.blade.php
... ... @@ -0,0 +1,11 @@
  1 +@extends('layout.admin', ['title' => 'Админка - Добавление новой группы'])
  2 +
  3 +@section('content')
  4 + <h4 class="mb-4 text-lg font-semibold text-gray-600 dark:text-gray-300">
  5 + Добавление новой группы
  6 + </h4>
  7 + <form method="POST" action="{{ route('admin.add-group-store') }}">
  8 + @csrf
  9 + @include('admin.groups.form')
  10 + </form>
  11 +@endsection
resources/views/admin/groups/edit.blade.php
... ... @@ -0,0 +1,11 @@
  1 +@extends('layout.admin', ['title' => 'Админка - Редактирование группы'])
  2 +
  3 +@section('content')
  4 + <h4 class="mb-4 text-lg font-semibold text-gray-600 dark:text-gray-300">
  5 + Редактирование группы
  6 + </h4>
  7 + <form method="POST" action="{{ route('admin.update-group', ['group' => $group->id]) }}">
  8 + @csrf
  9 + @include('admin.groups.form')
  10 + </form>
  11 +@endsection
resources/views/admin/groups/form.blade.php
... ... @@ -0,0 +1,25 @@
  1 +<div class="px-4 py-3 mb-8 bg-white rounded-lg shadow-md dark:bg-gray-800">
  2 + <label class="block text-sm">
  3 + <span class="text-gray-700 dark:text-gray-400">Имя группы</span>
  4 + <input name="name_group" id="name_group"
  5 + class="block w-full mt-1 text-sm dark:border-gray-600 dark:bg-gray-700 focus:border-purple-400 focus:outline-none focus:shadow-outline-purple dark:text-gray-300 dark:focus:shadow-outline-gray form-input"
  6 + placeholder="Название группы" value="{{ old('name_group') ?? $group->name_group ?? '' }}"
  7 + />
  8 + @error('name_group')
  9 + <span class="text-xs text-red-600 dark:text-red-400">
  10 + {{ $message }}
  11 + </span>
  12 + @enderror
  13 + </label><br>
  14 +
  15 + <input type="hidden" name="user_id" id="user_id" value="{{ $editor }}"/>
  16 +
  17 + <div class="flex flex-col flex-wrap mb-4 space-y-4 md:flex-row md:items-end md:space-x-4">
  18 + <div>
  19 + <button type="submit" class="px-3 py-1 text-sm font-medium leading-5 text-white transition-colors duration-150 bg-purple-600 border border-transparent rounded-md active:bg-purple-600 hover:bg-purple-700 focus:outline-none focus:shadow-outline-purple">
  20 + Сохранить
  21 + </button>
  22 + </div>
  23 + </div>
  24 +</div>
  25 +
resources/views/admin/groups/index.blade.php
... ... @@ -0,0 +1,118 @@
  1 +@extends('layout.admin', ['title' => 'Админка - Группы пользователей'])
  2 +
  3 +@section('script')
  4 + <script>
  5 + $(document).ready(function() {
  6 + $(document).on('click', '.checkban', function () {
  7 + var this_ = $(this);
  8 + var value = this_.val();
  9 + var ajax_block = $('#ajax_block');
  10 + var bool = 0;
  11 +
  12 + if(this.checked){
  13 + bool = 1;
  14 + } else {
  15 + bool = 0;
  16 + }
  17 +
  18 + $.ajax({
  19 + type: "GET",
  20 + url: "{{ url()->full()}}",
  21 + data: "id=" + value + "&is_ban=" + bool,
  22 + success: function (data) {
  23 + console.log('Обновление таблицы пользователей ');
  24 + //data = JSON.parse(data);
  25 + //console.log(data);
  26 + ajax_block.html(data);
  27 + },
  28 + headers: {
  29 + 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
  30 + },
  31 + error: function (data) {
  32 + console.log('Error: ' + data);
  33 + }
  34 + });
  35 + });
  36 +
  37 + });
  38 + </script>
  39 +@endsection
  40 +
  41 +@section('search')
  42 + <!--<div class="absolute inset-y-0 flex items-center pl-2">
  43 + <svg
  44 + class="w-4 h-4"
  45 + aria-hidden="true"
  46 + fill="currentColor"
  47 + viewBox="0 0 20 20"
  48 + >
  49 + <path
  50 + fill-rule="evenodd"
  51 + d="M8 4a4 4 0 100 8 4 4 0 000-8zM2 8a6 6 0 1110.89 3.476l4.817 4.817a1 1 0 01-1.414 1.414l-4.816-4.816A6 6 0 012 8z"
  52 + clip-rule="evenodd"
  53 + ></path>
  54 + </svg>
  55 + </div>
  56 + <form action="" method="POST">
  57 + <div style="float:left;"><input
  58 + class="w-full pl-8 pr-2 text-sm text-gray-700 placeholder-gray-600 bg-gray-100 border-0 rounded-md dark:placeholder-gray-500 dark:focus:shadow-outline-gray dark:focus:placeholder-gray-600 dark:bg-gray-700 dark:text-gray-200 focus:placeholder-gray-500 focus:bg-white focus:border-purple-300 focus:outline-none focus:shadow-outline-purple form-input"
  59 + style="width: 400px"
  60 + type="text"
  61 + placeholder="Искать..."
  62 + aria-label="Search"
  63 + /></div>
  64 + <div style="float: left">
  65 + <button type="submit" class="px-3 py-1 rounded-md focus:outline-none focus:shadow-outline-purple">Искать</button>
  66 + </div>
  67 + </form>-->
  68 +@endsection
  69 +
  70 +@section('content')
  71 + <div class="w-full overflow-hidden rounded-lg shadow-xs" id="ajax_block">
  72 + <div class="w-full overflow-x-auto">
  73 + <a class="px-3 py-1 text-sm font-medium leading-5 text-white transition-colors duration-150 bg-purple-600 border border-transparent rounded-md active:bg-purple-600 hover:bg-purple-700 focus:outline-none focus:shadow-outline-purple" href="{{ route('admin.add-group') }}">Создать группу</a><br><br>
  74 + <table class="w-full whitespace-no-wrap">
  75 + <thead>
  76 + <tr
  77 + class="text-xs font-semibold tracking-wide text-left text-gray-500 uppercase border-b dark:border-gray-700 bg-gray-50 dark:text-gray-400 dark:bg-gray-800"
  78 + >
  79 + <th class="px-4 py-3">№</th>
  80 + <th class="px-4 py-3">Название группы</th>
  81 + <th class="px-4 py-3">Создатель группы</th>
  82 + <th class="px-4 py-3">Кол-во участников</th>
  83 + <th class="px-4 py-3">Дата регистрации</th>
  84 + <th class="px-4 py-3">Изменить</th>
  85 + </tr>
  86 + </thead>
  87 + <tbody class="bg-white divide-y dark:divide-gray-700 dark:bg-gray-800">
  88 + @foreach($groups as $group)
  89 + <tr class="text-gray-700 dark:text-gray-400">
  90 + <td class="px-4 py-3">
  91 + {{$group->id}}
  92 + </td>
  93 + <td class="px-4 py-3">
  94 + {{$group->name_group}}
  95 + </td>
  96 + <td class="px-4 py-3">
  97 + {{$group->user->name}}
  98 + </td>
  99 + <td class="px-4 py-3">
  100 + {{$group->ingroup->count()}}
  101 + </td>
  102 + <td class="px-4 py-3 text-sm">
  103 + {{ $group->created_at }}
  104 + </td>
  105 + <td class="px-4 py-3 text-sm">
  106 + <a href="{{ route('admin.edit-group', ['group' => $group->id]) }}">Изменить</a>
  107 + </td>
  108 + </tr>
  109 + @endforeach
  110 + </tbody>
  111 + </table>
  112 + </div>
  113 +
  114 + <div class="grid px-4 py-3 text-xs font-semibold tracking-wide text-gray-500 uppercase border-t dark:border-gray-700 bg-gray-50 sm:grid-cols-9 dark:text-gray-400 dark:bg-gray-800">
  115 + <?=$groups->appends($_GET)->links('admin.pagginate'); ?>
  116 + </div>
  117 + </div>
  118 +@endsection
resources/views/admin/index.blade.php
... ... @@ -422,6 +422,32 @@
422 422 сентябрь 2023
423 423 </td>
424 424 </tr>
  425 + <tr class="text-gray-700 dark:text-gray-400">
  426 + <td class="px-4 py-3">
  427 + <div class="flex items-center text-sm">
  428 + <div class="relative hidden w-8 h-8 mr-3 rounded-full md:block">
  429 + <div class="absolute inset-0 rounded-full shadow-inner" aria-hidden="true"></div>
  430 + </div>
  431 + <div>
  432 + <p class="font-semibold"><a href="{{ route('admin.answers') }}">Модерация</a></p>
  433 + <p class="text-xs text-gray-600 dark:text-gray-400">
  434 + Модерация отзывов о работодателе
  435 + </p>
  436 + </div>
  437 + </div>
  438 + </td>
  439 + <td class="px-4 py-3 text-sm">
  440 + answers
  441 + </td>
  442 + <td class="px-4 py-3 text-xs">
  443 + <span class="px-2 py-1 font-semibold leading-tight text-green-700 bg-green-100 rounded-full dark:bg-green-700 dark:text-green-100">
  444 + Доступно
  445 + </span>
  446 + </td>
  447 + <td class="px-4 py-3 text-sm">
  448 + сентябрь 2023
  449 + </td>
  450 + </tr>
425 451  
426 452 <!--<tr class="text-gray-700 dark:text-gray-400">
427 453 <td class="px-4 py-3">
resources/views/admin/messages.blade.php
... ... @@ -0,0 +1,90 @@
  1 +@extends('layout.admin', ['title' => 'Админка - Вакансии'])
  2 +
  3 +@section('script')
  4 +@endsection
  5 +
  6 +@section('search')
  7 + <!--<div class="absolute inset-y-0 flex items-center pl-2">
  8 + <svg
  9 + class="w-4 h-4"
  10 + aria-hidden="true"
  11 + fill="currentColor"
  12 + viewBox="0 0 20 20"
  13 + >
  14 + <path
  15 + fill-rule="evenodd"
  16 + d="M8 4a4 4 0 100 8 4 4 0 000-8zM2 8a6 6 0 1110.89 3.476l4.817 4.817a1 1 0 01-1.414 1.414l-4.816-4.816A6 6 0 012 8z"
  17 + clip-rule="evenodd"
  18 + ></path>
  19 + </svg>
  20 + </div>
  21 + <form action="" method="POST">
  22 + <div style="float:left;"><input
  23 + class="w-full pl-8 pr-2 text-sm text-gray-700 placeholder-gray-600 bg-gray-100 border-0 rounded-md dark:placeholder-gray-500 dark:focus:shadow-outline-gray dark:focus:placeholder-gray-600 dark:bg-gray-700 dark:text-gray-200 focus:placeholder-gray-500 focus:bg-white focus:border-purple-300 focus:outline-none focus:shadow-outline-purple form-input"
  24 + style="width: 400px"
  25 + type="text"
  26 + placeholder="Искать компанию или вакансию"
  27 + aria-label="Search"
  28 + /></div>
  29 + <div style="float: left">
  30 + <button type="submit" class="px-3 py-1 rounded-md focus:outline-none focus:shadow-outline-purple">Поиск</button>
  31 + </div>
  32 + </form>-->
  33 +@endsection
  34 +
  35 +@section('content')
  36 + <div class="w-full overflow-hidden rounded-lg shadow-xs" id="ajax_block">
  37 + <div class="w-full overflow-x-auto">
  38 + <table class="w-full whitespace-no-wrap">
  39 + <thead>
  40 + <tr
  41 + class="text-xs font-semibold tracking-wide text-left text-gray-500 uppercase border-b dark:border-gray-700 bg-gray-50 dark:text-gray-400 dark:bg-gray-800"
  42 + >
  43 + <th class="px-4 py-3">№</th>
  44 + <th class="px-4 py-3">От юзера</th>
  45 + <th class="px-4 py-3">К юзеру</th>
  46 + <th class="px-4 py-3">Заголовок</th>
  47 + <th class="px-4 py-3">Отклик</th>
  48 + <th class="px-4 py-3">Дата</th>
  49 + </tr>
  50 + </thead>
  51 + <tbody class="bg-white divide-y dark:divide-gray-700 dark:bg-gray-800">
  52 + @foreach($Msgs as $msg)
  53 + <tr class="text-gray-700 dark:text-gray-400">
  54 + <td class="px-4 py-3">
  55 + {{$msg->id}}
  56 + </td>
  57 + <td class="px-4 py-3">
  58 + {{$msg->user_from->name}} ({{$msg->user_from->id}})
  59 + </td>
  60 + <td class="px-4 py-3">
  61 + {{$msg->user_to->name}} ({{$msg->user_to->id}})
  62 + </td>
  63 + <td class="px-4 py-3">
  64 + {{$msg->title}}
  65 + </td>
  66 + <td class="px-4 py-3">
  67 + <div class="flex items-center text-sm">
  68 + <div>
  69 + @if ($msg->response->count())
  70 + Да
  71 + @else
  72 + Нет
  73 + @endif
  74 + </div>
  75 + </div>
  76 + </td>
  77 + <td class="px-4 py-3 text-sm">
  78 + {{ $msg->created_at }}
  79 + </td>
  80 + </tr>
  81 + @endforeach
  82 + </tbody>
  83 + </table>
  84 + </div>
  85 +
  86 + <div class="grid px-4 py-3 text-xs font-semibold tracking-wide text-gray-500 uppercase border-t dark:border-gray-700 bg-gray-50 sm:grid-cols-9 dark:text-gray-400 dark:bg-gray-800">
  87 + <?=$Msgs->appends($_GET)->links('admin.pagginate'); ?>
  88 + </div>
  89 + </div>
  90 +@endsection
resources/views/layout/admin.blade.php
... ... @@ -235,6 +235,26 @@
235 235 <span class="ml-4">Статистика</span>
236 236 </a>
237 237 </li>
  238 + <li class="relative px-6 py-3">
  239 + <a
  240 + class="inline-flex items-center w-full text-sm font-semibold transition-colors duration-150 hover:text-gray-800 dark:hover:text-gray-200"
  241 + href="{{ route('admin.answers') }}"
  242 + >
  243 + <svg
  244 + class="w-5 h-5"
  245 + aria-hidden="true"
  246 + fill="none"
  247 + stroke-linecap="round"
  248 + stroke-linejoin="round"
  249 + stroke-width="2"
  250 + viewBox="0 0 24 24"
  251 + stroke="currentColor"
  252 + >
  253 + <path d="M4 6h16M4 10h16M4 14h16M4 18h16"></path>
  254 + </svg>
  255 + <span class="ml-4">Модерация</span>
  256 + </a>
  257 + </li>
238 258 <!-- Справочники -->
239 259 <li class="relative px-6 py-3" x-data="{ open1: false }">
240 260 <button
... ... @@ -608,6 +628,26 @@
608 628 <span class="ml-4">Статистика</span>
609 629 </a>
610 630 </li>
  631 + <li class="relative px-6 py-3">
  632 + <a
  633 + class="inline-flex items-center w-full text-sm font-semibold transition-colors duration-150 hover:text-gray-800 dark:hover:text-gray-200"
  634 + href="{{ route('admin.messages') }}"
  635 + >
  636 + <svg
  637 + class="w-5 h-5"
  638 + aria-hidden="true"
  639 + fill="none"
  640 + stroke-linecap="round"
  641 + stroke-linejoin="round"
  642 + stroke-width="2"
  643 + viewBox="0 0 24 24"
  644 + stroke="currentColor"
  645 + >
  646 + <path d="M4 6h16M4 10h16M4 14h16M4 18h16"></path>
  647 + </svg>
  648 + <span class="ml-4">Сообщения</span>
  649 + </a>
  650 + </li>
611 651 <!-- Справочники -->
612 652 <li class="relative px-6 py-3" x-data="{ open2: false }">
613 653 <button
... ... @@ -13,6 +13,8 @@ use App\Http\Controllers\HomeController;
13 13 use Illuminate\Support\Facades\Route;
14 14 use App\Http\Controllers\Admin\CompanyController;
15 15 use App\Http\Controllers\Admin\Ad_EmployersController;
  16 +use App\Http\Controllers\Admin\MsgAnswersController;
  17 +use App\Http\Controllers\Admin\GroupsController;
16 18  
17 19  
18 20 /*
... ... @@ -135,10 +137,18 @@ Route::group([
135 137 Route::get('job-titles', [AdminController::class, 'index'])->name('job-titles');
136 138  
137 139 // кабинет - сообщения
138   - Route::get('messages', [AdminController::class, 'index'])->name('messages');
  140 + Route::get('messages', [MsgAnswersController::class, 'messages'])->name('messages');
139 141  
140 142 // кабинет - группы пользователей
141   - Route::get('groups', [AdminController::class, 'index'])->name('groups');
  143 + Route::get('groups', [GroupsController::class, 'index'])->name('groups');
  144 + // кабинет - добавление форма группы пользователей
  145 + Route::get('groups/add', [GroupsController::class, 'add'])->name('add-group');
  146 + // кабинет - сохранение формы группы пользователей
  147 + Route::post('groups/add', [GroupsController::class, 'store'])->name('add-group-store');
  148 + // кабинет - редактирование форма группы пользователей
  149 + Route::get('groups/edit/{group}', [GroupsController::class, 'edit'])->name('edit-group');
  150 + // кабинет - сохранение редактированной формы группы пользователей
  151 + Route::post('groups/edit/{group}', [GroupsController::class, 'update'])->name('update-group');
142 152  
143 153 // кабинет - список админов
144 154 Route::get('group-admin', [AdminController::class, 'index'])->name('group-admin');