> ## Documentation Index
> Fetch the complete documentation index at: https://docs.str.keroshospitality.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Login and get access token

> Authenticate with username/password and receive JWT tokens



## OpenAPI

````yaml /openapi.json post /auth/token
openapi: 3.0.3
info:
  title: STR Uploader API
  description: >
    The Taxis uploader API provides endpoints for uploading reservations to
    Government's Short Term Rental Registry and filing the Climate Crisis
    Resilience Fee Statement (TAKK).


    ## Overview


    This API allows you to:

    * Upload short-term rental records

    * Query sn str task's upload status

    * Uploading Climate Crisis Resilience Fee Statement

    * Query a TAKK statement's upload task status



    ## Authentication


    All API endpoints require JWT Bearer token authentication. The applicable
    roles for this API are: `str-uploader`, `takk-uploader`, `client-manager`.


    ### How to get a JWT token:

    1. Use your client ID and client secret obtained from your administrator

    2. Send a POST request to `/auth/token` with your credentials

    3. Use the returned `access_token` in the Authorization header: `Bearer
    <access_token>`


    ### Example with curl:

    ```bash

    curl -X POST {server}/api/v1/auth/token \

    -H "Content-Type: application/json" \

    -d '{

    "clientId": "your-client-id",

    "secret": "your-client-secret"

    }'

    ```


    ### Using the token:

    ```bash

    curl -X GET {server}/api/v1/clients \

    -H "Authorization: Bearer <your-access-token>"

    ```


    ### Token refresh:

    When your access token expires, use the refresh token:

    ```bash

    curl -X POST {server}/api/v1/auth/refresh \

    -H "Content-Type: application/json" \

    -d '{

    "refreshToken": "your-refresh-token-here"

    }'

    ```


    **Note:** Replace `{server}` with your actual server URL (e.g.,
    `https://api.yourdomain.com` or `http://localhost:8080` for local
    development).


    ## Response Formats


    All responses are in JSON format. Successful responses use HTTP 2xx status
    codes:

    * 200: Successful operation with response body

    * 201: Resource created

    * 202: Request accepted for processing

    * 204: Successful operation with no response body


    ## Error Responses


    Unsuccessful requests return a response with an error-indicating status
    code, and a json object with a 'errorMessage' and requestId field:

    ```json

    {

    "errorMessage": "Not found"

    "requestId": "a1b2c3d4-e5f6-7890-a1b2-c3d4e5f67890"

    }

    ```


    ## Apartment Owner Credentials Security Documentation


    ### Overview


    The Taxis Uploader service now implements a secure approach for managing
    Taxis user credentials (apartment owners).

    This document outlines our approach to securely storing, encrypting, and
    managing these credentials with security best practices.


    ### Credential Storage and Management

    Storage Model


    Taxis user credentials are stored in the database using the apartment_owners
    table

    Credentials are associated with a unique taxis_username

    Passwords are never stored in plain text in the database

    Clients reference Taxis users by username only, without needing to transmit
    passwords with each request


    ### Password Encryption


    All Taxis passwords are encrypted using AES-256-GCM symmetric encryption
    before storage

    Each password is encrypted with:


    A secure 256-bit encryption key stored separately from the database

    A unique random nonce (number used once) that is stored with the encrypted
    data


    The encryption process ensures:


    * The same password will encrypt to different ciphertext values each time

    * Patterns in the original data are obscured in the encrypted output

    * Decryption is only possible with access to both the encryption key and the
    ciphertext


    ### Security Mechanisms


    #### Key Management


    The 32-byte (256-bit) encryption key is stored in environment variables /
    KMS system, not in the codebase or database

    Different keys are used for each environment (development, staging,
    production)

    Access to the encryption key is strictly limited


    ### Nonce Handling


    A unique nonce is generated for each encryption operation

    The nonce is prepended to the ciphertext for decryption

    This prevents identical passwords from producing identical encrypted values


    ### API Security


    - Passwords are never returned in API responses

    - Response models explicitly omit password fields

    - HTTPS is enforced for all API communications

    - Proper authentication and authorization controls restrict access to
    credential management


    #### Benefits of This Approach


    Reduced Transmission Risk: Credentials are only transmitted when initially
    set up or updated, not with every reservation upload request

    Defense in Depth: Even if the database is compromised, the attacker would
    still need the encryption key to access passwords

    Improved User Experience: Clients don't need to store and transmit sensitive
    Taxis credentials with each request

    Better Auditability: Credential usage can be tracked and monitored centrally


    ### Technical Implementation Details


    Encryption: AES-256-GCM (Galois/Counter Mode)

    Key: 256-bit random key

    Nonce: 12 bytes of random data generated for each encryption operation


    ### Operational Considerations


    Passwords are only decrypted in memory when needed for Taxis operations

    Encryption keys are rotated periodically (recommended: every 90 days)

    During key rotation, all passwords are re-encrypted with the new key

    Monitoring should be in place to detect unusual access patterns to apartment
    owner records


    ### DefaultWebUser Developer Guidelines


    When using the Taxis Uploader service:


    - Store only the taxis_username in your application

    - Reference this username when submitting upload tasks

    - Do not attempt to retrieve or cache the password



    When creating or updating apartment owners:


    - Transmit credentials over HTTPS only

    - Don't log or store the plaintext password in your application

    = Confirm credentials are valid before storing them in our system


    ### Developer Contact
  version: 1.0.0
  contact:
    name: Mike Mylonakis
    email: contact@mikemylonakis.com
    url: https://mikemylonakis.com
servers:
  - url: https://str.keroshospitality.com/api/v1
    description: Production server
  - url: '{protocol}://{host}:{port}/api/v1'
    description: Configurable server
    variables:
      protocol:
        enum:
          - http
          - https
        default: http
      host:
        default: localhost
      port:
        default: '8081'
security:
  - BearerAuth: []
paths:
  /auth/token:
    post:
      tags:
        - Authentication
      summary: Login and get access token
      description: Authenticate with username/password and receive JWT tokens
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/LoginRequest'
      responses:
        '200':
          description: Login successful
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TokenResponse'
        '401':
          description: Invalid credentials
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
      security: []
components:
  schemas:
    LoginRequest:
      description: LoginRequest defines the authentication request payload
      type: object
      required:
        - clientId
        - secret
      properties:
        clientId:
          type: string
          description: ClientID is the unique identifier for the client
          example: keros
        secret:
          type: string
          description: Secret is the client's password or secret key
          example: password
    TokenResponse:
      description: TokenResponse defines the authentication response payload
      type: object
      properties:
        access_token:
          type: string
          description: JWT token for authentication
          example: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
        expires_in:
          type: integer
          description: Number of seconds until the access token expires
          example: 86400
        refresh_token:
          type: string
          description: Token used to obtain new access tokens
          example: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
    ErrorResponse:
      type: object
      properties:
        errorMessage:
          type: string
        requestId:
          type: string
  securitySchemes:
    BearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: >-
        JWT Authorization header using the Bearer scheme. Example:
        "Authorization: Bearer {token}"

````