{"record":{"id":"a9b0281cd39f0b3f","repo":"a-b-street/abstreet","slug":"doesn-t-touch","errorCode":null,"errorMessage":"{} doesn't touch {}","messagePattern":"(.+?) doesn't touch (.+?)","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"map_model/src/objects/road.rs","lineNumber":490,"sourceCode":"pub fn other_endpt(&self, i: IntersectionID) -> IntersectionID {\n    if self.src_i == i {\n        self.dst_i\n    } else if self.dst_i == i {\n        self.src_i\n    } else {\n        panic!(\"{} doesn't touch {}\", self.id, i);\n    }\n}","sourceCodeStart":472,"sourceCodeEnd":508,"githubUrl":"https://github.com/a-b-street/abstreet/blob/0964f29315820c91b171b585eb51e300164e9197/map_model/src/objects/road.rs#L472-L508","documentation":"other_endpt is called with an IntersectionID that is neither this road's src_i nor dst_i, so the road has no 'other' endpoint to return. The caller assumed the road touches the given intersection, but it doesn't — usually a mixup of road/intersection IDs or a caller that skipped checking road.endpoints().","triggerScenarios":"Calling road.other_endpt(i) with an intersection not equal to src_i or dst_i — often from iterating intersections adjacent to a node and confusing road/intersection pairs, or stale IDs after regeneration.","commonSituations":"Graph traversal code building turns or shortest paths; manual construction of movement data; IDs carried across map reloads.","solutions":["Check src_i == i || dst_i == i before the call, or obtain the intersection from road.src_i/dst_i directly.","Use the road's own endpoint fields instead of a separately tracked intersection ID.","Avoid persisting map-local IDs across reloads; look them up fresh."],"exampleFix":"// before\nlet other = road.other_endpt(i);\n// after\nlet other = if road.src_i == i { road.dst_i } else if road.dst_i == i { road.src_i } else { anyhow::bail!(\"{} not endpoint of {}\", i, road.id) };","handlingStrategy":"type-guard","validationCode":null,"typeGuard":"fn other_endpt_safe(road: &Road, i: IntersectionID) -> Option<IntersectionID> {\n    if road.src_i == i { Some(road.dst_i) }\n    else if road.dst_i == i { Some(road.src_i) }\n    else { None }\n}","tryCatchPattern":null,"preventionTips":["Iterate road.src_i/dst_i directly in traversal code","Check incidence (src_i == i || dst_i == i) before endpoint helpers","Refresh all IDs after map regeneration"],"tags":["graph","invariant","wrong-argument","roads"],"backgroundTag":"invalid-argument-value","analyzedSha":"0964f29315820c91b171b585eb51e300164e9197","analyzedAt":"2026-09-13T18:02:03.421Z","contentChangedAt":"2026-09-13T18:02:03.421Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}