crudIndex($request); if ($request->ajax()) { return $view; } if ($request->search and ($models = $view->getData()['models'])->count() === 1) { return \redirect()->route('invoices.edit', $models->first()); } return view('invoices.index', $view->getData()); } /** * Index query middleware * * @param Builder $query * @return Builder * @throws \ErrorException If account is missing in url. */ public function indexQuery(Builder $query): Builder { $query->orderBy('created_at', 'DESC'); return $query->orWhere(function (Builder $q) { $q->whereHas('site', function ($q) { $q->where('name', 'LIKE', '%' . \filter_var(request()->search, \FILTER_SANITIZE_STRING) . '%'); })->orWhereHas('company', function ($q) { $q->where('name', 'LIKE', '%' . \filter_var(request()->search, \FILTER_SANITIZE_STRING) . '%'); })->orWhereHas('companyInvoiced', function ($q) { $q->where('name', 'LIKE', '%' . \filter_var(request()->search, \FILTER_SANITIZE_STRING) . '%'); }); }); } /** * Show model action * * @param \Illuminate\Http\Request $request * @param mixed ...$params * @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory|\Illuminate\Http\JsonResponse */ public function show(Request $request, ...$params) { /** @var \Illuminate\View\View|\Illuminate\Http\JsonResponse */ $view = call_user_func_array([$this, 'crudShow'], \array_merge([$request], $params)); if ($view instanceof \Illuminate\Http\JsonResponse) { return $view; } /** @var \Illuminate\Database\Eloquent\Collection<\App\Models\Package> */ $packages = Package::get()->keyBy('id')->all(); return view('invoices.show', \array_merge($view->getData(), ['packages' => $packages])); } /** * Crud create view * * @param \Kwaadpepper\CrudPolicies\Http\Requests\CrudIndexRequest $request * @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory */ public function create(CrudIndexRequest $request) { /** @var \Illuminate\View\View */ $view = $this->crudCreate($request); $companies = Company::get(); $packages = Package::get(); $taskRowModel = Invoice::getTaskStructure(); return view('invoices.create', \array_merge($view->getData(), [ 'companies' => $companies, 'packages' => $packages, 'taskRowModel' => $taskRowModel, ])); } /** * Before store model middleware * * @param \App\Models\Invoice $model * @return void */ public function storeModel(Invoice &$model) { $this->validateTasks($model); } /** * Before update model middleware * * @param \App\Models\Invoice $model * @return void * @throws \Illuminate\Validation\ValidationException If invoice is signed. */ public function updateModel(Invoice &$model) { if ($model->signed_date) { throw ValidationException::withMessages([ 'erreur' => trans('Il n\'est pas possible de mettre a jour un devis qui est signé') ]); } $this->validateTasks($model); } /** * Edit model action * * @param mixed ...$params * @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory */ public function edit(...$params) { /** @var \Illuminate\View\View */ $view = call_user_func_array([$this, 'crudEdit'], $params); $companies = Company::get(); $packages = Package::get(); $taskRowModel = Invoice::getTaskStructure(); return view('invoices.edit', \array_merge($view->getData(), [ 'companies' => $companies, 'packages' => $packages, 'taskRowModel' => $taskRowModel, ])); } /** * Validate Tasks * * @param \App\Models\Invoice $invoice * @return void * @throws \Illuminate\Validation\ValidationException If tasks are not valid. */ private function validateTasks(Invoice $invoice): void { $tasks = \collect(\json_decode($invoice->tasks, true)) ->map(function ($task) { if (\is_array($task)) { return \array_intersect_key($task, Invoice::getTaskStructure()); } }); $invoice->tasks = Validator::make(['tasks' => $tasks->all()], [ 'tasks' => 'required|array|min:1', 'tasks.*' => 'required|array', 'tasks.*.days' => 'required|numeric|min:0.125', 'tasks.*.amount' => 'required|numeric|min:0.125', 'tasks.*.desc' => 'required|string|min:10', 'tasks.*.type' => [ 'required', new EnumIsValidRule(TaskType::class) ], 'tasks.*.package' => 'required_if:tasks.*.type,' . TaskType::package()->value . '|nullable|exists:packages,id', ], [], [ 'tasks' => trans('Tâches') ])->validated()['tasks']; } /** * Download Invoice * * @param \App\Models\Invoice $invoice * @return \Symfony\Component\HttpFoundation\Response */ public function download(Invoice $invoice) { $this->authorize($invoice, 'download'); return $invoice->generateInvoice() ->stream(Str::slug(trans('Devis :appname :date - ref :ref', [ 'appname' => config('app.name'), 'date' => $invoice->created_at->isoFormat('YYYY-MM-DD'), 'ref' => $invoice->ref, ])) . '.pdf'); } /** * Set signed date * * @param \App\Http\Requests\Invoice\InvoiceSetDateRequest $request * @param \App\Models\Invoice $invoice * @return \Illuminate\Http\RedirectResponse * @throws \Illuminate\Validation\ValidationException If already signed. */ public function setSignedDate(InvoiceSetDateRequest $request, Invoice $invoice) { if ($invoice->signed_date) { throw ValidationException::withMessages([ 'erreur' => trans('La date de signature est déjà actée.') ]); } $invoice->signed_date = $request->date; $invoice->saveOrFail(); return \back()->with('success', trans('La date de signature à bien été enregistrée')); } /** * Set client signed date * * @param \App\Http\Requests\Invoice\InvoiceSetDateRequest $request * @param \App\Models\Invoice $invoice * @return \Illuminate\Http\RedirectResponse * @throws \Illuminate\Validation\ValidationException If already signed. */ public function setClientSentDate(InvoiceSetDateRequest $request, Invoice $invoice) { if ($invoice->sent_client_date) { throw ValidationException::withMessages([ 'erreur' => trans('La date de signature client est déjà actée.') ]); } $invoice->sent_client_date = $request->date; $invoice->saveOrFail(); return \back()->with('success', trans('La date de signature client à bien été enregistrée')); } /** * Set compta signed date * * @param \App\Http\Requests\Invoice\InvoiceSetDateRequest $request * @param \App\Models\Invoice $invoice * @return \Illuminate\Http\RedirectResponse * @throws \Illuminate\Validation\ValidationException If already signed. */ public function setComptaSentDate(InvoiceSetDateRequest $request, Invoice $invoice) { if ($invoice->sent_accounting_date) { throw ValidationException::withMessages([ 'erreur' => trans('La date de signature compta est déjà actée.') ]); } $invoice->sent_accounting_date = $request->date; $invoice->saveOrFail(); return \back()->with('success', trans('La date de signature compta à bien été enregistrée')); } }