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

Enhance createapplication command to display autogenerated secret #1152

Merged
merged 4 commits into from
May 7, 2022
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [unreleased]

### Changed
* `createpplication` management command enhanced to display an auto-generated secret before it gets hashed.
n2ygk marked this conversation as resolved.
Show resolved Hide resolved

## [2.0.0] 2022-04-24

This is a major release with **BREAKING** changes. Please make sure to review these changes before upgrading:
Expand Down
45 changes: 37 additions & 8 deletions docs/management_commands.rst
Original file line number Diff line number Diff line change
Expand Up @@ -34,28 +34,57 @@ The ``createapplication`` management command provides a shortcut to create a new

.. code-block:: sh

usage: manage.py createapplication [-h] [--client-id CLIENT_ID] [--user USER] [--redirect-uris REDIRECT_URIS]
[--client-secret CLIENT_SECRET] [--name NAME] [--skip-authorization] [--version] [-v {0,1,2,3}]
[--settings SETTINGS] [--pythonpath PYTHONPATH] [--traceback] [--no-color] [--force-color]
usage: manage.py createapplication [-h] [--client-id CLIENT_ID] [--user USER]
[--redirect-uris REDIRECT_URIS]
[--client-secret CLIENT_SECRET]
[--name NAME] [--skip-authorization]
[--algorithm ALGORITHM] [--version]
[-v {0,1,2,3}] [--settings SETTINGS]
[--pythonpath PYTHONPATH] [--traceback]
[--no-color] [--force-color]
[--skip-checks]
client_type authorization_grant_type

Shortcut to create a new application in a programmatic way

positional arguments:
client_type The client type, can be confidential or public
client_type The client type, one of: confidential, public
authorization_grant_type
The type of authorization grant to be used
The type of authorization grant to be used, one of:
authorization-code, implicit, password, client-
credentials, openid-hybrid

optional arguments:
-h, --help show this help message and exit
--client-id CLIENT_ID
The ID of the new application
--user USER The user the application belongs to
--redirect-uris REDIRECT_URIS
The redirect URIs, this must be a space separated string e.g 'URI1 URI2'
The redirect URIs, this must be a space separated
string e.g 'URI1 URI2'
--client-secret CLIENT_SECRET
The secret for this application
--name NAME The name this application
--skip-authorization The ID of the new application
...
--skip-authorization If set, completely bypass the authorization form, even
on the first use of the application
--algorithm ALGORITHM
The OIDC token signing algorithm for this application,
one of: RS256, HS256
--version Show program's version number and exit.
-v {0,1,2,3}, --verbosity {0,1,2,3}
Verbosity level; 0=minimal output, 1=normal output,
2=verbose output, 3=very verbose output
--settings SETTINGS The Python path to a settings module, e.g.
"myproject.settings.main". If this isn't provided, the
DJANGO_SETTINGS_MODULE environment variable will be
used.
--pythonpath PYTHONPATH
A directory to add to the Python path, e.g.
"/home/djangoprojects/myproject".
--traceback Raise on CommandError exceptions.
--no-color Don't colorize the command output.
--force-color Force colorization of the command output.
--skip-checks Skip system checks.

If you let `createapplication` auto-generate the secret then it displays the value before hashing it.

19 changes: 15 additions & 4 deletions oauth2_provider/management/commands/createapplication.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,13 @@ def add_arguments(self, parser):
parser.add_argument(
"client_type",
type=str,
help="The client type, can be confidential or public",
help="The client type, one of: %s" % ", ".join([ctype[0] for ctype in Application.CLIENT_TYPES]),
)
parser.add_argument(
"authorization_grant_type",
type=str,
help="The type of authorization grant to be used",
help="The type of authorization grant to be used, one of: %s"
% ", ".join([gtype[0] for gtype in Application.GRANT_TYPES]),
)
parser.add_argument(
"--client-id",
Expand Down Expand Up @@ -54,7 +55,8 @@ def add_arguments(self, parser):
parser.add_argument(
"--algorithm",
type=str,
help="The OIDC token signing algorithm for this application (e.g., 'RS256' or 'HS256')",
help="The OIDC token signing algorithm for this application, one of: %s"
% ", ".join([atype[0] for atype in Application.ALGORITHM_TYPES if atype[0]]),
)

def handle(self, *args, **options):
Expand Down Expand Up @@ -82,5 +84,14 @@ def handle(self, *args, **options):
)
self.stdout.write(self.style.ERROR("Please correct the following errors:\n %s" % errors))
else:
cleartext_secret = new_application.client_secret
new_application.save()
self.stdout.write(self.style.SUCCESS("New application created successfully"))
# Display the newly-created client_name or id.
client_name_or_id = application_data.get("name", new_application.client_id)
self.stdout.write(
self.style.SUCCESS("New application %s created successfully." % client_name_or_id)
)
# Print out the cleartext client_secret if it was autogenerated.
if "client_secret" not in application_data:
self.stdout.write(self.style.SUCCESS("client_secret: %s" % cleartext_secret))
self.stdout.write(self.style.WARNING(Application.client_secret.field.help_text))
2 changes: 1 addition & 1 deletion tests/test_commands.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ def test_command_creates_application(self):
stdout=output,
)
self.assertEqual(Application.objects.count(), 1)
self.assertIn("New application created successfully", output.getvalue())
self.assertIn("created successfully", output.getvalue())

def test_missing_required_args(self):
self.assertEqual(Application.objects.count(), 0)
Expand Down