{"record":{"id":"ddfca176c9a7330f","repo":"pinpoint-apm/pinpoint","slug":"ptransactionid-is-not-set","errorCode":null,"errorMessage":"PTransactionId is not set","messagePattern":"PTransactionId is not set","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"commons-server/src/main/java/com/navercorp/pinpoint/common/server/io/GrpcSpanBinder.java","lineNumber":309,"sourceCode":"        SpanChunkBo spanChunkBo = new SpanChunkBo(traceSourceType, owner);\n        return bind(spanChunkBo, pSpanChunk, requestTime);\n    }\n\n    public SpanChunkBo bind(SpanChunkBo spanChunkBo, PSpanChunk pSpanChunk, long requestTime) {\n        spanChunkBo.setCollectorAcceptTime(requestTime);\n\n        spanChunkBo.setApplicationServiceType((short) pSpanChunk.getApplicationServiceType());\n\n        if (pSpanChunk.hasTransactionId()) {\n            PTransactionId pTransactionId = pSpanChunk.getTransactionId();\n            ServerTraceId transactionId = newTransactionId(pTransactionId, spanChunkBo.getAgentId());\n            spanChunkBo.setTransactionId(transactionId);\n        } else {\n            if (logger.isWarnEnabled()) {\n                SpanOwner owner = spanChunkBo.getSpanOwner();\n                logger.warn(\"PTransactionId is not set {}/{}/{}\", owner.getServiceName(), owner.getApplicationName(), owner.getAgentId());\n            }\n            throw new IllegalStateException(\"PTransactionId is not set\");\n        }\n\n        spanChunkBo.setTraceTime(pSpanChunk.getVersion(), pSpanChunk.getKeyTime());\n\n        spanChunkBo.setSpanId(pSpanChunk.getSpanId());\n        spanChunkBo.setEndPoint(pSpanChunk.getEndPoint());\n        return spanChunkBo;\n    }\n\n    private ServerTraceId newTransactionId(PTransactionId pTransactionId, String spanAgentId) {\n        final String transactionAgentId = pTransactionId.getAgentId();\n        if (StringUtils.hasLength(transactionAgentId)) {\n            return new PinpointServerTraceId(transactionAgentId, pTransactionId.getAgentStartTime(), pTransactionId.getSequence());\n        } else {\n            return new PinpointServerTraceId(spanAgentId, pTransactionId.getAgentStartTime(), pTransactionId.getSequence());\n        }\n    }\n","sourceCodeStart":291,"sourceCodeEnd":327,"githubUrl":"https://github.com/pinpoint-apm/pinpoint/blob/744c3d3075e595656abb1ae331ad2c0e4c9eb996/commons-server/src/main/java/com/navercorp/pinpoint/common/server/io/GrpcSpanBinder.java#L291-L327","documentation":"GrpcSpanBinder throws IllegalStateException when a received span/spanChunk has no transactionId (PTransactionId unset). Without a transactionId the SpanBo/SpanChunkBo cannot be assembled, since it is the trace identity key, so binding is aborted.","triggerScenarios":"Agent sends PSpan or PSpanChunk with transactionId unset/empty, e.g. a buggy or very old agent, or data corrupted in transit/proxying.","commonSituations":"Mismatched agent/collector versions after upgrade; third-party or custom instrumented agents emitting incomplete spans; test harness sending hand-crafted protobuf messages missing transactionId.","solutions":["Upgrade or fix the agent identified by the logged serviceName/applicationName/agentId to send a valid transactionId","Check network intermediaries/proxies for payload corruption","Validate any custom span-producing code sets transactionId before sending","Drop/reject such spans upstream if agents cannot be fixed"],"exampleFix":"// before (hand-crafted protobuf)\nPSpanChunk chunk = PSpanChunk.newBuilder().setSpanId(1L).build();\n// after\nPSpanChunk chunk = PSpanChunk.newBuilder()\n    .setTransactionId(ByteString.copyFromUtf8(\"trace-1\"))\n    .setSpanId(1L)\n    .build();","handlingStrategy":"validation","validationCode":"boolean hasTransactionId(PSpanChunk chunk) {\n    return chunk.hasTransactionId() && !chunk.getTransactionId().isEmpty();\n}\n// call before binding; skip/reject chunk when false","typeGuard":"boolean isValidSpan(PSpanChunk chunk) {\n    return chunk != null && chunk.hasTransactionId();\n}","tryCatchPattern":"try {\n    SpanBo bo = spanBinder.bindSpanChunk(pSpanChunk);\n} catch (IllegalStateException e) {\n    if (\"PTransactionId is not set\".equals(e.getMessage())) {\n        // drop span and count metric; fix the emitting agent\n    }\n}","preventionTips":["Ensure every agent sets transactionId on spans/spanChunks before sending","Pin agent and collector to compatible versions during upgrades","Add an ingestion-side validation/counter for spans missing transactionId","Test custom instrumentation with hand-crafted protobuf against the binder"],"tags":["grpc","span","validation","pinpoint"],"backgroundTag":"empty-required-field","analyzedSha":"744c3d3075e595656abb1ae331ad2c0e4c9eb996","analyzedAt":"2026-09-07T18:48:45.289Z","contentChangedAt":"2026-09-07T18:48:45.289Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}