25 lines
6.7 KiB
PHP
25 lines
6.7 KiB
PHP
<?php
|
|
use Illuminate\Support\Facades\Auth;use Illuminate\Support\Str;use App\Shared\Context\CompanyContext;use App\Modules\Workshop\{WorkshopOrderRead,WorkshopWorkflow};
|
|
require __DIR__.'/sgf-ledger-proof-bootstrap.php';
|
|
set_exception_handler(function($e){echo json_encode(['passed'=>false,'type'=>get_class($e),'message'=>$e->getMessage()]).PHP_EOL;exit(1);});
|
|
$select=function($role)use($profiles,$f,$app){Auth::forgetGuards();Auth::shouldUse('web');$u=App\Models\User::findOrFail($profiles[$role]['user_id']);Auth::guard('web')->setUser($u);$r=Illuminate\Http\Request::create('/api/workshop/orders','GET');$r->attributes->set('sgf_module','workshop');$r->setUserResolver(fn()=>$u);$session=app('session')->driver();$session->start();$session->put('company_context',$f['scope']+['module_id'=>'workshop','token'=>'orders-'.$role]);$r->setLaravelSession($session);$app->instance('request',$r);app(CompanyContext::class)->selectFor($u->id,1,2,2);return $u->id;};
|
|
$reject=function($fn,$status,$name)use($ok){$actual=null;try{$fn();}catch(Symfony\Component\HttpKernel\Exception\HttpExceptionInterface$e){$actual=$e->getStatusCode();}catch(Illuminate\Validation\ValidationException){$actual=422;}$ok($actual===$status,$name);};
|
|
$tables=['wo_orders','wo_entries','wo_decisions','wo_equipment','wo_commands','wo_events','wo_outbox','permission_grants'];$before=[];foreach($tables as$t)$before[$t]=$host->table($t)->orderBy($t==='wo_outbox'?'event_id':'id')->get()->toJson();$host->beginTransaction();try{
|
|
$actor=$select('workshop_manage');$reader=app(WorkshopOrderRead::class);$original=app(WorkshopWorkflow::class)->listing($actor);$p=$reader->listing($actor,['per_page'=>100]);$indexed=collect($p['orders']->items())->keyBy('id');foreach($original['orders']as$o)$ok(isset($indexed[$o['id']])&&$indexed[$o['id']]->state===$o['state']&&$indexed[$o['id']]->minutes_verified===$o['minutes_verified'],'original state and verified time preserved '.$o['id']);
|
|
$template=(array)$host->table('wo_orders')->first();unset($template['id']);$prefix='QA-PAGED-'.Str::uuid();$ids=[];for($i=0;$i<27;$i++)$ids[]=$host->table('wo_orders')->insertGetId(array_replace($template,['reference'=>$prefix.'-'.$i]));
|
|
$p1=$reader->listing($actor,['search'=>$prefix,'per_page'=>25]);$p2=$reader->listing($actor,['search'=>$prefix,'page'=>2,'per_page'=>25]);$p100=$reader->listing($actor,['search'=>$prefix,'per_page'=>100]);$ok($p1['orders']->total()===27&&count($p1['orders']->items())===25&&count($p2['orders']->items())===2,'SQL pages25 and2 from27 fixtures');$ok(count(array_intersect($p1['orders']->pluck('id')->all(),$p2['orders']->pluck('id')->all()))===0,'distinct order pages');$ok(count($p100['orders']->items())===27,'page100 equivalent ordered universe');$ok(array_merge($p1['orders']->pluck('id')->all(),$p2['orders']->pluck('id')->all())===$p100['orders']->pluck('id')->all(),'stable descending ordering');
|
|
$techId=$profiles['workshop_record']['user_id'];
|
|
$add=function($id,$kind,$extra=[])use($host,$actor,$techId){$revision=(int)$host->selectOne('SELECT sgf_wo_revision(?) AS v',[$id])->v;return$host->table('wo_entries')->insertGetId(array_replace(['order_id'=>$id,'kind'=>$kind,'origin'=>(string)Str::uuid(),'version'=>1,'revision'=>$revision,'outside_authority'=>false,'technician_id'=>$kind==='assignment'?$techId:$techId,'data'=>json_encode(['policy'=>WorkshopWorkflow::POLICY,'description'=>'Fixture SQL de consulta paginada','correction_reason'=>'Nova versão sintética para conferir projecção']),'actor_id'=>$kind==='assignment'?$actor:$techId,'created_at'=>now()],$extra));};
|
|
$tech=$select('workshop_record');$ok($reader->listing($tech,['search'=>$prefix])['orders']->total()===0,'unassigned synthetic orders hidden from technician');$select('workshop_manage');foreach(array_slice($ids,0,3)as$id)$add($id,'assignment');
|
|
$task=$add($ids[0],'task');$exception=$add($ids[1],'task',['outside_authority'=>true]);$verifiedTask=$add($ids[2],'task');
|
|
$decide=function($entry,$order)use($host,$profiles){$host->table('wo_decisions')->insert(['entry_id'=>$entry,'entry_version'=>1,'revision'=>(int)$host->selectOne('SELECT sgf_wo_revision(?) AS v',[$order])->v,'decision'=>'verified','reason'=>'Fixture SQL de leitura isolada','actor_id'=>$profiles['workshop_verify']['user_id'],'created_at'=>now()]);};$decide($verifiedTask,$ids[2]);
|
|
foreach(['open'=>24,'in_review'=>1,'exception_review'=>1,'records_verified'=>1]as$state=>$count)$ok($reader->listing($actor,['search'=>$prefix,'state'=>$state])['orders']->total()===$count,'SQL state filter '.$state);
|
|
$verified=$reader->listing($actor,['search'=>$prefix,'state'=>'records_verified'])['orders']->items()[0];$ok($verified->points===1&&$verified->points_not_verified===0&&$verified->minutes_reported===0,'verified points do not invent time');
|
|
$newTask=$add($ids[0],'task',['previous_id'=>$task,'version'=>2,'origin'=>$host->table('wo_entries')->where('id',$task)->value('origin')]);$host->table('wo_decisions')->insert(['entry_id'=>$newTask,'entry_version'=>2,'revision'=>(int)$host->selectOne('SELECT sgf_wo_revision(?) AS v',[$ids[0]])->v,'decision'=>'verified','reason'=>'Correcção SQL de leitura','actor_id'=>$profiles['workshop_verify']['user_id'],'created_at'=>now()]);$ok($reader->listing($actor,['search'=>$prefix,'state'=>'in_review'])['orders']->total()===0,'superseded unverified task not current pending');
|
|
$ok($reader->listing($actor,['search'=>'%'])['orders']->total()===0,'wildcard literal not universe');$reject(fn()=>$reader->listing($actor,['tenant_id'=>2]),422,'tenant override refused');$reject(fn()=>$reader->listing($actor,['per_page'=>1000]),422,'unbounded page refused');$reject(fn()=>$reader->listing($actor,['state'=>'delivered']),422,'unimplemented phase not inferred');
|
|
$tech=$select('workshop_record');$ok($reader->listing($tech,['search'=>$prefix])['orders']->total()===3,'technician sees only three assigned fixtures');
|
|
$select('commercial_prepare');$reject(fn()=>$reader->listing($profiles['commercial_prepare']['user_id'],[]),403,'view absent cannot read orders');$actor=$select('workshop_manage');$reject(fn()=>$reader->listing($tech,[]),403,'actor mismatch refused');request()->attributes->set('sgf_module','finance');$reject(fn()=>$reader->listing($actor,[]),403,'other module refused');
|
|
}finally{while($host->transactionLevel()>0)$host->rollBack();}
|
|
foreach($before as$t=>$json)$ok($host->table($t)->orderBy($t==='wo_outbox'?'event_id':'id')->get()->toJson()===$json,'original '.$t.' intact');
|
|
file_put_contents($work.'/workshop-orders-result.json',json_encode(['passed'=>true,'checks'=>$checks,'fixture_rows_rolled_back'=>true,'new_rights'=>0,'no_writer_changes'=>true,'browser_visual_review'=>false],JSON_PRETTY_PRINT));echo json_encode(['passed'=>true,'checks'=>count($checks),'proof'=>$work.'/workshop-orders-result.json']).PHP_EOL;
|