{"record":{"id":"837fb5a109339aaa","repo":"alibaba/nacos","slug":"parameter-validate-error-837fb5","errorCode":"PARAMETER_VALIDATE_ERROR","errorMessage":"Unsupported uploadAction: {uploadAction}","messagePattern":"Unsupported uploadAction: (.+?)","errorType":"validation","errorClass":"NacosApiException","httpStatus":400,"severity":"warning","filePath":"ai/src/main/java/com/alibaba/nacos/ai/service/skills/SkillOperationServiceImpl.java","lineNumber":407,"sourceCode":"        if (StringUtils.isBlank(uploadAction)) {\n            if (overwrite) {\n                return overwriteUploadedSkill(namespaceId, skill, targetVersion, meta, false,\n                    commitMsg);\n            }\n            return createUploadedSkillDraft(namespaceId, skill, targetVersion, meta, commitMsg);\n        }\n        if (SkillUploadPrecheckResult.ACTION_CREATE_DRAFT.equals(uploadAction)) {\n            return createUploadedSkillDraft(namespaceId, skill, targetVersion, meta, commitMsg);\n        }\n        if (SkillUploadPrecheckResult.ACTION_OVERWRITE_DRAFT.equals(uploadAction)) {\n            return overwriteUploadedSkill(namespaceId, skill, targetVersion, meta, true,\n                commitMsg);\n        }\n        if (SkillUploadPrecheckResult.ACTION_DELETE_DRAFT_AND_CREATE.equals(uploadAction)) {\n            return overwriteUploadedSkill(namespaceId, skill, targetVersion, meta, true,\n                commitMsg);\n        }\n        throw new NacosApiException(NacosException.INVALID_PARAM,\n            ErrorCode.PARAMETER_VALIDATE_ERROR, \"Unsupported uploadAction: \" + uploadAction);\n    }\n    \n    private void checkWritableUploadResource(AiResource meta) throws NacosException {\n        try {\n            VisibilityHelper.checkWritableResource(meta);\n        } catch (NacosException e) {\n            if (e.getErrCode() != NacosException.NO_RIGHT || StringUtils.isBlank(meta.getOwner())) {\n                throw e;\n            }\n            throw new NacosApiException(NacosException.NO_RIGHT, ErrorCode.ACCESS_DENIED,\n                e.getErrMsg() + \", owner: \" + meta.getOwner());\n        }\n    }\n    \n    /**\n     * Bootstrap a built-in skill from a ZIP archive (delegates to the overload with null source).\n     */","sourceCodeStart":389,"sourceCodeEnd":425,"githubUrl":"https://github.com/alibaba/nacos/blob/9b989acdf181d00898f2e8839257bb2b2a3cefe3/ai/src/main/java/com/alibaba/nacos/ai/service/skills/SkillOperationServiceImpl.java#L389-L425","documentation":"An INVALID_PARAM (HTTP 400, ErrorCode PARAMETER_VALIDATE_ERROR/20002) from doUploadSingleSkill: the uploadAction field is non-blank but not one of the recognized constants (CREATE_DRAFT, OVERWRITE_DRAFT, DELETE_DRAFT_AND_CREATE). A blank uploadAction is valid and routes via the overwrite boolean, so only an unrecognized non-blank value triggers this.","triggerScenarios":"Sending an upload request with an uploadAction like 'replace', 'overwrite', 'CREATE', or any string not exactly matching a SkillUploadPrecheckResult.ACTION_* constant.","commonSituations":"Client SDK version mismatch (action names renamed across versions); hand-crafted API call with a guessed action string; copy/paste from outdated docs.","solutions":["Use exactly one of CREATE_DRAFT, OVERWRITE_DRAFT, or DELETE_DRAFT_AND_CREATE.","Or omit uploadAction (send blank) and drive behavior with the overwrite boolean instead.","Re-run precheck and pass back the action string the server itself returned to avoid drift."],"exampleFix":"// before\nrequest.setUploadAction(\"replace\"); // throws 328\n\n// after — pick a recognized constant\nrequest.setUploadAction(SkillUploadPrecheckResult.ACTION_OVERWRITE_DRAFT);\n// or leave blank and use overwrite flag\nrequest.setUploadAction(\"\");\nrequest.setOverwrite(true);","handlingStrategy":"validation","validationCode":"private static final Set<String> VALID_ACTIONS = Set.of(\n    SkillUploadPrecheckResult.ACTION_CREATE_DRAFT,\n    SkillUploadPrecheckResult.ACTION_OVERWRITE_DRAFT,\n    SkillUploadPrecheckResult.ACTION_DELETE_DRAFT_AND_CREATE);\n\nString action = request.getUploadAction();\nif (StringUtils.isNotBlank(action) && !VALID_ACTIONS.contains(action)) {\n    // reject early; or set blank and rely on the overwrite boolean\n    request.setUploadAction(\"\");\n}","typeGuard":"// narrows an action string to a known constant or empty\nstatic String normalizeUploadAction(String raw) {\n    if (StringUtils.isBlank(raw)) return \"\";\n    return switch (raw) {\n        case SkillUploadPrecheckResult.ACTION_CREATE_DRAFT,\n             SkillUploadPrecheckResult.ACTION_OVERWRITE_DRAFT,\n             SkillUploadPrecheckResult.ACTION_DELETE_DRAFT_AND_CREATE -> raw;\n        default -> \"\"; // let overwrite boolean drive behavior\n    };\n}","tryCatchPattern":null,"preventionTips":["Use the SkillUploadPrecheckResult.ACTION_* constants verbatim, never hand-typed strings.","Keep client and server versions in sync so action names match.","Prefer passing the action string the server returned from precheck."],"tags":["upload","action","validation","parameter","skill"],"backgroundTag":null,"analyzedSha":"9b989acdf181d00898f2e8839257bb2b2a3cefe3","analyzedAt":"2026-08-14T07:17:31.569Z","schemaVersion":2},"datasetVersion":"2026-08-14T10:17:34.591Z"}