BuyWhere · API Governance Rules

BuyWhere API Rules

Spectral linting rules defining API design standards and conventions for BuyWhere.

14 Rules error 3 warn 9 info 2
View Rules File View on GitHub

Rule Categories

buywhere

Rules

warn
buywhere-summary-title-case
Operation summaries should use Title Case.
$.paths[*][get,put,post,delete,patch].summary
error
buywhere-operation-id-camelcase
operationId should be lowerCamelCase verbNoun.
$.paths[*][get,put,post,delete,patch].operationId
error
buywhere-operation-id-required
All operations must have an operationId.
$.paths[*][get,put,post,delete,patch]
warn
buywhere-operation-tagged
Every operation must be tagged for Documentation grouping.
$.paths[*][get,put,post,delete,patch]
warn
buywhere-paths-kebab-case
Path segments should be lowercase kebab-case (allows {paramName}).
$.paths
error
buywhere-server-url-versioned
Server URLs must include a version segment (e.g. /v1).
$.servers[*].url
warn
buywhere-bearer-required
Non-auth operations must require BearerAuth security.
$.paths[?(@property != '/auth/register' && @property != '/auth')][get,put,post,delete,patch]
warn
buywhere-product-id-uuid
Product `id` path parameters must be format uuid.
$.paths[*][get,put,post,delete,patch].parameters[?(@.in=='path' && @.name=='id')].schema
warn
buywhere-limit-bounded
limit parameters should declare a maximum.
$.paths[*][get].parameters[?(@.name=='limit')].schema
info
buywhere-currency-enum
Currency parameter examples should be in the supported set (SGD, USD, VND, THB, MYR).
$.paths[*][get].parameters[?(@.name=='currency')].schema.default
warn
buywhere-401-response
Authenticated operations must document a 401 response.
$.paths[?(@property != '/auth/register' && @property != '/auth')][get,put,post,delete,patch].responses
warn
buywhere-429-on-search
Search endpoints must document a 429 (rate limit) response.
$.paths['/products/search'][get].responses
warn
buywhere-info-contact
API info must include contact email.
$.info.contact
info
buywhere-external-docs
API should reference MCP / external documentation.
$

Spectral Ruleset

Raw ↑
extends:
  - spectral:oas

functions: []

rules:
  # Style
  buywhere-summary-title-case:
    description: Operation summaries should use Title Case.
    message: "Operation summary should use Title Case: {{value}}"
    severity: warn
    given: "$.paths[*][get,put,post,delete,patch].summary"
    then:
      function: pattern
      functionOptions:
        match: "^([A-Z0-9][A-Za-z0-9-]*)([ /-][A-Z0-9][A-Za-z0-9-]*)*( By [A-Z][A-Za-z]*)?$"

  buywhere-operation-id-camelcase:
    description: operationId should be lowerCamelCase verbNoun.
    message: "operationId should be lowerCamelCase: {{value}}"
    severity: error
    given: "$.paths[*][get,put,post,delete,patch].operationId"
    then:
      function: pattern
      functionOptions:
        match: "^[a-z][a-zA-Z0-9]+$"

  buywhere-operation-id-required:
    description: All operations must have an operationId.
    severity: error
    given: "$.paths[*][get,put,post,delete,patch]"
    then:
      field: operationId
      function: truthy

  buywhere-operation-tagged:
    description: Every operation must be tagged for Documentation grouping.
    severity: warn
    given: "$.paths[*][get,put,post,delete,patch]"
    then:
      field: tags
      function: truthy

  buywhere-paths-kebab-case:
    description: Path segments should be lowercase kebab-case (allows {paramName}).
    severity: warn
    given: "$.paths"
    then:
      function: pattern
      functionOptions:
        match: "^/[a-z0-9{}\\-/_]*$"
      field: "@key"

  buywhere-server-url-versioned:
    description: Server URLs must include a version segment (e.g. /v1).
    severity: error
    given: "$.servers[*].url"
    then:
      function: pattern
      functionOptions:
        match: "/v[0-9]+(/|$)"

  buywhere-bearer-required:
    description: Non-auth operations must require BearerAuth security.
    severity: warn
    given: "$.paths[?(@property != '/auth/register' && @property != '/auth')][get,put,post,delete,patch]"
    then:
      field: security
      function: truthy

  buywhere-product-id-uuid:
    description: Product `id` path parameters must be format uuid.
    severity: warn
    given: "$.paths[*][get,put,post,delete,patch].parameters[?(@.in=='path' && @.name=='id')].schema"
    then:
      field: format
      function: pattern
      functionOptions:
        match: "^uuid$"

  buywhere-limit-bounded:
    description: limit parameters should declare a maximum.
    severity: warn
    given: "$.paths[*][get].parameters[?(@.name=='limit')].schema"
    then:
      field: maximum
      function: truthy

  buywhere-currency-enum:
    description: Currency parameter examples should be in the supported set (SGD, USD, VND, THB, MYR).
    severity: info
    given: "$.paths[*][get].parameters[?(@.name=='currency')].schema.default"
    then:
      function: enumeration
      functionOptions:
        values: ["SGD", "USD", "VND", "THB", "MYR"]

  buywhere-401-response:
    description: Authenticated operations must document a 401 response.
    severity: warn
    given: "$.paths[?(@property != '/auth/register' && @property != '/auth')][get,put,post,delete,patch].responses"
    then:
      field: "401"
      function: truthy

  buywhere-429-on-search:
    description: Search endpoints must document a 429 (rate limit) response.
    severity: warn
    given: "$.paths['/products/search'][get].responses"
    then:
      field: "429"
      function: truthy

  buywhere-info-contact:
    description: API info must include contact email.
    severity: warn
    given: "$.info.contact"
    then:
      field: email
      function: truthy

  buywhere-external-docs:
    description: API should reference MCP / external documentation.
    severity: info
    given: "$"
    then:
      field: externalDocs
      function: truthy