{"record":{"id":"0836cb8d4dda288e","repo":"alibaba/nacos","slug":"latest-label-and-versioncatalog-latestversion-must","errorCode":null,"errorMessage":"latest label and versionCatalog.latestVersion must match","messagePattern":"latest label and versionCatalog\\.latestVersion must match","errorType":"validation","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"api/src/main/java/com/alibaba/nacos/api/ai/utils/AgentModelValidator.java","lineNumber":443,"sourceCode":"            || onlineVersionValues.contains(reviewingVersion)) {\n            throw new IllegalArgumentException(\n                \"editingVersion and reviewingVersion must not identify online Versions\");\n        }\n        for (Map.Entry<String, String> label : versionInfo.getLabels().entrySet()) {\n            if (label.getValue().equals(editingVersion)\n                || label.getValue().equals(reviewingVersion)) {\n                throw new IllegalArgumentException(\n                    \"Labels must not identify editing or reviewing Versions\");\n            }\n        }\n        String latestLabelVersion = versionInfo.getLabels().get(\"latest\");\n        if (catalog.getLatestVersion() == null) {\n            if (latestLabelVersion != null) {\n                throw new IllegalArgumentException(\n                    \"latest label must be absent when no online Version exists\");\n            }\n        } else if (!catalog.getLatestVersion().equals(latestLabelVersion)) {\n            throw new IllegalArgumentException(\n                \"latest label and versionCatalog.latestVersion must match\");\n        }\n        for (AgentVersionCatalogEntry entry : onlineVersions) {\n            for (String label : entry.getLabels()) {\n                if (!entry.getVersion().equals(versionInfo.getLabels().get(label))) {\n                    throw new IllegalArgumentException(\n                        \"Version catalog label does not match versionInfo: \" + label);\n                }\n            }\n        }\n        for (Map.Entry<String, String> label : versionInfo.getLabels().entrySet()) {\n            if (\"latest\".equals(label.getKey())\n                || !onlineVersionValues.contains(label.getValue())) {\n                continue;\n            }\n            boolean presentInCatalog = false;\n            for (AgentVersionCatalogEntry entry : onlineVersions) {\n                if (entry.getVersion().equals(label.getValue())","sourceCodeStart":425,"sourceCodeEnd":461,"githubUrl":"https://github.com/alibaba/nacos/blob/9b989acdf181d00898f2e8839257bb2b2a3cefe3/api/src/main/java/com/alibaba/nacos/api/ai/utils/AgentModelValidator.java#L425-L461","documentation":"Thrown by validateVersionInfoCatalogConsistency when versionCatalog.latestVersion is non-null but versionInfo.labels[\"latest\"] is either absent or a different value. The two representations of \"latest\" (the catalog field and the versionInfo label) must agree exactly. This is the non-null-catalog branch paired with error 489.","triggerScenarios":"Updating catalog.latestVersion during a publish but not updating labels[\"latest\"], or vice versa; deserializing a payload where the two fields were written by different code paths.","commonSituations":"A publish operation that sets the catalog latest pointer centrally but expects each client to mirror it into labels; partial updates that touch only one of the two fields.","solutions":["Set versionInfo.labels[\"latest\"] to the exact same string as versionCatalog.latestVersion whenever a latest online Version exists.","Centralize latest-pointer assignment so both fields are written together.","After any publish/unpublish, recompute catalog.latestVersion and mirror it into the label in the same mutation."],"exampleFix":"// before\ncatalog.setLatestVersion(\"1.3.0\"); versionInfo.getLabels().put(\"latest\", \"1.2.0\");\n// after\nString latest = catalog.getLatestVersion();\nversionInfo.getLabels().put(\"latest\", latest);","handlingStrategy":"validation","validationCode":"static void syncLatestLabel(AgentVersionInfo info, AgentVersionCatalog catalog) {\n    if (catalog.getLatestVersion() != null) {\n        info.getLabels().put(\"latest\", catalog.getLatestVersion());\n    }\n}","typeGuard":"static boolean latestLabelMatches(AgentVersionInfo info, AgentVersionCatalog catalog) {\n    String latest = catalog.getLatestVersion();\n    return latest == null || latest.equals(info.getLabels().get(\"latest\"));\n}","tryCatchPattern":"try {\n    AgentModelValidator.validateAgent(agent);\n} catch (IllegalArgumentException e) {\n    if (e.getMessage().contains(\"latest label and versionCatalog.latestVersion must match\")) {\n        agent.getVersionInfo().getLabels().put(\"latest\",\n            agent.getVersionCatalog().getLatestVersion());\n    }\n}","preventionTips":["Mirror catalog.latestVersion into labels[\"latest\"] whenever it changes.","Centralize latest-pointer assignment so both fields are written together.","Recompute latest on every publish/unpublish and update both representations atomically."],"tags":["ai-agent","validation","version-info","labels","consistency","illegal-argument"],"backgroundTag":null,"analyzedSha":"9b989acdf181d00898f2e8839257bb2b2a3cefe3","analyzedAt":"2026-08-14T07:17:31.569Z","schemaVersion":2},"datasetVersion":"2026-08-14T10:17:34.591Z"}