Skip to content
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

Create a mechanism for the listener to pass system-level data to the authenticator #199

Closed
paulhowardarm opened this issue Jul 8, 2020 · 2 comments
Labels
enhancement New feature or request

Comments

@paulhowardarm
Copy link
Collaborator

Summary

Create a mechanism where the front-end listener can pass implementation-specific metadata alongside the request so that the authenticator can use it as an additional source of validation.

Rationale

At the moment, the authenticator only has one source of input: namely the authentication header bytes that are read from the request. But there are situations where other pieces of data can be obtained from the environment to help with the authentication and validation process. One example of this is peer metadata when unix domain socket is used as the transport. Unix domain sockets allow any incoming connection to be queried for peer metadata, which is a triplet value combining the user ID (UID), group ID (GID) and process ID (PID) of the peer process that is connecting. This information is sourced from the OS, and hence is trusted insofar as the OS is trusted. If this kind of information was made available to the authenticator, then it would allow for the caller's identity to be verified purely by the OS, without the need to resort to an external identity provider service. This mechanism would only be valuable in certain use cases. For example, if the transport is not based on domain sockets, then it clearly doesn't work. It clearly also doesn't work if the UID/GID/PID triplet does not adequately differentiate between client workloads. However, there could be an important class of deployment where these constraints and conventions are followed. In these deployments, an ability to use the peer metadata would represent a significant simplification relative to the complexity of an identity provider.

Details

TBD - requires some design. There will have to be an abstraction in place for the metadata, and a suitable means of passing it from the Listener to the FrontEndHandler and subsequently the Authenticator. This could be done as either a "push" (where the listener populates the data in advance), or a "pull" (where the listener gets the data on request). One thing to make sure of is that we need to treat the metadata itself as opaque. It happens to be a triplet of UID/GID/PID values in the case of domain sockets, but we can't rule out other packets of metadata that might be quite different. Several different designs are possible, but the important thing is that a specific listener such as the DomainSocketListener would be able to populate the metadata by making the appropriate method to get the peer credentials. (One wrinkle in the story is that the standard Rust UnixListener doesn't seem to have a method to get the peer cred, so we may also have to investigate other UDS support crates).

It will be important to maintain the design principles of Parsec, one of which is that it does not prescribe any specific transport for the wire protocol. Unix domain socket is just one possible transport. So it will be important to design this with suitable abstractions to maintain this loose coupling. Some types of transport might have no concept of metadata whatsoever, or might support types of metadata wholly different from the UID/GID/PID triple.

Definition of Done

This request is just to introduce the mechanism for passing data from the transport to the authenticator. Provided that an appropriate design is in place, perhaps covered with some unit tests to show the mechanism in principle, then we can consider this to be done. In particular, this request is not to produce a UID-based authenticator - that would be a separate issue, but with a dependency on this one.

@paulhowardarm paulhowardarm added the enhancement New feature or request label Jul 8, 2020
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 23, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an enum instance that captures metadata about the
  connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 24, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an optional enum instance that captures metadata about
  the connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 24, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an optional enum instance that captures metadata about
  the connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 24, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an optional enum instance that captures metadata about
  the connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 24, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an optional enum instance that captures metadata about
  the connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
joechrisellis pushed a commit to joechrisellis/parsec that referenced this issue Jul 24, 2020
This commit is in response to issue parallaxsecond#199. Here, we introduce a
`Connection` struct which currently contains two things:

* `stream` -- an object representing the communication stream between
  client and service.
* `metadata` -- an optional enum instance that captures metadata about
  the connection.

This abstraction allows us to carry more information forwards toward the
frontend/authenticator/... .

Specifically, this abstraction was created with UNIX domain sockets in
mind (but the usefulness is not limited here). UNIX domain sockets allow
incoming connections to be queried for peer metadata, which is a triple
(uid, gid, pid) of the peer process that is connecting. Under certain
configurations, this can be used for authentication.

This commit places us in a position of being able to use said metadata
for authentication if needed.

Signed-off-by: Joe Ellis <[email protected]>
@joechrisellis
Copy link
Contributor

Pull request merged so I think this can be closed now. 🙂

@hug-dev
Copy link
Member

hug-dev commented Aug 6, 2020

Thanks @joechrisellis !

@hug-dev hug-dev closed this as completed Aug 6, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

3 participants