Members
Organisation members are human users who belong to your Phase organisation, each assigned a Role that governs their permissions. On this page, we'll look at the API endpoints for listing members, inviting new members, updating roles, managing app and environment access, and removing members.
The Member model
Properties
- Name
id- Type
- string
- Description
Unique identifier for the organisation membership.
- Name
username- Type
- string
- Description
The member's username.
- Name
fullName- Type
- string
- Description
The member's full name, populated from their OAuth profile if available.
- Name
email- Type
- string
- Description
The member's email address.
- Name
role- Type
- object
- Description
The assigned role, with
idandname.
- Name
createdAt- Type
- timestamp
- Description
Timestamp of when the member joined the organisation.
- Name
updatedAt- Type
- timestamp
- Description
Timestamp of when the membership was last updated.
List Members
Retrieve all active members of the organisation.
Request
curl https://api.phase.dev/v1/members/ \
-H "Authorization: Bearer {token}"
Response
[
{
"id": "3f2e1d0c-9b8a-7654-3210-fedcba987654",
"username": "alice",
"fullName": "Alice Smith",
"email": "alice@example.com",
"role": {
"id": "6aec9df5-cd75-4645-a9d0-8b6f6aff78d6",
"name": "Developer"
},
"createdAt": "2024-06-01T12:00:00Z",
"updatedAt": "2024-06-01T12:00:00Z"
}
]
Invite Member
Send an invitation to a new member. An invite email is sent to the specified address, and the invite expires after 14 days.
This endpoint creates an invite, not a direct membership. The invited user must accept the invite via the console to become a member. Use the Invites API to list or cancel pending invites.
Constraints
- The role must not have global access (i.e. Owner and Admin roles cannot be invited to).
- The role must not permit creating service account tokens.
- The email is validated against RFC format; whitespace is trimmed and the local + domain parts are lowercased. Invalid emails return
400 Bad Request. - The email must not already belong to an active member or a pending invite. Duplicate invites return
409 Conflictwith{"error": "An active invite already exists for '<email>'."}.
The optional apps array on an invite is metadata recorded against the pending invite. Because Phase is end-to-end encrypted, no apps or environments can actually be granted to the invitee until they accept the invite and register their identity key — at which point the inviter (or another member with the appropriate permissions) must call the Manage Access endpoint.
JSON Body
Required fields
- Name
email- Type
- string
- Description
The email address of the person to invite.
- Name
role_id- Type
- string
- Description
The ID of the role to assign on acceptance.
Optional fields
- Name
apps- Type
- array
- Description
An array of App IDs to pre-scope the invite to. The invited member will be granted access to these apps on acceptance.
Request
curl -X POST https://api.phase.dev/v1/members/ \
-H "Authorization: Bearer {token}" \
-H "Content-Type: application/json" \
-d '{
"email": "bob@example.com",
"role_id": "6aec9df5-cd75-4645-a9d0-8b6f6aff78d6"
}'
Response
{
"id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"inviteeEmail": "bob@example.com",
"role": {
"id": "6aec9df5-cd75-4645-a9d0-8b6f6aff78d6",
"name": "Developer"
},
"invitedBy": {
"type": "member",
"email": "alice@example.com"
},
"createdAt": "2024-06-02T10:00:00Z",
"expiresAt": "2024-06-16T10:00:00Z",
"valid": true
}
Get Member
Retrieve a single member by their membership ID.
URL parameters
- Name
id- Type
- string
- Description
The unique identifier of the organisation membership.
Request
curl https://api.phase.dev/v1/members/3f2e1d0c-9b8a-7654-3210-fedcba987654/ \
-H "Authorization: Bearer {token}"
Response
{
"id": "3f2e1d0c-9b8a-7654-3210-fedcba987654",
"username": "alice",
"fullName": "Alice Smith",
"email": "alice@example.com",
"role": {
"id": "6aec9df5-cd75-4645-a9d0-8b6f6aff78d6",
"name": "Developer"
},
"createdAt": "2024-06-01T12:00:00Z",
"updatedAt": "2024-06-01T12:00:00Z"
}
Update Member Role
Update a member's assigned role.
Constraints
- The Owner's role is immutable via the API. Any attempt to PUT the Owner's membership returns
403 Forbiddenwith{"error": "The Owner's role cannot be changed via the API. Use the ownership transfer flow."}. Ownership transfer is a console-only flow. - Users cannot update their own role (
403). - User callers cannot update a member who holds a global-access role (e.g. Admin) unless they themselves hold a global-access role (
403). - Service Account callers cannot update any member who holds a global-access role (
403), nor can they assign a global-access role to any member (403).
URL parameters
- Name
id- Type
- string
- Description
The unique identifier of the organisation membership.
JSON Body
Required fields
- Name
role_id- Type
- string
- Description
The ID of the new role to assign.
Request
curl -X PUT https://api.phase.dev/v1/members/3f2e1d0c-9b8a-7654-3210-fedcba987654/ \
-H "Authorization: Bearer {token}" \
-H "Content-Type: application/json" \
-d '{
"role_id": "d3a2124c-9770-42d5-abf8-599b4a372e9d"
}'
Response
{
"id": "3f2e1d0c-9b8a-7654-3210-fedcba987654",
"username": "alice",
"fullName": "Alice Smith",
"email": "alice@example.com",
"role": {
"id": "d3a2124c-9770-42d5-abf8-599b4a372e9d",
"name": "Manager"
},
"createdAt": "2024-06-01T12:00:00Z",
"updatedAt": "2024-06-03T09:00:00Z"
}
Remove Member
Remove a member from the organisation. The user retains their account and can be re-invited later.
Constraints
- The Owner cannot be removed via the API (
403). Ownership must be transferred first via the console. - Users cannot remove themselves from the organisation (
403). - Service Account callers cannot remove a member who holds a global-access role (
403).
URL parameters
- Name
id- Type
- string
- Description
The unique identifier of the organisation membership.
Request
curl -X DELETE https://api.phase.dev/v1/members/3f2e1d0c-9b8a-7654-3210-fedcba987654/ \
-H "Authorization: Bearer {token}"
Response
204 No Content
Manage Access
Set the app and environment access for a member. This is a declarative endpoint — the request body represents the entire desired access state.
- Apps not in the list will have their access revoked.
- Each app entry must include at least one environment.
- To revoke all access for a member, send an empty
appsarray.
The server handles cryptographic key wrapping for each environment — it re-encrypts environment keys for the member's identity key using server-side encryption.
This endpoint only works for apps with Server-side Encryption (SSE) enabled. SSE can be enabled from the App settings page. Non-SSE apps return 400 Bad Request.
The target member must also have logged in to the Phase console at least once so their identity key is registered. If the member's identity key is missing or blank, the endpoint returns 400 Bad Request with {"error": "Member has not set up their identity key yet. They must log in to the console first."}.
URL parameters
- Name
id- Type
- string
- Description
The unique identifier of the organisation membership.
JSON Body
- Name
apps- Type
- array
- Description
An array of app access objects. Each object must have:
id(string): The app ID.environments(array): A list of environment IDs to grant access to. Must not be empty.
To revoke all access, pass an empty array.
Request
curl -X PUT https://api.phase.dev/v1/members/3f2e1d0c-9b8a-7654-3210-fedcba987654/access/ \
-H "Authorization: Bearer {token}" \
-H "Content-Type: application/json" \
-d '{
"apps": [
{
"id": "72b9ddd5-8fce-49ab-89d9-c431d53a9552",
"environments": [
"af6b7a8e-c268-48c2-967c-032e86e26110",
"c23d4e5f-6789-01bc-def2-3456789012cd"
]
}
]
}'
Response
{
"id": "3f2e1d0c-9b8a-7654-3210-fedcba987654",
"username": "alice",
"fullName": "Alice Smith",
"email": "alice@example.com",
"role": {
"id": "6aec9df5-cd75-4645-a9d0-8b6f6aff78d6",
"name": "Developer"
},
"createdAt": "2024-06-01T12:00:00Z",
"updatedAt": "2024-06-03T10:00:00Z"
}