A package for creating a client credentials oAuth2.0 workflow.
Project description
Welcome to Steelcut-OAuth
A tool written in Python 3.13 to implement OAuth2.0 using the client credentials grant type. This is intended for machine to machine APIs and integrates with a PostgreSQL server for storing client ids and hashed/salted client secrets. Please see requirements.txt for the full list of dependencies.
Installation
Prior to installing this Python package, PostgreSQL must be installed on the target machine. This README is focused on Linux; however, with appropriate adjustments the program should run on Windows and Mac OS as well.
Install PostgreSQL:
sudo apt install postgresql
Install all psycopg build prerequistes including libpq and python3-dev.
PostgreSQL will create a postgres superuser by default. We recommend creating two new users: one user that creates a table for storing client ids and hashed/salted client secrets and one user that has "SELECT" only rights to the table. This can be created as follows:
-
sudo -sto switch to root. -
su - postgresto switch to postgres super user. -
psqlto launch the postgreSQL cli. -
CREATE USER your_admin_username WITH PASSWORD 'your_password';For the admin that will create and maintain the database of client ids and secrets we suggest a user name that is meaningful to the specific user and a strong password.
-
CREATE USER your_viewer_username WITH PASSWORD 'your_password';For the viewer that will have "SELECT" only privileges, we suggest "auth_client" for the user name and a strong password.
Create the database that will store the credentials. We suggest using 'clientdb'.
-
CREATE DATABASE clientdb; -
exitto exit the psql cli. -
su - your-admin-usernameto switch to admin user and use the strong password that was created for this admin.Create the table to store client credentials. We suggest "stored_tokens".
-
CREATE TABLE stored_tokens; -
GRANT SELECT ON stored_tokens TO auth_client;to allow the viewer user access to view the contents of the table.
After all the prerequisites have been met, you can install the package:
pip install steelcut-oauth
Program Structure
The oauth_client package contains three (3) critical components for enabling OAuth.
-
Client creation using client ids and client secrets.
-
An Authorization server that checks that a client is allowed access to the protected resource and grants a json web token (jwt).
-
A Protected Resource Server that verifies that the token is valid and responds with a protected json file.
For more details, click this link for the full OAuth2.0 Specification
Example Usage
The following examples demonstrate some of the basic capabilities. Please note that it is up to the user to ensure that they maintain good separation of resources. For instance, the Authorization server and Resource server should not reside on the same server. Similarly, the client data should not reside with the resource server.
Create the OAuth Class
from oauth_client import OAuth, client_request_token, client_request_resource
oauth = OAuth(db_name='clientdb',
db_host='127.0.0.1',
db_table_name='stored_tokens',
db_create_table=False,
resource_owner_username='admin',
jwt_issuer='admin',
jwt_audience='client',
jwt_subject='client')
Create a Signature
This creates assymetric public and private key pairs for the admin. The signature is required for the admin to sign jwt tokens and is stored in a keyring. The private key and public key are both required to sign the jwt; however, only the public key is used to validate that the jwt is authentic. The signature should be stored on the authorization server.
oauth.create_signature()
Create a New Authorized Client
Note The client secret will be printed locally to the terminal. It will not be retrievable again after. All of the client ids and secrets are for demonstration purposes only. Please do not ever share or store client secrets in plain text.
oauth.add_client(client_name='Jane Doe',
grant_type='client_credentials',
resource='api_v0.0.1')
# this will print the following to the console:
# {
# "grant_type": "client_credentials",
# "client_id": "0083c1b7e3a6ceeac4a4f47bd3a1b501",
# "client_secret": "PRIVATE-qGSUlXIyQVFB_xfPnHOy6WWGMER5uCgZyaKWgJw-ggQ"
# "resource": "api_v0.0.1"
# }
Make Changes to an Existing Client
Client grant type and resource can be modified in the database. In addition, a new client secret can be generated if new_client_secret is set to True.
oauth.update_client(client_id='0083c1b7e3a6ceeac4a4f47bd3a1b501',
grant_type='another grant type',
resource='another resource',
new_client_secret=True)
Run the Authorization Server
The authorization server is a Flask server configured with a "/token" route.
app = oauth.auth_server()
app.run(debug=True)
The run method of app is appropriate for testing locally. In production, please use a WSGI production server such as Gunicorn
Request a Token
The Authorization server must be running to request a token.
token = client_request_token('client_credentials',
'0083c1b7e3a6ceeac4a4f47bd3a1b501',
'PRIVATE-qGSUlXIyQVFB_xfPnHOy6WWGMER5uCgZyaKWgJw-ggQ',
'api_v0.0.1',
'http://127.0.0.1:5001/token')
Run the Resource Server
The resource server is a Flask server. The user can specify two parameters:
- The default api route ('api_v0.0.1' in the example below).
- The path and filename of the protected resource. Note the protected resource must be a json file.
- As with the Authorization server, the run method is appropriate for local testing but a production WSGI server should be used in production.
app = oauth.resource_server('api_v0.0.1','protected_resource.json')
app.run(debug=True, port=5001)
Request Protected Resource
The Resource Server must be running to request the protected resource. Note The route /api_v0.0.1 is the same route specified when starting the Resource Server.
# This uses the token variable from the initial token request.
client_request_resource('http://127.0.0.1:5001/api_v0.0.1',token)
# returns the protected resource as a json string.
# {"about": "This is a protected resource"}
Future Efforts
Add targeted error handling classes to improve user experience.
License
MIT
Authors
John Glauber
Contact
For any questions, comments, or suggestions please reach out via email to:
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file steelcut_oauth-0.0.1.tar.gz.
File metadata
- Download URL: steelcut_oauth-0.0.1.tar.gz
- Upload date:
- Size: 20.8 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f8ae5fbae3ebe7e36414b7dd566676c0ec3baa8600f89dd6e3ae9388dd3492a5
|
|
| MD5 |
401222a294e15b090e4b98b18eb8f955
|
|
| BLAKE2b-256 |
bc0d8b6a5405dddffc1a74e4a0af49b162c6b16cdbe8d4ddac604747e576e468
|
File details
Details for the file steelcut_oauth-0.0.1-py3-none-any.whl.
File metadata
- Download URL: steelcut_oauth-0.0.1-py3-none-any.whl
- Upload date:
- Size: 21.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.13.2
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c8c281ea94dcfab0f28faded9ccb8b0af46fe0399b82cf32e68ea49bd8dff767
|
|
| MD5 |
864bfa5a67fccbff204cc10bce55c37a
|
|
| BLAKE2b-256 |
85f4341620efa3eeeecdc499712b6088a79818732d701856811cb7b34c4d3c55
|