{"record":{"id":"eb507710e600047a","repo":"hashicorp/terraform","slug":"key-can-not-start-and-end-with","errorCode":null,"errorMessage":"key can not start and end with '/'","messagePattern":"key can not start and end with '/'","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/backend/remote-state/cos/backend.go","lineNumber":148,"sourceCode":"\t\t\t\tType:        schema.TypeString,\n\t\t\t\tOptional:    true,\n\t\t\t\tDescription: \"The directory for saving the state file in bucket\",\n\t\t\t\tValidateFunc: func(v interface{}, s string) ([]string, []error) {\n\t\t\t\t\tprefix := v.(string)\n\t\t\t\t\tif strings.HasPrefix(prefix, \"/\") || strings.HasPrefix(prefix, \"./\") {\n\t\t\t\t\t\treturn nil, []error{fmt.Errorf(\"prefix must not start with '/' or './'\")}\n\t\t\t\t\t}\n\t\t\t\t\treturn nil, nil\n\t\t\t\t},\n\t\t\t},\n\t\t\t\"key\": {\n\t\t\t\tType:        schema.TypeString,\n\t\t\t\tOptional:    true,\n\t\t\t\tDescription: \"The path for saving the state file in bucket\",\n\t\t\t\tDefault:     \"terraform.tfstate\",\n\t\t\t\tValidateFunc: func(v interface{}, s string) ([]string, []error) {\n\t\t\t\t\tif strings.HasPrefix(v.(string), \"/\") || strings.HasSuffix(v.(string), \"/\") {\n\t\t\t\t\t\treturn nil, []error{fmt.Errorf(\"key can not start and end with '/'\")}\n\t\t\t\t\t}\n\t\t\t\t\treturn nil, nil\n\t\t\t\t},\n\t\t\t},\n\t\t\t\"encrypt\": {\n\t\t\t\tType:        schema.TypeBool,\n\t\t\t\tOptional:    true,\n\t\t\t\tDescription: \"Whether to enable server side encryption of the state file\",\n\t\t\t\tDefault:     true,\n\t\t\t},\n\t\t\t\"acl\": {\n\t\t\t\tType:        schema.TypeString,\n\t\t\t\tOptional:    true,\n\t\t\t\tDescription: \"Object ACL to be applied to the state file\",\n\t\t\t\tDefault:     \"private\",\n\t\t\t\tValidateFunc: func(v interface{}, s string) ([]string, []error) {\n\t\t\t\t\tvalue := v.(string)\n\t\t\t\t\tif value != \"private\" && value != \"public-read\" {","sourceCodeStart":130,"sourceCodeEnd":166,"githubUrl":"https://github.com/hashicorp/terraform/blob/d32a084675427f5ac3f7d2868578ef8b2c1dc525/internal/backend/remote-state/cos/backend.go#L130-L166","documentation":"Schema-level ValidateFunc for the COS backend 'key' attribute (the object filename). Leading or trailing slashes would create an empty path segment or a directory-like key, so they are rejected at terraform init time.","triggerScenarios":"terraform init with a `key` value starting with '/' or ending with '/'.","commonSituations":"User sets key = '/terraform.tfstate' by analogy with S3; sets key = 'envs/' intending a folder; copies a full path with slashes at both ends.","solutions":["Use a bare filename or a slash-separated path with no leading or trailing slash, e.g. 'terraform.tfstate' or 'prod/terraform.tfstate'.","Re-run terraform init."],"exampleFix":"// before\nterraform {\n  backend \"cos\" {\n    key = \"/terraform.tfstate\"\n  }\n}\n\n// after\nterraform {\n  backend \"cos\" {\n    key = \"terraform.tfstate\"\n  }\n}","handlingStrategy":"validation","validationCode":"// Validate the COS backend key before terraform init.\nfunc validateCOSKey(key string) error {\n    if strings.HasPrefix(key, \"/\") || strings.HasSuffix(key, \"/\") {\n        return fmt.Errorf(\"key can not start and end with '/'\")\n    }\n    return nil\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Use a bare filename or a slash-separated path with no leading/trailing slash.","Lint backend blocks in CI.","Remember COS keys are object names, not POSIX paths.","Keep key stable for the life of the workspace; renaming is a migration."],"tags":["cos","tencent-cloud","config-validation","backend"],"backgroundTag":null,"analyzedSha":"d32a084675427f5ac3f7d2868578ef8b2c1dc525","analyzedAt":"2026-08-11T18:43:52.779Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}