Neoteroi / essentials-openapi

Functions to handle OpenAPI Documentation.
MIT License
21 stars 9 forks source link

Cannot generate Markdown file from valid API definition in YAML #34

Open volphy opened 11 months ago

volphy commented 11 months ago

I cannot generate Markdown file from properly validated API definition file:

$ oad --verbose gen-docs -s docs/api/swagger.yaml -d api.md
[08/07/23 12:35:24] DEBUG    Running in --verbose mode                                                                                                                                                   main.py:27
                    DEBUG    Reading from file docs/api/swagger.yaml                                                                                                                                   source.py:77
Traceback (most recent call last):
  File "<redacted_path>/.venv/bin/oad", line 8, in <module>
    sys.exit(main())
             ^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/click/core.py", line 1157, in __call__
    return self.main(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/click/core.py", line 1078, in main
    rv = self.invoke(ctx)
         ^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/click/core.py", line 1688, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
                           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/click/core.py", line 1434, in invoke
    return ctx.invoke(self.callback, **ctx.params)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/click/core.py", line 783, in invoke
    return __callback(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/openapidocs/commands/docs.py", line 51, in generate_documents_command
    generate_document(source, destination, style)
  File "<redacted_path>/.venv/lib/python3.11/site-packages/openapidocs/mk/generate.py", line 14, in generate_document
    html = handler.write()
           ^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/openapidocs/mk/v3/__init__.py", line 427, in write
    operations=self.get_operations(),
               ^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/openapidocs/mk/v3/__init__.py", line 181, in get_operations
    tag = self.get_tag(path_item) or ""
          ^^^^^^^^^^^^^^^^^^^^^^^
  File "<redacted_path>/.venv/lib/python3.11/site-packages/openapidocs/mk/v3/__init__.py", line 219, in get_tag
    tags = operation.get("tags")
           ^^^^^^^^^^^^^
AttributeError: 'str' object has no attribute 'get'

API definition file swagger.yaml (validated with https://github.com/OpenAPITools/openapi-generator):

openapi: 3.0.3
info:
  title: My API
  description: My API
  version: 1.0.0
servers:
  - url: 'http://localhost:8080/'

paths:
  /client:
    description: Client onboarding operations

    post:
      description: Onboard a new client
      responses:
        201:
          description: Client onboarded successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OnboardedClientDetails'
        400:
          description: Missing attribute in the payload
        403:
          description: Not authorized
        422:
          description: Payload formatted incorrectly
        500:
          description: Internal server error
      requestBody:
        description: Payload to be sent
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/OnboardClientRequest'
      x-amazon-apigateway-integration:
        type: "aws_proxy"
        httpMethod: "POST"
        uri:
          Fn::Sub: "arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/arn:aws:lambda:${AWS::Region}:${AWS::AccountId}:function:integration-layer-client-management/invocations"
        responses:
          default:
            statusCode: "201"
        passthroughBehavior: "when_no_match"
        contentHandling: "CONVERT_TO_TEXT"
      security:
        - Authorize: [ ]

  /client/{clientId}:
    description: Operations on a specific client

    delete:
      description: Delete a given client
      parameters:
        - in: path
          name: clientId
          required: true
          schema:
            type: string
      responses:
        204:
          description: Client deleted successfully
        404:
          description: Not available or user not authorized to see this client
        500:
          description: Internal server error
      x-amazon-apigateway-integration:
        httpMethod: "POST"
        uri:
          Fn::Sub: "arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/arn:aws:lambda:${AWS::Region}:${AWS::AccountId}:function:integration-layer-client-management/invocations"
        responses:
          default:
            statusCode: "204"
        passthroughBehavior: "when_no_match"
        contentHandling: "CONVERT_TO_TEXT"
        type: "aws_proxy"
      security:
        - Authorize: [ ]

  /otp:
    description: OTP API key generation

    parameters:
      - in: query
        name: systemId
        required: true
        schema:
          type: string
        description: Client identifier
        example: '3907f492-3af3-4c0d-a09f-81c6ec0e4b3d'
      - in: query
        name: customerId
        required: true
        schema:
          type: string
        description: Customer Id
        example: '121032'

    post:
      description: Generate OTP API key
      responses:
        200:
          description: OTP API key generated successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/OTPResponse'
        400:
          description: Missing attribute in the payload
        409:
          description: System already registered with different customerId
        500:
          description: Internal server error
      x-amazon-apigateway-integration:
        type: "aws_proxy"
        httpMethod: "POST"
        uri:
          Fn::Sub: "arn:aws:apigateway:${AWS::Region}:lambda:path/2015-03-31/functions/arn:aws:lambda:${AWS::Region}:${AWS::AccountId}:function:otp/invocations"
        responses:
          default:
            statusCode: "200"
        passthroughBehavior: "when_no_match"
        contentHandling: "CONVERT_TO_TEXT"
      security:
        - Authorize-otp: [ ]

components:
  schemas:
    OnboardClientRequest:
      type: object
      required:
        - publicKey
      properties:
        publicKey:
          type: string
          description: Public key in PEM format
          example: '-----BEGIN PUBLIC KEY-----\nPUBLIC\nKEY\nLINES\nSEPARATED\nWITH\n-----END PUBLIC KEY-----'
    OnboardedClientDetails:
      type: object
      properties:
        client_name:
          type: string
          description: Name of the client (equal to systemId with added timestamp)
          example: '3907f492-3af3-4c0d-a09f-81c6ec0e4b3d_1685686753'
        clientId:
          type: string
          description: Unique identifier of the client
          example: '33333333334444444445555555555555444555555'
        x5c:
          type: string
          description: x5c (X.509 certificate chain) indicates a chain of one or more PKIX certificates
          example: "<redacted>"
    OTPResponse:
      type: object
      properties:
        otp:
          type: string
          description: OTP API key
          example: '<redacted>'

In my virtual environment (venv) the following PyPi dependencies are used:

mkdocs-material==9.1.21
mkdocs-mermaid2-plugin==1.0.6
python-markdown-comments==1.1.0
essentials-openapi[full]==1.0.8
neoteroi-mkdocs==1.0.4
pymdown-extensions==10.1

My environment:

Am I missing something?

alexmarco commented 7 months ago

Same problem. I have the suspect that is a problem with list structures in get_tag