microsoft / kiota

OpenAPI based HTTP Client code generator
https://aka.ms/kiota/docs
MIT License
3.01k stars 210 forks source link

HTTP Snippet Format #5543

Open sebastienlevert opened 1 month ago

sebastienlevert commented 1 month ago

Based on this OpenAPI : https://github.com/sebastienlevert/jsonplaceholder-api/blob/main/openapi.yaml

(I made edits to the operation to illustrate some use cases.)

And this operation:

/posts:
    get:
      description: Get posts
      operationId: list-posts
      parameters:
      - name: userId
        in: query
        description: Filter results by user ID
        required: true
        style: form
        schema:
          type: integer
          maxItems: 1
      - name: title
        in: query
        description: Filter results by title
        required: false
        style: form
        schema:
          type: string
          maxItems: 1
      responses:
        '200':
          description: OK
          content:
            application/json:
              schema:
                type: array
                items:
                  $ref: '#/components/schemas/post'

    post:
      description: 'Create post'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/post'
      responses:
        '201':
          description: Created
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/post'

components:
  schemas:
    post:
      type: object
      properties:
        userId:
          type: integer
        id:
          type: integer
        title:
          type: string
        body:
          type: string
  parameters:
    post-id:
      name: post-id
      in: path
      description: 'key: id of post'
      required: true
      style: simple
      schema:
        type: integer

The format should be the following:

# Base URL
@url = https://jsonplaceholder.typicode.com

### GET /posts?userId={userId}{&title}
# Filter results by user ID
@userId = 1

# Get posts
GET {{url}}/posts?userId={{userId}}

### POST /posts
# Create posts
POST {{url}}/posts
Content-Type: application/json

{
  "title": "",
  "body": "",
  "userId": 1
}
maisarissi commented 1 month ago

Should we consider some sort of auth as part of the snippet?

sebastienlevert commented 1 month ago

@maisarissi we could, based on the auth schemes and have the right Auth headers. What would be your suggestion on automating this?

maisarissi commented 1 month ago

I would suggest:

1 - use the settings.json file. So instead of the bellow code in the .http snippet file:

# Base URL
@url = https://jsonplaceholder.typicode.com

I would suggest the .http snippet file be:

### GET /posts?userId={userId}{&title}
# Filter results by user ID
@userId = 1

# Get posts
GET {{HostAddress}}/posts?userId={{userId}}

### POST /posts
# Create posts
POST {{HostAddress}}/posts
Content-Type: application/json

{
  "title": "",
  "body": "",
  "userId": 1
}

and add a rest-client.environmentVariables entry in the settings.json file with a remote or prod node:

{
    "rest-client.environmentVariables": {
        "$shared": { },
        "remote": {
            "hostAddress": "https://jsonplaceholder.typicode.com",
            "basicAuth": "Basic dXNlcm5hbWU6c2VjcmV0",
            "bearer": " Bearer AAAACSSXSXSV....SDSDSD"
        }
    }
}

This would allow folks to easily add as many environments as needed (like dev) later and then change easily the env that is been called, like the screenshot below: {0B0917F0-E7EC-4E8D-B37B-DFE72B84007E}

If we go that way, we need to remove the @url from the .http file, because variable definitions in .http files override environment definitions.

2 - For the auth, based in auth scheme described in the OpenAPI description, I believe we should create/add the environment variables in the settings.json. So for example, if the /posts requires Basic auth, the .http file should be:

POST {{HostAddress}}/posts
Content-Type: application/json
Authorization: {{basicAuth}}

{
  "title": "",
  "body": "",
  "userId": 1
}

3 - I would say we should support "basicAuth", "bearer" and "apiKey". For Oauth2, we might want to also use "bearer" where the user would need to use a browser to authenticate and copy the token. Another possibility would be to have something like this blog where we use info from the settings.json

@name oauth2
POST {{accessTokenUri}}?grant_type=client_credentials&client_id={{clientId}}&client_secret={{clientSecret}}
Content-Type: application/x-www-form-urlencoded

###
GET https://{hostAddress}/api/endpoint HTTP/1.1
Authorization: Bearer {{oauth2.response.body.access_token}}