{"record":{"id":"8685812eed1da7f7","repo":"grpc-ecosystem/grpc-gateway","slug":"encountered-object-type-with-a-summary-but-no-des","errorCode":null,"errorMessage":"encountered object type with a summary, but no description","messagePattern":"encountered object type with a summary, but no description","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"protoc-gen-openapiv2/internal/genopenapi/template.go","lineNumber":2959,"sourceCode":"\t\tusingTitle = true\n\t}\n\n\tparagraphs := strings.Split(comment, paragraphDeliminator)\n\n\t// If there is a summary (or summary-equivalent) and it's empty, use the first\n\t// paragraph as summary, and the rest as description.\n\tif summaryValue.CanSet() {\n\t\tsummary := strings.TrimSpace(paragraphs[0])\n\t\tdescription := strings.TrimSpace(strings.Join(paragraphs[1:], paragraphDeliminator))\n\t\tif !usingTitle || (len(summary) > 0 && summary[len(summary)-1] != '.') {\n\t\t\t// overrides the schema value only if it's empty\n\t\t\t// keep the comment precedence when updating the package definition\n\t\t\tif summaryValue.Len() == 0 || isPackageObject {\n\t\t\t\tsummaryValue.Set(reflect.ValueOf(summary))\n\t\t\t}\n\t\t\tif len(description) > 0 {\n\t\t\t\tif !descriptionValue.CanSet() {\n\t\t\t\t\treturn errors.New(\"encountered object type with a summary, but no description\")\n\t\t\t\t}\n\t\t\t\t// overrides the schema value only if it's empty\n\t\t\t\t// keep the comment precedence when updating the package definition\n\t\t\t\tif descriptionValue.Len() == 0 || isPackageObject {\n\t\t\t\t\tdescriptionValue.Set(reflect.ValueOf(description))\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn nil\n\t\t}\n\t}\n\n\t// There was no summary field on the swaggerObject. Try to apply the\n\t// whole comment into description if the OpenAPI object description is empty.\n\tif descriptionValue.CanSet() {\n\t\tif descriptionValue.Len() == 0 || isPackageObject {\n\t\t\tdescriptionValue.Set(reflect.ValueOf(strings.Join(paragraphs, paragraphDeliminator)))\n\t\t}\n\t\treturn nil","sourceCodeStart":2941,"sourceCodeEnd":2977,"githubUrl":"https://github.com/grpc-ecosystem/grpc-gateway/blob/a58a4436a376a4bcc7d8f10c4d4f919a8438bba9/protoc-gen-openapiv2/internal/genopenapi/template.go#L2941-L2977","documentation":"This error comes from the reflection-based logic in template.go that copies proto comments (summary/description) onto schema objects. When a description paragraph was found but the target struct's Description field cannot be set via reflection (CanSet() false, meaning the field is unexported or the value is not a settable addressable field), the generator returns \"encountered object type with a summary, but no description\". It indicates an internal mismatch while populating comments on an OpenAPI object.","triggerScenarios":"Applying proto file/field comments to an OpenAPI schema object whose description property is not reflectively settable while a non-empty description exists — triggered during applyTemplate/template rendering when processing custom schema or extension types that lack a settable Description field.","commonSituations":"Using custom schema definitions/extensions with proto comments configured (e.g. openapiv2_field/schema options) where the target object struct does not expose a settable Description; library version drift between the generator's expected types and custom types.","solutions":["Ensure the schema object being annotated has a normal, exported Description field (i.e. use the library's own OpenAPI types rather than a custom replacement).","Remove or adjust proto comment annotations for the offending object so no description is attached to a non-settable target.","Update grpc-gateway to the latest patch version; this reflection path has had fixes around summary/description handling.","If embedding custom types, add a settable Description field of type string."],"exampleFix":"// before\ntype mySchema struct {\n    description string // unexported -> CanSet() == false\n}\n// after\ntype mySchema struct {\n    Description string // exported -> settable\n}","handlingStrategy":"type-guard","validationCode":"// ensure target object has a settable Description before attaching comments\nv := reflect.ValueOf(obj).Elem()\nd := v.FieldByName(\"Description\")\nif !d.IsValid() || !d.CanSet() {\n    return fmt.Errorf(\"object %T has no settable Description\", obj)\n}","typeGuard":"func hasSettableDescription(obj interface{}) bool {\n    v := reflect.ValueOf(obj)\n    if v.Kind() != reflect.Ptr || v.Elem().Kind() != reflect.Struct { return false }\n    f := v.Elem().FieldByName(\"Description\")\n    return f.IsValid() && f.CanSet()\n}","tryCatchPattern":"if err := applyTemplate(...); err != nil {\n    if strings.Contains(err.Error(), \"summary, but no description\") {\n        return fmt.Errorf(\"schema object lacks settable Description; check custom types: %w\", err)\n    }\n    return err\n}","preventionTips":["Use the library's own OpenAPI struct types rather than substitutes in custom hooks.","Keep Description fields exported in any custom schema types.","Keep grpc-gateway and go-openapi/spec versions aligned."],"tags":["openapi","reflection","code-generation","proto-comments"],"backgroundTag":"reflection-field-not-settable","analyzedSha":"a58a4436a376a4bcc7d8f10c4d4f919a8438bba9","analyzedAt":"2026-09-02T10:28:31.537Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-09T16:17:10.729Z"}