Skip to content

auth

← All modules

13 endpoints.

POST /api/v1/auth/send-verification

Send Verification

Admin-triggered: send a verification email for a specific user. Returns success/failure so the grid can show a toast.

Request body

json
{
  "properties": {
    "user_id": {
      "type": "integer",
      "title": "User Id"
    }
  },
  "type": "object",
  "required": [
    "user_id"
  ],
  "title": "SendVerificationRequest"
}

200 — Successful Response

json
{
  "properties": {
    "detail": {
      "type": "string",
      "title": "Detail"
    }
  },
  "type": "object",
  "required": [
    "detail"
  ],
  "title": "MessageResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/resend-verification

Resend Verification

Self-serve resend for a user blocked at login by the email-verification gate (login's email_unverified 403) — no auth, since they can't sign in yet. Always returns the same generic message regardless of whether the email is registered/verified, mirroring forgot_password's no-enumeration behaviour.

Request body

json
{
  "properties": {
    "email": {
      "type": "string",
      "title": "Email"
    }
  },
  "type": "object",
  "required": [
    "email"
  ],
  "title": "ResendVerificationRequest"
}

200 — Successful Response

json
{
  "properties": {
    "detail": {
      "type": "string",
      "title": "Detail"
    }
  },
  "type": "object",
  "required": [
    "detail"
  ],
  "title": "MessageResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

GET /api/v1/auth/verify-email

Verify Email

Click-through from the verification email link. Marks the user's email as verified and shows a simple success page the user can close. The token is single-use — subsequent clicks are rejected.

Parameters

NameInRequiredTypeDescription
tokenqueryyesstring

200 — Successful Response

json
{}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/signup

Signup

Request body

json
{
  "properties": {
    "email": {
      "type": "string",
      "format": "email",
      "title": "Email"
    },
    "password": {
      "type": "string",
      "maxLength": 128,
      "minLength": 8,
      "title": "Password"
    },
    "full_name": {
      "type": "string",
      "maxLength": 255,
      "minLength": 1,
      "title": "Full Name"
    },
    "org_name": {
      "type": "string",
      "maxLength": 255,
      "minLength": 1,
      "title": "Org Name"
    },
    "org_slug": {
      "type": "string",
      "maxLength": 100,
      "minLength": 2,
      "title": "Org Slug"
    }
  },
  "type": "object",
  "required": [
    "email",
    "password",
    "full_name",
    "org_name",
    "org_slug"
  ],
  "title": "SignupRequest",
  "description": "Self-serve signup: creates the user, their first organization, and an\nowner membership in one step."
}

201 — Successful Response

json
{
  "properties": {
    "access_token": {
      "type": "string",
      "title": "Access Token"
    },
    "refresh_token": {
      "type": "string",
      "title": "Refresh Token"
    },
    "token_type": {
      "type": "string",
      "title": "Token Type",
      "default": "bearer"
    }
  },
  "type": "object",
  "required": [
    "access_token",
    "refresh_token"
  ],
  "title": "TokenResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/login

Login

Request body

json
{
  "properties": {
    "email": {
      "type": "string",
      "format": "email",
      "title": "Email"
    },
    "password": {
      "type": "string",
      "title": "Password"
    }
  },
  "type": "object",
  "required": [
    "email",
    "password"
  ],
  "title": "LoginRequest"
}

200 — Successful Response

json
{
  "properties": {
    "access_token": {
      "type": "string",
      "title": "Access Token"
    },
    "refresh_token": {
      "type": "string",
      "title": "Refresh Token"
    },
    "token_type": {
      "type": "string",
      "title": "Token Type",
      "default": "bearer"
    }
  },
  "type": "object",
  "required": [
    "access_token",
    "refresh_token"
  ],
  "title": "TokenResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/forgot-password

Forgot Password

Always returns the same generic message, whether or not the email is registered, so this endpoint can't be used to enumerate accounts.

Request body

json
{
  "properties": {
    "email": {
      "type": "string",
      "format": "email",
      "title": "Email"
    }
  },
  "type": "object",
  "required": [
    "email"
  ],
  "title": "ForgotPasswordRequest"
}

200 — Successful Response

json
{
  "properties": {
    "detail": {
      "type": "string",
      "title": "Detail"
    }
  },
  "type": "object",
  "required": [
    "detail"
  ],
  "title": "MessageResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/reset-password

Reset Password

Request body

json
{
  "properties": {
    "token": {
      "type": "string",
      "title": "Token"
    },
    "password": {
      "type": "string",
      "maxLength": 128,
      "minLength": 8,
      "title": "Password"
    }
  },
  "type": "object",
  "required": [
    "token",
    "password"
  ],
  "title": "ResetPasswordRequest"
}

200 — Successful Response

json
{
  "properties": {
    "detail": {
      "type": "string",
      "title": "Detail"
    }
  },
  "type": "object",
  "required": [
    "detail"
  ],
  "title": "MessageResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/refresh

Refresh

Request body

json
{
  "properties": {
    "refresh_token": {
      "type": "string",
      "title": "Refresh Token"
    }
  },
  "type": "object",
  "required": [
    "refresh_token"
  ],
  "title": "TokenRefresh"
}

200 — Successful Response

json
{
  "properties": {
    "access_token": {
      "type": "string",
      "title": "Access Token"
    },
    "refresh_token": {
      "type": "string",
      "title": "Refresh Token"
    },
    "token_type": {
      "type": "string",
      "title": "Token Type",
      "default": "bearer"
    }
  },
  "type": "object",
  "required": [
    "access_token",
    "refresh_token"
  ],
  "title": "TokenResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

POST /api/v1/auth/impersonate

Impersonate

Exchange a one-time impersonation code — minted by a staff superuser's "Log in as" button (see app.services.impersonation) — for portal session tokens. The code IS the authorization: single-use, short-lived, and only ever issued by a superuser, so this endpoint is intentionally unauthenticated (like accepting an invite). Consumed on first use; rejected if used/expired.

Request body

json
{
  "properties": {
    "code": {
      "type": "string",
      "title": "Code"
    }
  },
  "type": "object",
  "required": [
    "code"
  ],
  "title": "_ImpersonateRequest"
}

200 — Successful Response

json
{
  "properties": {
    "access_token": {
      "type": "string",
      "title": "Access Token"
    },
    "refresh_token": {
      "type": "string",
      "title": "Refresh Token"
    },
    "token_type": {
      "type": "string",
      "title": "Token Type",
      "default": "bearer"
    }
  },
  "type": "object",
  "required": [
    "access_token",
    "refresh_token"
  ],
  "title": "TokenResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

GET /api/v1/auth/me

Me

Return the user plus the tenants for their switcher.

Superusers can act on ANY tenant (see get_tenant_context), so we return every active org for them (role "owner") — otherwise a platform admin with no membership would have an empty switcher and couldn't scope any request. Regular users get exactly the tenants they hold an active membership in.

200 — Successful Response

json
{
  "properties": {
    "id": {
      "type": "string",
      "title": "Id"
    },
    "email": {
      "type": "string",
      "title": "Email"
    },
    "full_name": {
      "type": "string",
      "title": "Full Name"
    },
    "is_superuser": {
      "type": "boolean",
      "title": "Is Superuser"
    },
    "management_read_only": {
      "type": "boolean",
      "title": "Management Read Only",
      "default": false
    },
    "customer_facing": {
      "type": "boolean",
      "title": "Customer Facing",
      "default": false
    },
    "is_reseller": {
      "type": "boolean",
      "title": "Is Reseller",
      "default": false
    },
    "is_reseller_user": {
      "type": "boolean",
      "title": "Is Reseller User",
      "default": false
    },
    "tenants": {
      "items": {
        "properties": {
          "id": {
            "type": "string",
            "title": "Id"
          },
          "name": {
            "type": "string",
            "title": "Name"
          },
          "slug": {
            "type": "string",
            "title": "Slug"
          },
          "plan_tier": {
            "type": "string",
            "title": "Plan Tier"
          },
          "status": {
            "type": "string",
            "title": "Status"
          },
          "role": {
            "type": "string",
            "title": "Role"
          },
          "icon_url": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Icon Url"
          },
          "domain_name": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Domain Name"
          },
          "domain_names": {
            "items": {
              "type": "string"
            },
            "type": "array",
            "title": "Domain Names",
            "default": []
          },
          "parent_tenant_id": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Parent Tenant Id"
          },
          "is_reseller": {
            "type": "boolean",
            "title": "Is Reseller",
            "default": false
          }
        },
        "type": "object",
        "required": [
          "id",
          "name",
          "slug",
          "plan_tier",
          "status",
          "role"
        ],
        "title": "TenantSummary",
        "description": "A tenant the current user belongs to, plus their role in it."
      },
      "type": "array",
      "title": "Tenants"
    }
  },
  "type": "object",
  "required": [
    "id",
    "email",
    "full_name",
    "is_superuser",
    "tenants"
  ],
  "title": "MeResponse"
}

PUT /api/v1/auth/me

Update Me

Self-service profile update — change own name, email and/or password. Bumps token_version when the password changes so existing sessions are revoked (same mechanism as the reset-password flow).

Request body

json
{
  "properties": {
    "full_name": {
      "anyOf": [
        {
          "type": "string",
          "maxLength": 255,
          "minLength": 1
        },
        {
          "type": "null"
        }
      ],
      "title": "Full Name"
    },
    "email": {
      "anyOf": [
        {
          "type": "string",
          "format": "email"
        },
        {
          "type": "null"
        }
      ],
      "title": "Email"
    },
    "password": {
      "anyOf": [
        {
          "type": "string",
          "maxLength": 128,
          "minLength": 8
        },
        {
          "type": "null"
        }
      ],
      "title": "Password"
    }
  },
  "type": "object",
  "title": "UpdateProfileRequest",
  "description": "Self-service profile edit — the user can change their own name, email,\nand/or password.  Only supplied fields are updated (all optional)."
}

200 — Successful Response

json
{
  "properties": {
    "id": {
      "type": "string",
      "title": "Id"
    },
    "email": {
      "type": "string",
      "title": "Email"
    },
    "full_name": {
      "type": "string",
      "title": "Full Name"
    },
    "is_superuser": {
      "type": "boolean",
      "title": "Is Superuser"
    },
    "management_read_only": {
      "type": "boolean",
      "title": "Management Read Only",
      "default": false
    },
    "customer_facing": {
      "type": "boolean",
      "title": "Customer Facing",
      "default": false
    },
    "is_reseller": {
      "type": "boolean",
      "title": "Is Reseller",
      "default": false
    },
    "is_reseller_user": {
      "type": "boolean",
      "title": "Is Reseller User",
      "default": false
    },
    "tenants": {
      "items": {
        "properties": {
          "id": {
            "type": "string",
            "title": "Id"
          },
          "name": {
            "type": "string",
            "title": "Name"
          },
          "slug": {
            "type": "string",
            "title": "Slug"
          },
          "plan_tier": {
            "type": "string",
            "title": "Plan Tier"
          },
          "status": {
            "type": "string",
            "title": "Status"
          },
          "role": {
            "type": "string",
            "title": "Role"
          },
          "icon_url": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Icon Url"
          },
          "domain_name": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Domain Name"
          },
          "domain_names": {
            "items": {
              "type": "string"
            },
            "type": "array",
            "title": "Domain Names",
            "default": []
          },
          "parent_tenant_id": {
            "anyOf": [
              {
                "type": "string"
              },
              {
                "type": "null"
              }
            ],
            "title": "Parent Tenant Id"
          },
          "is_reseller": {
            "type": "boolean",
            "title": "Is Reseller",
            "default": false
          }
        },
        "type": "object",
        "required": [
          "id",
          "name",
          "slug",
          "plan_tier",
          "status",
          "role"
        ],
        "title": "TenantSummary",
        "description": "A tenant the current user belongs to, plus their role in it."
      },
      "type": "array",
      "title": "Tenants"
    }
  },
  "type": "object",
  "required": [
    "id",
    "email",
    "full_name",
    "is_superuser",
    "tenants"
  ],
  "title": "MeResponse"
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

GET /api/v1/auth/me/notifications

Get Notification Preferences

No row yet ⇒ the dialog's own defaults (nothing persisted until Save).

200 — Successful Response

json
{
  "properties": {
    "low_balance_airtime_reminder": {
      "type": "boolean",
      "title": "Low Balance Airtime Reminder",
      "default": true
    },
    "marketing_emails": {
      "type": "boolean",
      "title": "Marketing Emails",
      "default": true
    }
  },
  "type": "object",
  "title": "NotificationPreferences",
  "description": "My Notifications dialog state. Security emails (sign-in alerts) aren't\nhere — they're mandatory, no opt-out (see app.services.sign_in_alert)."
}

PUT /api/v1/auth/me/notifications

Update Notification Preferences

Request body

json
{
  "properties": {
    "low_balance_airtime_reminder": {
      "type": "boolean",
      "title": "Low Balance Airtime Reminder",
      "default": true
    },
    "marketing_emails": {
      "type": "boolean",
      "title": "Marketing Emails",
      "default": true
    }
  },
  "type": "object",
  "title": "NotificationPreferences",
  "description": "My Notifications dialog state. Security emails (sign-in alerts) aren't\nhere — they're mandatory, no opt-out (see app.services.sign_in_alert)."
}

200 — Successful Response

json
{
  "properties": {
    "low_balance_airtime_reminder": {
      "type": "boolean",
      "title": "Low Balance Airtime Reminder",
      "default": true
    },
    "marketing_emails": {
      "type": "boolean",
      "title": "Marketing Emails",
      "default": true
    }
  },
  "type": "object",
  "title": "NotificationPreferences",
  "description": "My Notifications dialog state. Security emails (sign-in alerts) aren't\nhere — they're mandatory, no opt-out (see app.services.sign_in_alert)."
}

422 — Validation Error

json
{
  "properties": {
    "detail": {
      "items": {
        "properties": {
          "loc": {
            "items": {
              "anyOf": [
                {
                  "type": "string"
                },
                {
                  "type": "integer"
                }
              ]
            },
            "type": "array",
            "title": "Location"
          },
          "msg": {
            "type": "string",
            "title": "Message"
          },
          "type": {
            "type": "string",
            "title": "Error Type"
          }
        },
        "type": "object",
        "required": [
          "loc",
          "msg",
          "type"
        ],
        "title": "ValidationError"
      },
      "type": "array",
      "title": "Detail"
    }
  },
  "type": "object",
  "title": "HTTPValidationError"
}

Lubb ERP Documentation