question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Details of model composition should be documented

See original GitHub issue

OASv3.0 says:

The OpenAPI Specification allows combining and extending model definitions using the allOf property of JSON Schema, in effect offering model composition. allOf takes an array of object definitions that are validated independently but together compose a single object.

However, the spec does not define how this composition should be done. In particular, it is unclear how to interpret an “allOf” composition when a property appears in more than one component of the “allOf”. For example, in this schema:

      "Thing": {
        "allOf": [
          {
            "properties": {
              "foo": {
                "type": "string"
              }
            }
          },
          {
            "properties": {
              "foo": {
                "type": "string"
              }
            },
            "required": [
              "foo"
            ]
          }
        ]
      },

it is not clear from the specification whether foo is required or optional in the Thing schema.

Multiple interpretations are possible, including “first occurrence of the property wins” or “last occurrence of the property wins”. However, to be consistent with JSON Schema, it seems that we need a more complicated interpretation. The JSON Schema spec says:

An instance validates successfully against [allOf] if it validates successfully against all schemas defined by this keyword’s value.

To be consistent with JSON schema, it seems that we should “compose” like-named properties in a “allOf” in a way that produces the “most restrictive” property definition. For example, a property that is required in any component of the “allOf” would be required in the composed model. Or if one property specifies a maximum, the composed property would have that maximum.

Whether it is the “composed property” interpretation or some other that is appropriate, it should be clearly documented in the spec.

Issue Analytics

  • State:closed
  • Created 6 years ago
  • Reactions:2
  • Comments:15 (9 by maintainers)

github_iconTop GitHub Comments

1reaction
handrewscommented, Mar 12, 2021

@spacether it’s too late at night here for me to attempt schema algebra but let me sketch out a few things:

  1. You’re using oneOf a lot here, and oneOf is much more complex to work with than allOf. You usually can’t rearrange a schema to totally eliminate a oneOf, except in a few cases where other keywords produce similar behavior (e.g. the array form of type or certain arrangements of if/then/else). not is the really hard one, actually- you can rework oneOf into a combination of allOfs and nots but that’s really hard to read.
  2. If the only combinatorial or conditional applicator keyword involved is allOf, you can generally collapse it, although it’s non-trivial and some cases cannot be collapsed because they involve the same keyword used multiple times in a way that is not contradictory and cannot be reduced to one use of the keyword. I wrote a partial implementation of this back in the draft-07 days, although I don’t think that package has been significantly maintained since I left that job.

As you can see if you poke around in that repo, I did the collapsing because we were using schemas for documentation and having a ton of allOfs show up when they were often just artifacts of making schemas modular rather than being significant to end-users cluttered the documentation. So I was reducing that clutter as much as possible. It’s debatable as to whether that’s really the “right” thing to do. But that sort of thing- reducing clutter without changing functionality- is the main reason I’d ever do that. As far as validation, there’s no reason to collapse things.

If you’re making use of annotations, which your application might interpret based on their location in the schema (e.g. a title outside of a $ref might override one inside of the $ref) then doing a lot of de-referencing and collapsing is not advised.

Philosophically, I’d like to encourage folks to design annotation vocabularies (now that extension vocabularies are supported in OAS 3.1 and JSON Schema 2020-12) to give tools hints as to how to handle things like allOf. You can find examples of this in other issues here. But the general idea is to add keywords that don’t do any validation, but indicate whether an adjacent** allOf should be treated as composition or some sort of inheritance for code generation purposes. The validation is the same either way. This is how I want to bridge the gap between JSON Schema being a constraint validation system while tools like code and documentation generation want a data definition language. These are not the same things, and a lot of difficult problems have arisen by trying to make a constraint system a data definition system. Annotations provide a flexible way to solve those problems.

**adjacent keywords are keywords in the same schema object

1reaction
handrewscommented, Dec 8, 2017

Or maybe more simply, just state that the composition should be interpreted consistent with the JSON schema interpretation of allOf (though that leaves it up to the reader to understand the nuances of this).

As one of the editors of the JSON Schema spec, I would prefer this 😃

More broadly, I am hoping that we can converge the JSON Schema spec and Open API uses of JSON Schema spec to the point where little or even no special wording on the part of OAI is necessary, primarily through improving the modularity of JSON Schema. Embedding a subset of JSON Schema into a larger document is done in several projects (OAI is the largest that I know of) so we should address that on the JSON Schema spec side.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Composition: Proposed behavior — Documentation - SDFormat
The frames, links, and joints in a model (implicit and explicit) should be considered the public "API" of the model. If an intermediate...
Read more >
Writing Effective Model Documentation - SOA
Provide a detailed description of the input facility for the model, such as groups, tables, variables; these should include naming conventions.
Read more >
Composition - FHIR v5.0.0-snapshot3
A Composition defines the structure and narrative content necessary for a document. However, a Composition alone does not constitute a document. Rather, the ......
Read more >
What is Document Composition Software? | HotDocs
Powerful document composition systems will allow for data to be drawn from one or more external data sources, thus eliminating, in some instances,...
Read more >
Model Composition for Integration Scenarios - SAP Help Portal
Model composition is provided for complex scenarios for the integration topics, such as SAP Business Warehouse, GenIL and SPI. It allows mashing up...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found