-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
network mode #589
base: master
Are you sure you want to change the base?
network mode #589
Changes from all commits
e08cc4f
758b15f
75ccf61
799ad23
5d22688
4c79d8a
2c2fd34
35090da
79714b2
18ccc4c
7ec1c9b
50aa4e5
3e266c7
38410de
4a6ed0d
d690c41
5f4087d
18ee9dd
a3aa357
1bf5584
3e94161
5ec26f9
c632d08
50a86b7
c32501b
521af09
1029847
9be6121
aa1e9e4
ef2ebd1
b337464
f5de462
72d2bb3
93d177f
fedc5ed
7f6a8a0
249f4a1
df90ba2
9de7fee
e56504e
aa8f43d
d4b01b1
cd9c048
8107ebb
18bc104
add132e
a140783
34a1dd0
7002b2d
336e5c3
704f2bc
5f587de
76944c4
8c03aab
a34a060
ae9caf6
37b9f62
c8385c9
bd2da76
c5057cb
9a839b7
64894e3
3e903fd
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -56,3 +56,7 @@ magpie_delete_users*.txt | |
requirements-all.txt | ||
gunicorn.app.wsgiapp | ||
error_log.txt | ||
|
||
# Secrets | ||
*.pem | ||
*.key |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -422,3 +422,116 @@ Furthermore, as described in the `procedure`_, :envvar:`MAGPIE_USER_REGISTRATION | |
specify whether administrator approval is required or not. This additional step is purely up to the developers and | ||
server managers that use `Magpie` to decide if they desire more control over which individuals can join and access | ||
their services. | ||
|
||
.. _Network Mode: | ||
|
||
Network Mode | ||
------------ | ||
|
||
If the :envvar:`MAGPIE_NETWORK_ENABLED` is enabled, `Magpie` instances can be linked in a network which allows them to | ||
associate user accounts across the network and provide limited resource access to users who have accounts on other | ||
`Magpie` instances in the network. Each `Magpie` instance is considered a node in the network. | ||
|
||
Users who have an account on one `Magpie` instance can request an access token from another instance in the network | ||
which the user can use to access resources protected by the other `Magpie` instance. | ||
|
||
Users with accounts on multiple instances in the network can also choose to link their accounts. This allows users who | ||
use access tokens to ensure that they have the same access to resources that they would have if they logged in to | ||
`Magpie` using any other method. | ||
|
||
|
||
Managing the Network | ||
~~~~~~~~~~~~~~~~~~~~ | ||
|
||
Each `Magpie` instance must be made aware of the existence of the other instances in the network so that they know where | ||
to send token requests and account linking requests. | ||
|
||
In order to register another `Magpie` instance as part of the same network, an admin user can create a | ||
:term:`Network Node` with a request to ``POST /network/nodes``. The parameters given to that request includes | ||
|
||
* ``name``: | ||
* the name of that other `Magpie` instance in the network and should correspond to the same value as the | ||
:envvar:`MAGPIE_NETWORK_INSTANCE_NAME` value set by the other `Magpie` instance. | ||
* ``jwks_url``: | ||
* URL that provides the instance's public key in the form of a JSON Web Key Set. | ||
* This is usually ``https://{hostname}/network/jwks`` where ``{hostname}`` is the hostname of the other instance | ||
* ``authorization_url`` | ||
* URL that provides the instance's Oauth authorize endpoint. | ||
* This is usually ``https://{hostname}/ui/network/authorize`` where ``{hostname}`` is the hostname of the other | ||
instance. | ||
* ``token_url`` | ||
* URL that provides the instances Oauth token endpoint. | ||
* This is usually ``https://{hostname}/network/token`` where ``{hostname}`` is the hostname of the other instance. | ||
* ``redirect_uris`` | ||
* JSON array of valid redirect URIs for the instance. These are used by the instance's Oauth authorize | ||
endpoint to safely redirect the user back once they have authorized `Magpie` to link their accounts on two | ||
different instances. | ||
* This is usually ``https://{hostname}/network/link`` where ``{hostname}`` is the hostname of the other | ||
instance. | ||
|
||
|
||
Once a :term:`Network Node` is registered, `Magpie` can treat the other instance as if they are in the same network as | ||
long as: | ||
|
||
* Both instances have :envvar:`MAGPIE_NETWORK_ENABLED` enabled | ||
* Both instances have :envvar:`MAGPIE_NETWORK_INSTANCE_NAME` set | ||
* Both instances have :envvar:`MAGPIE_NETWORK_PEM_FILES` set in order to verify communication between nodes using an | ||
asymmetric public/private key-pair. | ||
|
||
|
||
Managing Personal Access Tokens | ||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | ||
|
||
A :term:`User` can request a new access token from another node with a request to the | ||
``GET /network/nodes/{node_name}/token`` route. | ||
|
||
Every time a :term:`User` makes a request to this route, `Magpie` send a request to the other instance, and provides it | ||
to the user. A new token is generated every time. This effectively cancels all previously created tokens for that user. | ||
|
||
To cancel an existing token without generating a new one. A :term:`User` can make a request to the | ||
``DELETE /network/nodes/{node_name}/token`` route. | ||
|
||
Authentication | ||
~~~~~~~~~~~~~~ | ||
|
||
Once a :term:`User` gets an access token, they can use that token to authenticate with the instance that issued that | ||
token. | ||
|
||
When a user makes a request, they should set the ``provider_name`` parameter to the value of | ||
:envvar:`MAGPIE_NETWORK_PROVIDER` and provide the network token in the Authorization header in the following format: | ||
|
||
.. code-block:: http | ||
|
||
Authorization: Bearer <network_token> | ||
|
||
When using the :ref:`Magpie Adapter <utilities_adapter>`, the token can also be passed as a parameter to the request, | ||
where the parameter name set by :envvar:`MAGPIE_NETWORK_TOKEN_NAME` and the value is the personal network token. | ||
|
||
Authorization | ||
~~~~~~~~~~~~~ | ||
|
||
Managing authorization for :term:`Users` who authenticate using access tokens is complicated by the fact that | ||
a :term:`User` is not required to have a full account on both `Magpie` instances in order to using this authentication | ||
mechanism. This means that a :term:`User` may be logged in as a node-specific "anonymous" user. | ||
|
||
When another `Magpie` instance is registered as a :term:`Network Node`, a few additional entities are created: | ||
|
||
#. a group used to manage the permissions of all users who authenticate using the new :term:`Network Node`. | ||
* this group's name will be the :envvar:`MAGPIE_NETWORK_NAME_PREFIX` followed by the :term:`Network Node` name | ||
#. a group used to manage the permissions of all users who authenticate using *any* other instance in the network | ||
* this group's name will be the :envvar:`MAGPIE_NETWORK_GROUP_NAME` | ||
* this group will only be created once, when the first :term:`Network Node` is registered | ||
#. an anonymous user that belongs to the two groups that were just created. | ||
* this user name will be the :envvar:`MAGPIE_NETWORK_NAME_PREFIX` followed by the :term:`Network Node` name | ||
|
||
Here is an example to illustrate this point: | ||
|
||
* There are 3 `Magpie` instances in the network named A, B, and C | ||
* There is a :term:`User` named ``"toto"`` registered on instance A | ||
* There is no :term:`User` named ``"toto"`` who belongs to the ``"anonymous_network_A"`` group registered on instance B | ||
* There is a :term:`User` named ``"toto"`` who belongs to the ``"anonymous_network_A"`` group registered on instance C | ||
* Instance A is registered as a :term:`Network Node` on instances B and C | ||
* when ``"toto"`` gets a personal network token from instance A and uses it to log in on instance B they log in as the | ||
the temporary ``"anonymous_network_A"`` user. | ||
* when ``"toto"`` gets a personal network token from instance A and uses it to log in on instance C they log in as the | ||
``"toto"`` user on instance C. | ||
Comment on lines
+536
to
+537
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What happens if user There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. They are logged in at the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ok. Will need to investigate more how conflicting user names are handled. Basically, we shouldn't assume that a name would necessarily be exactly the same on other Magpie instances. Preferably, alternative/remote Magpie instances should allow to "link" users of different names, similarly to how you can have 2 distinct user names on distinct social media platforms, but link accounts together. Retrieving the "resolved There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yeah I see what you mean. I'm feeling strongly from this review that we should be handling these remote users by storing them separately in another db table. That would resolve a lot of the issues that you raise here about conflicting names as well There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Remote users are now stored in a different table: |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,2 @@ | ||
0 * * * * /bin/bash -c "set -a ; source <($MAGPIE_ENV_DIR/*.env) ; set +a ; magpie_sync_resources" | ||
1 0 * * * /bin/bash -c "set -a ; source <($MAGPIE_ENV_DIR/*.env) ; set +a ; magpie_purge_expired_network_tokens" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If a valid user name (eg:
pavics
) was created on a node that hadMAGPIE_NETWORK_NAME_PREFIX=pavics
, another Magpie instance (eg:daccs
) using network mode will not be able to distinguish that userpavics
from that network node's anonymous user.Or maybe this is just an impression? But it looks like it could be possible to inject the "right values" to cause side effects.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If the
MAGPIE_NETWORK_NAME_PREFIX=pavics
then you shouldn't be able to create any new users whose name starts withpavics
. Even so, the anonymous user for thedaccs
node would bepavicsdaccs
(the prefix followed by the network name).Now, if you already had a user in the system named
pavicsdaccs
that could be a bit confusing but they should still be able to differentiate them because one would belong to thepavicsdaccs
group and the original user would not.If this is easier though, I'm happy to split these users out into different tables as you suggest (#589 (review)) if that will keep things cleaner.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, I think that would make it easier conceptually. The API endpoints however would still need to consider these conditions to allow user names or not. I think you mostly already did it with the regexes, but tests must be done to make sure it works everywhere (trying to purposely cause conflict, edge cases and such).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah I have some tests on the way but they're still in progress :)