OpenAPI2Apigee - 0.2.1 Version - Securing APIs using Swagger Spec & Apigee-127 Extensions

Hello Everyone,

In previous article, you saw how Apigee-127 extensions can be used to generate Apigee Policies & attach same to different resources / conditions flows in Apigee Edge automatically. We have updated the policies list in this release.

Swagger2Api version 0.2.1 version now supports Response Cache Policy, Verify API Key Policy, OAuth Verify Access Token Policy from swagger 2.0 spec using Apigee-127 extensions. In this article let's see how to convert swagger 2.0 spec to above mentioned policies.

Take a look at below swagger 2.0 spec that gives an idea how to use same in your swagger specification...

swagger: "2.0"
info:
  version: 1.0.0
  title: Swagger Petstore
  license:
    name: MIT
host: petstore.swagger.io
basePath: /v1
schemes:
  - http
consumes:
  - application/json
produces:
  - application/json
x-a127-services:
  quotaAnil:
    provider: volos-quota-memory
    options:
      timeUnit: day
      interval: 2
      allow: 2500
  spikearrest:
    provider: "volos-spikearrest-memory"
    options:
      timeUnit: "minute"
      bufferSize: 10
      allow: 10
  cache:
    provider: volos-cache-memory
    options:
      name: hello-cache
      ttl: 60000
  apiKeyHeader:
    provider: volos-oauth-apigee
    options:
      key: sss
      uri: ssss
  oauth2:
    provider: volos-oauth-apigee
    options:
      tokenLifetime: 300000
      key: apigeeProxyKey
      uri: apigeeProxyUri
      validGrantTypes:
        - client_credentials
        - authorization_code
        - implicit_grant
        - password
      tokenPaths:  # These will be added to your paths section for you
        authorize: /authorize
        token: /accesstoken
        invalidate: /invalidate
        refresh: /refresh
paths:
  /pets:
    get:
      x-a127-apply:
        quotaAnil:
          pipe: request
          endPoint: proxy
        spikearrest:
          pipe: request
          endPoint: proxy
        cache:
          pipe: request,response
          endPoint: proxy
      summary: List all pets
      operationId: listPets
      tags:
        - pets
      parameters:
        - name: limit
          in: query
          description: How many items to return at one time (max 100)
          required: false
          type: integer
          format: int32
      responses:
        200:
          description: An paged array of pets
          headers:
            x-next:
              type: string
              description: A link to the next page of responses
          schema:
            $ref: Pets
        default:
          description: unexpected error
          schema:
            $ref: Error
    post:
      summary: Create a pet
      operationId: createPets
      tags:
        - pets
      responses:
        201:
          description: Null response
        default:
          description: unexpected error
          schema:
            $ref: Error
  /pets/{petId}:
    get:
      summary: Info for a specific pet
      operationId: showPetById
      security:
        - apiKeyHeader: []
        - oauth2: []
      tags:
        - pets
      parameters:
        - name: petId
          in: path
          required: true
          description: The id of the pet to retrieve
          type: string
      responses:
        200:
          description: Expected response to a valid request
          schema:
            $ref: Pets
        default:
          description: unexpected error
          schema:
            $ref: Error
definitions:
  Pet:
    required:
      - id
      - name
    properties:
      id:
        type: integer
        format: int64
      name:
        type: string
      tag:
        type: string
  Pets:
    type: array
    items:
      $ref: Pet
  Error:
    required:
      - code
      - message
    properties:
      code:
        type: integer
        format: int32
      message:
        type: string


OpenAPI2Apigee 0.2.1 Version Supported Apigee-127 Extensions :

At present , Swagger2Api 0.2.1 version supports following Apigee-127 policies,

  • Quota
  • Spike Arrest
  • Cache - Added in 0.2.1
  • verifyApiKey - Added in 0.2.1
  • OAuth Verify Access Token - Added in 0.2.1

Let's implement them and see how they work,

Swagger2Api - Cache - Policy :

V 0.2.0 partially supported cache policy where policy was generated but not attached to conditional flows (resources). V 0.2.1 supports attaching policy to conditions flows nothing but API Proxy resources. See swagger 2.0 code below that explains attaching response cache policy to conditional flow.

x-a127-apply:
  cache:
    pipe: request,response
    endPoint: proxy

