{"record":{"id":"1b80011d4ac27983","repo":"grpc/grpc-go","slug":"method-name-must-be-non-empty","errorCode":null,"errorMessage":"method name must be non empty","messagePattern":"method name must be non empty","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"gcp/observability/config.go","lineNumber":68,"sourceCode":"\t\tlogger.Infof(\"Failed to find project ID in default credential: %v\", err)\n\t\treturn \"\"\n\t}\n\tlogger.Infof(\"Found project ID from Google Default Credential: %v\", credentials.ProjectID)\n\treturn credentials.ProjectID\n}\n\n// validateMethodString validates whether the string passed in is a valid\n// pattern.\nfunc validateMethodString(method string) error {\n\tif strings.HasPrefix(method, \"/\") {\n\t\treturn errors.New(\"cannot have a leading slash\")\n\t}\n\tserviceMethod := strings.Split(method, \"/\")\n\tif len(serviceMethod) != 2 {\n\t\treturn errors.New(\"/ must come in between service and method, only one /\")\n\t}\n\tif serviceMethod[1] == \"\" {\n\t\treturn errors.New(\"method name must be non empty\")\n\t}\n\tif serviceMethod[0] == \"*\" {\n\t\treturn errors.New(\"cannot have service wildcard * i.e. (*/m)\")\n\t}\n\treturn nil\n}\n\nfunc validateLogEventMethod(methods []string, exclude bool) error {\n\tfor _, method := range methods {\n\t\tif method == \"*\" {\n\t\t\tif exclude {\n\t\t\t\treturn errors.New(\"cannot have exclude and a '*' wildcard\")\n\t\t\t}\n\t\t\tcontinue\n\t\t}\n\t\tif err := validateMethodString(method); err != nil {\n\t\t\treturn fmt.Errorf(\"invalid method string: %v, err: %v\", method, err)\n\t\t}","sourceCodeStart":50,"sourceCodeEnd":86,"githubUrl":"https://github.com/grpc/grpc-go/blob/0c51461d27177d997e14c642fe18c11668fc09a3/gcp/observability/config.go#L50-L86","documentation":"Returned by validateMethodString when the method part (the segment after the '/') is empty. The function splits by '/' and checks serviceMethod[1] == \"\". This catches patterns like pkg.Service/ where the service is specified but no method name follows the slash.","triggerScenarios":"A method entry in the observability config ends with a trailing slash and no method name, e.g., foo.Bar/. The split produces [\"foo.Bar\", \"\"], and the empty second element triggers the error.","commonSituations":"Developers use a trailing slash intending it as a prefix or directory separator (common in REST-style path thinking), or accidentally leave it after editing. Also from templated config generation that appends '/' unconditionally.","solutions":["Provide a concrete method name (foo.Bar/Method) or use the wildcard (foo.Bar/*) to match all methods.","Fix config-generation templates that append a trailing slash without a method suffix."],"exampleFix":"// before\n{\"methods\":[\"foo.Bar/\"]} // trailing slash, empty method\n// after\n{\"methods\":[\"foo.Bar/*\"]} // match all methods in service","handlingStrategy":"validation","validationCode":"parts := strings.Split(method, \"/\")\nif len(parts) == 2 && parts[1] == \"\" {\n    return fmt.Errorf(\"method name after / must be non-empty; use * for wildcard\")\n}","typeGuard":"func isValidMethodPattern(m string) bool {\n    parts := strings.Split(m, \"/\")\n    return len(parts) == 2 && parts[1] != \"\"\n}","tryCatchPattern":null,"preventionTips":["Never leave the method part empty; use * for all methods in a service.","Fix config templates that append a trailing slash unconditionally.","Validate patterns before applying the config."],"tags":["go","grpc","observability","config","validation"],"backgroundTag":null,"analyzedSha":"0c51461d27177d997e14c642fe18c11668fc09a3","analyzedAt":"2026-08-11T14:49:15.055Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}