{
    "swagger": "2.0",
    "info": {
        "description": "Welcome to the sample Cheese Store API reference. This is a live example of how you can use [Spectacle](http://sourcey.com/spectacle) in conjunction with [Swagger](http://swagger.io) to generate beautiful static documentation for your own APIs.\n\nThe Cheese Store API is organized around the [REST](http://en.wikipedia.org/wiki/Representational_State_Transfer) mothodology, and it uses resource-oriented URLs, and common HTTP response codes to indicate API errors. All requests are authenticated using an `api-key` which can be obtained from your developer dashboard. And now, more cheese...\n\nHard cheese gouda say cheese. Ricotta cauliflower cheese cheesecake bocconcini edam bocconcini fromage feta. Who moved my cheese bocconcini cheese and wine cottage cheese cheese on toast who moved my cheese caerphilly stinking bishop. Bocconcini cheesy feet the big cheese macaroni cheese cheesy feet mascarpone.\n",
        "version": "1.0.0",
        "title": "Cheese Store",
        "termsOfService": "http://cheesy.sourcey.com/terms",
        "contact": {
            "email": "cheesy@sourcey.com"
        },
        "license": {
            "name": "Apache 2.0",
            "url": "http://www.apache.org/licenses/LICENSE-2.0.html"
        }
    },
    "host": "cheesy.sourcey.com",
    "basePath": "/v1",
    "tags": [
        {
            "name": "Cheese",
            "description": "Cheese methods provide access to information and operations relating to the cheese available in the store.",
            "externalDocs": {
                "description": "Find out more",
                "url": "http://cheesy.sourcey.com"
            }
        },
        {
            "name": "Store",
            "description": "Store methods provide access to cheese store orders."
        },
        {
            "name": "Customer",
            "description": "Customer methods contain operations relating to customer accounts.",
            "externalDocs": {
                "description": "Find out more",
                "url": "http://cheesy.sourcey.com"
            }
        }
    ],
    "schemes": [
        "http",
        "https"
    ],
    "paths": {
        "/cheeses": {
            "post": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Add a new cheese to the store",
                "description": "",
                "operationId": "addCheese",
                "consumes": [
                    "application/json",
                    "application/xml"
                ],
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "in": "body",
                        "name": "body",
                        "description": "Cheese object to be added to the store",
                        "required": true,
                        "schema": {
                            "$ref": "#/definitions/Cheese"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Cheese"
                        }
                    },
                    "422": {
                        "description": "Invalid input",
                        "schema": {
                            "$ref": "#/definitions/ValidationError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            },
            "put": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Update an existing cheese",
                "description": "",
                "operationId": "updateCheese",
                "consumes": [
                    "application/json",
                    "application/xml"
                ],
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "in": "body",
                        "name": "body",
                        "description": "Cheese object that needs to be updated",
                        "required": true,
                        "schema": {
                            "$ref": "#/definitions/Cheese"
                        }
                    }
                ],
                "responses": {
                    "404": {
                        "description": "Cheese not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    },
                    "422": {
                        "description": "Validation exception",
                        "schema": {
                            "$ref": "#/definitions/ValidationError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            }
        },
        "/cheeses/findByTags": {
            "get": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Finds cheeses by tags",
                "description": "Muliple tags can be provided with comma separated strings. Use tag1, tag2, tag3 for testing.",
                "operationId": "findCheesesByTags",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "tags",
                        "in": "query",
                        "description": "Tags to filter by",
                        "required": true,
                        "type": "array",
                        "items": {
                            "type": "string"
                        },
                        "collectionFormat": "multi"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "type": "array",
                            "items": {
                                "$ref": "#/definitions/Cheese"
                            }
                        }
                    },
                    "404": {
                        "description": "Invalid tag value",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ],
                "deprecated": true
            }
        },
        "/cheeses/{cheeseId}": {
            "get": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Find cheese by ID",
                "description": "Return a specific cheese by it's ID.",
                "operationId": "getCheeseById",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "cheeseId",
                        "in": "path",
                        "description": "ID of cheese to return",
                        "required": true,
                        "type": "integer",
                        "format": "int64"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Cheese"
                        }
                    },
                    "404": {
                        "description": "Cheese not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                },
                "security": [
                    {
                        "api_key": []
                    }
                ]
            },
            "post": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Update a cheese",
                "description": "Updates a cheese in the Store with form data.",
                "operationId": "updateCheeseWithForm",
                "consumes": [
                    "application/x-www-form-urlencoded"
                ],
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "cheeseId",
                        "in": "path",
                        "description": "ID of the cheese to be updated",
                        "required": true,
                        "type": "integer",
                        "format": "int64"
                    },
                    {
                        "name": "name",
                        "in": "formData",
                        "description": "Updated name of the cheese",
                        "required": false,
                        "type": "string"
                    },
                    {
                        "name": "status",
                        "in": "formData",
                        "description": "Updated status of the cheese",
                        "required": false,
                        "type": "string"
                    }
                ],
                "responses": {
                    "422": {
                        "description": "Cannot update cheese",
                        "schema": {
                            "$ref": "#/definitions/ValidationError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            },
            "delete": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Deletes a cheese",
                "description": "",
                "operationId": "deleteCheese",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "api_key",
                        "in": "header",
                        "required": false,
                        "type": "string"
                    },
                    {
                        "name": "cheeseId",
                        "in": "path",
                        "description": "Cheese ID to delete",
                        "required": true,
                        "type": "integer",
                        "format": "int64"
                    }
                ],
                "responses": {
                    "404": {
                        "description": "Cheese not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            }
        },
        "/cheeses/findByStatus": {
            "get": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Finds cheeses by status",
                "description": "Multiple status values can be provided with comma separated strings.",
                "operationId": "findCheesesByStatus",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "status",
                        "in": "query",
                        "description": "Status values that need to be considered for filter",
                        "required": true,
                        "type": "array",
                        "items": {
                            "type": "string",
                            "enum": [
                                "available",
                                "pending",
                                "sold"
                            ],
                            "default": "available"
                        },
                        "collectionFormat": "multi"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "type": "array",
                            "items": {
                                "$ref": "#/definitions/Cheese"
                            }
                        }
                    },
                    "404": {
                        "description": "Invalid status value",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            }
        },
        "/cheeses/{cheeseId}/uploadImage": {
            "post": {
                "tags": [
                    "Cheese"
                ],
                "summary": "Upload a cheese image",
                "description": "",
                "operationId": "uploadImage",
                "consumes": [
                    "multipart/form-data"
                ],
                "produces": [
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "cheeseId",
                        "in": "path",
                        "description": "ID of cheese to update",
                        "required": true,
                        "type": "integer",
                        "format": "int64"
                    },
                    {
                        "name": "additionalMetadata",
                        "in": "formData",
                        "description": "Additional data to pass to server",
                        "required": false,
                        "type": "string"
                    },
                    {
                        "name": "file",
                        "in": "formData",
                        "description": "Image file to upload",
                        "required": false,
                        "type": "file"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Cheese"
                        }
                    }
                },
                "security": [
                    {
                        "cheesy_auth": [
                            "write:cheeses",
                            "read:cheeses"
                        ]
                    }
                ]
            }
        },
        "/store/inventory": {
            "get": {
                "tags": [
                    "Store"
                ],
                "summary": "Return cheese inventories by available status",
                "description": "Returns a list of available cheeses.",
                "operationId": "getInventory",
                "produces": [
                    "application/json"
                ],
                "parameters": [],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "type": "array",
                            "items": {
                                "$ref": "#/definitions/Cheese"
                            }
                        }
                    }
                },
                "security": [
                    {
                        "api_key": []
                    }
                ]
            }
        },
        "/store/order": {
            "post": {
                "tags": [
                    "Store"
                ],
                "summary": "Place a cheese order",
                "description": "Place an order to purchase cheese from the store.",
                "operationId": "placeOrder",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "in": "body",
                        "name": "body",
                        "description": "Order to place for purchasing the cheese.",
                        "required": true,
                        "schema": {
                            "$ref": "#/definitions/Order"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Order"
                        }
                    },
                    "422": {
                        "description": "Invalid order",
                        "schema": {
                            "$ref": "#/definitions/ValidationError"
                        }
                    }
                }
            }
        },
        "/store/order/{orderId}": {
            "get": {
                "tags": [
                    "Store"
                ],
                "summary": "Find purchase order by ID",
                "description": "For valid response try integer IDs with value >= 1 and <= 10. Other values will generate exceptions.",
                "operationId": "getOrderById",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "orderId",
                        "in": "path",
                        "description": "ID of cheese that needs to be fetched",
                        "required": true,
                        "type": "integer",
                        "maximum": 10,
                        "minimum": 1,
                        "format": "int64"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Order"
                        }
                    },
                    "404": {
                        "description": "Order not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Store"
                ],
                "summary": "Delete purchase order by ID",
                "description": "For valid response try integer IDs with positive integer value. Negative or non-integer values will generate API errors.",
                "operationId": "deleteOrder",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "orderId",
                        "in": "path",
                        "description": "ID of the order that needs to be deleted",
                        "required": true,
                        "type": "integer",
                        "minimum": 1,
                        "format": "int64"
                    }
                ],
                "responses": {
                    "404": {
                        "description": "Order not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                }
            }
        },
        "/customer": {
            "post": {
                "tags": [
                    "Customer"
                ],
                "summary": "Create customer account",
                "description": "This can only be done by the logged in customer.",
                "operationId": "createCustomer",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "in": "body",
                        "name": "body",
                        "description": "Created customer object",
                        "required": true,
                        "schema": {
                            "$ref": "#/definitions/Customer"
                        }
                    }
                ],
                "responses": {
                    "default": {
                        "description": "Successful operation"
                    }
                }
            }
        },
        "/customer/createMultiple": {
            "post": {
                "tags": [
                    "Customer"
                ],
                "summary": "Create multiple customers",
                "description": "Create a list of customers from the given input array.",
                "operationId": "createMultipleCustomers",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "in": "body",
                        "name": "body",
                        "description": "List of created customer objects",
                        "required": true,
                        "schema": {
                            "type": "array",
                            "items": {
                                "$ref": "#/definitions/Customer"
                            }
                        }
                    }
                ],
                "responses": {
                    "default": {
                        "description": "Successful operation"
                    }
                }
            }
        },
        "/customer/login": {
            "post": {
                "tags": [
                    "Customer"
                ],
                "summary": "Customer login",
                "description": "Log a customer into the system and create a new user session.",
                "operationId": "loginCustomer",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "username",
                        "in": "query",
                        "description": "The username for login",
                        "required": true,
                        "type": "string"
                    },
                    {
                        "name": "password",
                        "in": "query",
                        "description": "The password for login in clear text",
                        "required": true,
                        "type": "string"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "type": "string"
                        },
                        "headers": {
                            "X-Rate-Limit": {
                                "type": "integer",
                                "format": "int32",
                                "description": "Calls per hour allowed by the customer"
                            },
                            "X-Expires-After": {
                                "type": "string",
                                "format": "date-time",
                                "description": "Date in UTC when token expires"
                            }
                        }
                    },
                    "422": {
                        "description": "Invalid username/password supplied",
                        "schema": {
                            "$ref": "#/definitions/ValidationError"
                        }
                    }
                }
            }
        },
        "/customer/logout": {
            "get": {
                "tags": [
                    "Customer"
                ],
                "summary": "Customer logout",
                "description": "Log the currently the authenticated customer out of the system and end the user session.",
                "operationId": "logoutCustomer",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [],
                "responses": {
                    "default": {
                        "description": "Successful operation"
                    }
                }
            }
        },
        "/customer/{username}": {
            "get": {
                "tags": [
                    "Customer"
                ],
                "summary": "Get customer by username",
                "description": "Get customer by their customer username.",
                "operationId": "getCustomerByName",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "username",
                        "in": "path",
                        "description": "The username of the customer to be fetched.",
                        "required": true,
                        "type": "string"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Successful operation",
                        "schema": {
                            "$ref": "#/definitions/Customer"
                        }
                    },
                    "404": {
                        "description": "Customer not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Customer"
                ],
                "summary": "Update customer",
                "description": "This can only be done by the logged in customer.",
                "operationId": "updateCustomer",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "username",
                        "in": "path",
                        "description": "Username of the customer to update.",
                        "required": true,
                        "type": "string"
                    },
                    {
                        "in": "body",
                        "name": "body",
                        "description": "Customer object to be updated.",
                        "required": true,
                        "schema": {
                            "$ref": "#/definitions/Customer"
                        }
                    }
                ],
                "responses": {
                    "400": {
                        "description": "Invalid customer supplied"
                    },
                    "404": {
                        "description": "Customer not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Customer"
                ],
                "summary": "Delete customer",
                "description": "Datate a customer by their username.",
                "operationId": "deleteCustomer",
                "produces": [
                    "application/xml",
                    "application/json"
                ],
                "parameters": [
                    {
                        "name": "username",
                        "in": "path",
                        "description": "Username of the customer to delete.",
                        "required": true,
                        "type": "string"
                    }
                ],
                "responses": {
                    "400": {
                        "description": "Invalid username supplied"
                    },
                    "404": {
                        "description": "Customer not found",
                        "schema": {
                            "$ref": "#/definitions/NotFoundError"
                        }
                    }
                }
            }
        }
    },
    "securityDefinitions": {
        "cheesy_auth": {
            "type": "oauth2",
            "authorizationUrl": "http://cheesy.sourcey.com/api/oauth/dialog",
            "flow": "implicit",
            "scopes": {
                "write:cheeses": "Modify cheeses in your account",
                "read:cheeses": "Read your cheeses"
            }
        },
        "api_key": {
            "type": "apiKey",
            "name": "api_key",
            "in": "header"
        }
    },
    "definitions": {
        "Order": {
            "type": "object",
            "properties": {
                "id": {
                    "type": "integer",
                    "format": "int64"
                },
                "cheeseId": {
                    "type": "integer",
                    "format": "int64"
                },
                "quantity": {
                    "type": "integer",
                    "format": "int32"
                },
                "shipDate": {
                    "type": "string",
                    "format": "date-time"
                },
                "status": {
                    "type": "string",
                    "description": "Order Status",
                    "enum": [
                        "placed",
                        "approved",
                        "delivered"
                    ]
                },
                "complete": {
                    "type": "boolean",
                    "default": false
                }
            },
            "example": {
                "cheeseId": "1",
                "complete": "true",
                "id": "1",
                "quantity": "66",
                "shipDate": "04-10-2017 00:09:21 UTC",
                "status": "available"
            },
            "xml": {
                "name": "Order"
            }
        },
        "Category": {
            "type": "object",
            "properties": {
                "id": {
                    "type": "integer",
                    "format": "int64",
                    "example": 1
                },
                "name": {
                    "type": "string",
                    "example": "Italian Cheese"
                }
            },
            "xml": {
                "name": "Category"
            }
        },
        "Customer": {
            "type": "object",
            "properties": {
                "id": {
                    "type": "integer",
                    "format": "int64",
                    "example": 1
                },
                "username": {
                    "type": "string",
                    "example": "gordo"
                },
                "firstName": {
                    "type": "string",
                    "description": "Customer first name",
                    "example": "Alotta"
                },
                "lastName": {
                    "type": "string",
                    "description": "Customer last name",
                    "example": "Cheese"
                },
                "email": {
                    "type": "string",
                    "example": "love@cheese.com"
                },
                "password": {
                    "type": "string",
                    "example": "secret"
                },
                "phone": {
                    "type": "string",
                    "example": "+3344556677"
                },
                "customerStatus": {
                    "type": "string",
                    "description": "Customer status (the heavier the better)",
                    "enum": [
                        "skinny",
                        "average",
                        "fat",
                        "obese"
                    ],
                    "example": "obese"
                }
            },
            "xml": {
                "name": "Customer"
            }
        },
        "Tag": {
            "type": "object",
            "properties": {
                "id": {
                    "type": "integer",
                    "format": "int64",
                    "example": 1
                },
                "name": {
                    "type": "string",
                    "example": "Manchego"
                }
            },
            "xml": {
                "name": "Tag"
            }
        },
        "Error": {
            "type": "object",
            "properties": {
                "code": {
                    "type": "integer",
                    "format": "int32"
                },
                "type": {
                    "type": "string",
                    "example": "No cheese found"
                },
                "message": {
                    "type": "string",
                    "example": "No cheese for you!"
                }
            }
        },
        "ValidationError": {
            "type": "object",
            "properties": {
                "code": {
                    "type": "integer",
                    "format": "int32",
                    "example": 422
                },
                "type": {
                    "type": "string",
                    "example": "Validation error"
                },
                "message": {
                    "type": "string",
                    "example": "Your cheese is not mouldy enough"
                }
            }
        },
        "NotFoundError": {
            "type": "object",
            "properties": {
                "code": {
                    "type": "integer",
                    "format": "int32",
                    "example": 404
                },
                "type": {
                    "type": "string",
                    "example": "Not found"
                },
                "message": {
                    "type": "string",
                    "example": "Your cheese has already been eaten"
                }
            }
        },
        "Cheese": {
            "type": "object",
            "required": [
                "name",
                "photoUrls"
            ],
            "properties": {
                "id": {
                    "type": "integer",
                    "format": "int64",
                    "example": 1
                },
                "category": {
                    "$ref": "#/definitions/Category"
                },
                "name": {
                    "type": "string",
                    "example": "Gorgonzola"
                },
                "photoUrls": {
                    "type": "array",
                    "xml": {
                        "name": "photoUrl",
                        "wrapped": true
                    },
                    "items": {
                        "type": "string"
                    },
                    "example": [ 
                        "https://wannabechef.com/gorgonzola.jpg" 
                    ]
                },
                "tags": {
                    "type": "array",
                    "xml": {
                        "name": "tag",
                        "wrapped": true
                    },
                    "items": {
                        "$ref": "#/definitions/Tag"
                    }
                },
                "status": {
                    "type": "string",
                    "description": "Cheese status in the store",
                    "enum": [
                        "available",
                        "pending",
                        "sold"
                    ],
                    "example": "available"
                }
            },
            "xml": {
                "name": "Cheese"
            }
        }
    },
    "externalDocs": {
        "description": "Find out more about Swagger",
        "url": "http://swagger.io"
    }
}
