{"record":{"id":"0f4f6266b14305b2","repo":"sgl-project/sglang","slug":"duplicate-request-id-request-id","errorCode":null,"errorMessage":"Duplicate request_id: {request_id}","messagePattern":"Duplicate request_id: (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"python/sglang/multimodal_gen/runtime/disaggregation/request_state.py","lineNumber":86,"sourceCode":"\n    def elapsed_s(self) -> float:\n        return time.monotonic() - self.submit_time\n\n    def is_terminal(self) -> bool:\n        return self.state in _TERMINAL_STATES\n\n\nclass RequestTracker:\n    \"\"\"Thread-safe tracker for request state machines.\"\"\"\n\n    def __init__(self):\n        self._lock = threading.Lock()\n        self._requests: dict[str, RequestRecord] = {}\n\n    def submit(self, request_id: str) -> RequestRecord:\n        with self._lock:\n            if request_id in self._requests:\n                raise ValueError(f\"Duplicate request_id: {request_id}\")\n            record = RequestRecord(request_id=request_id)\n            self._requests[request_id] = record\n            return record\n\n    def transition(\n        self,\n        request_id: str,\n        new_state: RequestState,\n        *,\n        error: str | None = None,\n        encoder_instance: int | None = None,\n        denoiser_instance: int | None = None,\n        decoder_instance: int | None = None,\n    ) -> RequestRecord:\n        with self._lock:\n            record = self._requests.get(request_id)\n            if record is None:\n                raise ValueError(f\"Unknown request_id: {request_id}\")","sourceCodeStart":68,"sourceCodeEnd":104,"githubUrl":"https://github.com/sgl-project/sglang/blob/0132848349585cfe6aae51c4941cbae872505f8a/python/sglang/multimodal_gen/runtime/disaggregation/request_state.py#L68-L104","documentation":"Raised by RequestStateStore.submit when a request_id already exists in the store. The store keys every in-flight request by a unique request_id, and re-submitting an id would corrupt state tracking, so duplicates are rejected at insertion time under the store's lock.","triggerScenarios":"Calling submit(request_id) twice without the first request reaching a terminal state and being removed — e.g. a client retrying a request with the same id, or two concurrent client requests arriving with colliding ids at _handle_client_request.","commonSituations":"Client-side retries (timeout + retry with the same id), id generation based on non-unique input (hash of prompt), reconnections replaying queued requests, or a bug where the same frame is handled twice.","solutions":["Generate globally unique request ids (UUID4) per submission on the client side","On retry, first check whether the id already exists (store.get/lookup) and resume that request instead of resubmitting","Catch the ValueError and return an idempotent 'duplicate request' response to the client rather than crashing the handler","Ensure terminal requests are cleaned up from the store so ids can be safely reused if ids are scoped per session"],"exampleFix":"# before\nstore.submit(request_id)  # ValueError on retry\n\n# after\nimport uuid\nrequest_id = str(uuid.uuid4())  # fresh id per submission\nstore.submit(request_id)","handlingStrategy":"validation","validationCode":"import uuid\nrequest_id = str(uuid.uuid4())\ntry:\n    record = store.submit(request_id)\nexcept ValueError:\n    # id collision: resume or regenerate\n    record = store.submit(str(uuid.uuid4()))","typeGuard":null,"tryCatchPattern":"try:\n    store.submit(request_id)\nexcept ValueError as e:\n    if \"Duplicate request_id\" in str(e):\n        return existing_response_or_conflict(request_id)\n    raise","preventionTips":["Always generate request ids with uuid4 on the client","Make submission endpoints idempotent: on duplicate, return the existing request's status","Scope custom ids per client session and never derive them solely from input content"],"tags":["disaggregation","request-state","duplicate-id","idempotency"],"backgroundTag":"duplicate-request-id","analyzedSha":"0132848349585cfe6aae51c4941cbae872505f8a","analyzedAt":"2026-08-28T05:10:05.995Z","schemaVersion":2},"datasetVersion":"2026-08-28T06:17:29.519Z"}