# Copyright 2016 OpenMarket Ltd
# Copyright 2022 The Matrix.org Foundation C.I.C.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
openapi: 3.1.0
info:
  title: Matrix Client-Server Registration API
  version: 1.0.0
paths:
  /register:
    post:
      summary: Register for an account on this homeserver.
      description: |-
        This API endpoint uses the [User-Interactive Authentication API](/client-server-api/#user-interactive-authentication-api), except in
        the cases where a guest account is being registered.

        Register for an account on this homeserver.

        There are two kinds of user account:

        - `user` accounts. These accounts may use the full API described in this specification.

        - `guest` accounts. These accounts may have limited permissions and may not be supported by all servers.

        If registration is successful, this endpoint will issue an access token
        the client can use to authorize itself in subsequent requests.

        If the client does not supply a `device_id`, the server must
        auto-generate one.

        The server SHOULD register an account with a User ID based on the
        `username` provided, if any. Note that the grammar of Matrix User ID
        localparts is restricted, so the server MUST either map the provided
        `username` onto a `user_id` in a logical manner, or reject any
        `username` which does not comply to the grammar with
        `M_INVALID_USERNAME`.

        Matrix clients MUST NOT assume that localpart of the registered
        `user_id` matches the provided `username`.

        The returned access token must be associated with the `device_id`
        supplied by the client or generated by the server. The server may
        invalidate any access token previously associated with that device. See
        [Relationship between access tokens and devices](/client-server-api/#relationship-between-access-tokens-and-devices).

        When registering a guest account, all parameters in the request body
        with the exception of `initial_device_display_name` MUST BE ignored
        by the server. The server MUST pick a `device_id` for the account
        regardless of input.

        Any user ID returned by this API must conform to the grammar given in the
        [Matrix specification](/appendices/#user-identifiers).
      operationId: register
      parameters:
        - in: query
          name: kind
          required: false
          description: The kind of account to register. Defaults to `user`.
          # swagger-UI overrides the default with the example, so better make the
          # example the default.
          example: user
          schema:
            type: string
            enum:
              - guest
              - user
            default: user
      requestBody:
        content:
          application/json:
            schema:
              type: object
              properties:
                auth:
                  description: |-
                    Additional authentication information for the
                    user-interactive authentication API. Note that this
                    information is *not* used to define how the registered user
                    should be authenticated, but is instead used to
                    authenticate the `register` call itself.
                  allOf:
                    - $ref: definitions/auth_data.yaml
                username:
                  type: string
                  description: |-
                    The basis for the localpart of the desired Matrix ID. If omitted,
                    the homeserver MUST generate a Matrix ID local part.
                  example: cheeky_monkey
                password:
                  type: string
                  description: The desired password for the account.
                  example: ilovebananas
                device_id:
                  type: string
                  description: |-
                    ID of the client device. If this does not correspond to a
                    known client device, a new device will be created. The server
                    will auto-generate a device_id if this is not specified.
                  example: GHTYAJCE
                initial_device_display_name:
                  type: string
                  description: |-
                    A display name to assign to the newly-created device. Ignored
                    if `device_id` corresponds to a known device.
                  example: Jungle Phone
                inhibit_login:
                  type: boolean
                  description: |-
                    If true, an `access_token` and `device_id` should not be
                    returned from this call, therefore preventing an automatic
                    login. Defaults to false.
                  example: false
                refresh_token:
                  type: boolean
                  description: If true, the client supports refresh tokens.
                  x-addedInMatrixVersion: "1.3"
        required: true
      responses:
        "200":
          description: The account has been registered.
          content:
            application/json:
              schema:
                type: object
                properties:
                  user_id:
                    type: string
                    description: |-
                      The fully-qualified Matrix user ID (MXID) that has been registered.

                      Any user ID returned by this API must conform to the grammar given in the
                      [Matrix specification](/appendices/#user-identifiers).
                  access_token:
                    type: string
                    description: |-
                      An access token for the account.
                      This access token can then be used to authorize other requests.
                      Required if the `inhibit_login` option is false.
                  refresh_token:
                    type: string
                    description: |-
                      A refresh token for the account. This token can be used to
                      obtain a new access token when it expires by calling the
                      `/refresh` endpoint.

                      Omitted if the `inhibit_login` option is true.
                    x-addedInMatrixVersion: "1.3"
                  expires_in_ms:
                    type: integer
                    description: |-
                      The lifetime of the access token, in milliseconds. Once
                      the access token has expired a new access token can be
                      obtained by using the provided refresh token. If no
                      refresh token is provided, the client will need to re-log in
                      to obtain a new access token. If not given, the client can
                      assume that the access token will not expire.

                      Omitted if the `inhibit_login` option is true.
                    x-addedInMatrixVersion: "1.3"
                  home_server:
                    type: string
                    description: |-
                      The server_name of the homeserver on which the account has
                      been registered.

                      **Deprecated**. Clients should extract the server_name from
                      `user_id` (by splitting at the first colon) if they require
                      it. Note also that `homeserver` is not spelt this way.
                  device_id:
                    type: string
                    description: |-
                      ID of the registered device. Will be the same as the
                      corresponding parameter in the request, if one was specified.
                      Required if the `inhibit_login` option is false.
                required:
                  - user_id
              examples:
                response:
                  value: {
                    "user_id": "@cheeky_monkey:matrix.org",
                    "access_token": "abc123",
                    "device_id": "GHTYAJCE"
                  }
        "400":
          description: |-
            Part of the request was invalid. This may include one of the following error codes:

            * `M_USER_IN_USE` : The desired user ID is already taken.
            * `M_INVALID_USERNAME` : The desired user ID is not a valid user name.
            * `M_EXCLUSIVE` : The desired user ID is in the exclusive namespace
              claimed by an application service.

            These errors may be returned at any stage of the registration process,
            including after authentication if the requested user ID was registered
            whilst the client was performing authentication.

            Homeservers MUST perform the relevant checks and return these codes before
            performing User-Interactive Authentication, although they may also return
            them after authentication is completed if, for example, the requested user ID
            was registered whilst the client was performing authentication.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_USER_IN_USE",
                    "error": "Desired user ID is already taken."
                  }
        "401":
          description: The homeserver requires additional authentication information.
          content:
            application/json:
              schema:
                $ref: definitions/auth_response.yaml
        "403":
          description: |-
            The homeserver does not permit registering the account. This response
            can be used to identify that a particular `kind` of account is not
            allowed, or that registration is generally not supported by the homeserver.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_FORBIDDEN",
                    "error": "Registration is disabled"
                  }
        "429":
          description: This request was rate-limited.
          content:
            application/json:
              schema:
                $ref: definitions/errors/rate_limited.yaml
      tags:
        - Account management
  /register/email/requestToken:
    post:
      summary: Begins the validation process for an email to be used during
        registration.
      description: |-
        The homeserver must check that the given email address is **not**
        already associated with an account on this homeserver. The homeserver
        should validate the email itself, either by sending a validation email
        itself or by using a service it has control over.
      operationId: requestTokenToRegisterEmail
      requestBody:
        content:
          application/json:
            schema:
              $ref: definitions/request_email_validation.yaml
        required: true
      responses:
        "200":
          description: |-
            An email has been sent to the specified address. Note that this
            may be an email containing the validation token or it may be
            informing the user of an error.
          content:
            application/json:
              schema:
                $ref: definitions/request_token_response.yaml
        "400":
          description: |-
            Part of the request was invalid. This may include one of the following error codes:

            * `M_THREEPID_IN_USE` : The email address is already registered to an account on this server.
              However, if the homeserver has the ability to send email, it is recommended that the server
              instead send an email to the user with instructions on how to reset their password.
              This prevents malicious parties from being able to determine if a given email address
              has an account on the homeserver in question.
            * `M_SERVER_NOT_TRUSTED` : The `id_server` parameter refers to an identity server
              that is not trusted by this homeserver.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_IN_USE",
                    "error": "The specified address is already in use"
                  }
        "403":
          description: The homeserver does not permit the address to be bound.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_DENIED",
                    "error": "Third-party identifier is not allowed"
                  }
      tags:
        - Account management
  /register/msisdn/requestToken:
    post:
      summary: Requests a validation token be sent to the given phone number for the
        purpose of registering an account
      description: |-
        The homeserver must check that the given phone number is **not**
        already associated with an account on this homeserver. The homeserver
        should validate the phone number itself, either by sending a validation
        message itself or by using a service it has control over.
      operationId: requestTokenToRegisterMSISDN
      requestBody:
        content:
          application/json:
            schema:
              $ref: definitions/request_msisdn_validation.yaml
        required: true
      responses:
        "200":
          description: |-
            An SMS message has been sent to the specified phone number. Note
            that this may be an SMS message containing the validation token or
            it may be informing the user of an error.
          content:
            application/json:
              schema:
                $ref: definitions/request_token_response.yaml
        "400":
          description: |-
            Part of the request was invalid. This may include one of the following error codes:

            * `M_THREEPID_IN_USE` : The phone number is already registered to an account on this server.
              However, if the homeserver has the ability to send SMS message, it is recommended that the server
              instead send an SMS message to the user with instructions on how to reset their password.
              This prevents malicious parties from being able to determine if a given phone number
              has an account on the homeserver in question.
            * `M_SERVER_NOT_TRUSTED` : The `id_server` parameter refers to an identity server
              that is not trusted by this homeserver.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_IN_USE",
                    "error": "The specified address is already in use"
                  }
        "403":
          description: The homeserver does not permit the address to be bound.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_DENIED",
                    "error": "Third-party identifier is not allowed"
                  }
      tags:
        - Account management
  /account/password:
    post:
      summary: Changes a user's password.
      description: |-
        Changes the password for an account on this homeserver.

        This API endpoint uses the [User-Interactive Authentication API](/client-server-api/#user-interactive-authentication-api) to
        ensure the user changing the password is actually the owner of the
        account.

        An access token should be submitted to this endpoint if the client has
        an active session.

        The homeserver may change the flows available depending on whether a
        valid access token is provided. The homeserver SHOULD NOT revoke the
        access token provided in the request. Whether other access tokens for
        the user are revoked depends on the request parameters.
      security:
        - {}
        - accessTokenQuery: []
        - accessTokenBearer: []
      operationId: changePassword
      requestBody:
        content:
          application/json:
            schema:
              type: object
              properties:
                new_password:
                  type: string
                  description: The new password for the account.
                  example: ihatebananas
                logout_devices:
                  type: boolean
                  description: |-
                    Whether the user's other access tokens, and their associated devices, should be
                    revoked if the request succeeds. Defaults to true.

                    When `false`, the server can still take advantage of the [soft logout method](/client-server-api/#soft-logout)
                    for the user's remaining devices.
                  example: true
                auth:
                  description: Additional authentication information for the user-interactive
                    authentication API.
                  allOf:
                    - $ref: definitions/auth_data.yaml
              required:
                - new_password
        required: true
      responses:
        "200":
          description: The password has been changed.
          content:
            application/json:
              schema:
                type: object
              examples:
                response:
                  value: {}
        "401":
          description: The homeserver requires additional authentication information.
          content:
            application/json:
              schema:
                $ref: definitions/auth_response.yaml
        "429":
          description: This request was rate-limited.
          content:
            application/json:
              schema:
                $ref: definitions/errors/rate_limited.yaml
      tags:
        - Account management
  /account/password/email/requestToken:
    post:
      summary: Requests a validation token be sent to the given email address for the
        purpose of resetting a user's password
      description: |-
        The homeserver must check that the given email address **is
        associated** with an account on this homeserver. This API should be
        used to request validation tokens when authenticating for the
        `/account/password` endpoint.

        This API's parameters and response are identical to that of the
        [`/register/email/requestToken`](/client-server-api/#post_matrixclientv3registeremailrequesttoken)
        endpoint, except that
        `M_THREEPID_NOT_FOUND` may be returned if no account matching the
        given email address could be found. The server may instead send an
        email to the given address prompting the user to create an account.
        `M_THREEPID_IN_USE` may not be returned.

        The homeserver should validate the email itself, either by sending a
        validation email itself or by using a service it has control over.
      operationId: requestTokenToResetPasswordEmail
      requestBody:
        content:
          application/json:
            schema:
              $ref: definitions/request_email_validation.yaml
        required: true
      responses:
        "200":
          description: An email was sent to the given address.
          content:
            application/json:
              schema:
                $ref: definitions/request_token_response.yaml
        "400":
          description: |-
            The referenced third-party identifier is not recognised by the
            homeserver, or the request was invalid. The error code `M_SERVER_NOT_TRUSTED`
            can be returned if the server does not trust/support the identity server
            provided in the request.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_NOT_FOUND",
                    "error": "Email not found"
                  }
        "403":
          description: |-
            The homeserver does not allow the third-party identifier as a
            contact option.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_DENIED",
                    "error": "Third-party identifier is not allowed"
                  }
      tags:
        - Account management
  /account/password/msisdn/requestToken:
    post:
      summary: Requests a validation token be sent to the given phone number for the
        purpose of resetting a user's password.
      description: |-
        The homeserver must check that the given phone number **is
        associated** with an account on this homeserver. This API should be
        used to request validation tokens when authenticating for the
        `/account/password` endpoint.

        This API's parameters and response are identical to that of the
        [`/register/msisdn/requestToken`](/client-server-api/#post_matrixclientv3registermsisdnrequesttoken)
        endpoint, except that
        `M_THREEPID_NOT_FOUND` may be returned if no account matching the
        given phone number could be found. The server may instead send the SMS
        to the given phone number prompting the user to create an account.
        `M_THREEPID_IN_USE` may not be returned.

        The homeserver should validate the phone number itself, either by sending a
        validation message itself or by using a service it has control over.
      operationId: requestTokenToResetPasswordMSISDN
      requestBody:
        content:
          application/json:
            schema:
              $ref: definitions/request_msisdn_validation.yaml
        required: true
      responses:
        "200":
          description: An SMS message was sent to the given phone number.
          content:
            application/json:
              schema:
                $ref: definitions/request_token_response.yaml
        "400":
          description: |-
            The referenced third-party identifier is not recognised by the
            homeserver, or the request was invalid. The error code `M_SERVER_NOT_TRUSTED`
            can be returned if the server does not trust/support the identity server
            provided in the request.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_NOT_FOUND",
                    "error": "Phone number not found"
                  }
        "403":
          description: |-
            The homeserver does not allow the third-party identifier as a
            contact option.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_THREEPID_DENIED",
                    "error": "Third-party identifier is not allowed"
                  }
      tags:
        - Account management
  /account/deactivate:
    post:
      summary: Deactivate a user's account.
      description: |-
        Deactivate the user's account, removing all ability for the user to
        login again.

        This API endpoint uses the [User-Interactive Authentication API](/client-server-api/#user-interactive-authentication-api).

        An access token should be submitted to this endpoint if the client has
        an active session.

        The homeserver may change the flows available depending on whether a
        valid access token is provided.

        Unlike other endpoints, this endpoint does not take an `id_access_token`
        parameter because the homeserver is expected to sign the request to the
        identity server instead.
      security:
        - {}
        - accessTokenQuery: []
        - accessTokenBearer: []
      operationId: deactivateAccount
      requestBody:
        content:
          application/json:
            schema:
              type: object
              properties:
                auth:
                  description: Additional authentication information for the user-interactive
                    authentication API.
                  allOf:
                    - $ref: definitions/auth_data.yaml
                id_server:
                  type: string
                  description: |-
                    The identity server to unbind all of the user's 3PIDs from.
                    If not provided, the homeserver MUST use the `id_server`
                    that was originally use to bind each identifier. If the
                    homeserver does not know which `id_server` that was,
                    it must return an `id_server_unbind_result` of
                    `no-support`.
                  example: example.org
                erase:
                  x-addedInMatrixVersion: "1.10"
                  type: boolean
                  description: |-
                    Whether the user would like their content to be erased as
                    much as possible from the server.

                    Erasure means that any users (or servers) which join the
                    room after the erasure request are served redacted copies of
                    the events sent by this account. Users which had visibility
                    on those events prior to the erasure are still able to see
                    unredacted copies. No redactions are sent and the erasure
                    request is not shared over federation, so other servers
                    might still serve unredacted copies.

                    The server should additionally erase any non-event data
                    associated with the user, such as [account data](/client-server-api/#client-config)
                    and [contact 3PIDs](/client-server-api/#adding-account-administrative-contact-information).

                    Defaults to `false` if not present.
        required: true
      responses:
        "200":
          description: The account has been deactivated.
          content:
            application/json:
              schema:
                type: object
                properties:
                  id_server_unbind_result:
                    type: string
                    enum:
                      - success
                      - no-support
                    description: |-
                      An indicator as to whether or not the homeserver was able to unbind
                      the user's 3PIDs from the identity server(s). `success` indicates
                      that all identifiers have been unbound from the identity server while
                      `no-support` indicates that one or more identifiers failed to unbind
                      due to the identity server refusing the request or the homeserver
                      being unable to determine an identity server to unbind from. This
                      must be `success` if the homeserver has no identifiers to unbind
                      for the user.
                    example: success
                required:
                  - id_server_unbind_result
        "401":
          description: The homeserver requires additional authentication information.
          content:
            application/json:
              schema:
                $ref: definitions/auth_response.yaml
        "429":
          description: This request was rate-limited.
          content:
            application/json:
              schema:
                $ref: definitions/errors/rate_limited.yaml
      tags:
        - Account management
  /register/available:
    get:
      summary: Checks to see if a username is available on the server.
      description: |-
        Checks to see if a username is available, and valid, for the server.

        The server should check to ensure that, at the time of the request, the
        username requested is available for use. This includes verifying that an
        application service has not claimed the username and that the username
        fits the server's desired requirements (for example, a server could dictate
        that it does not permit usernames with underscores).

        Matrix clients may wish to use this API prior to attempting registration,
        however the clients must also be aware that using this API does not normally
        reserve the username. This can mean that the username becomes unavailable
        between checking its availability and attempting to register it.
      operationId: checkUsernameAvailability
      parameters:
        - in: query
          name: username
          required: true
          description: The username to check the availability of.
          example: my_cool_localpart
          schema:
            type: string
            default: my_cool_localpart
      responses:
        "200":
          description: The username is available
          content:
            application/json:
              schema:
                type: object
                properties:
                  available:
                    type: boolean
                    description: |-
                      A flag to indicate that the username is available. This should always
                      be `true` when the server replies with 200 OK.
              examples:
                response:
                  value: {
                    "available": true
                  }
        "400":
          description: |-
            Part of the request was invalid or the username is not available. This may
            include one of the following error codes:

            * `M_USER_IN_USE` : The desired username is already taken.
            * `M_INVALID_USERNAME` : The desired username is not a valid user name.
            * `M_EXCLUSIVE` : The desired username is in the exclusive namespace
              claimed by an application service.
          content:
            application/json:
              schema:
                $ref: definitions/errors/error.yaml
              examples:
                response:
                  value: {
                    "errcode": "M_USER_IN_USE",
                    "error": "Desired user ID is already taken."
                  }
        "429":
          description: This request was rate-limited.
          content:
            application/json:
              schema:
                $ref: definitions/errors/rate_limited.yaml
      tags:
        - Account management
servers:
  - url: "{protocol}://{hostname}{basePath}"
    variables:
      protocol:
        enum:
          - http
          - https
        default: https
      hostname:
        default: localhost:8008
      basePath:
        default: /_matrix/client/v3
components:
  securitySchemes:
    accessTokenQuery:
      $ref: definitions/security.yaml#/accessTokenQuery
    accessTokenBearer:
      $ref: definitions/security.yaml#/accessTokenBearer
