Skip to content

Add support for ffextensions#208

Open
chrisbygrave wants to merge 4 commits intohyperledger:mainfrom
chrisbygrave:ff-openapi-extensions
Open

Add support for ffextensions#208
chrisbygrave wants to merge 4 commits intohyperledger:mainfrom
chrisbygrave:ff-openapi-extensions

Conversation

@chrisbygrave
Copy link
Contributor

This PR adds support for a gostruct tag ffextensions that allows a comma-separated list of key/value pairs to be added as extensions to the schema generated into the OpenAPI document. Keys must be of the format x-<name>.

For example, the following structure:

type TestExtensions struct {
	MyString string `ffstruct:"mystruct" json:"mystring" ffextensions:"x-key=value"`
}

Would generate a schema:

mystring:
  description: mystruct.mystring
  type: string
  x-key: value

- a go struct tag that enables extensions to be introduced to the generated OpenAPI documents

Signed-off-by: Chris Bygrave <chris.bygrave@kaleido.io>
@chrisbygrave chrisbygrave requested a review from a team as a code owner February 17, 2026 15:22
Copy link
Contributor

@EnriqueL8 EnriqueL8 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good - a question and needs gofmt formatting

chrisbygrave and others added 2 commits February 17, 2026 16:49
Co-authored-by: Enrique Lacal <enrique.lacal@kaleido.io>
Signed-off-by: Chris Bygrave <chris.bygrave@kaleido.io>
Signed-off-by: Chris Bygrave <chris.bygrave@kaleido.io>
Copy link
Contributor

@EnriqueL8 EnriqueL8 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me @chrisbygrave - thanks!

if tag == "" {
return nil
}
for _, extension := range strings.Split(tag, ",") {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The restriction that , is a special character for which there is no escape, probably needs calling out.

Another option would be to use query syntax parsing, which would mean & separator (rather than ,), but also a complete set of pre-built parsing logic and escaping rules

Copy link
Contributor Author

@chrisbygrave chrisbygrave Mar 2, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My thinking here was to follow the pattern of https://github.com/invopop/jsonschema which provides jsonschema_extras which uses a comma separator. It looked like a reasonably popular package and so conforming with their spelling seemed appropriate.

Happy to re-work using query syntax parsing if we think that would be less restrictive though.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Happy to see you take either as inspiration. I did take your hint to go and look at what invopop does on escaping:
https://github.com/invopop/jsonschema/blob/328cc73c3399c73df18b708fa00d29669cb0e4cc/reflect.go#L1121-L1144

if ffEnum := tag.Get("ffenum"); ffEnum != "" {
schema.Enum = fftypes.FFEnumValues(ffEnum)
}
if ffExtensions := tag.Get("ffextensions"); ffExtensions != "" {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

type TestExtensions struct {
	MyString string `ffstruct:"mystruct" json:"mystring" ffextensions:"x-key=value"`
}

I found ffextensions a little hard as a term here. All the ffxyz tags are "extensions", so it's a little bit of a mental jump from ffextensions to "These key+value pairs will make their way into the JSON schema, as extensions under the type of this field".

My counter proposal is probably ffschemaext (I think ffschemaextensions is way too long)

Copy link
Contributor

@peterbroadhurst peterbroadhurst left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Couple of thoughts here @chrisbygrave

- ffextensions -> ffschemaext
- use query-like format with well-defined escaping strategy

Signed-off-by: Chris Bygrave <chris.bygrave@kaleido.io>
@chrisbygrave
Copy link
Contributor Author

Thanks for the steer @peterbroadhurst - I've updated the PR to support query syntax parsing, and added a couple of tests to catch encoding issues.

I've also switched out ffextensions for ffschemaext - it does indeed feel clearer.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants