Encryption algorithm implementation

Encryption algorithms
Encryption algorithms can be classified into three categories: hash algorithms, symmetric encryption algorithms, and asymmetric encryption algorithms

1. The DES algorithm is used for encryption and decryption; later people felt that DES was not safe enough and invented the 3DES algorithm; and the most popular symmetric encryption algorithm today is the AES algorithm.
The advantage of the symmetric algorithm is that the efficiency of encryption and decryption is relatively high. Correspondingly, the disadvantage of symmetric algorithms is that they are not secure enough.

2. The RSA algorithm is the most common asymmetric encryption algorithm. The obvious difference from symmetric encryption algorithms such as DES is that the keys used for encryption and decryption are different. Using the RSA algorithm,
as long as the key is long enough (generally requires 1024bit), the encrypted information cannot be cracked.

3. The information digest algorithm is also called encrypted hash algorithm. The encryption process does not require a key. Common encrypted hash algorithms include MD series and SHA series.
Strictly speaking, the hash algorithm is not an encryption algorithm, but it plays an important role in the field of information security. The most important role is to generate information summaries
to verify the integrity of the original information and the reliability of the source.

An ideal cryptographic hash function should have the following characteristics:
1. After any information is passed in, the output length is always fixed;
2. The message digest looks "random", so it is difficult to guess the value based on the original information;
3. The collision probability of a good hash function should be extremely low, that is, the probability of obtaining the same value after different information is passed in;

Solution: Do not directly store the original password in the database, but store the ciphertext of the password. The ciphertext is the result of performing a message digest calculation over the original text. It can be considered to use
the md5 algorithm provided by JDK for encryption processing, but due to the development of the collision algorithm, the result of direct encryption can be decrypted by the collision algorithm.

Solution: Introduce an encryption algorithm parameter – salt value, and perform multiple hash calculations to obtain encrypted fingerprint data, which can be
decrypted using the collision algorithm to a certain extent

JDK provides the implementation of md5 and sha-1 algorithms, here choose to use md5 for encryption

User tracking is a problem when front-end and back-end are developed separately or when multiple applications are deployed using horizontal scaling.
1. Rely on the proxy server Nginx to achieve
2. You can use spring session to rely on redis to achieve
3. Rely on the token authentication method to achieve

Token is an authentication method with higher scalability and security, which is very suitable for use in web applications and mobile development applications.

1. Token verification process
With token authentication, the server will not store user login records.
(1) The client uses the username and password to request login;
(2) The server receives the request and verifies the username and password;
(3) After the verification is successful, the server will issue a Token, and then send the Token to the client
(4) After receiving the Token, the client can store it, such as in a cookie or in Local Storage; (
5) Every time the client requests resources from the server, it needs to bring the Token issued by the server;
(6) The server receives the request, and then verifies the Token carried in the client request. If the verification is successful, it returns the requested data to the client.

Compared with the traditional session authentication method, the token authentication method saves server resources and is more friendly to mobile terminals and distribution. Its advantages are as follows:
1. Support cross-domain access: cookies cannot cross domains, and tokens do not use cookies (the premise is to put the token in the request header), so there will be no
information loss after crossing domains
. 2. No Status: The token mechanism does not need to store session information on the server, because the token itself contains information of all logged-in users, so it can reduce the pressure on the server
. Applicable to the mobile terminal: when the client is a non-browser platform, cookies are not supported, and the token authentication method will be much simpler at this time . CSRF, so there is no need to consider CSRF defense


2. JWT is json web token, which is an open standard rfc7519, which defines a compact and self-contained method for
securely transmitting information between parties as JSON objects. It is used as a token in web applications in JSON form, and is used to securely transfer information between parties as JSON objects. In the process of data transmission,
related processing such as data encryption and signature can also be completed.

The http protocol is stateless, so the authentication mechanism of sessionId or token is required, and the token authentication mechanism of jwt does not need to retain the user's authentication information
or session information on the server. This means that the application based on the jwt authentication mechanism does not need to consider which server the user is logged in, which facilitates the expansion of the application, and
jwt is more suitable for distributed applications

1. The front-end sends its user name and password to the back-end interface through the web form. This process is generally a POST request. The recommended method is to use SSL-encrypted
transmission (HTTPS) to avoid sensitive information from being sniffed.
2. After the backend checks the user name and password successfully, use the data containing user information as the JWT Payload, and base64 it and the JWT Header separately. Sign after encoding and splicing
to form a JWT Token. The formed JWT Token is a string like lll.zzz.xxx.
3. The backend returns the JWT Token string to the frontend as the result of successful login. The front end can save the returned result in the browser, and delete the saved
JWT Token
when logging out. 4. The front end puts the JWT Token into the Authorization attribute in the HTTP request header for each request (solves XSS and XSRF problems)
5. The back-end checks the JWT Token passed from the front-end to verify its validity, such as checking whether the signature is correct, whether it has expired, whether the recipient of the token is yourself, etc. 6. After the verification is passed, the back-end parses out the user contained in the JWT
Token Information, perform other logical operations (generally obtain permissions based on user information, etc.), and return the result

