The Profile page was three tabs, each a box inside a box with horizontal
labels: the SSH keys a centred bare row with a grey trash icon, a tall
empty textarea under them, and the user known only by the heading.
Now the user's name, username, role, email and last login head a card
that holds the profile form and the password link; beside it the SSH
keys and the API tokens are cards with their count, a line on what
they are for, one row each with Delete in a menu, and the form to add
one behind a button. Adding or deleting a key returns to #sshkeys.
The token rows are a list-group include that the administrator's view
of a user shares.
Settings > Users was a bold title, an unlabelled "+" and a table of
names with a trash icon. The owner chose this layout from three
rendered options: one list of owners, each with what it may do
(change settings, delete the VM, change console settings, or power and
console only), Edit rights and Remove, an empty state, and a labelled
"Add owner".
- Remove and Edit rights come back to the VM's Users tab: the return
address carried #users unencoded, so it was lost, and Edit rights
went to the user's account page. Both accounts views now go to a
?next page of this site.
- The add-owner list offers only users who are not owners yet and not
administrators, who can use every VM anyway; a superuser owner also
took the only place when a VM may have one owner.
- The unused del_owner view and URL are removed: the list uses the
accounts page, which asks before removing an owner.
XML:
- An XML edit not saved yet is kept: the page no longer reloads itself
when the VM's state changes, and the browser asks before leaving it.
A state change lost the edit.
- The button that opens the review dialog reads "Review changes"; it
did not save, as "Change" suggested. Closing the dialog gives focus
back to the editor.
With "Multiple Owner for VM" off, the ownership form counted the
ownership being edited as another owner, so changing the only owner's
rights (change, delete, console) always failed with "Instance owned by
another user". The check now leaves out the ownership being edited; a
second owner is still refused.
The login page showed its sign-in card to a user who was already signed
in, with the navbar squeezed beside it. Both login views, with and
without OTP, now send that user to the page in next, or to the default
page when next is missing or points elsewhere. Every permission check
answers 403 instead of redirecting to the login, so this cannot loop.
The page test renders the login page signed out.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
131 test modules sat next to the code they test; instances alone had
51 of them beside views.py and utils.py. They move into a
tests/ package per app, and the JavaScript checks into
webvirtcloud/tests/js. Each non-empty tests.py becomes tests/test_views.py;
the empty generated stubs are removed.
Imports of the app's own modules become absolute, paths built from
__file__ go one level up, the live helper is instances.tests.livetest,
and coverage omits */tests/*. The suite discovers the same 960 tests as
before.