fix: retry unchanged reschedule intent after stale revision (Closes #1311)
This commit is contained in:
1 parent
544ffb4ae7
commit
75846cf045
2 files changed
+106
-5
No files matched your search
@@ -64,6 +64,73 @@ console.log(JSON.stringify({opened,confirmed,requests,adoptedToday,weekState}));
|
||||
assert result["confirmed"]["today"]["revision"] == 5
|
||||
|
||||
|
||||
def test_reschedule_controller_retries_one_stale_revision_when_active_intent_is_unchanged():
|
||||
result = run_controller("""
|
||||
const requests=[];
|
||||
let attempts=0;
|
||||
const weekState={revision:7,offline_snapshot:false,timezone:'UTC',days:[
|
||||
{plan_date:'2026-08-25',ids:[],capacity_minutes:90,estimates:{}}
|
||||
]};
|
||||
const week={
|
||||
load:async()=>weekState,
|
||||
review:()=>({days:[{...weekState.days[0],label:'Tue',planned_minutes:0}]}),
|
||||
adopt:value=>Object.assign(weekState,value),
|
||||
};
|
||||
const api=async(url,options)=>{
|
||||
if(url==='api/v1/today')return {revision:5,ids:['active'],estimates:{active:45}};
|
||||
if(url==='api/v1/week')return {revision:8,offline_snapshot:false,timezone:'UTC',days:[
|
||||
{plan_date:'2026-08-25',ids:[],capacity_minutes:90,estimates:{}}
|
||||
]};
|
||||
const body=JSON.parse(options.body);requests.push(body);attempts++;
|
||||
if(attempts===1){const error=new Error('stale revision');error.status=409;throw error;}
|
||||
return {today:{revision:6,ids:[],estimates:{}},week:{revision:9,timezone:'UTC',days:[
|
||||
{plan_date:'2026-08-25',ids:['active'],capacity_minutes:90,estimates:{active:45}}
|
||||
]}};
|
||||
};
|
||||
const controller=createReschedule({week,api,getToday:()=>null,adoptToday:()=>{},operationId:()=> 'move-active'});
|
||||
await controller.open('active');
|
||||
let message='',confirmed=null;
|
||||
try{confirmed=await controller.confirm('2026-08-25',45);}catch(error){message=error.message;}
|
||||
console.log(JSON.stringify({message,confirmed,requests}));
|
||||
""")
|
||||
|
||||
assert result["message"] == ""
|
||||
assert result["confirmed"]["today"]["revision"] == 6
|
||||
assert [request["today_revision"] for request in result["requests"]] == [5, 5]
|
||||
assert [request["week_revision"] for request in result["requests"]] == [7, 8]
|
||||
assert result["requests"][0]["operation_id"] == result["requests"][1]["operation_id"]
|
||||
|
||||
|
||||
def test_reschedule_controller_rebases_admitted_move_once_after_stale_revision():
|
||||
result = run_controller("""
|
||||
const values=new Map();
|
||||
const storage={getItem:key=>values.get(key)||null,setItem:(key,value)=>values.set(key,value),removeItem:key=>values.delete(key)};
|
||||
const requests=[];let attempts=0;
|
||||
const initialWeek={revision:7,offline_snapshot:false,timezone:'UTC',days:[
|
||||
{plan_date:'2026-08-25',ids:[],capacity_minutes:90,estimates:{}}
|
||||
]};
|
||||
const week={load:async()=>initialWeek,review:()=>({days:[{...initialWeek.days[0],label:'Tue',planned_minutes:0}]}),adopt:()=>{}};
|
||||
const api=async(url,options)=>{
|
||||
if(url==='api/v1/today')return {revision:5,ids:['active'],estimates:{active:45}};
|
||||
if(url==='api/v1/week')return {revision:8,offline_snapshot:false,timezone:'UTC',days:initialWeek.days};
|
||||
const body=JSON.parse(options.body);requests.push(body);attempts++;
|
||||
if(attempts===1){const error=new Error('stale revision');error.status=409;throw error;}
|
||||
return {today:{revision:6,ids:[],estimates:{}},week:{revision:9,timezone:'UTC',days:[]}};
|
||||
};
|
||||
const controller=createReschedule({week,api,adoptToday:()=>{},storage,getLogin:()=> 'timmy',operationId:()=> 'move-active'});
|
||||
await controller.open('active');
|
||||
let message='',confirmed=null;
|
||||
try{confirmed=await controller.confirm('2026-08-25',45);}catch(error){message=error.message;}
|
||||
console.log(JSON.stringify({message,confirmed,requests,remaining:values.size}));
|
||||
""")
|
||||
|
||||
assert result["message"] == ""
|
||||
assert result["confirmed"]["today"]["revision"] == 6
|
||||
assert [request["today_revision"] for request in result["requests"]] == [5, 5]
|
||||
assert [request["week_revision"] for request in result["requests"]] == [7, 8]
|
||||
assert result["remaining"] == 0
|
||||
|
||||
|
||||
def test_reschedule_controller_blocks_offline_full_and_overloaded_days_without_mutation():
|
||||
result = run_controller("""
|
||||
let calls=0;
|
||||
|
||||
Reference in new issue
Block a user