Files
SGF/packages/payables/tests/seed.php
T
2026-10-29 18:43:29 +02:00

57 lines
6.5 KiB
PHP

<?php
// Called only after a fresh, restricted QA database has been provisioned.
$mode=$argv[1]??'';$root=$mode==='compras'?'C:/laragon/www/compras':'C:/laragon/www/sgf-tempo';
require $root.'/vendor/autoload.php';$app=require $root.'/bootstrap/app.php';$app->make(\Illuminate\Contracts\Console\Kernel::class)->bootstrap();
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
$db=DB::connection();$name=$db->getDatabaseName();
if(!preg_match('/^(compras_receipts_test_|payable_sgf_)[a-f0-9]{12}$/D',$name)||$db->selectOne('select current_database() as d')->d!==$name||Schema::hasTable('users'))throw new LogicException('Fresh QA only.');
$file=getenv('PAYABLE_ACCESS_FILE');$bundle=getenv('PAYABLE_BUNDLE');
if($mode==='compras'){
\Illuminate\Support\Facades\Artisan::call('migrate',['--force'=>true]);
require __DIR__.'/../qa-schema.php';require __DIR__.'/ReceiptFixture.php';
$f=payableReceiptFixture();
app(\App\Services\ReceiptWorkflow::class)->confirm($f['receiver'],$f['order'],payableReceiptPayload($f,'1.000'));
$p=\App\Models\User::factory()->create(['tenant_id'=>$f['tenant']->id,'department_id'=>$f['department']->id,'purchasing_role'=>'finance']);
$v=\App\Models\User::factory()->create(['tenant_id'=>$f['tenant']->id,'department_id'=>$f['department']->id,'purchasing_role'=>'finance']);
$q=\App\Models\User::factory()->create(['tenant_id'=>$f['tenant']->id,'department_id'=>$f['department']->id,'purchasing_role'=>'admin']);
auth()->guard()->setUser($p);
\App\Models\Budget::query()->create(['tenant_id'=>$f['tenant']->id,'cost_center_id'=>$f['r']->cost_center_id,'year'=>now()->year,'amount_minor'=>2000000,'includes_tax'=>true,'approved_by'=>$v->id,'created_by'=>$p->id,'reason'=>'Only synthetic source preparation']);
DB::transaction(function()use($p,$f){app(\App\Services\BudgetWorkflow::class)->record($p,$f['r'],'reserve',1160000,1000000);app(\App\Services\BudgetWorkflow::class)->record($p,$f['r'],'commit',1160000,1000000);});
$invoice=app(\App\Services\InvoiceWorkflow::class)->register($p,$f['order'],['number'=>'FT-SIM-11600','issued_on'=>now()->format('Y-m-d'),'subtotal'=>'10000.00','tax'=>'1600.00','total'=>'11600.00','items'=>[['purchase_order_item_id'=>$f['line']->id,'quantity'=>'1.000','unit'=>'cx','unit_price'=>'10000.00','tax_rate'=>'16']]]);
auth()->guard()->setUser($v);app(\App\Services\InvoiceWorkflow::class)->validate($v,$invoice);
$scope=['tenant_id'=>$f['tenant']->id,'company_id'=>0,'unit_id'=>0];
auth()->guard()->setUser($p);$source=app(\App\Services\SupplierPayables::class)->document($p,$invoice->id);
if($source['total_minor']!==1160000||$source['tax_minor']!==160000||$source['status']!=='validated'||!$source['validation_audit_id'])throw new RuntimeException('Source scenario mismatch.');
file_put_contents($bundle,\Tempo\Finance\Payables\Payables::canonical($source),LOCK_EX);
$sourceId=$invoice->id;
}else{
foreach(['0001_01_01_000000_create_users_table.php','2026_10_25_000000_create_identity_foundation.php','2026_10_25_010000_add_identity_workflow.php'] as $m)(require $root.'/database/migrations/'.$m)->up();
require __DIR__.'/../qa-schema.php';
DB::statement('ALTER TABLE permission_grants DROP CONSTRAINT permission_grants_scope_check');
DB::statement("ALTER TABLE permission_grants ADD CONSTRAINT permission_grants_scope_check CHECK ((permission IN ('company.view','company.edit','unit.create','access.manage') AND unit_id IS NULL) OR (permission IN ('unit.view','unit.edit','supplier_payables.view') AND unit_id IS NOT NULL))");
$now=now();$tenant=DB::table('tenants')->insertGetId(['name'=>'Tenant sintético','created_at'=>$now,'updated_at'=>$now]);
DB::table('companies')->insert(['tenant_id'=>$tenant,'name'=>'Empresa não autorizada','created_at'=>$now,'updated_at'=>$now]);
$company=DB::table('companies')->insertGetId(['tenant_id'=>$tenant,'name'=>'Horizonte Sintética — Obrigações','created_at'=>$now,'updated_at'=>$now]);
DB::table('units')->insert(['tenant_id'=>$tenant,'company_id'=>$company,'name'=>'Unidade reservada','created_at'=>$now,'updated_at'=>$now]);
$unit=DB::table('units')->insertGetId(['tenant_id'=>$tenant,'company_id'=>$company,'name'=>'Unidade de obrigações','created_at'=>$now,'updated_at'=>$now]);
$scope=['tenant_id'=>$tenant,'company_id'=>$company,'unit_id'=>$unit];
$p=\App\Models\User::create(['name'=>'Preparador','email'=>'seed-p@example.test','password'=>bin2hex(random_bytes(20))]);
$v=\App\Models\User::create(['name'=>'Validador','email'=>'seed-v@example.test','password'=>bin2hex(random_bytes(20))]);
$q=\App\Models\User::create(['name'=>'Consulta','email'=>'seed-q@example.test','password'=>bin2hex(random_bytes(20))]);
foreach([$p,$v,$q] as $u){DB::table('company_memberships')->insert(['user_id'=>$u->id,'tenant_id'=>$tenant,'company_id'=>$company]);foreach(['company.view'=>null,'unit.view'=>$unit,'supplier_payables.view'=>$unit] as $right=>$which)DB::table('permission_grants')->insert(['tenant_id'=>$tenant,'company_id'=>$company,'unit_id'=>$which,'user_id'=>$u->id,'permission'=>$right,'created_at'=>$now,'updated_at'=>$now]);}
Schema::create('pa_imported_sources',function(Blueprint $t){$t->id();foreach(['tenant_id','company_id','unit_id'] as $k)$t->unsignedBigInteger($k);$t->jsonb('payload');$t->string('receipt_hash',64);});
$source=json_decode(file_get_contents($bundle),true,64,JSON_THROW_ON_ERROR);
if(\Tempo\Finance\Payables\Payables::missing($source)!==[])throw new RuntimeException('Conferred Compras source required.');
$sourceId=DB::table('pa_imported_sources')->insertGetId($scope+['payload'=>\Tempo\Finance\Payables\Payables::canonical($source),'receipt_hash'=>hash('sha256',\Tempo\Finance\Payables\Payables::canonical($source))]);
}
$accounts=[];
foreach(['preparacao'=>[$p,['view','prepare']],'validacao'=>[$v,['view','validate']],'consulta'=>[$q,['view']]] as $role=>[$user,$rights]){
$password=bin2hex(random_bytes(20));$user->forceFill(['name'=>'Obrigações — '.$role,'email'=>$role.'-obrigacoes@example.test','password'=>$password]);$user->save();
foreach($rights as $right)DB::table('pa_access')->insert($scope+['user_id'=>$user->id,'person'=>'synthetic-person-'.$role,'action'=>$right]);
$accounts[$role]=['id'=>$user->id,'email'=>$user->email,'password'=>$password];
}
file_put_contents($file,json_encode(['mode'=>$mode,'scope'=>$scope,'source_id'=>$sourceId,'accounts'=>$accounts],JSON_THROW_ON_ERROR),LOCK_EX);
echo "Synthetic conferred-source scenario prepared; obligations remain unrecognised for team testing.\n";