You might have noticed that pipe option take both request and response. Because, Response Cache Policy should be attached to both request & response pipelines.

Swagger2Api - Verify API Key - Policy :

Now, You can secure your proxies by defining them using Swagger 2.0 & Apigee-127 extensions. See implementation below for verifyApiKey policy.

x-a127-services:
  apiKeyHeader:
    provider: volos-oauth-apigee
    options:
      key: XXXXXXX
      uri: XXXXXXX
x-a127-services:
  apiKeyQuery:
    provider: volos-oauth-apigee
    options:
      key: XXXXXXX
      uri: XXXXXXX

You can apply same to resources using security option under your path,

/pets/{petId}:
  get:
    summary: Info for a specific pet
    operationId: showPetById
    security:
      - apiKeyHeader: []

Swagger2Api - OAuth 2.0 - Verify Access Token - Policy :

You can also secure your API using most secure mechanism OAuth 2.0 via access tokens. Now, You can verify access token just by defining it in swagger spec and using swagger2api tool. This tool doesn't cover generating OAuth 2.0 proxies in Apigee but what it does is generates and attaches the oAuth2 verify access token policy to your resources.

oauth2:
  provider: volos-oauth-apigee
  options:
    tokenLifetime: 300000
    key: apigeeProxyKey
    uri: apigeeProxyUri
    validGrantTypes:
      - client_credentials
      - authorization_code
      - implicit_grant
      - password
    tokenPaths:  # These will be added to your paths section for you
      authorize: /authorize
      token: /accesstoken
      invalidate: /invalidate
      refresh: /refresh

You can apply policy to resources using security option under your path,

/pets/{petId}:
  get:
    summary: Info for a specific pet
    operationId: showPetById
    security:
      - oauth2: []

See an attached screenshot of API Proxy generated in Apigee Edge with above mentioned policies from swagger 2.0 spec.

1108-screen-shot-2015-09-08-at-60528-pm.png

Please feel free to post your questions & suggestions here in Apigee Community. Looking forward to great suggestions & feedback. More exciting tools are coming up, keep watching this space.

Cheers,

Anil Sagar

Comments
Not applicable

Thanks for this great tool! I'm running into an issue, and I'm not sure if it's my own misunderstanding, a shortcoming in Swagger, or something that could be fixed in swagger2api.

When I deploy with swagger2api, the proxy name I choose also becomes the proxy endpoint basepath (which is not what I want). I have to go into the proxy endpoint and change the basepath from /<proxyname> to /v1.

Is there any way to set the proxy's basePath in Swagger, rather than having to edit it manually? If not, could it be added to swagger2api as an option?

anilsr
Staff

@Lee Grey,

Thank you for valuable feedback & using the tool. Yes, Agree. I have come across this issue and i believe it's not a great design. I can think of below pattern for now, Let us know what do you think..

/V{VERSIONNUMBER}/{APIPROXYNAME} 

Reason we have chosen proxy name as basePath is basically assume you are developing multiple apiProxies in Apigee Edge then same basepath will result into an error while deploying another Api Proxy with same basepath. Swagger Spec 2.0 defines base path spec but it is used to connect to target.

Keep us posted with your suggestions & comments.

Cheers,

Anil Sagar

Not applicable

@Anil Sagar, I appreciate your response. I spent some time grappling with this yesterday and am starting to believe that a facade such as Edge essentially needs two Swagger descriptions: one to describe the proxy endpoint, and another to describe the target endpoint. It is the mixing of the two into a single Swagger that is causing confusion.

Since the goal of Swagger2api is to create a proxy, it seems to me that the host and basePath should refer to the proxy being created, not to the target. Perhaps you could use a Swagger extension to set the target URL?

That's just today's opinion, and it's almost certain to change. 🙂 But what do you think?

Thanks,

Lee

anilsr
Staff

@Lee Grey , Agree. I think we should add a custom swagger extension to set missing pieces.

anilsr
Staff

@Lee Grey , Created a github issue same here to track it.. In next iteration i will add an option to command line to specify proxy base path.. Feel free to submit Pull Request in github if you get a chance. Thank you sharing your valuable feedback 🙂

Not applicable

I see that the word "here" is a link, but clicking it does nothing. Are you able to fix that?

anilsr
Staff

@Lee Grey , Fixed the link..

Version history
Last update:
‎09-08-2015 05:39 AM
Updated by: