swagger-editor icon indicating copy to clipboard operation
swagger-editor copied to clipboard

CORS policy issue

Open ddevashish opened this issue 3 years ago • 3 comments

Q&A

  • OS: Windows 10 Pro
  • Browser: chrome
  • Version: 89.0.4389.90 (Official Build) (64-bit)
  • Method of installation: npm
  • Swagger-Editor version: v3.15.10
  • Swagger/OpenAPI version: 3.45.1

Content & configuration

Loaded OpenAPI Yml from https://raw.githubusercontent.com/OAI/OpenAPI-Specification/master/examples/v2.0/yaml/uber.yaml

Example Swagger/OpenAPI definition:

# this is an example of the Uber API
# as a demonstration of an API spec in YAML
swagger: "2.0"
info:
  title: Uber API
  description: Move your app forward with the Uber API
  version: "1.0.0"
# the domain of the service
host: api.uber.com
# array of all schemes that your API supports
schemes:
  - https
# will be prefixed to all paths
basePath: /v1
securityDefinitions:
  apikey:
    type: apiKey
    name: server_token
    in: query
produces:
  - application/json
paths:
  /products:
    get:
      summary: Product Types
      description: The Products endpoint returns information about the Uber products offered at a given location. The response includes the display name and other details about each product, and lists the products in the proper display order.
      parameters:
        - name: latitude
          in: query
          description: Latitude component of location.
          required: true
          type: number
          format: double
        - name: longitude
          in: query
          description: Longitude component of location.
          required: true
          type: number
          format: double
      security: 
        - apikey: []
      tags: 
        - Products
      responses:  
        "200":
          description: An array of products
          schema:
            type: array
            items:
              $ref: '#/definitions/Product'
        default:
          description: Unexpected error
          schema:
            $ref: '#/definitions/Error'
  /estimates/price:
    get:
      summary: Price Estimates
      description: The Price Estimates endpoint returns an estimated price range for each product offered at a given location. The price estimate is provided as a formatted string with the full price range and the localized currency symbol.<br><br>The response also includes low and high estimates, and the [ISO 4217](http://en.wikipedia.org/wiki/ISO_4217) currency code for situations requiring currency conversion. When surge is active for a particular product, its surge_multiplier will be greater than 1, but the price estimate already factors in this multiplier.
      parameters:
        - name: start_latitude
          in: query
          description: Latitude component of start location.
          required: true
          type: number
          format: double
        - name: start_longitude
          in: query
          description: Longitude component of start location.
          required: true
          type: number
          format: double
        - name: end_latitude
          in: query
          description: Latitude component of end location.
          required: true
          type: number
          format: double
        - name: end_longitude
          in: query
          description: Longitude component of end location.
          required: true
          type: number
          format: double
      tags: 
        - Estimates
      responses:  
        "200":
          description: An array of price estimates by product
          schema:
            type: array
            items:
              $ref: '#/definitions/PriceEstimate'
        default:
          description: Unexpected error
          schema:
            $ref: '#/definitions/Error'
  /estimates/time:
    get:
      summary: Time Estimates
      description: The Time Estimates endpoint returns ETAs for all products offered at a given location, with the responses expressed as integers in seconds. We recommend that this endpoint be called every minute to provide the most accurate, up-to-date ETAs.
      parameters:
        - name: start_latitude
          in: query
          description: Latitude component of start location.
          required: true
          type: number
          format: double
        - name: start_longitude
          in: query
          description: Longitude component of start location.
          required: true
          type: number
          format: double
        - name: customer_uuid
          in: query
          type: string
          format: uuid
          description: Unique customer identifier to be used for experience customization.
        - name: product_id
          in: query
          type: string
          description: Unique identifier representing a specific product for a given latitude & longitude.
      tags: 
        - Estimates
      responses:  
        "200":
          description: An array of products
          schema:
            type: array
            items:
              $ref: '#/definitions/Product'
        default:
          description: Unexpected error
          schema:
            $ref: '#/definitions/Error'
  /me:
    get:
      summary: User Profile
      description: The User Profile endpoint returns information about the Uber user that has authorized with the application.
      tags: 
        - User
      responses:
        "200":
          description: Profile information for a user
          schema:
            $ref: '#/definitions/Profile'
        default:
          description: Unexpected error
          schema:
            $ref: '#/definitions/Error'
  /history:
    get:
      summary: User Activity
      description: The User Activity endpoint returns data about a user's lifetime activity with Uber. The response will include pickup locations and times, dropoff locations and times, the distance of past requests, and information about which products were requested.<br><br>The history array in the response will have a maximum length based on the limit parameter. The response value count may exceed limit, therefore subsequent API requests may be necessary.
      parameters:
        - name: offset
          in: query
          type: integer
          format: int32
          description: Offset the list of returned results by this amount. Default is zero.
        - name: limit
          in: query
          type: integer
          format: int32 
          description: Number of items to retrieve. Default is 5, maximum is 100.
      tags: 
        - User
      responses:
        "200":
          description: History information for the given user
          schema:
            $ref: '#/definitions/Activities'
        default:
          description: Unexpected error
          schema:
            $ref: '#/definitions/Error'
definitions:
  Product:
    properties:
      product_id:
        type: string
        description: Unique identifier representing a specific product for a given latitude & longitude. For example, uberX in San Francisco will have a different product_id than uberX in Los Angeles.
      description:
        type: string
        description: Description of product.
      display_name:
        type: string
        description: Display name of product.
      capacity:
        type: integer
        description: Capacity of product. For example, 4 people.
      image:
        type: string
        description: Image URL representing the product.
  ProductList:
    properties:
      products:
        description: Contains the list of products
        type: array
        items: 
          $ref: "#/definitions/Product"
  PriceEstimate:
    properties:
      product_id:
        type: string
        description: Unique identifier representing a specific product for a given latitude & longitude. For example, uberX in San Francisco will have a different product_id than uberX in Los Angeles
      currency_code:
        type: string
        description: "[ISO 4217](http://en.wikipedia.org/wiki/ISO_4217) currency code."
      display_name:
        type: string
        description: Display name of product.
      estimate: 
        type: string
        description: Formatted string of estimate in local currency of the start location. Estimate could be a range, a single number (flat rate) or "Metered" for TAXI.
      low_estimate:
        type: number
        description: Lower bound of the estimated price.
      high_estimate:
        type: number
        description: Upper bound of the estimated price.
      surge_multiplier:
        type: number
        description: Expected surge multiplier. Surge is active if surge_multiplier is greater than 1. Price estimate already factors in the surge multiplier.
  Profile:
    properties:
      first_name:
        type: string
        description: First name of the Uber user.
      last_name:
        type: string
        description: Last name of the Uber user.
      email:
        type: string
        description: Email address of the Uber user
      picture:
        type: string
        description: Image URL of the Uber user.
      promo_code:
        type: string
        description: Promo code of the Uber user.   
  Activity:
    properties:
      uuid:
        type: string
        description: Unique identifier for the activity
  Activities:
    properties:
      offset:
        type: integer
        format: int32
        description: Position in pagination.
      limit:
        type: integer
        format: int32
        description: Number of items to retrieve (100 max).
      count:
        type: integer
        format: int32
        description: Total number of items available.
      history:
        type: array
        items:
          $ref: '#/definitions/Activity'
  Error:
    properties:
      code:
        type: integer
        format: int32
      message:
        type: string
      fields:
        type: string

Swagger-Editor configuration options:

  • No specific configuration.
  • Used open Swagger Editor
  • No Query String Passed

Describe the bug you're encountering

Access to fetch at 'https://api.uber.com/v1/me' from origin 'https://editor.swagger.io' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.

To reproduce...

Steps to reproduce the behavior:

  1. Go to 'https://editor.swagger.io/'
  2. Load above YAML in the editor
  3. Click tab 'User'
  4. Click on tab 'Get /me User Profile'
  5. Click on button 'Try it out'
  6. Click on button 'Execute'
  7. See error

Error Details

Failed to fetch. Possible Reasons:

  • CORS
  • Network Failure
  • URL scheme must be "http" or "https" for CORS request.

Expected behavior

Application should display the response in json format like below

{
  "first_name": "string",
  "last_name": "string",
  "email": "string",
  "picture": "string",
  "promo_code": "string"
}

Screenshots

image

Additional context or thoughts

CORS issue is occuring for almost every openAPI. Tested for few openAPI from here https://github.com/OAI/OpenAPI-Specification/tree/master/examples

ddevashish avatar Mar 25 '21 12:03 ddevashish

Hey there, I am facing a similar issue with the same error mentioned above. Except that my API key is in the header.

I debugged for a while and found that when we set the api key or value for our api key, swagger replaces all existing headers before request and appends the api key. When I remove the value of the api key, the request goes through - hence I am now attaching my api key via a chrome extension "mod header" because swagger is behaving weirdly here.

Headers with api key entered in swagger:

accept: application/json
Referer: http://localhost:8081/
sec-ch-ua: ".Not/A)Brand";v="99", "Google Chrome";v="103", "Chromium";v="103"
sec-ch-ua-mobile: ?0
sec-ch-ua-platform: "macOS"
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36
my-api-key: <secret>

Headers without api key entered in swagger and using mod-header chrome extension only for adding api key:

:authority: <secret>
:method: GET
:path: /api/<secret>
:scheme: https
accept: application/json
accept-encoding: gzip, deflate, br
accept-language: en-US,en;q=0.9
cache-control: no-cache
origin: http://localhost:8081
pragma: no-cache
referer: http://localhost:8081/
sec-ch-ua: ".Not/A)Brand";v="99", "Google Chrome";v="103", "Chromium";v="103"
sec-ch-ua-mobile: ?0
sec-ch-ua-platform: "macOS"
sec-fetch-dest: empty
sec-fetch-mode: cors
sec-fetch-site: cross-site
user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36
my-api-key: <secret>

FYI I've replaced confidential information with <secret> for security purposes.

I request someone from swagger to please fix this issue. 🙏 🙏

valentinoPereira avatar Aug 01 '22 10:08 valentinoPereira

Hi, was there any update to this?

I feel like I might be setting up my header data or securitySchema incorrectly, however, would still like to double check. Did you guys have any success later? Did installing their plugin make any difference (swagger inspector extension)?

makgah avatar Jun 05 '23 17:06 makgah

you should enable CORS either in your server side application or HTTP Proxys like nginx, caddy...

swagger makes a request with these headers and it should be responded properly otherwise you get CORS issue.

sample request while running swagger from vscode

"origin": "vscode-webview://***************vjiod**************jc8g********************",
"sec-fetch-site": "cross-site",
"sec-fetch-mode": "cors",

possible OK reply from the server app

sending response: Response {
    status: 200,
    version: HTTP/1.1,
    headers: {
        "content-type": "application/json",
        "server": "Rocket",
        "permissions-policy": "interest-cohort=()",
        "x-content-type-options": "nosniff",
        "x-frame-options": "SAMEORIGIN",
        "access-control-allow-origin": "vscode-webview://***************vjiod**************jc8g********************",
        "vary": "Origin",
        "content-length": "136",
    },

NIDRIVEProjects avatar Dec 22 '23 12:12 NIDRIVEProjects