{"record":{"id":"5966e39f10fce081","repo":"facebook/flow","slug":"autofix-error-additionally-failed-to-stop-flow","errorCode":null,"errorMessage":"{autofix_error}; additionally failed to stop Flow: {stop_error}","messagePattern":"(.+?); additionally failed to stop Flow: (.+?)","errorType":"exception","errorClass":"std::io::Error","httpStatus":null,"severity":"error","filePath":"rust_port/crates/flow_dev_tools/src/runtests/check_annotate_exports.rs","lineNumber":404,"sourceCode":"        Ok(())\n    })();\n\n    let stop_result = exec_file(\n        &flow_bin.to_string_lossy(),\n        &[\"stop\".to_owned(), \".\".to_owned()],\n        &ExecOptions {\n            cwd: Some(test_dir.clone()),\n            env: Some(env.clone()),\n            max_buffer: Some(100 * 1024 * 1024),\n            ..ExecOptions::default()\n        },\n        None,\n    );\n    match (autofix_result, stop_result) {\n        (Ok(()), Ok(_)) => {}\n        (Err(error), Ok(_)) | (Ok(()), Err(error)) => return Err(error),\n        (Err(autofix_error), Err(stop_error)) => {\n            return Err(io::Error::new(\n                autofix_error.kind(),\n                format!(\"{autofix_error}; additionally failed to stop Flow: {stop_error}\"),\n            ));\n        }\n    }\n\n    // Keep copies of autofix-ed files\n    for file in &files {\n        fs::copy(\n            test_dir.join(file),\n            test_dir.join(format!(\"{file}.autofix\")),\n        )?;\n    }\n\n    // Compare autofix-ed with original\n    for file in &files {\n        let original = fs::read_to_string(test_dir.join(format!(\"{file}.orig\")))?;\n        let autofix = fs::read_to_string(test_dir.join(format!(\"{file}.autofix\")))?;","sourceCodeStart":386,"sourceCodeEnd":422,"githubUrl":"https://github.com/facebook/flow/blob/5c865861998a8ccb7dbc82b0c1f511e9ef60c3d9/rust_port/crates/flow_dev_tools/src/runtests/check_annotate_exports.rs#L386-L422","documentation":"In flow_dev_tools' check-annotate-exports runtest with autofix enabled, the harness runs the autofix command over the test files and afterwards stops the Flow test server. If BOTH fail, it returns the autofix error annotated with \"; additionally failed to stop Flow: {stop_error}\". The primary defect is the autofix error printed before the semicolon; the stop error is secondary cleanup noise from an already-unhealthy test session.","triggerScenarios":"Running `flow runtests check-annotate-exports --autofix ...` (or the equivalent runtests entry point) where the autofix exec over the test dir exits with an error AND the subsequent server-stop step also fails (server already gone, lock/socket conflict).","commonSituations":"A test tree with violations the autofix command cannot rewrite; a leftover Flow server from a previously crashed run holding the lock/socket for the test dir; two runtests sessions pointed at the same test directory concurrently.","solutions":["Fix the primary autofix error — the text before '; additionally failed to stop Flow' — by rerunning that autofix command manually to see its full output.","Kill leftover flow server processes and remove stale lock/socket/pids files for the test dir, then rerun the check.","Do not run two runtests sessions against the same test directory at the same time."],"exampleFix":"# before: stale server from a crashed run makes both steps fail\nflow runtests check-annotate-exports --autofix $TEST_DIR\n\n# after: clear stale server state, then rerun and read the primary (first) error\npgrep -af flow | xargs -r kill\nrm -f \"$TEST_DIR\"/.flow*lock \"$TEST_DIR\"/.flow*sock\nflow runtests check-annotate-exports --autofix $TEST_DIR","handlingStrategy":"try-catch","validationCode":null,"typeGuard":"fn is_compound_autofix_stop_error(e: &std::io::Error) -> bool {\n    e.to_string().contains(\"additionally failed to stop Flow\")\n}","tryCatchPattern":"When catching this error, split the message on '; additionally failed to stop Flow:' — diagnose and fix the first half (the autofix failure) first; the second half only matters for cleaning up stale server state (kill leftover flow processes, remove lock/socket files) before rerunning.","preventionTips":["Clean stale flow server processes and lock/socket files before running runtests sessions.","Run one runtests session per test directory at a time.","Make autofix steps idempotent so a rerun after cleanup converges."],"tags":["runtests","autofix","compound-error","server-cleanup","rust"],"backgroundTag":"autofix-failed","analyzedSha":"5c865861998a8ccb7dbc82b0c1f511e9ef60c3d9","analyzedAt":"2026-08-20T10:41:37.992Z","contentChangedAt":"2026-08-20T10:41:37.992Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}