{"record":{"id":"8156ae84c332bd01","repo":"alibaba/spring-ai-alibaba","slug":"unable-to-load-checkpoint-8156ae","errorCode":null,"errorMessage":"Unable to load checkpoint","messagePattern":"Unable to load checkpoint","errorType":"exception","errorClass":"Exception","httpStatus":null,"severity":"error","filePath":"spring-ai-alibaba-graph-core/src/main/java/com/alibaba/cloud/ai/graph/checkpoint/savers/postgresql/PostgresSaver.java","lineNumber":448,"sourceCode":"\t}\n\n\t@Override\n\tprotected Optional<Checkpoint> selectCheckpointById(String threadId, String checkpointId) throws Exception {\n\t\ttry (Connection conn = getConnection();\n\t\t\t\tPreparedStatement ps = conn.prepareStatement(SELECT_CHECKPOINT_BY_ID)) {\n\n\t\t\tlog.trace(\"Executing select checkpoint by id:\\n---\\n{}---\", SELECT_CHECKPOINT_BY_ID);\n\t\t\tps.setString(1, threadId);\n\t\t\tps.setObject(2, UUID.fromString(checkpointId), Types.OTHER);\n\t\t\ttry (ResultSet rs = ps.executeQuery()) {\n\t\t\t\tif (rs.next()) {\n\t\t\t\t\treturn Optional.of(readCheckpoint(rs));\n\t\t\t\t}\n\t\t\t\treturn Optional.empty();\n\t\t\t}\n\t\t}\n\t\tcatch (SQLException | IOException | ClassNotFoundException ex) {\n\t\t\tthrow new Exception(\"Unable to load checkpoint\", ex);\n\t\t}\n\t}\n\n\t@Override\n\tprotected void insertCheckpoint(String threadId, Checkpoint checkpoint) throws Exception {\n\t\tConnection conn = null;\n\t\ttry (Connection ignored = conn = getConnection()) {\n\t\t\tconn.setAutoCommit(false);\n\t\t\tinsertCheckpoint(conn, threadId, checkpoint);\n\t\t\tconn.commit();\n\t\t\tlog.debug(\"Checkpoint {} for thread {} inserted successfully.\", checkpoint.getId(), threadId);\n\t\t}\n\t\tcatch (SQLException | IOException ex) {\n\t\t\tlog.error(\"Error inserting checkpoint with id {} in thread {}\", checkpoint.getId(), threadId, ex);\n\t\t\trollback(conn, checkpoint, threadId);\n\t\t\tthrow new Exception(\"Unable to insert checkpoint\", ex);\n\t\t}\n\t}","sourceCodeStart":430,"sourceCodeEnd":466,"githubUrl":"https://github.com/alibaba/spring-ai-alibaba/blob/f82da0b50f35744c13968191be2b1cd2452ef550/spring-ai-alibaba-graph-core/src/main/java/com/alibaba/cloud/ai/graph/checkpoint/savers/postgresql/PostgresSaver.java#L430-L466","documentation":"PostgresSaver.selectCheckpointById wraps SQLException, IOException, and ClassNotFoundException from fetching a specific checkpoint by threadId and checkpointId into Exception('Unable to load checkpoint'). It indicates the SELECT or row deserialization via readCheckpoint failed for that specific record.","triggerScenarios":"Loading a checkpoint by explicit id when the query fails (connectivity, schema mismatch) or the row's serialized state cannot be decoded (wrong serializer/content type, ClassNotFoundException, corrupted payload).","commonSituations":"Time-travel/replay to a specific checkpoint id created by an older app version with different serialization; renamed state classes causing ClassNotFoundException; DB connectivity hiccups.","solutions":["Read the cause: SQLException vs ClassNotFoundException vs IOException to target the fix.","Match the StateSerializer to the one used when the checkpoint was written.","Keep backward-compatible state classes (same package/name, serialVersionUID) for old checkpoints.","If the record is corrupt, remove it or recreate the checkpoint."],"exampleFix":"// before\n// state class moved package -> ClassNotFoundException\npackage com.newpkg; public class MyState implements Serializable {...}\n// after\npackage com.oldpkg; public class MyState implements Serializable {...} // preserve original FQCN","handlingStrategy":"try-catch","validationCode":"// Java: validate ids are well-formed before lookup\nUUID.fromString(checkpointId); // throws IllegalArgumentException early if malformed","typeGuard":null,"tryCatchPattern":"try {\n    var cp = saver.get(config, checkpointId);\n} catch (Exception e) {\n    if (\"Unable to load checkpoint\".equals(e.getMessage()) && e.getCause() instanceof ClassNotFoundException cnfe) {\n        // restore old state class or migrate data\n    }\n}","preventionTips":["Preserve serialVersionUID and package names of serializable state classes.","Verify ids exist before time-travel/replay operations.","Keep serializer configuration consistent across app versions.","Log causes distinctly: SQL vs ClassNotFound vs IO."],"tags":["postgres","checkpoint","deserialization","database"],"backgroundTag":"database-query-failed","analyzedSha":"f82da0b50f35744c13968191be2b1cd2452ef550","analyzedAt":"2026-09-09T15:32:42.421Z","contentChangedAt":"2026-09-09T15:32:42.421Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}