From 215ac23d362ef5064c94860fa1764bde8892c035 Mon Sep 17 00:00:00 2001 From: mahdihty Date: Sat, 6 Mar 2021 11:49:43 +0330 Subject: [PATCH 1/3] add middleware --- routes/api.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/routes/api.php b/routes/api.php index a51789c..4a40912 100644 --- a/routes/api.php +++ b/routes/api.php @@ -16,7 +16,7 @@ $router->get('/{transaction}/redirection', 'CreditController@redirection'); $router->group(['prefix' => 'auth'], function () use ($router) { $router->get('/', 'AuthController@auth')->middleware('auth:api'); $router->delete('/', 'AuthController@delete'); - $router->get('/info', 'AuthController@authWithInfo'); + $router->get('/info', 'AuthController@authWithInfo')->middleware('auth:api'); $router->post('login', 'AuthController@login'); $router->post('logout', 'AuthController@logout')->middleware('auth:api'); $router->post('register', 'AuthController@register'); From 3cf22ba2674629f85c254e4d61ba54b3c1372f70 Mon Sep 17 00:00:00 2001 From: mahdihty Date: Sat, 6 Mar 2021 16:21:45 +0330 Subject: [PATCH 2/3] add activity => model, controller, migration, routes also add event and listener for model saved --- app/Events/ModelSaved.php | 38 ++++++ app/Http/Controllers/ActivityController.php | 110 ++++++++++++++++++ app/Listeners/ActivityRegistration.php | 73 ++++++++++++ app/Models/Model.php | 27 +++-- app/Providers/EventServiceProvider.php | 5 + ...1_03_06_085855_create_activities_table.php | 45 +++++++ ..._03_06_114918_create_failed_jobs_table.php | 36 ++++++ routes/api.php | 5 + 8 files changed, 327 insertions(+), 12 deletions(-) create mode 100644 app/Events/ModelSaved.php create mode 100644 app/Http/Controllers/ActivityController.php create mode 100644 app/Listeners/ActivityRegistration.php create mode 100644 database/migrations/2021_03_06_085855_create_activities_table.php create mode 100644 database/migrations/2021_03_06_114918_create_failed_jobs_table.php diff --git a/app/Events/ModelSaved.php b/app/Events/ModelSaved.php new file mode 100644 index 0000000..32a28cc --- /dev/null +++ b/app/Events/ModelSaved.php @@ -0,0 +1,38 @@ +message = $message; + } + + /** + * Get the channels the event should broadcast on. + * + * @return \Illuminate\Broadcasting\Channel|array + */ + public function broadcastOn() + { + return new PrivateChannel('channel-name'); + } +} diff --git a/app/Http/Controllers/ActivityController.php b/app/Http/Controllers/ActivityController.php new file mode 100644 index 0000000..870279c --- /dev/null +++ b/app/Http/Controllers/ActivityController.php @@ -0,0 +1,110 @@ +indexValidation($request); + $per_page = $request->limit > 100 ? 10 : $request->limit; + return $this->indexFiltering($business)->paginate($per_page); + } + + public function indexValidation($request) + { + $bound = 10; + $this->validate($request, [ + 'filter.project_id' => [new MaxBound($bound)] , + 'filter.system_id' => [new MaxBound($bound)] , + 'filter.workflow_id' => [new MaxBound($bound)] , + 'filter.status_id' => [new MaxBound($bound)] , + 'filter.sprint_id' => [new MaxBound($bound)] , + 'filter.actor_id' => [new MaxBound($bound)] , + 'filter.user_id' => [new MaxBound($bound)] , + 'filter.subject_id' => [new MaxBound($bound)] , + //todo: validation for crud_id and table_id + 'filter.creates_before' => 'bail|nullable|date|date_format:Y-m-d' , + 'filter.creates_after' => 'bail|nullable|date|date_format:Y-m-d' , + 'filter.creates_in' => 'bail|nullable|numeric|max:90' , + ]); + } + public function indexFiltering($business) + { + $query = Activity::where('business_id', $business); + $activityQ = QueryBuilder::for($query) + ->allowedFilters([ + AllowedFilter::exact('project_id'), + AllowedFilter::exact('system_id'), + AllowedFilter::exact('workflow_id'), + AllowedFilter::exact('status_id'), + AllowedFilter::exact('sprint_id'), + AllowedFilter::exact('task_id'), + AllowedFilter::exact('actor_id'), + AllowedFilter::exact('user_id'), + AllowedFilter::exact('crud_id'), + AllowedFilter::exact('table_id'), + AllowedFilter::exact('subject_id'), + AllowedFilter::scope('creates_before'), + AllowedFilter::scope('creates_after'), + AllowedFilter::scope('creates_in'), + ]) + ->defaultSort('-id') + ->allowedSorts('id', 'created_at'); + if (\request('_business_info')['info']['users'][\auth()->id()]['level'] != enum('levels.owner.id')) { + $requested_projects = isset(\request('filter')['project_id']) ? + array_unique(explode(',',\request('filter')['project_id'] ?? null )) : + null; + $requested_projects = collect($requested_projects)->keyBy(null)->toArray(); + $project_ids = $this->myStateProjects($requested_projects); + $activityQ->where(function ($q) use ($project_ids) { + $q->whereIn('project_id', $project_ids['non_guest_ids']) + ->orWhere(function ($q) use ($project_ids) { + $q->whereIn('project_id', $project_ids['guest_ids']) + ->where('user_id', auth()->id()); + }); + }); + } + return $activityQ; + } + + public function myStateProjects($requested_projects) + { + $non_guest_ids = []; + $guest_ids = []; + $is_empty = empty($requested_projects); + + foreach (\request('_business_info')['info']['projects'] as $p_id => $p) { + + $level = \request('_business_info')['info']['projects'][$p_id]['members'][\auth()->id()]['level']; + + if (( $is_empty || isset($requested_projects[$p_id])) + && $level > enum('levels.guest.id')) { + array_push($non_guest_ids, $p_id); + } + if (( $is_empty || isset($requested_projects[$p_id])) + && $level == enum('levels.guest.id')) { + array_push($guest_ids, $p_id); + } + } + + return ['non_guest_ids' => $non_guest_ids, 'guest_ids' => $guest_ids]; + } + + public function store($business, Request $request) + { + return Activity::create($request->merge(['business_id' => $business])->all()); + } + + public function delete() + { + + } +} diff --git a/app/Listeners/ActivityRegistration.php b/app/Listeners/ActivityRegistration.php new file mode 100644 index 0000000..90b97b8 --- /dev/null +++ b/app/Listeners/ActivityRegistration.php @@ -0,0 +1,73 @@ +message)); + $message = json_decode($event->message); + Activity::create([ + 'business_id' => $message->business, + 'project_id' => $message->project, + 'actor_id' => $message->auth, + 'system_id' => $message->data->system_id, + 'workflow_id' => $message->data->workflow_id, + 'status_id' => $message->data->status_id, + 'sprint_id' => $message->data->sprint_id, + 'task_id' => $message->data->task_id ?? null, + 'subject_id' => $message->data->subject_id ?? null, + 'user_id' => $message->data->user_id, + 'crud_id' => $message->data->crud_id, + 'table_id' => enum('tables.'.$message->data->table_name.'.id'), + 'original' => $message->data->original, + 'diff' => $message->data->diff, + ]); + } +} diff --git a/app/Models/Model.php b/app/Models/Model.php index db30979..05ae626 100644 --- a/app/Models/Model.php +++ b/app/Models/Model.php @@ -4,6 +4,7 @@ namespace App\Models; use Anik\Amqp\Exchange; use Anik\Amqp\Facades\Amqp; +use App\Events\ModelSaved; use PhpAmqpLib\Wire\AMQPTable; use Anik\Amqp\PublishableMessage; use Illuminate\Http\JsonResponse; @@ -196,19 +197,21 @@ class Model extends EloquentModel $message = new PublishableMessage(json_encode($payload)); - $routers = [ - "activity_exchange" => ["name" => "activity",], - "notif_exchange" => ["name" => "notif",], - "socket_exchange" => ["name" => "socket",], - ]; - - foreach ($routers as $exchange => $properties) { - $message->setProperties(["application_headers" => new AMQPTable($properties)]); - - $message->setExchange(new Exchange($exchange)); + ModelSaved::dispatch(json_encode($payload)); - Amqp::publish($message, ""); - } +// $routers = [ +// "activity_exchange" => ["name" => "activity",], +// "notif_exchange" => ["name" => "notif",], +// "socket_exchange" => ["name" => "socket",], +// ]; +// +// foreach ($routers as $exchange => $properties) { +// $message->setProperties(["application_headers" => new AMQPTable($properties)]); +// +// $message->setExchange(new Exchange($exchange)); +// +// Amqp::publish($message, ""); +// } } /** diff --git a/app/Providers/EventServiceProvider.php b/app/Providers/EventServiceProvider.php index a9f10a6..4d702ef 100644 --- a/app/Providers/EventServiceProvider.php +++ b/app/Providers/EventServiceProvider.php @@ -2,6 +2,8 @@ namespace App\Providers; +use App\Events\ModelSaved; +use App\Listeners\ActivityRegistration; use Illuminate\Auth\Events\Registered; use Illuminate\Auth\Listeners\SendEmailVerificationNotification; use Illuminate\Foundation\Support\Providers\EventServiceProvider as ServiceProvider; @@ -18,6 +20,9 @@ class EventServiceProvider extends ServiceProvider Registered::class => [ SendEmailVerificationNotification::class, ], + ModelSaved::class => [ + ActivityRegistration::class + ] ]; /** diff --git a/database/migrations/2021_03_06_085855_create_activities_table.php b/database/migrations/2021_03_06_085855_create_activities_table.php new file mode 100644 index 0000000..ee00afe --- /dev/null +++ b/database/migrations/2021_03_06_085855_create_activities_table.php @@ -0,0 +1,45 @@ +id(); + $table->unsignedBigInteger('business_id'); + $table->unsignedBigInteger('project_id')->nullable(); + $table->unsignedBigInteger('system_id')->nullable(); + $table->unsignedBigInteger('workflow_id')->nullable(); + $table->unsignedBigInteger('status_id')->nullable(); + $table->unsignedBigInteger('sprint_id')->nullable(); + $table->unsignedBigInteger('task_id')->nullable(); + $table->unsignedBigInteger('subject_id')->nullable();//row id + $table->unsignedBigInteger('actor_id'); + $table->unsignedBigInteger('user_id')->nullable(); + $table->unsignedBigInteger('crud_id')->nullable(); + $table->unsignedBigInteger('table_id')->nullable(); + $table->json('original')->nullable(); // a unique identifier that represent the type of action + $table->json('diff')->nullable(); // all data that has been changed + $table->timestamps(); + }); + } + + /** + * Reverse the migrations. + * + * @return void + */ + public function down() + { + Schema::dropIfExists('activities'); + } +} diff --git a/database/migrations/2021_03_06_114918_create_failed_jobs_table.php b/database/migrations/2021_03_06_114918_create_failed_jobs_table.php new file mode 100644 index 0000000..6aa6d74 --- /dev/null +++ b/database/migrations/2021_03_06_114918_create_failed_jobs_table.php @@ -0,0 +1,36 @@ +id(); + $table->string('uuid')->unique(); + $table->text('connection'); + $table->text('queue'); + $table->longText('payload'); + $table->longText('exception'); + $table->timestamp('failed_at')->useCurrent(); + }); + } + + /** + * Reverse the migrations. + * + * @return void + */ + public function down() + { + Schema::dropIfExists('failed_jobs'); + } +} diff --git a/routes/api.php b/routes/api.php index 4a40912..be7bd04 100644 --- a/routes/api.php +++ b/routes/api.php @@ -182,6 +182,11 @@ $router->group(['prefix' => 'businesses', 'middleware' => 'auth:api'], function $router->delete('/', 'BusinessController@deleteUser'); }); }); + + $router->group(['prefix' => 'activities'], function () use ($router) { + $router->post('/', 'ActivityController@store'); + $router->get('/', 'ActivityController@index'); + }); }); }); From 42ff4828866fa4133b3ca522876067ec059b35d0 Mon Sep 17 00:00:00 2001 From: mahdihty Date: Sat, 6 Mar 2021 16:22:03 +0330 Subject: [PATCH 3/3] add model --- app/Models/Activity.php | 31 ++++++++++++++++++++++++++++++- 1 file changed, 30 insertions(+), 1 deletion(-) diff --git a/app/Models/Activity.php b/app/Models/Activity.php index 805e4a8..ed20699 100644 --- a/app/Models/Activity.php +++ b/app/Models/Activity.php @@ -2,8 +2,37 @@ namespace App\Models; -use App\Models\Model; +use Carbon\Carbon; +use Illuminate\Database\Eloquent\Factories\HasFactory; +use Illuminate\Database\Eloquent\Model; + class Activity extends Model { + use HasFactory; + + protected $fillable = [ + 'business_id', 'project_id', 'system_id', 'workflow_id', 'status_id', 'sprint_id', + 'actor_id', 'task_id', 'subject_id', 'user_id', 'crud_id', 'table_id', 'original', 'diff' + ]; + + public $casts = [ + 'original' => 'array', + 'diff' => 'array', + ]; + + public function scopeCreatesBefore($query, $date) + { + return $query->whereDate('created_at', '<=', Carbon::parse($date)); + } + public function scopeCreatesAfter($query, $date) + { + return $query->whereDate('created_at', '>=', Carbon::parse($date)); + } + public function scopeCreatesIn($query, $days) + { + return $days != "" ? + $query->whereDate('created_at', '>=', Carbon::now()->modify('-'.$days.' day')->toDate()) : + $query; + } }