@@ -0,0 +1,80 @@
|
||||
<?php
|
||||
|
||||
use App\Enums\PurchasingRole;
|
||||
use App\Models\User;
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Support\Facades\Auth;
|
||||
use Illuminate\Support\Facades\DB;
|
||||
use Illuminate\Support\Facades\Route;
|
||||
|
||||
// Only the existing isolated local Compras evaluation database may use this entry.
|
||||
$evaluationScope = static function (Request $request): User {
|
||||
abort_unless(app()->environment('payable-testing')
|
||||
&& in_array($request->ip(), ['127.0.0.1', '::1'], true)
|
||||
&& in_array($request->getHost(), ['127.0.0.1', 'localhost', '::1'], true), 404);
|
||||
$db = DB::connection();
|
||||
abort_unless($db->getDriverName() === 'pgsql' && $db->getConfig('host') === '127.0.0.1'
|
||||
&& preg_match('/^compras_receipts_test_[a-f0-9]{12}$/D', $db->getDatabaseName()), 404);
|
||||
$identity = $db->selectOne('select current_database() as db, current_user as role');
|
||||
abort_unless($identity->db === $db->getDatabaseName()
|
||||
&& $identity->role === 'payable_qa_'.substr($identity->db, -12), 404);
|
||||
return User::where('email', 'preparacao-obrigacoes@example.test')->firstOrFail();
|
||||
};
|
||||
|
||||
$evaluationPages = [
|
||||
'/dashboard' => 'Visão geral', '/empresa' => 'Empresa e equipa',
|
||||
'/requisicoes' => 'Requisições', '/planeamento' => 'Planeamento',
|
||||
'/fornecedores' => 'Fornecedores', '/cotacoes' => 'Cotações', '/ordens' => 'Ordens de compra',
|
||||
'/recepcoes' => 'Recepções', '/stock' => 'Stock e movimentos', '/stock/operacoes' => 'Saídas e inventários',
|
||||
'/equipamentos' => 'Equipamentos e peças', '/orcamentos' => 'Orçamentos',
|
||||
'/regras-investimento' => 'Regras de investimento', '/facturas' => 'Facturas',
|
||||
'/pagamentos' => 'Pagamentos externos', '/obrigacoes-fornecedores' => 'Obrigações a fornecedores',
|
||||
'/conflitos' => 'Conflitos de interesses', '/revisao-compras' => 'Revisão e cancelamento',
|
||||
'/politica-admissao' => 'Política de admissão', '/politica-recomendacao' => 'Política de recomendação',
|
||||
];
|
||||
|
||||
Route::get('/avaliar', function (Request $request) use ($evaluationScope, $evaluationPages) {
|
||||
$evaluationScope($request);
|
||||
$token = htmlspecialchars(csrf_token(), ENT_QUOTES, 'UTF-8');
|
||||
$html = '<!doctype html><html lang="pt"><meta charset="utf-8"><meta name="viewport" content="width=device-width,initial-scale=1"><title>Explorar Compras</title><style>body{font:18px system-ui;background:#f4f6f5;color:#183d35;margin:0}main{max-width:1000px;margin:auto;padding:28px}section{background:white;padding:24px;border-radius:12px;margin:20px 0}button{font:inherit;padding:14px;border:0;border-radius:8px;background:#125a4b;color:white;cursor:pointer}a{color:#125a4b}li{margin:12px 0}form{margin:12px 0}</style><main><h1>Explorar Compras</h1><p>Entrada local sem palavra-passe. Os exemplos e alterações ficam guardados nesta instalação de testes.</p><section><h2>Acesso de proprietário</h2><form method="post" action="/avaliar/entrar"><input type="hidden" name="_token" value="'.$token.'"><input type="hidden" name="role" value="admin"><button>Entrar como proprietário</button></form><p>Abre a administração e as páginas dos módulos abaixo. As regras dos processos e as funções operacionais continuam visíveis.</p></section>';
|
||||
if ($request->user()) {
|
||||
$html .= '<section><h2>Áreas da aplicação</h2><ul>';
|
||||
foreach ($evaluationPages as $path => $label) {
|
||||
$html .= '<li><a href="'.$path.'">'.$label.'</a></li>';
|
||||
}
|
||||
$html .= '</ul></section>';
|
||||
}
|
||||
$html .= '<section><h2>Experimentar funções operacionais</h2><p>Para preparar ou decidir passos específicos, podes entrar nestes perfis sintéticos sem pedir contas ou credenciais.</p>';
|
||||
foreach (PurchasingRole::cases() as $role) {
|
||||
if ($role === PurchasingRole::Admin) continue;
|
||||
$html .= '<form method="post" action="/avaliar/entrar"><input type="hidden" name="_token" value="'.$token.'"><input type="hidden" name="role" value="'.$role->value.'"><button>'.$role->label().'</button></form>';
|
||||
}
|
||||
return response($html.'</section><p>Ambiente sintético partilhado. Sem transferências bancárias. Não altera a instalação habitual na porta 8015. Aprovações próprias e restantes regras de integridade não são dispensadas.</p></main></html>')->header('Cache-Control', 'no-store')->header('X-Robots-Tag', 'noindex, nofollow');
|
||||
});
|
||||
|
||||
Route::post('/avaliar/entrar', function (Request $request) use ($evaluationScope) {
|
||||
$source = $evaluationScope($request);
|
||||
$data = $request->validate(['role' => ['required', \Illuminate\Validation\Rule::enum(PurchasingRole::class)]]);
|
||||
abort_if(array_diff(array_keys($request->all()), ['role', '_token']) !== [], 422);
|
||||
$role = PurchasingRole::from($data['role']);
|
||||
$user = DB::transaction(function () use ($source, $role) {
|
||||
DB::select('select pg_advisory_xact_lock(?)', [80502910]);
|
||||
$user = User::firstOrCreate(['email' => 'avaliacao-'.$role->value.'@example.test'],
|
||||
['name' => $role === PurchasingRole::Admin ? 'Proprietário — avaliação local' : $role->label().' — avaliação local', 'password' => bin2hex(random_bytes(32))]);
|
||||
abort_if($user->tenant_id !== null && (int) $user->tenant_id !== (int) $source->tenant_id, 403);
|
||||
$user->forceFill(['tenant_id' => $source->tenant_id, 'department_id' => $source->department_id,
|
||||
'purchasing_role' => $role, 'email_verified_at' => $user->email_verified_at ?? now()])->save();
|
||||
// The isolated payables workspace has its own explicit action grants.
|
||||
foreach ($role === PurchasingRole::Admin ? ['view', 'prepare', 'validate'] : ['view'] as $action) {
|
||||
DB::table('pa_access')->insertOrIgnore(['user_id' => $user->id, 'tenant_id' => $source->tenant_id, 'company_id' => 0, 'unit_id' => 0, 'person' => 'evaluation-person-'.$user->id, 'action' => $action]);
|
||||
}
|
||||
return $user;
|
||||
});
|
||||
Auth::logout();
|
||||
$request->session()->invalidate();
|
||||
$request->session()->regenerateToken();
|
||||
Auth::login($user, false);
|
||||
$request->session()->regenerate();
|
||||
app(\App\Services\RequisitionWorkflow::class)->audit($user, 'evaluation.entered', null, null, ['role' => $role->value, 'synthetic' => true]);
|
||||
return redirect('/dashboard');
|
||||
})->middleware('throttle:30,1');
|
||||
Reference in New Issue
Block a user