The advantages of JWT are:
1. Conciseness: JWT Token has small data volume and fast transmission speed
2. Because JWT Token is stored on the client in JSON encrypted form, so JWT is cross-language. In principle, any web form supports
3 , There is no need to save session information on the server side, that is to say, it does not depend on cookies and sessions, so there is no disadvantage of traditional session authentication, especially suitable for
distributed microservices
4. Single sign-on friendly: If you use Session for identity authentication, due to Cookies cannot cross domains, making it difficult to implement single sign-on. However, if token is used for authentication
, token can be stored in memory anywhere on the client, not necessarily a cookie, so it does not depend on cookie, and these problems will not exist
. It is necessary to save a piece of information on the server side, and this method will rely on cookies (requires
cookies to save SessionId), so it is not suitable for mobile terminals

3. The components of jwt The
standard jwt token is divided into three parts, namely Header, payload, signature; used in the token string to split

3.1. Header
consists of two points: parameter type jwt, signature algorithm hs256

3.2.
The composition of Payload is some information of the login user, token issuance and expiration time, etc.; some of these contents are standard fields, and you can also add other required contents.
iss: Issuer, issuer
sub: Subject, subject
aud: Audience, audience
exp: Expiration time, expiration time
nbf: Not before
iat: Issued at, issue time
jti: JWT ID
Finally it will also be encoded by Base64 encryption

5. Signature
is composed of 3 parts. First, the header and payload are encoded with Base64, and then encrypted with an encryption algorithm. When encrypting, a Secret should be put in. This is equivalent to a password, which is secretly stored
on the server.

The secret is the salt added during the last second encryption, which is regarded as a secret key (only kept on the server) and not disclosed to the outside.

The role of each part of JWT, after the server receives the JWT token sent by the client: the
header and payload can directly use base64 to decode the original text, obtain the hash signature algorithm from the header, and obtain valid data from the payload.
The signature cannot decode the original text due to the use of an irreversible encryption algorithm. Its function is to verify whether the token has been tampered with. After the server obtains the encryption algorithm in the header
, it uses the algorithm plus the secretKey to encrypt the header and payload, and compares whether the encrypted data is consistent with the one sent by the client
. Note that the secretKey can only be saved on the server, and its meaning is different for different encryption algorithms. Generally, for the MD5 type digest encryption algorithm,
the secretKey actually represents the salt value

// Specify the token expiration time as 10 seconds
Calendar calendar = Calendar.getInstance();
calendar.add(Calendar.SECOND, 10);

    String token = JWT.create()
            .withHeader(new HashMap<>())  // Header
            .withClaim("userId", 21)  // Payload
            .withClaim("userName", "baobao")
            .withExpiresAt(calendar.getTime())  // 过期时间
            .sign(Algorithm.HMAC256("!34ADAS"));  // 签名用的secret

    System.out.println(token);

Parsing JWT string
// Create parsing object, use the same algorithm and secret as when creating token
JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256(“!34ADAS”)).build();
// Parse the specified token
DecodedJWT decodedJWT = jwtVerifier.verify(“eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyTmFtZSI6ImJhb2JhbyIsImV4cCI6MTU5OTkyMjUyOCwidXNlcklkIjoyMX0.YhA3kh9 KZOAb7om1C7o3vBhYp0f61mhQWWOoCrrhqvo”);
// Obtain the payload information in the parsed token
Claim userId = decodedJWT.getClaim(“userId”);
Claim userName = decodedJWT.getClaim(“userName”) ;
System.out.println(userId.asInt());
System.out.println(userName.asString());
// output timeout
System.out.println(decodedJWT.getExpiresAt());

In the actual SpringBoot project, the general login process:
1. After the login verification is passed, a corresponding random token is generated for the user (note that this token does not refer to jwt, which can be generated using algorithms such as uuid), and then this token is used as part of the
key , the user information is stored in Redis as a value, and the expiration time is set. This expiration time is the time when the login becomes invalid.
2. Use the random token generated in step 1 as the JWT payload to generate a JWT string and return it to the front end.
3. Every time after the front end All requests carry the JWT string in the Authorization field in the request header.
4. The backend defines an interceptor. Every time a front-end request is received, the JWT string is first taken out of the Authorization field in the request header and verified. After passing, analyze
the random token in the payload, and then use this random token to get the key, and get the user information from Redis. If it can be obtained, it means that the user has logged in

Development process:
1. Rely on Java-jwt
2. Define tool class
// Generate jwt token
JWTCreator.Builder builder = JWT.create(); // Create an object for generating jwt token
builder.withClaim("username", "yanjun ”); //Add payload, use the data passed by token
Date nowDate = new Date();
Date expireDate = new Date(nowDate.getTime() + 10 * 1000);
builder.withExpiresAt(expireDate); //Expiration time , Expired after 10s
String token=builder.sign(Algorithm.HMAC256("zhangsan")); //The specified algorithm is used to generate the corresponding signature, and the parameter is the salt value used when generating the signature System.out.println
(token) ;

//获取token中传递的数据
String token="eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE2NzUxNTc0OTksInVzZXJuYW1lIjoieWFuanVuIn0.cGjegObynlTwixTQNetYSIu1yFjSrjgVfSQNFBKV3vg";
    JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256("zhangsan")).build();
    //会针对token进行验证,如果过期或者签名出错则报异常
    DecodedJWT verify = jwtVerifier.verify(token);

    System.out.println(verify.getHeader());
    System.out.println(verify.getToken());
    System.out.println(verify.getPayload());
    System.out.println(verify.getSignature());

    //从payload中获取传递的数据
    String username = verify.getClaim("username").asString();
    System.out.println(username);
}

Guess you like

Origin blog.csdn.net/qq_39756007/article/details/128817878