Writing in the front

Django REST Framework full-text search combat

The DRF account system is Django admin login system, which needs to be combined with the admin form to use, so today we will talk about the IMPLEMENTATION of JWT based on DRF

The code in this article is developed based on the Django REST Framework (2)

Extension project

Json Web Token (JWT) is an open jSON-based standard (RFC 7519) implemented for the transfer of declarations between network application environments. The JWT declaration is generally used to pass authenticated user identity information between the identity provider and the service provider to obtain resources from the resource server, and to add some additional declaration information necessary for other business logic. The token can also be used directly for authentication or can be encrypted.

What is JWT?

JWT is an encrypted string consisting of three parts

  • Header Specifies the header type and encryption algorithm
  • The payload data field contains user-defined data, such as the author expiration time
  • The signature signature is calculated by header + Payload based on the encryption algorithm specified in the header to prevent tampering

Payload is also a JSON object. There are seven official fields for you to choose from.

Iss (Issuer) : exp (expiration time) : expiration time sub (subject) : aud (audience) : NBF (Not Before) : iAT (Issued At) : Issue time JTI (JWT ID) : numberCopy the code

The demo details are displayed

# jwt string
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.
eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.
SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

# HEADER:ALGORITHM & TOKEN TYPE
{
  "alg": "HS256"."typ": "JWT"
}

# PAYLOAD:DATA
{
  "sub": "1234567890"."name": "John Doe"."iat": 1516239022}# VERIFY SIGNATURE

HMACSHA256(
  base64UrlEncode(header) + "." +
  base64UrlEncode(payload),
) 

Copy the code

1. Install dependencies

pipenv install djangorestframework-jwt
Copy the code

2. Configure the project


# demo/settings.py

REST_FRAMEWORK = {
    #...
    'DEFAULT_AUTHENTICATION_CLASSES': (
        'rest_framework_jwt.authentication.JSONWebTokenAuthentication'.'rest_framework.authentication.SessionAuthentication'.'rest_framework.authentication.BasicAuthentication',),#...
}

# demo/urls.py

from rest_framework_jwt.views import obtain_jwt_token
#...

urlpatterns = [
    ' '.#...
    url(r'^jwt-token-verify/', verify_jwt_token),
    url(r'^api-token-auth/', obtain_jwt_token),
]
Copy the code

3. View the result

JWT login account


# 1. Test returns results
$ curl -X POST -H "Accept: application/json; indent=4"  -d "username=admin&password=admin" http://localhost:8000/jwt-token-auth/ 

{
    "token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoxLCJ1c2VybmFtZSI6ImFkbWluIiwiZXhwIjoxNjIzMDM5MDE5LCJlbWFpbCI6ImFkbW luQGFkbWluLmNvbSJ9.uAXhriWcnDrY6-JyeO1Wb8Un1X4tUE8Xb4pEBmtGJaI"
}

# 2. The parsed parameter is
# HEADER:ALGORITHM & TOKEN TYPE
{
  "typ": "JWT"."alg": "HS256"
}
# PAYLOAD:DATA

{
  "user_id": 1,
  "username": "admin"."exp": 1623036515,
  "email": "[email protected]"
}
# VERIFY SIGNATURE

HMACSHA256(
  base64UrlEncode(header) + "." +
  base64UrlEncode(payload)
)
Copy the code

Authentication token

$ curl --location --request POST 'http://localhost:8000/jwt-token-verify/' --header 'Content-Type: application/json; indent=4' --data-raw '{"token":"eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoxLCJ1c2VybmFtZSI6ImFkbWluIiwiZXhwIjoxNjIzMTMxNzM2LCJlbWFp bCI6ImFkbWluQGFkbWluLmNvbSJ9.NvcNYUIQhJGZFTr7dYftu_8uWgHBhSqw4t_3etF9AS8"}'

{"token":"eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoxLCJ1c2VybmFtZSI6ImFkbWluIiwiZXhwIjoxNjIzMTMxNzM2LCJlbWFpbCI6ImFkbW luQGFkbWluLmNvbSJ9.NvcNYUIQhJGZFTr7dYftu_8uWgHBhSqw4t_3etF9AS8"}
Copy the code

Request to carry JWT

$ curl -H  "Accept: application/json; indent=4" -H "Authorization: JWT eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoxLCJ1c2VybmFtZSI6ImFkbWluIiwiZXhwIjoxNjIzMDM5MDE5LCJlbWFpbCI6ImFkbWl uQGFkbWluLmNvbSJ9.uAXhriWcnDrY6-JyeO1Wb8Un1X4tUE8Xb4pEBmtGJaI"  http://localhost:8000/api/article/1/
{
    "id": 1,
    "creator": "admin"."tag": "Modern Poetry"."title": "如果"."content": "I'll never think of you again in this life, except in some night, when tears are wet with tears, if you will."
}

Copy the code

4. More configurations

# Settings. Py new
JWT_AUTH = {
    'JWT_EXPIRATION_DELTA': datetime.timedelta(hours=24),}Copy the code

See the documentation for more configurations and usage

  • Configure the encryption mode and use asymmetric encryption to configure public and private keys.
  • Custom token generation logic (useful when using user tables without Django)
  • · · · · · ·

conclusion

Advantages:

  1. JWT is not encrypted by default, but it can be encrypted. Once the original Token is generated, it can be encrypted again with the key.
  2. Secret data cannot be written to the JWT without encryption.
  3. JWT can be used not only for authentication, but also for information exchange. Using JWT effectively can reduce the number of times the server queries the database.

Disadvantages:

  1. Since the server does not store session state, it is not possible to revoke a token or change the permission of the token during use. That is, once a JWT is issued, it remains valid until expiration, unless the server deploys additional logic.
  2. The JWT itself contains authentication information, and if it is disclosed, anyone can gain full access to the token. To reduce theft, JWT expiration dates should be shorter. For some important permissions, the user should be authenticated again.
  3. To reduce theft, JWT should use HTTPS instead of HTTP.

To sum up, in the microservice system, the server does not need to record session information, all authentication is carried by the front-end JWT, and the back-end authenticates the JWT. In this way, not only session sharing problems can be avoided, but also cross-domain and CSRF problems can be effectively avoided.

The resources

  • REST framework JWT Auth
  • Jwt.io