The ISPyB authenticator provides the Fragalysis Stack with a centralised service that can be utilised by any number of stacks, and yields Target Access Strings based on User. The authenticator is designed to replace the stack's internal security module that is partly responsible for caching the regular SSH and MySQL ISPyB database access mechanism that restricts user access to objects in the stack based on their membership of Proposals and Visits.
By providing an abstraction of the original security logic in an independent Pod (and Service) an administrator can replace it with another with its own implementation. For example, when testing you could replace the official ISPyB service with a custom or mock implementation that provides a well-known set of responses for your users. In this way you can develop code and not have to rely on access to the true source of target access strings.
Any service implementation can be deployed, this one provides remote (SSH) access to ISPyB using a container image based on Python and FastAPI.
The stack's contract with the TA authenticator requires the following endpoints from any implementation of the authenticator: -
That returns a 200 response with the following properties: -
{
"version": "1.0.0",
"kind": "ISPYB",
"name": "XChem Python FastAPI TAS Authenticator"
}
The stack can use the response as it sees fit, but it might want to display the response in the UI.
A stack requests Target Access Strings from the authenticator based on URL-encoded usernames, and the authenticator returns a count and an array of those the user is entitled to access.
The response should be a 200 and a 4XX for errors: -
{
"count": 2,
"target_access": [ "lb00000-1", "lb000001-1" ]
}
For a query to be successful the client must provide a
X_TAAQueryKey
header value that matches theTAA_QUERY_KEY
environment value supplied to the image. This proves a crude but effective protection mechanism that prevents queries from clients that have not been supplied with the query key.
{
"ping": "OK"
}
It returns a 200 response with a ping
string property that is OK
if the
authenticator is able to connect to the underlying (ISPyB) service. The string
is not OK
if there are problems.
A number of debug tools are shipped with the image. If you can shell into the corresponding container you can run them from the command line. The authenticator is typically deployed in a kubernetes Pod as a container called ta-authenticator, co-located with a memcached container (in the same Pod).
To display detailed "global" stats for the authentication container you can run: -
./stats.py
You can display (but not get) the cached target-access strings
for a given user (along with the cache collection time and age)
by providing a username to the tas.py
utility: -
./tas.py abc12345
You can clear individual user records with clear.py
.
This simply clears the cache, forcing a new collection of
values at the next opportunity: -
./clear.py abc12345
`get.py uses the local API to simulate a stack query which will refresh the cache if it required while also printing the results; -
./get.py 'dave lister'
'{"count":3,"target_access":["aa00000-1","aa00000-254","aa00000-2"]}'
The project uses: -
- pre-commit to enforce linting of files prior to committing them to the upstream repository
- Commitizen to enforce a Conventional Commit commit message format
- Black as a code formatter
- Poetry as a package manager (for the b/e)
You MUST comply with these choices in order to contribute to the project.
To get started review the pre-commit utility and the conventional commit style and then set-up your local clone by following the Installation and Quick Start sections: -
poetry shell
poetry install --with dev
pre-commit install -t commit-msg -t pre-commit
Now the project's rules will run on every commit, and you can check the current health of your clone with: -
pre-commit run --all-files
There's a docker-compose.yml
file to deploy the authenticator and memcached.
It also relies on environment variables that you can easily set using a .env
file
(which is excluded from any repository commits).
Build and launch the code using the docker compose
file: -
docker compose up --build --detach
We rely on docker compose extend
capability to use a base-services.yml
compose file
that is then "sepcialised" by either a docker-compose.yml
or
docker-compose-private-key.yml
. The former uses SSH passwords, the latter a
private key file. So, if you want to use a private key file for SSH connections
(and have a ~/.ssh/fragalysis-stack
key-file) run: -
docker compose --file docker-compose-private-key.yml up --build --detach
In order to use the target access endpoint, which relies on a pre-shared key for
authentication, you will need to provide the key that is set in the docker compose file
via the request header X-TAAQueryKey
(this is set to blob1234
)
With the containers running you should be able to query
target access results for a user with httpie
. Here we query user abc
(whose name has to be url encoded): -
http localhost:8080/target-access/abc 'x-taaquerykey:blob1234'
To get some test results, if you've set the TAA_ENABLE_DAVE_LISTER
environment
variable to yes
, you can get some realistic test results with that username.
This is not a real user, it is simply one that the authentication "simulates" with
a fixed set of target access strings: -
http localhost:8080/target-access/dave%20lister 'x-taaquerykey:blob1234'
You can execute the ping and version endpoints too...
http localhost:8080/ping/
http localhost:8080/version/
You can terminate the local installation with: -
docker compose down
We have also developed a "mock" authenticator that "looks and feels" like the real thing. It offers the same API, can run locally, and is configured using text files that list users and their target-access strings. It does not need an ISPyB service but behaves as though it has one.
See: -