<?php
declare(strict_types=1);require __DIR__.'/cli-common.php';
$approved=['B'=>'db74684022319c160b79816201e437fda0e4f8146be7220d6d8ca9f741a20931','C'=>'b030d2a72730d5cc9eb8b57196146a3ea0d81733549297a6845fbbe60047ce5d'];
$planFile=__DIR__.'/fixture-proposal-'.$lane.'.json';$check(hash_file('sha256',$planFile)===$approved[$lane],'Exact Root-approved13 INSERT plan');$plan=json_decode(file_get_contents($planFile),true);$check(count($plan['plans'])===13,'Exactly13 preparation INSERT');
$check(!file_exists($runtime.'/fixture-journal.json'),'Never replay successful/uncertain sent preparation');
if($dm){$r=json_decode(file_get_contents(__DIR__.'/img-repair-result.json'),true);$check($r['success']===true&&$r['original_rows']===1775&&$r['DDL']===2,'IMG independent repair complete first');}
$pks=['user'=>'user_id','upload_file'=>'file_id','goods'=>'goods_id','order'=>'order_id','order_goods'=>'order_goods_id','order_address'=>'order_address_id','order_delivery'=>'delivery_id','order_delivery_goods'=>'id','payment_trade'=>'trade_id','express'=>'express_id','order_refund'=>'order_refund_id','order_refund_image'=>'id','order_refund_address'=>'id','goods_sku'=>'id','goods_image'=>'id','goods_category_rel'=>'id','goods_service_rel'=>'id','goods_spec_rel'=>'id','printer'=>'printer_id','recharge_order'=>'order_id','recharge_order_plan'=>'order_plan_id','order_export'=>'id','store_user'=>'store_user_id','store_user_role'=>'id','store_user_relation'=>'id','store_role'=>'role_id','store_role_menu'=>'id','store'=>'store_id','equipment'=>'id','dishes'=>'id','dishes_img'=>'id','store_setting'=>$dm?'"KEY"':'`key`','user_points_log'=>'log_id','user_balance_log'=>'log_id','user_feedback'=>'id','user_grade'=>'grade_id','staff'=>'id','nutrition_meals'=>'id','nutrition_lack'=>'id','nurtrition'=>'id','staff_store_user'=>'id','staff_face'=>'id'];
$all=static function($pdo)use($pks,$query){$out=[];foreach($pks as $table=>$pk)$out[$table]=$query($pdo,'SELECT * FROM yoshop_'.$table.' WHERE store_id IN (2147001111,2147001112,2147001113) ORDER BY '.$pk);return $out;};
$before=$all($connect());
$prior=json_decode(file_get_contents($runtime.'/previous-protection-'.$lane.'.json'),true)['original'];
foreach($prior as $table=>$old)$check($before[$table]===$old,'Prior frozen36 exact '.$table);
foreach(['staff','nutrition_meals','nutrition_lack','nurtrition','staff_store_user','staff_face'] as $table)$check($before[$table]===[],'No unreviewed existing fixture data '.$table);
$baseline=json_decode(file_get_contents(__DIR__.'/preflight-stage2-'.$lane.'.json'),true); // Public schema counts only; full schema comes from private preflight below.
$raw=json_decode(file_get_contents($runtime.'/preflight-stage2-'.$lane.'.json'),true);
foreach(['staff','nutrition_meals','nutrition_lack','nurtrition'] as $table){$t=$dm?strtoupper('yoshop_'.$table):'yoshop_'.$table;
 $columns=$dm?$read('SELECT COLUMN_NAME,DATA_TYPE,NULLABLE,DATA_DEFAULT,DATA_LENGTH,DATA_PRECISION,DATA_SCALE FROM USER_TAB_COLUMNS WHERE TABLE_NAME=? ORDER BY COLUMN_ID',[$t]):$read('SELECT COLUMN_NAME,DATA_TYPE,COLUMN_TYPE,IS_NULLABLE,COLUMN_DEFAULT,CHARACTER_MAXIMUM_LENGTH,NUMERIC_PRECISION,NUMERIC_SCALE,EXTRA FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME=? ORDER BY ORDINAL_POSITION',[$t]);
 $old=$raw['schema'][$table]['columns'];foreach($old as &$col)$col['column_name']=strtolower($col['column_name']);unset($col);foreach($columns as &$col)$col['column_name']=strtolower($col['column_name']);unset($col);
 $canon=static function($rows){foreach($rows as &$r)ksort($r);unset($r);return $rows;};
 if($dm&&$table==='staff'){$check(count($columns)===21&&$canon(array_slice($columns,0,20))===$canon($old),'Only independently repaired IMG changes original staff20');$check($columns[20]['column_name']==='img','New IMG present');}elseif($canon($columns)!==$canon($old)){$persist('metadata-gate-mismatch-'.$table.'.json',['actual'=>$columns,'frozen'=>$old]);throw new RuntimeException('Fresh full schema '.$table);}
 $fk=$dm?$read("SELECT COUNT(*) n FROM USER_CONSTRAINTS WHERE CONSTRAINT_TYPE='R' AND (TABLE_NAME=? OR R_CONSTRAINT_NAME IN (SELECT CONSTRAINT_NAME FROM USER_CONSTRAINTS WHERE TABLE_NAME=?))",[$t,$t]):$read('SELECT COUNT(*) n FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE WHERE TABLE_SCHEMA=DATABASE() AND REFERENCED_TABLE_NAME IS NOT NULL AND (TABLE_NAME=? OR REFERENCED_TABLE_NAME=?)',[$t,$t]);
 $tr=$dm?$read('SELECT COUNT(*) n FROM USER_TRIGGERS WHERE TABLE_NAME=?',[$t]):$read('SELECT COUNT(*) n FROM INFORMATION_SCHEMA.TRIGGERS WHERE TRIGGER_SCHEMA=DATABASE() AND EVENT_OBJECT_TABLE=?',[$t]);$check((int)$fk[0]['n']===0&&(int)$tr[0]['n']===0,'Fresh FK/trigger0 '.$table);
}
$collision=$read('SELECT COUNT(*) n FROM yoshop_staff WHERE name LIKE ? OR create_by=?',['CDXRR11A8F4_%','CDXRR11A8F4']);$check((int)$collision[0]['n']===0,'Fresh global marked Staff collision0');
$journal=['lane'=>$lane,'approved_plan_sha256'=>$approved[$lane],'before'=>$before,'statements'=>[],'owned'=>[],'committed'=>false];$persist('fixture-journal.json',$journal);$refs=[];
$db->beginTransaction();try{
 foreach($plan['plans'] as $i=>$p){$values=$p['values'];foreach($values as &$value){if(is_string($value)&&strpos($value,'@')===0){$check(isset($refs[$value]),'Only actual generated reference '.$value);$value=$refs[$value];}}unset($value);
  if($p['table']==='staff'){$u=array_values(array_filter($before['user'],static function($u)use($values){return (int)$u['user_id']===$values['user_id']&&(int)$u['store_id']===$values['store_id'];}));$check(count($u)===1&&(int)$u[0]['is_delete']===0&&$u[0]['nick_name']==='CDXLF11F86A_'.($values['store_id']===2147001111?'store':'terminal'),'Exact active original user relation');}
  $record=['table'=>$p['table'],'reference'=>$p['generated_reference'],'queryString'=>$p['sql'],'bindValue'=>[],'sent'=>false,'executed'=>false,'rowCount'=>null];
  foreach(array_values($values) as $j=>$value)$record['bindValue'][]=['position'=>$j+1,'value'=>(string)$value,'pdo_type'=>PDO::PARAM_STR];
  $journal['statements'][$i]=$record;$persist('fixture-journal.json',$journal);$s=$db->prepare($p['sql']);foreach($record['bindValue'] as $b)$s->bindValue($b['position'],$b['value'],$b['pdo_type']);
  $journal['statements'][$i]['sent']=true;$persist('fixture-journal.json',$journal);$s->execute();$journal['statements'][$i]['executed']=true;$journal['statements'][$i]['rowCount']=$s->rowCount();$persist('fixture-journal.json',$journal);$check($s->rowCount()===1,'One affected INSERT only');
  $where='store_id=?';$bind=[$values['store_id']];foreach(['create_by','staff_id','user_id','set_date','type','reference_id','name'] as $field)if(array_key_exists($field,$values)){$where.=' AND '.($dm?'"'.strtoupper($field).'"':'`'.$field.'`').'=?';$bind[]=$values[$field];}
  $rows=$query($db,'SELECT * FROM yoshop_'.$p['table'].' WHERE '.$where,$bind);$check(count($rows)===1,'Actual generated own row unique');$row=$rows[0];$check((int)$row['id']>0,'Positive real generated ID');
  $expectedKeys=array_merge(array_keys($values),['id']);sort($expectedKeys);$actualKeys=array_keys($row);sort($actualKeys);$check($actualKeys===$expectedKeys,'Every original column represented');
  foreach($values as $field=>$value){if(is_int($value))$check(is_numeric($row[$field])&&(int)$row[$field]===$value,'Exact physical integer '.$field);elseif(in_array($field,['height','weight'],true))$check(is_numeric($row[$field])&&bccomp((string)$row[$field],$value,2)===0,'Exact physical DEC5,2 '.$field);elseif(in_array($field,['create_time','update_time'],true))$check(preg_match('/^'.preg_quote($value,'/').'(?:\.0+)?$/D',(string)$row[$field])===1,'Exact second/time-zero-fraction '.$field);elseif(in_array($field,['birthday','set_date'],true))$check(preg_match('/^'.preg_quote($value,'/').'(?: 00:00:00(?:\.0+)?)?$/D',(string)$row[$field])===1,'Exact physical calendar date '.$field);else $check($row[$field]===$value,'Exact original text '.$field);}
  $refs[$p['generated_reference']]=(int)$row['id'];$journal['owned'][]=['table'=>$p['table'],'reference'=>$p['generated_reference'],'id'=>(int)$row['id'],'original'=>$row];$persist('fixture-journal.json',$journal);
 }
 $inside=$all($db);foreach($before as $table=>$old){$ids=[];foreach($journal['owned'] as $o)if($o['table']===$table)$ids[]=$o['id'];$remaining=array_values(array_filter($inside[$table],static function($r)use($ids,$pks,$table){return !in_array((int)$r[$pks[$table]],$ids,true);}));$check($remaining===$old,'Every old row unchanged '.$table);$check(count($inside[$table])===count($old)+count($ids),'Only exact new rows '.$table);}
 $db->commit();$journal['committed']=true;$persist('fixture-journal.json',$journal);$after=$all($connect());$check($after===$inside,'New independent PDO full42 exact after commit');$journal['after']=$after;$journal['refs']=$refs;$persist('fixture-journal.json',$journal);
 $out=['lane'=>$lane,'INSERT'=>13,'affected'=>13,'UPDATE'=>0,'DELETE'=>0,'DDL'=>0,'HTTP'=>0,'old36_exact'=>true,'new6_groups_exact'=>true,'independent_new_PDO'=>true,'retained'=>true,'refs'=>$refs];file_put_contents(__DIR__.'/fixture-result-'.$lane.'.json',json_encode($out,JSON_PRETTY_PRINT));echo json_encode($out),"\n";
}catch(Throwable $e){if($db->inTransaction())$db->rollBack();$journal['error']=['class'=>get_class($e),'code'=>$e->getCode(),'message'=>$e->getMessage()];$persist('fixture-journal.json',$journal);throw $e;}
