# M2M authorization

M2M authorization is authorization between applications without user participation. When you want to partially open your business API to others, such as your outsourcer, the outsourcer needs to perform M2M authorization before you can access your business API. Suppose your company wants to develop a large-screen display of some data, and several outsourcers participate in it. You want to authorize certain non-core data API access rights to outsourcers, and let the outsourcers complete this part of the non-core development. At this time, M2M authorization is required, because no user is required to participate in this process, we only need to determine which outsourcer the visitor is and what interface access rights he has.

# Authority Management and Assignment

Create an application in Authing called "Big Screen Display".

Define some resources under the "big screen display" application, and each resource corresponds to the actual resource in the "big screen display" application. Here we add some resources, including user-growth, customer, announcement, and revenue. The name of these resources is API scope.

After defining the resources and operations, add a programming access account to the application. The programming access account is the caller of the current application API interface. Programming access account has a pair of AK and SK, which are used by the outsourcer to call the "big screen display" application interface. We can hand over AK and SK with different permissions to different outsourcers, so that they have different permissions and can access different APIs.

Create two programming access accounts, fill in the AccessToken expiration time and remarks, and click OK.

If the program access account is deleted, the caller will lose the ability to obtain user authorization.

# AccessToken expiration time

When you create a programmatic access account, you need to specify the AccessToken expiration time. Authing uses the RS256 signature algorithm to sign when issuing the AccessToken to ensure that the AccessToken will not be tampered with.

Token signature is a part of JWT. For more information, please refer to JWT Interpretation and Use.

-RS256 is an asymmetric signature algorithm. Authing holds the private key to sign the Token, and consumers of JWT use the public key to verify the signature. The RS256 signature algorithm has the following benefits:

  1. Anyone can use the application public key to verify the signature, and the signer must be Authing.
  2. There is no risk of private key leakage. If you use HS256 but leak the application key, you need to refresh the key and redeploy all APIs.

For more details on signature issues, please refer to Verify Token.

We have just created two programming access accounts, which will need to be handed over to outsourcers in the future.

Next we need to give them resource permissions. On the Resource Authorization tab, click Add.

For the authorized subject type, select Programming Access Account, and then select the programming access account of A Outsourcing Company.

In authorization rules, resource type select announcement information, resource identifier fill in * to authorize all announcement resources, select specific operation for operation, and then select announce:read operation . Finally click OK. The function of this rule is to authorize the read permission of all announcement information resources to A outsourcing company.

Next, we add authorization for outsourcer B, first select the program access account of outsourcer B.

Next, we want to add three rules:

  1. Authorize all operation rights of user growth data in 2019 to outsourcer B. Click Add Authorization Rule at the top right to add multiple rules.

  2. Authorize the creation, reading, and modification permissions of all revenue records to outsourcer B.

  3. Authorize the read permission of all customer records to outsourcer B.

At this point, the administrator's rights management operations are all over. Let's follow the best practices of M2M authorization from the perspective of the caller and the resource.

# Obtain a permissioned AccessToken

OIDC authorization framework provides many authorization modes. In this scenario, obtaining the user's growth information belongs to M2M (machine-to-machine) authorization. Without the user's participation, the caller uses his own identity to access the API interface of the resource server. The **OIDC ClientCredentials mode is required here. **.

Through the OIDC ClientCredentials authorization mode, the caller needs to provide Authing with his ClientCredentials (that is, the Key and Secret of the programming access account) and the requested permission scope (that is, the resource identifier) to directly obtain An AccessToken with the API permissions.

  1. The caller sends the Key and Secret of the programming access account and the scope required to be requested to Authing.
  2. Authing verifies the Key and Secret of the programming access account, and verifies the scope permission items according to the permission rules configured by the administrator, and issues an AccessToken with resource permission, and the denied permission scope **no ** will appear in AccessToken.
  3. The caller carries the AccessToken to access the resource server.

In order to be able to access the protected API interface, the caller must first obtain a permissioned AccessToken. To do this, the caller needs to send a POST request to the following address.

Request Url:https://{应用域名}.authing.cn/oidc/token

Parameters:

Parameter name description
grant_type Fill in client_credentials.
client_id Programmatic access account key.
client_secret Programmatically access account Secret.
scope The requested permission items, the format of each permission item is resource identifier: operation separated by spaces.

Response result:

{
  "access_token": "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IjF6aXlIVG15M184MDRDOU1jUENHVERmYWJCNThBNENlZG9Wa3VweXdVeU0ifQ.eyJqdGkiOiJ2S1ZGV3FKemltTm5MSTlYZy0zam0iLCJpYXQiOjE2MTI1MDA2OTgsImV4cCI6MTYxMjUwNDI5OCwic2NvcGUiOiJib29rIiwiaXNzIjoiaHR0cHM6Ly9zdGVhbS10YWxrLmF1dGhpbmcuY24vb2lkYyIsImF1ZCI6IjYwMWJmMzVhY2E1ZDM4NzVjNDY3NDgyYyIsImF6cCI6IjYwMTkzYzYxMGY5MTE3ZTdjYjA0OTE1OSJ9.DS0l6zdlr_bGLqmDQRxvHUL4fmyLS5je6bqUCSSo06OIWSfcDZMZAqH5aYXP7Hzm4SiT6sfOCP_IiPSOxJPgFPYAmQTPSvJ5e6zs9jNeZyep_O6NWjlOGbDirskZE1pSZO_16ceiFr3jprSp13ff6O6Fa9YkY-8b_L3ouDqKhtb_4051pWZif-VzgXSkmvflTmqauJul9b5PzaeGWL-PKOrHrUiHjJwf9wqtR-3C8voFmi9pmxrUJYGSJoxwcxxSEceUY3d9oJU3v7e6FOnT_EMxfQCrAgzXR21bOitsAutOVXg1N9H0QJiNBESorCcj6yi1fVePTeDI5nY6xj9oDw",
  "expires_in": 3600,
  "token_type": "Bearer",
  "scope": "book",
  "rejected_scope": "message table"
}

Sample code:

const axios = require('axios').default;
const options = {
   method:'POST',
   url:'https://{application domain name}.authing.cn/oidc/token',
   headers: {'content-type':'application/x-www-form-urlencoded' },
   data: {
     grant_type:'client_credentials',
     client_id:'{Programming access account Key}',
     client_secret:'{Programming access account Secret}',
     scope:'{Permission items, separated by spaces}',
   },
};

axios
  .request(options)
  .then(function(response) {
    console.log(response.data);
  })
  .catch(function(error) {
    console.error(error);
  });

We only authorize outsourcing company A to read the announcement information. If outsourcing company A requests authorization, it carries other scopes, for example: announce:read announce:update revenue:read customer user-growth:read. Authing will deny all permissions except announce:read. The following is the result returned when outsourcing company A requests authorization. The denied permissions are in rejected_scope.

The AccessToken information contains the permission scope:

Let's look at the authorization of outsourcer B. If outsourcer B wants to request the following scope: user-growth:2020:read user-growth:2019:* user-growth:2019:read revenue:create revenue:*:read customer:read

The result of Authing is as follows:

It should be noted that the administrator only authorized all permissions for the user growth data in 2019 to the B outsourcing company, so when requesting the scope of the user growth data in 2020, it was rejected.

# Scope permission item specification

Authing's scope permission items are separated by spaces, and the format of each item is resource identifier: resource operation.

The following are all scope formats supported by Authing:

book:1:read means the read permission of the book resource numbered 1

book:*:read means the read permission of all book resources

book:read means the read permission of all book resources

book:*:* means all operation permissions for all book resources

book:* means all operation permissions for all book resources

book means all operation permissions for all book resources

*:*:* means all operation permissions for all resources

*:* means all operation permissions for all resources

* means all operation permissions for all resources

# Add API authentication interceptor

After Authing defines the API, you need to add an API authentication interceptor to your actual business API interface. For protected resources, only visitors who carry a legal AccessToken and have the required permissions are allowed. The code example is as follows:

var express = require('express');
var app = express();
var jwt = require('express-jwt');
var jwks = require('jwks-rsa');
var port = process.env.PORT || 8080;
var jwtCheck = jwt({
  secret: jwks.expressJwtSecret({
    cache: true,
    rateLimit: true,
    jwksRequestsPerMinute: 5,
    jwksUri:'https://{application domain name}.authing.cn/oidc/.well-known/jwks.json',
  }),
  audience:'{Programming access account ID}',
  issuer:'https://{application domain name}.authing.cn/oidc',
  algorithms: ['RS256'],
});
// Verify the legitimacy of AccessToken
app.use(jwtCheck);

app.post('/article', function(req, res) {
  // Verify that AccessToken has the required permissions
  if (!req.user.scope.split('').incldues('write:article')) {
    return res.status(401).json({ code: 401, message:'Unauthorized' });
  }
  res.send('Secured Resource');
});

app.listen(port);

Please refer to Verify Token for other content about Token verification.