[WebPlatform.org](http://WebPlatform.org) expressed the wish to incorporate compatibility tables on the website, and provide the compatibility data through an easy to use API. [testthewebforward.org](http://testthewebforward.org) is organizing a similar effort to expose the data it's going to collect through running the [Web Platform W3C test suites](https://github.com/w3c/web-platform-tests). Standardizing on a data model will help sync both of these efforts and allow sourcing data from multiple other sources that would adopt this data exchange model.
This document is a counter proposal to Ronald Mansveld's [original proposal](http://ronaldmansveld.github.io/webplatform-browser-compat/).
Defining a data model is tricky because different data sources have vastly different types of data. Some of this data is very much factual. For example, User Agent with UA string `uas` gets a score of `X` out of `Y` running the test suite `T` for spec `S` on date `t0`. Let's call this *raw data*. While this data is pretty much non-controversial, it is also not very valuable to the end-developer. Interpreting this data to conclude that User Agent `A` supports feature `F` is where the real value lies. Let's call this *interpreted data*. Ideally, we'd always be storing raw data. Unfortunately, that is not always possible. The challenge therefore consists in devising data models and transformation strategies which allow both raw and interpreted data to co-exist and be used together.
Format ------ The data format is [[JSON]]. User Agent data models ---------------------- ### Reference User Agent Parser Precisely identifying User Agents is a tricky business as camouflaging their true identity and impersonating others has been among User Agent's [earliest survival techniques](http://webaim.org/blog/user-agent-string-history/). Despite it's flaws, User Agent String parsing remains the best technique to identify browsers for analytics or testing purposes. Properly parsing a User Agent string is a dirty job and not one that could be specified easily. With specifying a UA parsing algorithm out of the question, our second best bet is to standardize on reference UA parser that fits our licensing requirements and doesn't tie us to one programming language: [`ua-parser`](https://github.com/tobie/ua-parser), the open-source parser extracted from the [Browserscope](http://www.browserscope.org/) project. It has [liberal licensing](https://github.com/tobie/ua-parser#license) and is polyglot by nature: the core of the parser is a [list of regexes](https://github.com/tobie/ua-parser/blob/master/regexes.yaml) which can be used to implement the parser in any language that supports regular expressions and is able to consume [[YAML]] (disclaimer, the editor of this document is also `ua-parser`'s co-maintainer). Currently, implementations exist in: C#, D, Go, Haskell, Java, JavaScript (node.js), Perl, PHP, Pig, Python, and Ruby. ### Incomplete Version Strings in UserAgentInfo and OperatingSystemInfo

How do we handle incomplete version strings? Consider `uainfo`, an instance of UserAgentInfo. Its `family` attribute is `"Foo"`; its `major` attribute, `"8"`; and its `minor` and `patch` attributes are both `null`. For the sake of argument, imagine we represent this User Agent as the string "Foo 8". Now consider `Feature` `f` which is determined to be supported by "Foo 8.1", but not by "Foo 8.0". Do we consider it is supported by "Foo 8" or not?

### The `UserAgent` object The UserAgentInfo, OperatingSystemInfo and DeviceInfo objects are usually obtained programmatically by parsing a User Agent string using the reference UA parser. However, these objects can also be manually authored. In such cases, their `family`, `brand` and `model` attributes MUST be a possible output value of the reference UA parser in order for the data set to be interoperable. So for example, if the reference UA parser identifies Internet Explorer's family as as `"IE"`, a manually authored UserAgentInfo object which would identify it as `"MSIE"` would **not** conform.

A list of possible values for the UserAgentInfo, OperatingSystemInfo and DeviceInfo `family`, `brand` and `model` attributes must be reverse-engineered from the reference UA parser and maintained.

DOMString? userAgentString
The User Agent String.
UserAgentInfo ua
Details of the User Agent's family and version number
OperatingSystemInfo os
Details of the Operating System the User Agent is running on
DeviceInfo device
Details of the Device the User Agent is running on
{
    "userAgentString": "Mozilla/5.0 (Linux; Android 4.1.1; SPH-L710 Build/JRO03L) AppleWebKit/535.19 (KHTML, like Gecko) Chrome/18.0.1025.166 Mobile Safari/535.19",
    "ua": {
        "family": "Chrome Mobile",
        "major": "18",
        "minor": "0",
        "patch": "1025"
    },
    "os": {
        "family": "Android",
        "major": "4",
        "minor": "1",
        "patch": "1",
        "patchMinor": null
    },
    "device": {
        "brand": "Samsung",
        "family": "Galaxy",
        "model": "S3"
    }
}
### The UserAgentInfo object If the value of the `family` attribute is `"Other"`, the value of the `major`, `minor` and `patch` attributes MUST be `null`. If the value of the `major` attribute is `null`, the value of the `minor` and `patch` attributes MUST be `null`. If the value of the `minor` attribute is `null`, the value of the `patch` attribute MUST be `null`.
DOMString family = "Other"
The name of the User Agent
DOMString? major
The version sequence's major number
DOMString? minor
The version sequence's minor number
DOMString? patch
The version sequence's patch number
### The OperatingSystemInfo object If the value of the `family` attribute is `"Other"`, the value of the `major`, `minor`, `patch` and `minorPatch` attributes MUST be `null`. If the value of the `major` attribute is `null`, the value of the `minor`, `patch` and `minorPatch` attributes MUST be `null`. If the value of the `major` attribute is `null`, the value of the `minor`, `patch` and `minorPatch` attributes MUST be `null`. If the value of the `minor` attribute is `null`, the value of the `patch` and `minorPatch` attributes MUST be `null`. If the value of the `patch` attribute is `null`, the value of the `minorPatch` attribute MUST be `null`.
DOMString family = "Other"
The name of the Operating System
DOMString? major
The version sequence's major number
DOMString? minor
The version sequence's minor number
DOMString? patch
The version sequence's patch number
DOMString? minorPatch
The version sequence's minor patch number
### The DeviceInfo object If the value of the `family` attribute is `"Other"`, the value of the `model` attribute MUST be `null`.
DOMString? brand
The device's brand
DOMString family = "Other"
The device's family
DOMString? model
The device's model
Features -------- Features are an abstraction that map to specs, their sections or subsections. ### The Feature object
DOMString url
The link to this feature's related spec or spec section/subsection
DOMString name
The name of this feature
  {
    "url":"http://www.w3.org/TR/IndexedDB/",
    "name":"IndexedDB"
  }
  {
    "url":"http://www.w3.org/TR/html5/embedded-content-0.html#attr-iframe-seamless",
    "name":"Seamless iframes"
  }
### The SupportLevel Enum
full
The Feature is fully supported on that UserAgent
partial
The Feature is partially supported on that UserAgent
none
The Feature is not supported on that UserAgent
polyfilled
The Feature is only supported on that UserAgent when polyfilled
### The FeatureSupport object
Feature feature
The corresponding Feature object
UserAgent userAgent
The corresponding UserAgent object
SupportLevel supportLevel
The level of support for this `feature` on that `userAgent`.