Skip to main content
Was this helpful?

Organization API

Organizations and Billing

Create organisations, switch active context, manage members, and administer Stripe Connect

This page documents the active-organisation model used by the enterprise reservation system. It covers organisation creation, membership, branding, billing-safe defaults, and the admin-only Stripe Connect routes.

JWT or user API keyPlan limitsActive organisationStripe Connect

Source

  • Main controller: backend-nestjs/src/organisations/organisations.controller.ts
  • Membership DTOs: backend-nestjs/src/dto/organisation-user.dto.ts
  • Organisation DTOs: backend-nestjs/src/dto/organisation.dto.ts
  • Billing DTOs: backend-nestjs/src/dto/organisation-stripe.dto.ts

Authentication and Permissions

  • All routes on this page require authentication.
  • The main controller uses JwtAuthGuard plus RbacAuthorizationGuard.
  • Additional route-level enforcement uses organisation ownership checks, organisation-scope decorators, role requirements, and permission decorators.
  • Tenant isolation comes from validated organisation membership and the authenticated user's active organisation, never from arbitrary client input.

Plan Limits

  • Store: the current user may own 1 active organisation
  • Enterprise: the current user may own up to 5 active organisations

These limits are enforced in the application layer and backed by the ownership model in the database.

Endpoint Reference

Core Organisation Surface

MethodPathPurposeRequest or queryAuthSource
POST/api/organisationsCreate an organisation owned by the current user.Body: organisation fieldsJWT or user API keyorganisations/organisations.controller.ts
GET/api/organisationsList organisations accessible to the current user.NoneJWT or user API keyorganisations/organisations.controller.ts
PATCH/api/organisations/activeSwitch the authenticated user's active organisation.Body: organisationIdJWT or user API keyorganisations/organisations.controller.ts
GET/api/organisations/:idGet one accessible organisation.Path: idJWT or user API keyorganisations/organisations.controller.ts
PATCH/api/organisations/:idUpdate organisation profile fields.Path: id, body: profile fieldsJWT or user API keyorganisations/organisations.controller.ts
DELETE/api/organisations/:idArchive an organisation.Path: idJWT or user API keyorganisations/organisations.controller.ts
PATCH/api/organisations/:id/billingUpdate billing-safe organisation settings.Path: id, body: defaultCurrencyJWT or user API keyorganisations/organisations.controller.ts
GET/api/organisations/:id/stripe/statusRead the Stripe Connect state for an organisation.Path: idJWT or user API keyorganisations/organisations.controller.ts
POST/api/organisations/:id/stripe/onboarding-linkCreate or refresh a Stripe onboarding link.Path: idJWT or user API keyorganisations/organisations.controller.ts
POST/api/organisations/:id/stripe/dashboard-linkCreate a Stripe dashboard login link.Path: idJWT or user API keyorganisations/organisations.controller.ts
POST/api/organisations/:id/stripe/disconnectDisconnect the stored Stripe account from the organisation.Path: idJWT or user API keyorganisations/organisations.controller.ts
PATCH/api/organisations/:id/colorUpdate the organisation color.Path: id, body: color,cascadeToResourceTypesJWT or user API keyorganisations/organisations.controller.ts

Membership Surface

MethodPathPurposeRequest or queryAuthSource
POST/api/organisations/:id/usersAssign a user to the organisation.Path: id, body: userIdJWT or user API keyorganisations/organisations.controller.ts
DELETE/api/organisations/:id/users/:userIdRemove a user from the organisation.Path: id,userIdJWT or user API keyorganisations/organisations.controller.ts
POST/api/organisations/:id/users/assignAssign a user with an explicit role.Path: id, body: userId,role,assignedById?JWT or user API keyorganisations/organisations.controller.ts
GET/api/organisations/:id/users/listList organisation users and roles.Path: idJWT or user API keyorganisations/organisations.controller.ts
PATCH/api/organisations/:id/users/:userId/roleUpdate a member role.Path: id,userId, body: roleJWT or user API keyorganisations/organisations.controller.ts
DELETE/api/organisations/:id/users/:userId/removeRemove a member through the alternate removal path.Path: id,userIdJWT or user API keyorganisations/organisations.controller.ts

Request Shapes

Organization profile

CreateOrganisationDto and UpdateOrganisationDto

  • name: required on create
  • description: optional string
  • address: optional string
  • phone: optional string
  • email: optional email
  • slug: optional kebab-case public booking slug
  • logoUrl: optional public logo URL
  • publicBookingHeadline: optional public page headline
  • publicBookingDescription: optional public page description
  • isActive: update-only optional boolean

Active organisation

SetActiveOrganisationDto

  • organisationId: required positive integer

Membership

  • AssignUserDto.userId: required number
  • AssignOrganisationUserDto.userId: required number
  • AssignOrganisationUserDto.role: required OrganisationRoleType
  • AssignOrganisationUserDto.assignedById: optional number
  • UpdateOrganisationUserRoleDto.role: required OrganisationRoleType

Billing and Stripe

UpdateOrganisationBillingDto

  • defaultCurrency: optional Stripe-supported three-letter currency code

Example Calls

Create an organisation

curl -X POST "$PRIMECAL_API/api/organisations" \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "Primecal Store Budapest",
"slug": "primecal-store-budapest",
"publicBookingHeadline": "Book your table",
"publicBookingDescription": "Choose a time and pay only when required."
}'

Switch the active organisation

curl -X PATCH "$PRIMECAL_API/api/organisations/active" \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"organisationId": 12
}'
curl -X POST "$PRIMECAL_API/api/organisations/12/stripe/onboarding-link" \
-H "Authorization: Bearer $TOKEN"

Example response:

{
"url": "https://connect.stripe.com/setup/...",
"stripeAccountId": "acct_1234567890",
"stripeConnectStatus": "pending"
}

Read Stripe status

curl "$PRIMECAL_API/api/organisations/12/stripe/status" \
-H "Authorization: Bearer $TOKEN"

Example response:

{
"organisationId": 12,
"stripeAccountId": "acct_1234567890",
"stripeConnectStatus": "active",
"defaultCurrency": "eur",
"chargesEnabled": true,
"payoutsEnabled": true,
"detailsSubmitted": true,
"requiresOnboarding": false,
"currentlyDue": [],
"pendingVerification": [],
"disabledReason": null
}

Response and Behavior Notes

  • GET /api/organisations returns membership-aware records including role, owner state, and active-organisation state.
  • DELETE /api/organisations/:id archives the organisation instead of hard-deleting it.
  • Resource, reservation, and MCP enterprise flows depend on the caller's active organisation, so switching context is part of the expected API usage.
  • Stripe status reads can sync the stored state from Stripe before the response is returned.
  • The organisation billing UI uses the status route and the organisation read route in parallel so admins can review Stripe readiness and billing defaults in one screen.

Best Practices

  • Set the active organisation explicitly at session start in multi-org clients.
  • Keep Stripe onboarding and billing routes admin-only in your UI as well as in the API.
  • Use role-based membership endpoints instead of encoding organisation access in client state.
  • Treat public booking slug and branding fields as customer-facing product content that deserves review before publishing.