docs: Add multiuser documentation and reposition Workflows#9099
docs: Add multiuser documentation and reposition Workflows#9099
Conversation
joshistoast
left a comment
There was a problem hiding this comment.
Good overall add, but needs some updates.
Notes:
-
I added some quick suggestions for reordering to keep the non subgrouped docs links at the top of the respective parent group.
-
Lots of areas where the
<Steps>component can be used for those instructional step-by-step ordered lists. -
I think we should move the spec to the corresponding invoke dir as a feature readme, as opposed to being a docs page.
-
Found a couple broken links and left the fix suggestions.
-
The multi user docs leaves a lot of "not right now, but in the future for sure" promises, maybe it'd be better to just say "Not at this time, create an issue if this is important to you" verbiage?
-
There seemed to be an instance or two of inconsistency between existence of a feature. For example the user vs administrative docs seem to have different opinions on the existence of a user management webui. And there is also documentation now of a board having a desciption- which unless I'm mistaken doesn't exist.
-
I can have my LLM do another pass over this to see if I missed anything, but this was everything I found initially.
Co-authored-by: Josh Corbett <joshwcorbett@icloud.com>
Co-authored-by: Josh Corbett <joshwcorbett@icloud.com>
|
Thanks for the thorough review. There was a lot more cruft in the docs than I realized. I've implemented all the suggested changes and removed redundant and out-of-date content. Let me know if I missed anything. |
joshistoast
left a comment
There was a problem hiding this comment.
PR remains inconsistent with real behavior. Features that don't exist, incorrect endpoints, inaccurate and conflicting feature behaviors, etc.
Also we should document GET /api/v1/auth/status
| **User Management:** | ||
|
|
||
| ```python | ||
| GET /api/v1/users # List users (admin only) |
There was a problem hiding this comment.
These all should begin with /api/v1/auth/users
| **Model Management (Write Operations):** | ||
|
|
||
| ```python | ||
| POST /api/v1/models/install # Install model (admin only) |
There was a problem hiding this comment.
These are all /api/v2/models
| **Model Management (Read Operations):** | ||
|
|
||
| ```python | ||
| GET /api/v1/models/ # List models (all users) |
|
|
||
| #### Change Password | ||
|
|
||
| **Endpoint:** `POST /api/v1/auth/change-password` |
|
|
||
| #### List Users | ||
|
|
||
| **Endpoint:** `GET /api/v1/users` |
There was a problem hiding this comment.
| **Endpoint:** `GET /api/v1/users` | |
| **Endpoint:** `GET /api/v1/auth/users` |
| 4. Cancel stuck or problematic tasks | ||
| </Steps> | ||
|
|
||
| **User Statistics:** |
There was a problem hiding this comment.
Can't find this feature
There was a problem hiding this comment.
Yeah, never got implemented, like a number of other nice to have features. Removed.
| - Full model management (add, delete, configure models) | ||
| - Create and manage user accounts | ||
| - View and manage all users' generation queues | ||
| - View and manage all users' boards, images, and workflows (including system-owned legacy content) |
There was a problem hiding this comment.
| - View and manage all users' boards, images, and workflows (including system-owned legacy content) | |
| - View and manage all users' boards, images, and workflows |
|
|
||
| **Response:** | ||
|
|
||
| ```json |
There was a problem hiding this comment.
Returns a plain array, no pagination
There was a problem hiding this comment.
Shape needs to be:
[
{
"user_id": "string",
"email": "string",
"display_name": "string",
"is_admin": false,
"is_active": true,
"created_at": "2026-05-07T21:12:09.008Z",
"updated_at": "2026-05-07T21:12:09.008Z",
"last_login_at": "2026-05-07T21:12:09.008Z"
}
]
Returns a plain array without items
| "display_name": "John Doe", | ||
| "is_admin": false, | ||
| "is_active": true, | ||
| "created_at": "2024-01-15T10:00:00Z", |
There was a problem hiding this comment.
Add updated_at field below here
|
|
||
| **Firewall Rules:** | ||
|
|
||
| It is best to restrict access to trusted networks and remote IP addresses, or use a VPN to connect to your home network. Rate limit connections to InvokeAI's authentication endpoint `http://your.host:9090/login`. |
There was a problem hiding this comment.
Login endpoint is /api/v1/auth/login
Co-authored-by: Josh Corbett <joshwcorbett@icloud.com>
joshistoast
left a comment
There was a problem hiding this comment.
Found a few more things, clarified another thing. We're getting closer.
|
|
||
| **Response:** | ||
|
|
||
| ```json |
There was a problem hiding this comment.
Shape needs to be:
[
{
"user_id": "string",
"email": "string",
"display_name": "string",
"is_admin": false,
"is_active": true,
"created_at": "2026-05-07T21:12:09.008Z",
"updated_at": "2026-05-07T21:12:09.008Z",
"last_login_at": "2026-05-07T21:12:09.008Z"
}
]
Returns a plain array without items
| # Session configuration (multi-user mode only) | ||
| jwt_secret_key: "your-secret-key-here" # Auto-generated if not specified | ||
| jwt_token_expiry_hours: 24 # Default session timeout | ||
| jwt_remember_me_days: 7 # "Remember me" duration |
There was a problem hiding this comment.
| # Session configuration (multi-user mode only) | |
| jwt_secret_key: "your-secret-key-here" # Auto-generated if not specified | |
| jwt_token_expiry_hours: 24 # Default session timeout | |
| jwt_remember_me_days: 7 # "Remember me" duration | |
| # Optional password policy | |
| strict_password_checking: true # Enforce uppercase/lowercase/number requirements |
There was a problem hiding this comment.
These seem to still be present
|
|
||
| 4. Restart InvokeAI | ||
|
|
||
| **Alternative:** Remove `jwt_secret_key` from config to trigger setup wizard (will create new admin). |
There was a problem hiding this comment.
| **Alternative:** Remove `jwt_secret_key` from config to trigger setup wizard (will create new admin). | |
| **Alternative:** There is no supported config-based shortcut to rerun the setup wizard once an administrator already exists. If the admin password is lost, reset it directly in the database or by using the user-management tooling. |
There was a problem hiding this comment.
Fixed, and gave the correct recipe for reentering setup mode.
| # Before (single-user) | ||
| GET /api/v1/boards/ # Returns all boards | ||
|
|
||
| # After (multi-user) | ||
| GET /api/v1/boards/ # Returns only current user's boards |
There was a problem hiding this comment.
| # Before (single-user) | |
| GET /api/v1/boards/ # Returns all boards | |
| # After (multi-user) | |
| GET /api/v1/boards/ # Returns only current user's boards | |
| # Before (single-user) | |
| GET /api/v1/boards/?all=true # Returns all boards | |
| # After (multi-user) | |
| GET /api/v1/boards/?all=true # Returns boards the current user can access, including their own boards plus shared/public boards; admins can see all boards |
| **Generate Image:** | ||
|
|
||
| ```bash | ||
| curl -X POST http://localhost:9090/api/v1/sessions/ \ |
There was a problem hiding this comment.
This endpoint does not exist
There was a problem hiding this comment.
Something was hallucinating. Wouldn't it be nice to have a simple image generation endpoint?
| cors_origins: | ||
| - "http://localhost:3000" | ||
| - "https://myapp.example.com" |
There was a problem hiding this comment.
| cors_origins: | |
| - "http://localhost:3000" | |
| - "https://myapp.example.com" | |
| allow_origins: | |
| - "http://localhost:3000" | |
| - "https://myapp.example.com" | |
| allow_credentials: true | |
| allow_methods: | |
| - "*" | |
| allow_headers: | |
| - "*" |
Co-authored-by: Josh Corbett <joshwcorbett@icloud.com>
Co-authored-by: Josh Corbett <joshwcorbett@icloud.com>
…er' into lstein/docs/multiuser
… password requirement
ffee730 to
0863f51
Compare
joshistoast
left a comment
There was a problem hiding this comment.
Almost there, found a few more discrepancies, and some were even from my own suggestions (left suggested fixes for those). Clarified what happens to boards on multiuser switching edge cases, a typo here or there, and highlighted some api response docs
|
|
||
| **Response:** | ||
|
|
||
| ```json |
| ```json | ||
| { | ||
| "success": true | ||
| } | ||
| ``` |
There was a problem hiding this comment.
On success it returns a 204 No Content not a json with status. If there's an error the response is 422 with json:
{
"detail": [
{
"loc": [
"string",
0
],
"msg": "string",
"type": "string"
}
]
}
| <Steps> | ||
| 1. Enter your email address (this will be your login name) | ||
| 2. Create a display name (this will be the name other users see) | ||
| 3. Choose a strong password. The following criteria are required with `strict_password_checking_enabled: true`. |
There was a problem hiding this comment.
| 3. Choose a strong password. The following criteria are required with `strict_password_checking_enabled: true`. | |
| 3. Choose a strong password. The following criteria are required with `strict_password_checking: true`. |
My bad on my last suggestion lol
| 5. Click **Create Administrator Account** | ||
| </Steps> | ||
|
|
||
| With `strict_password_checking_enabled` disabled, you'll be warned if you choose a |
There was a problem hiding this comment.
| With `strict_password_checking_enabled` disabled, you'll be warned if you choose a | |
| With `strict_password_checking` disabled, you'll be warned if you choose a |
My bad on my earlier suggestion
| - `shared` -- read/write to the owner and administrator, read-only to everyone else | ||
| - `public` -- read/write by everyone | ||
|
|
||
| #### List One Boards |
There was a problem hiding this comment.
| #### List One Boards | |
| #### Get One Board |
| JWT secrets are generated automatically and stored in the | ||
| database. You can hard-code a secret as shown above for | ||
| development/testing purposes. Session lifetimes default to 24 hours by | ||
| default, or 7 days when the user selects "Remember me", unless | ||
| manually overridden in `invokeai.yaml` as shown above. |
There was a problem hiding this comment.
| JWT secrets are generated automatically and stored in the | |
| database. You can hard-code a secret as shown above for | |
| development/testing purposes. Session lifetimes default to 24 hours by | |
| default, or 7 days when the user selects "Remember me", unless | |
| manually overridden in `invokeai.yaml` as shown above. | |
| JWT secrets are generated automatically and stored in the database. Session lifetimes default to 24 hours, or 7 days when the user selects "Remember me". See Secret Key Management below if you need to rotate the JWT secret. |
This is technically more correct, since there's no manual override 'above'. My bad.
|
|
||
| ### Going From Multi-User to Single-User Mode | ||
|
|
||
| If an InvokeAI instance was in multiuser mode and then restarted in single user mode (by setting `multiuser: false` in the configuration file), all users' boards will be consolidated in one place. Any images that were in "Uncategorized" will be merged together into a single Uncategorized board. If, at a later date, the server is restarted in multi-user mode, the boards and images will be separated and restored to their owners. |
There was a problem hiding this comment.
| If an InvokeAI instance was in multiuser mode and then restarted in single user mode (by setting `multiuser: false` in the configuration file), all users' boards will be consolidated in one place. Any images that were in "Uncategorized" will be merged together into a single Uncategorized board. If, at a later date, the server is restarted in multi-user mode, the boards and images will be separated and restored to their owners. | |
| If an InvokeAI instance was in multiuser mode and then restarted in single user mode (by setting `multiuser: false` in the configuration file), all users' boards will be consolidated in one place. Any images that were in "Uncategorized" will be merged together into a single Uncategorized board. If, at a later date, the server is restarted in multi-user mode, the boards and images will be assigned to the internal 'system' user. Admins can access this legacy content, and will not be restored to original owners. |
| def is_multiuser_enabled(base_url): | ||
| """Check if multi-user mode is enabled (authentication required).""" | ||
| response = requests.get(f"{base_url}/api/v1/boards/") | ||
| return response.status_code == 401 # 401 = auth required |
There was a problem hiding this comment.
| def is_multiuser_enabled(base_url): | |
| """Check if multi-user mode is enabled (authentication required).""" | |
| response = requests.get(f"{base_url}/api/v1/boards/") | |
| return response.status_code == 401 # 401 = auth required | |
| def is_multiuser_enabled(base_url): | |
| response = requests.get(f"{base_url}/api/v1/auth/status") | |
| response.raise_for_status() | |
| return response.json()["multiuser_enabled"] |
This is exposed in the auth status like so
|
|
||
| ### Adding and Modifying Users | ||
|
|
||
| If you are logged in as Administrator, you can add additional users. Click on the small "person silhouette" icon at the bottom left of the main Invoke screen and select "User Management:" |
There was a problem hiding this comment.
| If you are logged in as Administrator, you can add additional users. Click on the small "person silhouette" icon at the bottom left of the main Invoke screen and select "User Management:" | |
| If you are logged in as Administrator, you can add additional users. Click on the small "person silhouette" icon at the bottom left of the main Invoke screen and select "User Management" |
Summary
This PR migrates the multiuser documentation from
docs-oldinto the new astrodocsdirectory. It also moves the Workflows section into Features, which seems to be a more appropriate place for it than at the top level.For convenience, this PR also updates the
make docsMakefile target.Related Issues / Discussions
QA Instructions
make docswill fire up astroFeaturessection.Merge Plan
Simple merge.
Checklist
What's Newcopy (if doing a release after this PR)