Using Access Control Services

Creating Attributes for Resources and Subjects

Use the Attribute Management service to define subject and resource attributes for access-control policies.

Before You Begin

To use the Attribute Management service, the user/client must authenticate using a JSON Web Token (JWT) that includes the acs.attributes.read, acs.attributes.write and predix-acs.zones.<acs_instance_guid>.user scopes.

You must specify the Predix-Zone-Id header when you use this REST API to communicate with a deployed application about its environment.. For more information, see acs-getting-started.html#task_a2375607-175a-40bc-b53b-2133c16473ad.

Select a REST client (such as Postman) that can execute API requests for the Attribute Management service. For more information about this API, see the API Documentation (Predix.io home page – Documentation – Service APIs).

About This Task

Predix administrators define attributes about users and resources to evaluate conditions for authentication and authorization in access control policies.

Creating Attributes for a Resource
An administrator creates attributes for a resource based on the following API request.
HTTP PUT
https://<acs_url>/v1/resource/{resourceIdentifier}

The HTTP request body can have the following elements:

{
  "attributes": [
    {
      "issuer": "string",
      "name": "string",
      "value": "string"
    }
  ],
  "parents": [
    {
      "identifier": "string",
      "scopes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ]
    }
  ],
  "resourceIdentifier": "string"
}

For example:

HTTP PUT
https://predix-acs.run.aws-usw02-dev.ice.predix.io/v1/resource/asset123
{ "attributes": [ { "issuer": "https://acs.attributes.int", "name": "site", "value": "sanfrancisco" } ], "resourceIdentifier": "asset123" }

Creating Attributes for a Subject
An administrator creates attributes for a subject based on the following API request.
HTTP PUT 
http://<host>/v1/{subjectIdentifier}

The HTTP request body can have the following elements:

{
  "attributes": [
    {
      "issuer": "string",
      "name": "string",
      "value": "string"
    }
  ],
  "parents": [
    {
      "identifier": "string",
      "scopes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ]
    }
  ],
  "subjectIdentifier": "string"
}

The HTTP request body specifies a collection of attributes that a subject must possess for the policy to be considered.  At run time, the Policy Evaluation service compares the attributes of the user making a service request against the criteria specified in the subject specification of an access-control policy to determine if it applies to the incoming request.

Procedure

  1. Use the following REST API in a REST client to define the attributes of a resource:
    HTTP PUT
    https://<host>/v1/{resourceIdentifier}

    For example:

    HTTP PUT 
    https://acs.attributes.int/v1/Site1
  2. Enter the following information in the HTTP request body:
    {
      "attributes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ],
      "parents": [
        {
          "identifier": "string",
          "scopes": [
            {
              "issuer": "string",
              "name": "string",
              "value": "string"
            }
          ]
        }
      ],
      "resourceIdentifier": "string"
    }

    For example:

    {
      "attributes": {
              "name": "Site 1",
              "attributes": [
                  {
                      "uriTemplate": "/customers/{customer_id:\\w*}/sites/{site_id:\\w*}"
                  },
          ]
    A 201 status code is returned if the resource is created successfully.
  3. In a REST client, use the following REST API to define the attributes of a subject:
    HTTP PUT 
    http://<host>/v1/{subjectIdentifier}

    For example:

    HTTP PUT 
    https://acs.attributes.int/v1/Boss
  4. Enter the following information in the HTTP request body:
    {
      "attributes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ],
      "parents": [
        {
          "identifier": "string",
          "scopes": [
            {
              "issuer": "string",
              "name": "string",
              "value": "string"
            }
          ]
        }
      ],
      "subjectIdentifier": "string"
    }

    For example:

    {
    "attributes": {
              "name": "Site Director role",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                }
              ]
    A 201 status code is returned if the subject Boss is created successfully with Site Director role attributes.

What To Do Next

See acs-using-access-control-services.html#task_b15_1xv_fs for information on how to set up access-control policies based on resource and subject attributes.

Creating Access-Control Policies

Use the Policy Management service to create, read, update, and delete access-control policies.

Before You Begin

To use the Policy Management service, the user/client must authenticate using a JSON Web Token (JWT) that includes the predix-acs.zones.<acs_instance_guid>.user scope along with acs.policies.read scope for reading the policies or the acs.policies.write scope for writing the policies.

You must specify the Predix-Zone-Id header when you use this REST API to communicate with a deployed application about its environment.. For more information, see acs-getting-started.html#task_a2375607-175a-40bc-b53b-2133c16473ad.

Select a REST client (such as Postman) that can execute API requests for the Attribute Management service. For more information about this API, see the API Documentation (Predix.io home page – Documentation – Service APIs).

About This Task

An access-control policy contains a set of rules to determine the required permissions for the specified subjects and resources. The rules can take into consideration the user attributes, the action the user wants to perform, the resource URI, and any resource attributes that further describe the resource.

An administrator creates an access-control policy as a JSON string so that the Policy Evaluation service can handle web service requests for authorization. An administrator can combine access-control policy sets as ordered lists.

An administrator creates an access-control policy based on the following API request.
HTTP PUT
/v1/policy-set/{policySetId}

The HTTP request body can have the following elements:

{
  "name": "string",
  "policies": [
    {
      "conditions": [
        {
          "condition": "string",
          "name": "string"
        }
      ],
      "effect": "PERMIT",
      "name": "string",
      "target": {
        "action": "string",
        "name": "string",
        "resource": {
          "attributeUriTemplate": "string",
          "attributes": [
            {
              "issuer": "string",
              "name": "string",
              "value": "string"
            }
          ],
          "name": "string",
          "uriTemplate": "string"
        },
        "subject": {
          "attributes": [
            {
              "issuer": "string",
              "name": "string",
              "value": "string"
            }
          ],
          "name": "string"
        }
      }
    }
  ]
}

The main elements of an access-control policy are listed in the following table:

ElementDescription
nameOptional information to identify a policy.
targetSpecifies the matching criteria to determine if a particular policy is applicable to an incoming evaluation request. This element is optional. A target contains the following basic components that must match the context of an incoming request to make the policy applicable:
  • resource

    Specifies a URI template that the resource must match, and a collection of attributes the resource must possess, for the policy to apply. At run time, the Policy Evaluation service compares the attributes of a requested resource against the criteria in the resource specification within the policy target to determine if the policy is applicable to the incoming request.

    For example,

    ...
    "resource" : {             
              "uriTemplate" : "/v1/region/report/asset/{asset_id}",           
              "attributeUriTemplate": "/v1/region/report{attribute_uri}",           
              "attributes" : [               
                  { "issuer" : "https://acs.attributes.int",          
                    "name"  : "site" }  
              ]   
          }
    ...

    The resource criteria can contain the following values:

    • uriTemplate: Specifies the URI template that the resource URI in the evaluation request must match.

      In the example above, the uriTemplate is defined as /v1/region/report/asset/{asset_id}. Therefore this policy will be considered for an evaluation request with resource URI as /v1/region/report/asset/1234. For more information on URI templates, see Spring Framework.

    • attributeUriTemplate: Specifies the attribute URI template to extract a contiguous subset of resource URI.

      In the example above, the attributeUriTemplate is defined as /vi/region/report{attribute_uri}. An evaluation request for this policy with resource URI as /v1/region/report/asset/1234 will refer to resource attributes from /asset/1234 instead of  /v1/region/report/asset/1234.

    • attributes: Specifies the attributes that the resources must have for the policy to be considered.

  • action

    Specifies the following action in the RESTful endpoint that the policy permits for a specified resource.

    • GET
    • PUT, POST
    • DELETE

    You can specify multiple actions at a time as a comma separated list. If you specify multiple actions, the service uses any of the actions that matches the policy. If you do not specify an action, all operations are considered.

  • subject

    Specifies a collection of attributes that the user must possess for the policy to apply. At run time, the Policy Evaluation service compares the attributes of the user/agent making a service request against the criteria specified in the subject specification of the policy target to determine if the policy applies to the incoming request.

effectSpecifies the access-control decision the Policy Evaluation service returns when the policy target matches a request, and all policy conditions return true. The effect can be either DENY or PERMIT.
Note: If a policy condition returns false, the policy does not apply, and the overall state of the access control decision is NOT_APPLICABLE.
conditionSpecifies a predicate that must be satisfied for a rule to be assigned its effect. This element is optional.

If you specify multiple conditions, the default Boolean expression used between conditions is AND.

You can use the following evaluation methods:
  • attributes(attributeIssuer, attributeName)

    Returns a set of all values of a specific attribute. For example, the following condition returns all groups a subject belongs to:

    "condition" : "subject.attributes('https://acs.attributes.int', 'group')"

    Similarly the following condition evaluates to true if the subject and resource belong to the same groups:

    "condition" : "subject.attributes('https://acs.attributes.int', 'group').equals(resource.attributes('https://acs.attributes.int', 'group'))"

    For complete list of operations, see Groovy JDK API Documentation

  • match.single
    Returns true if attribute value is present in the source attribute values. For example, the following condition evaluates to true if subject has the records-viewer role:
    "condition" : "match.single(subject.attributes('https://acs.attributes.int', 'role'), 'records-viewer')" 
  • match.any

    Returns true if the intersection of source attributes and target attributes is non-empty. For example, the following condition evaluates to true if subject and resource belong to at least one common group:

    "condition" : "match.any(subject.attributes('https://acs.attributes.int', 'group'), resource.attributes('https://acs.attributes.int', 'group'))"

    Similarly, the following condition evaluates to true if subject name is listed among resource owners:

    "condition" : "match.any(subject.attributes('https://acs.attributes.int', 'name_id'), resource.attributes('https://acs.attributes.int', 'owner'))"
  • resource.uriVariable

    Returns a value for the path parameter in the resource URL.

    For example, the following condition validates that the user (subject) and resource are assigned to the same customer. The user can be assigned to multiple customers. However, the condition in this sample validates that at least one customer matches the resource URL.

    "condition" : "match.single(subject.attributes('https://acs.attributes.int', 'customer'), resource.uriVariable('customer_id'))"

    This example assumes that the following URI template defines the resource URL in the policy target:

    "/customers/{customer_id}/sites/{site_id}"
  • and, haveSame()

    Used together to validate that subject and resource have common attributes. For example, the following condition evaluates to true if subject and resource belong to at least one common group.

    "condition" : "resource.and(subject).haveSame('acs.example.org', 'group').result()"
You can use the following classes in a condition:
  • com.ge.predix.acs.commons.policy.condition.groovy.GroovySecureExtension
  • com.ge.predix.acs.commons.policy.condition.AbstractHandler
  • com.ge.predix.acs.commons.policy.condition.AbstractHandlers
  • com.ge.predix.acs.commons.policy.condition.ResourceHandler
  • com.ge.predix.acs.commons.policy.condition.SubjectHandler
  • com.ge.predix.acs.commons.policy.condition.groovy.AttributeMatcher
  • java.lang.Boolean
  • java.lang.Integer
  • java.lang.Iterable
  • java.lang.Object
  • java.lang.String
  • java.util.Collection
  • java.util.Set
The following methods are not allowed in a condition:
  • java.lang.System
  • groovy.util.Eval
  • java.io
  • execute

Procedure

  1. In a REST client, use the following REST API to create an access-control policy set for a zone:
    HTTP PUT
    /v1/policy-set/{policySetId}

    where {policySetId} is the name of the policy set.

  2. Enter one of the the following sample JSON strings iin the HTTP request body to create a specific access-control policiy set:
    • The following sample policy denies access to everything.
      {
        "name" : "simple-policy-1",
        "policies" : [
            {
               "name" : "deny-everything",
               "effect" : "DENY"
            }
         ]
      }
    • The following sample policy permits access to a specified resource:
      {
        "name" : "simple-policy-1",
        "policies" : [
            {
               "name" : "deny-everything",
               "effect" : "DENY"
            }
         ]
      }
    • The following sample policy permits a GET action for a specified resource:
      {
          "name" : "simple-policy-3",
          "policies" : [
              {
                  "name" : "permit-get-to-public-records",
                  "target" : {
                      "name" : "",
                      "action":"GET",
                      "resource" : {
                          "name" : "public-records-resource",
                          "uriTemplate" : "/api/public-records/{record_id}"
                      }
                  },
                  "effect" : "PERMIT"
              }
          ]
      }
    • The following sample policy permits both GET and POST actions for a specified resource:
      {
          "name" : "simple-policy-3a",
          "policies" : [
              {
                  "name" : "permit-get-and-post-to-public-records",
                  "target" : {
                      "name" : "",
                      "action":"GET,POST",
                      "resource" : {
                          "name" : "public-records-resource",
                          "uriTemplate" : "/api/public-records/{record_id}"
                      }
                  },
                  "effect" : "PERMIT"
              }
          ]
      }
    • The following policy permits a GET action for a specified resource by a specified subject (role). The policy contains a condition that matches the role of the user.
      {
          "name" : "simple-policy-4",
          "policies" : [
              {
                  "name" : "permit-get-to-public-records",
                  "target" : {
                      "name" : "",
                      "resource" : {
                          "name" : "public-records-resource",
                          "uriTemplate" : "/api/public-records/{record_id}"
                      },
                      "action":"GET",
                      "subject" : {
                          "name" : "has-role",
                          "attributes" : [
                              { "issuer" : "https://acs.attributes.int",
                                "name" : "role" }
                          ]
                      }
                  },
                  "conditions" : [
                      { "name" : "",
                        "condition" : "match.single(subject.attributes('https://acs.attributes.int', 'role'), 'records-viewer')" }
                  ],
                  "effect" : "PERMIT"
              }
          ]
      }
      

What To Do Next

See acs-using-access-control-services.html#task_ebaec591-a1c6-442d-8154-9d4785cd0e54 for information on how to make access-control policy decisions..

Using Resource URI Templates in Access-Control Policies

A uniform resource identifier (URI) template allows you to define a set of structurally similar URIs. URI Templates are composed of two parts, a path and a query. A path consists of a series of segments delimited by a slash (/). Each segment can have a literal value or a variable value.  Segments enclosed within curly braces {} are variables. You can omit the query expression entirely. When present, the query expression specifies an unordered series of name/value pairs. Elements of the query expression are either literal pairs (?x=2) or variable pairs (?x={val}).  For more information on URI template, see Spring Framework UriTemplate .

In ACS, resource URI template is specified in the resource specification of an access-control policy target.  Resource URI template specifies a template that the resource URI of the incoming evaluation request must match to determine if the policy is applicable to the request.  The ACS Policy Evaluation service tests a candidate URI from the incoming evaluation request at run time to see if it matches a URI template in the policy to determine if the policy is applicable to the request. If the URI is a match, then template variables are resolved to the actual values from the URI and the rest of the policy criteria is evaluated. For example, consider the following policy:


{
  "name": "Agents can access a site if they are stationed at the site.",
  "target": {
    "name": "When an agent accesses a site",
    "resource": {
      "name": "Site",
      "uriTemplate": "/sites/{site_id}"
    },
    "action": "GET",
    "subject": {
      "name": "Agent",
      "attributes": [
        {
          "issuer": "acs.example.org",
          "name": "site"
        }
      ]
    }
  },
  "conditions": [
    {
      "name": "is assigned to site",
      "condition": "match.single(subject.attributes('acs.example.org', 'site'), resource.uriVariable('site_id'))"
    }
  ],
  "effect": "PERMIT"
}

In the above example, the uriTemplate is defined as "/sites/{site_id}".  Therefore, this policy may be considered for evaluation requests with resource URI as “/sites/siteA”, “/sites/siteB” because these resource URIs match the template.

URI template variable {site_id} is resolved to the actual ID of the site from the URI: siteA or siteB, and is used to evaluate policy condition.  If condition evaluates to TRUE, a PERMIT decision is returned.

However, note that the above uriTemplate will also match requests for “/sites/siteA/financial-reports” and “/sites/siteB/financial-statements” which might require a more restrictive permissions to access. Current implementation of ACS access-control policies allows the flexibility of allowing or blocking subpathswhen matching resource URI by using regular expressions in URI template.

Allowing or Blocking Access to Subpaths

To control access to the resource URL subpaths, you can use regular expressions as part of the URI template. Using regular expressions as part of the URI template is optional. When used with the URI template, regular expressions allow you to implement a more fine-grained control on which resources can be accessed and which cannot. The syntax for using regular expressions in URI template is, {variable: regex}.  The regex must be a valid expression following the Java Regular Expression specifications. 

For example, to disallow access to the subpaths in resource URIs, change uriTemplate in the policy above to "/sites/{site_id:\\w*}". This will ensure that this policy is considered for the requests where resource URI contains only alphanumeric characters after "/sites/", disallowing any slashes and blocking the access to any subpaths. The acs-using-access-control-services.html#reference_zgp_d2w_ldb lists some examples that show how to use URI Templates to block access to various resources.

Examples: URI Templates for Policy Matching

The following examples list the URI Template Descriptions and Policy Examples that you can view to understand how you can modify your URI template to allow or block subpaths.

Example 1 — Allow or block subpaths at the end of resource URL

This policy will be considered by ACS Evaluation Service for HTTP GET requests to the resource URI that matches the following template:  /customers/{customer_id}


{
  "name": "Administrators can access all the customers",
  "target": {
    "name": "When an administrator accesses customers",
    "resource": {
      "name": "Customers",
      "uriTemplate": "/customers/{customer_id}"
    },
    "action": "GET",
    "subject": {
      "name": "Administrator Role",
      "attributes": [
        {
          "issuer": "https://acs/attributes.int",
          "name": "role"
        }
      ]
    }
  },
  "conditions": [
    ...
  ],
  "effect": "PERMIT"
}
Problem — This URI template allows access to the URLs listed below as well as the subpaths that you may not want to be included in the list of accessible URLs:
  • /customers/12345 and /customers/12345/sites
  • /customers/12345/sites/siteA
  • /customers/12345/sites/siteB
  • /customers/all_possible_subpaths_after_this

Solution — You can disallow access to the subpaths with the following modifications to the URI templates:

"uriTemplate":"/customers/{customer_id:\\w*}"

\w matches any alphanumeric character including underscore equivalent to [A-Za-z0-9_]

"uriTemplate":"/customers/{customer_id:[^/]+}"

Adding "[^/]+" matches any character after /customers/ but should not contain / because including the slash may translate it as a subpath call.

These URI templates match the following URL patterns:
  • /customers/12345/ and customers/customer1
  • /customers/abc_123
These URI templates do not match the following URL patterns:
  • /customers/12345/sites
  • /customers/12345/sites/siteA
  • /customers/12345/sites/siteB
  • /customers/all_possible_subpaths_after_this

Example 2 — Allow or block slash (/) at the end of resource URL

This policy will be considered by ACS Evaluation Service for HTTP GET requests to the resource URI that matches the following template: /customers


{
  "name": "Administrators can access all the customers",
  "target": {
    "name": "When an administrator accesses customers",
    "resource": {
      "name": "Customers",
      "uriTemplate": "/customers"
    },
    "action": "GET",
    "subject": {
      "name": "Administrator Role",
      "attributes": [
        {
          "issuer": "https://acs/attributes.int",
          "name": "role"
        }
      ]
    }
  },
  "conditions": [
    ...
  ],
  "effect": "PERMIT"
}

Problem —The "uriTemplate": "/customers" template will block access to /customers/

Solution — To allow access to both /customers and /customers/, the URI Template must be modified to the following:

"uriTemplate":"customers{optionalSlash:/?}" This URI now matches /customers and /customers/ but it does not match /customers/all_possible_subpaths_after_this.

Example 3 — Allow or block subpaths in the middle and at the end of resource URL

This policy will be considered by ACS Evaluation Service for HTTP GET requests to the resource URI that matches the following template: /customers/{customer_id}/sites/{site_id}


{
  "name": "Administrators can access all the customers",
  "target": {
    "name": "When an administrator accesses customers",
    "resource": {
      "name": "Customers",
      "uriTemplate": "/customers/{customer_id}/sites/{site_id}"
    },
    "action": "GET",
    "subject": {
      "name": "Administrator Role",
      "attributes": [
        {
          "issuer": "https://acs/attributes.int",
          "name": "role"
        }
      ]
    }
  },
  "conditions": [
    ...
  ],
  "effect": "PERMIT"
}
Problem — The "uriTemplate": "/customers/{customer_id}/sites/{site_id}" template matches the URL patterns including the subpaths, for example:
  • /customers/12345/sites/siteA
  • /customers/123345/sites/siteB
  • /customers/12345/sites/siteA/assets/asset-id
  • /customers/all_possible_subpaths_here/sites/siteB
  • /customers/all_possible_subpaths_here/sites/all_possible_subpaths_here

Solution — To block access to the subpaths consider using the URI template with some modification as shown in the following example:

"uriTemplate":"/customers/{customer_id:\\w*}/sites/{site_id:\\w*}"

Using \w matches any alphanumeric character including underscore, equivalent to [A-Za-z0-9_]

"uriTemplate":"/customers/{customer_id:[^/]+}/sites/{site_id:[^/]+}"

Including the expression "[^/]+" in the template, matches any character after /customers/ and /sites/ but should not contain /which may be translated as a subpaths call.

These new URI templates match the following URL patterns:
  • /customers/12345/sites/siteA
  • /customer/12345/sites/siteB
  • /customer/customer1/sites/siteA
These URI templates do not match the following URL patterns:
  • /customers/12345/sites
  • /customers/12345/sites/siteA/assets/asset-id
  • /customers/all_possible_subpaths_here/sites/siteB
  • /customers/all_possible_subpaths_here/sites/all_possible_subpaths_here

Example 4 — Allow or block subpaths inside resource URL

This policy will be considered by ACS Evaluation Service for HTTP GET requests to the resource URI that matches the following template: /customers/{customer_id:\\w*}/sites

{
  "name": "Administrators can access all the customers",
  "target": {
    "name": "When an administrator accesses customers",
    "resource": {
      "name": "Customers",
      "uriTemplate": "/customers/{customer_id:\\w*}/sites"
    },
    "action": "GET",
    "subject": {
      "name": "Administrator Role",
      "attributes": [
        {
          "issuer": "https://acs/attributes.int",
          "name": "role"
        }
      ]
    }
  },
  "conditions": [
    ...
  ],
  "effect": "PERMIT"
}

Problem — —This "uriTemplate": "/customers/{customer_id:\\w*}/sites" template matches all URL patterns and subpaths and allow all possible subpaths inside a resource URL .

Solution — Using \\w* ensures that the URI template matches only the following URL pattern examples:
  • /customers/12345/sites
  • /customers/abcd/sites

The URI template do not match the following URL pattern:

/customers/all_possible_subpaths_here/sites

Evaluating Access-Control Policies

Use the Policy Evaluation service to make access-control policy decisions.

Before You Begin

You must specify the Predix-Zone-Id header when you use this REST API to communicate with a deployed application about its environment.. For more information, see acs-getting-started.html#task_a2375607-175a-40bc-b53b-2133c16473ad.

Select a REST client (such as Postman) that can execute API requests for the Attribute Management service. For more information about this API, see the API Documentation (Predix.io home page – Documentation – Service APIs).

About This Task

The Policy Evaluation service performs access-control policy evaluation based on the following API request.

HTTP POST /v1/policy-evaluation
The HTTP policy evaluation request body can have the following elements:
{
  "action": "string",
  "policySetsEvaluationOrder": [
    "string"
  ],
  "resourceAttributes": [
    {
      "issuer": "string",
      "name": "string",
      "value": "string"
    }
  ],
  "resourceIdentifier": "string",
  "subjectAttributes": [
    {
      "issuer": "string",
      "name": "string",
      "value": "string"
    }
  ],
  "subjectIdentifier": "string"
}
where:
  • action: Specifies the action in the RESTful endpoint that the policy permits for a specified resource. (see acs-using-access-control-services.html#task_b15_1xv_fs).
  • policySetsEvaluationOrder: Specifies the order that access-control policies are evaluated. The first access-control policy set that satisfies the specified conditions is executed
  • resourceAttributes: Specifies a URI template that the resource must match, and a collection of attributes the resource must possess, for the policy to apply. At run time, the Policy Evaluation service compares the attributes of a requested resource against the criteria in the resource specification of an access-control policy to determine if the policy is applicable to the incoming request..
  • resourceIdentifier: The name of the resource,
  • subjectAttributes : Specifies a collection of attributes that the subject must possess for the policy to be considered.  At run time, the Policy Evaluation service compares the attributes of the user making a service request against the criteria specified in the subject specification of an access-control policy to determine if it applies to the incoming request..
  • subjectIdentifier : The name of the subject,

Procedure

  1. In a REST client, use the following REST API to evaluate an access-control policy:
    HTTP POST
    /v1/policy-evaluation
  2. Enter the following information in the HTTP request body:
    {
      "action": "string",
      "policySetsEvaluationOrder": [
        "string"
      ],
      "resourceAttributes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ],
      "resourceIdentifier": "string",
      "subjectAttributes": [
        {
          "issuer": "string",
          "name": "string",
          "value": "string"
        }
      ],
      "subjectIdentifier": "string"
    }

    For example:

    {
      "resourceIdentifier": "/customers",
      "subjectIdentifier": "pbadmin",
      "action": "GET",
      "policySetsEvaluationOrder" : ["pb-policy-set-1","pb-policy-set-2","pb-policy-set-3"],
      "subjectAttributes": [
        {
          "name": "role",
          "value": "PB_Admin",
          "issuer": "https://acs.attributes.int"
        }
      ],
      "tenantId": ""
    }

Example: Access Control Services Simple Use Case

A company has the following access-control requirements:

  • An administrator should be able to add, remove or modify users in Organization 1 and Organization 2.

  • A Site Director in Organization 1 should be able to access all the resources in all the sites in Organization 1 (Site 1 and Site 2).

  • A Production Manager of Site 1 should only be able to access resources in Site 1.

  • A Production Manager of Site 2 should only be able to access resources in Site 2.

The following diagram shows the company structure:

To implement this flow, an administrator can use the Policy Management service and the Attribute Management service APIs to specify the required policies and attributes and Policy Evaluation service to determine the access for web service calls.

The following sections demonstrate the use of ACS services for this use case:

  • Policy Management
  • Hierarchical Attribute Management
  • Policy Evaluation

Before You Begin

As a developer, you should review the following resources to understand the conceptual, task, and reference information needed to demonstrate the use of ACS services for this use case::

Select a REST client (such as Postman) that can execute API requests. For more information about these APIs, see the API Documentation (Predix.io home page – Documentation – Service APIs).

Policy Management

In a REST client, enter the following REST API to create an access control policy for a zone:

HTTP PUT
/v1/policy-set/{policySetId}
Note:

You must specify the Predix-Zone-Id header when you use the REST APIs.

In the response body, enter one of the following sample JSON strings to create a specific access-control policy:

  • A policy that gives an administrator HTTP GET access to the /customers resource. It contains a condition that validates that the user has the Administrator role.

    {
      "name": "sample-policy-set",
      "policies": [
        {
          "name": "Administrator can access all the customers.",
          "target": {
            "name": "When an Administrator accesses customers",
            "resource": {
              "name": "Customers",
              "uriTemplate": "/customers"
            },
            "subject": {
              "name": "Administrator role",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                }
              ]
            }
          },
          "conditions": [
            {
              "name": "is an Administrator",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'role'),
        'Administrator')"
            }
          ],
          "effect": "PERMIT"
        } 
        ]
    }
  • A policy that gives site directors HTTP GET access to the /sites resource. It contains a condition that validates that the user has the Site_Director role.

    {
          "name": "Site Directors can read a sites/site if they are assigned to the site.",
          "target": {
            "name": "When an Site Director reads his/her sites.",
            "resource": {
              "name": "Sites",
              "uriTemplate": "/sites"
            },
            "action": "GET",
            "subject": {
              "name": "Site Director role",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                }
              ]
            }
          },
          "conditions": [
            {
              "name": "is a Site Director",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'role'),
        'Site_Director')"
            }
          ],
          "effect": "PERMIT"
        }
  • A policy that gives site directors HTTP GET access to customers correlating to their sites. It contains the following conditions:
    • A condition that validates that the user has the Site_Director role.
    • A condition that validates that the user is assigned to the same customer. The user can be assigned to multiple customers. However, the condition in this sample validates that at least one customer matches the resource URL.
    Note:

    If you specify multiple conditions, the default Boolean expression used between conditions is AND.

    {
          "name": "Site Directors can read a sites/site if they have access to Customer",
          "target": {
            "name": "When an Site Director reads his/her sites.",
            "resource": {
              "name": "Customer Sites",
              "uriTemplate":
        "/customers/{customer_id:\\w*}/sites/{site_id}"
            },
            "action": "GET",
            "subject": {
              "name": "Site Director role",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                },
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "customer"
                }
              ]
            }
          },
          "conditions": [
            {
              "name": "is a Site Director",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'role'),
        'Site_Director')"
            },
            {
              "name": "is assigned to same customer",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
        resource.uriVariable('customer_id'))"
            }
          ],
          "effect": "PERMIT"
        }
  • A policy that gives a production manager HTTP GET access to the customers correlated to a specific site. It contains the following conditions:

    • A condition that validates that the user has the Production_Manager role.
    • A condition that validates that the user is assigned to the same customer. The user can be assigned to multiple customers. However the condition in this sample validates that at least one customer matches the resource URL.
            {
          "name": "Production Managers can read a site if they have access to Customer",
          "target": {
            "name": "When an Production Manager reads a site---this policy def assumes
        the site_id is unique in the system.",
            "resource": {
              "name": "Site",
              "uriTemplate":
      "/customers/{customer_id:\\w*}/sites"
            },
            "action": "GET",
            "subject": {
              "name": "Production Manager Role",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                },
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "customer"
                }
              ]
            }
          },
          "conditions": [
            {
              "name": "is a Production Manager",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'role'),
        'Production_Manager')"
            },
            {
              "name": "is assigned to same customer",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
        resource.uriVariable('customer_id'))"
            }
          ],
          "effect": "PERMIT"
        }
  • A policy that gives a production manager HTTP GET access to an assigned customer and site. It contains the following conditions:

    • A condition that validates that the user is assigned to a specific site.
    • A condition that validates that the user has the Production_Manager role.
    • A condition that validates that the user is assigned to the same customer. The user can be assigned to multiple customers. However, the condition in this sample validates that at least one customer matches the resource URL.
    {
          "name": "Production Managers can read a site if they are assigned to the site and Customer.",
          "target": {
            "name": "When an Production Manager reads a site---this policy def assumes
        the site_id is unique in the system.",
            "resource": {
              "name": "Site",
              "uriTemplate":
        "/customers/{customer_id:\\w*}/sites/{site_id:\\w*}"
            },
            "action": "GET",
            "subject": {
              "name": "Production_Manager",
              "attributes": [
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "site"
                },
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "role"
                },
                {
                  "issuer": "https://acs.attributes.int",
                  "name": "customer"
                }
              ]
            }
          },
          "conditions": [
            {
              "name": "has permissions to do a GET on the
      site",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'site'),
        resource.uriVariable('site_id'))"
            },
            {
              "name": "is a Production Manager",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'role'),
        'Production_Manager')"
            },
            {
              "name": "is assigned to same Customer",
              "condition":
        "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
        resource.uriVariable('customer_id'))"
            }
          ],
          "effect": "PERMIT"
        }
  • A default DENY policy if none of the other policies apply.

    {
                "name" : "Deny all other operations by
      default",
                "effect" : "DENY"
            }

The following sample access-control policy shows all the access-control policies assembled for the organization:

{
  "name": "sample-policy-set",
  "policies": [
    {
      "name": "Administrator can access all the customers.",
      "target": {
        "name": "When an Administrator accesses customers",
        "resource": {
          "name": "Customers",
          "uriTemplate": "/customers"
        },
        "subject": {
          "name": "Administrator role",
          "attributes": [
            {
              "issuer": "https://acs.attributes.int",
              "name": "role"
            }
          ]
        }
      },
      "conditions": [
        {
          "name": "is an Administrator",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'role'),
    'Administrator')"
        }
      ],
      "effect": "PERMIT"
    },
    {
      "name": "Site Directors can read a sites/site if they are assigned to the site and Customer.",
      "target": {
        "name": "When an Site Director reads his/her sites.",
        "resource": {
          "name": "Sites",
          "uriTemplate": "/sites"
        },
        "action": "GET",
        "subject": {
          "name": "Site Director role",
          "attributes": [
            {
              "issuer": "https://acs.attributes.int",
              "name": "role"
            }
          ]
        }
      },
      "conditions": [
        {
          "name": "is a Site Director",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'role'),
    'Site_Director')"
        }
      ],
      "effect": "PERMIT"
    },
    {
      "name": "Site Directors can read a sites/site if they have access to Customer",
      "target": {
        "name": "When an Site Director reads his/her sites.",
        "resource": {
          "name": "Customer Sites",
          "uriTemplate":
    "/customers/{customer_id:\\w*}/sites/{site_id}"
        },
        "action": "GET",
        "subject": {
          "name": "Site Director role",
          "attributes": [
            {
              "issuer": "https://acs.attributes.int",
              "name": "role"
            },
            {
              "issuer": "https://acs.attributes.int",
              "name": "customer"
            }
          ]
        }
      },
      "conditions": [
        {
          "name": "is a Site Director",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'role'),
    'Site_Director')"
        },
        {
          "name": "is assigned to same customer",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
    resource.uriVariable('customer_id'))"
        }
      ],
      "effect": "PERMIT"
    },
        {
      "name": "Production Managers can read a site if they have access to Customer",
      "target": {
        "name": "When an Production Manager reads a site---this policy def assumes
    the site_id is unique in the system.",
        "resource": {
          "name": "Site",
          "uriTemplate":
  "/customers/{customer_id:\\w*}/sites"
        },
        "action": "GET",
        "subject": {
          "name": "Production Manager Role",
          "attributes": [
            {
              "issuer": "https://acs.attributes.int",
              "name": "role"
            },
            {
              "issuer": "https://acs.attributes.int",
              "name": "customer"
            }
          ]
        }
      },
      "conditions": [
        {
          "name": "is a Production Manager",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'role'),
    'Production_Manager')"
        },
        {
          "name": "is assigned to same customer",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
    resource.uriVariable('customer_id'))"
        }
      ],
      "effect": "PERMIT"
    },
    {
      "name": "Production Managers can read a site if they are assigned to the site and Customer.",
      "target": {
        "name": "When an Production Manager reads a site---this policy def assumes
    the site_id is unique in the system.",
        "resource": {
          "name": "Site",
          "uriTemplate":
    "/customers/{customer_id:\\w*}/sites/{site_id:\\w*}"
        },
        "action": "GET",
        "subject": {
          "name": "Production_Manager",
          "attributes": [
            {
              "issuer": "https://acs.attributes.int",
              "name": "site"
            },
            {
              "issuer": "https://acs.attributes.int",
              "name": "role"
            },
            {
              "issuer": "https://acs.attributes.int",
              "name": "customer"
            }
          ]
        }
      },
      "conditions": [
        {
          "name": "has permissions to do a GET on the
  site",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'site'),
    resource.uriVariable('site_id'))"
        },
        {
          "name": "is a Production Manager",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'role'),
    'Production_Manager')"
        },
        {
          "name": "is assigned to same Customer",
          "condition":
    "match.single(subject.attributes('https://acs.attributes.int', 'customer'),
    resource.uriVariable('customer_id'))"
        }
      ],
      "effect": "PERMIT"
    },
        {
            "name" : "Deny all other operations by
  default",
            "effect" : "DENY"
        }
  ]
}

Attribute Management

In this example, several resources and subjects are defined to meet the access-control requirement.

In a REST client, enter the following REST API to create the resources:

HTTP POST
http://<host>/v1/resource

In the response body, enter the following sample JSON string to create the resources:

    [
         {
            "resourceIdentifier": "customers"
          },
          {
            "resourceIdentifier": "sites"
          },
          {
            "resourceIdentifier":
      "customers/customer1/sites/site1"
          },
          {
            "resourceIdentifier":
      "customers/customer1/sites/site2"
          },
          {
            "resourceIdentifier":
      "customers/customer2/sites/site1"
          }
         
        ]  

In a REST client, enter the following REST API to create the subjects:

HTTP POST
http://<host>/v1/subject

In the response body, enter one of the following sample JSON strings to create different subjects:

  • The following sample creates two users, Acme Admin and Acme User. While the Acme Admin user can access the /customer URL, the Acme User user cannot.

        [
          {
            "subjectIdentifier": “/subject/Acme Admin",
            "attributes": [
            {
              "name": "role",
              "value": "Administrator",
              "issuer": "https://acs.attributes.int"
            }
          ],
          },
    {
            "subjectIdentifier": “/subject/Acme User",
            "attributes": [
            {
              "name": "role",
              "value": "User1",
              "issuer": "https://acs.attributes.int"
            }
          ],
          }
        ]
  • The following sample creates two users, Acme Site Director and Acme Site User. While the Acme Site Director user can access the /site URL and access the /customers correlated to /site, the Acme Site User user cannot.

        [
          {
            "subjectIdentifier": “/subject/Acme Site Director",
            "attributes": [
            {
              "name": "role",
              "value": "Site_Director",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer1",
              "issuer": "https://acs.attributes.int"
            }
          ],
          },
    {
            "subjectIdentifier": “/subject/Acme Site User",
            "attributes": [
            {
              "name": "role",
              "value": "User",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer1",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer2",
              "issuer": "https://acs.attributes.int"
            }
          ],
          }
        ]
  • The following sample creates two users, Acme Production Manager and Acme Production User. While the Acme Production Manager user can access the /site URL and access the /customers correlated to /site, the Acme Production User user cannot.

        [
           {
            "subjectIdentifier": “/subject/Acme Production Manager",
            "attributes": [
            {
              "name": "role",
              "value": "Production_Manager",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "site",
              "value": "site1",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer1",
              "issuer": "https://acs.attributes.int"
            }
          ],
          },
    {
            "subjectIdentifier": “/subject/Acme Site User",
            "attributes": [
            {
              "name": "role",
              "value": "User",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer1",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "customer",
              "value": "customer2",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "site",
              "value": "site1",
              "issuer": "https://acs.attributes.int"
            },
            {
              "name": "site",
              "value": "site2",
              "issuer": "https://acs.attributes.int"
            }
          ],
          }
        ]

Policy Evaluation

The Policy Evaluation service performs policy evaluation based on the web service requests. The following samples show web service calls and their corresponding policy evaluation results based on the policies and attributes defined in this use case.

In a REST client, use the following REST API to evaluate an access-control policy:

HTTP POST
/v1/policy-evaluation
  • The following sample call shows how an administrator can access a resource:

        {
          "resourceIdentifier": "/customers",
          "subjectIdentifier": “/subject/Acme Admin",
          "action": "GET"
        }

    The call returns the following policy evaluation result:

        {
        "effect": "PERMIT",
        "subjectAttributes": [
        {
        "issuer": "https://acs.attributes.int",
        "name": "role",
        "value": "Administrator"
        }
        ],
        "resourceAttributes": [ ]
        }
  • The following sample call shows how a site director can access resources for a site:

        {
          "resourceIdentifier": "/sites",
          "subjectIdentifier": “/subject/Acme Site Director",
          "action": "GET"
        }

    The call returns the following policy evaluation result:

        {
        "effect": "PERMIT",
        "subjectAttributes": [
        {
        "issuer": "https://acs.attributes.int",
        "name": "customer",
        "value": "customer1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "role",
        "value": "Site_Director"
        }
        ],
        "resourceAttributes": [ ]
        }
  • The following sample call shows how a site director can access a resource in a site:

        {
          "resourceIdentifier": "/customers/customer1/sites/site1",
          "subjectIdentifier": “/subject/Acme Site Director",
          "action": "GET"
        }

    The call returns the following policy evaluation result:

        {
        "effect": "PERMIT",
        "subjectAttributes": [
        {
        "issuer": "https://acs.attributes.int",
        "name": "customer",
        "value": "customer1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "role",
        "value": "Site_Director"
        }
        ],
        "resourceAttributes": [ ]
        }
  • The following sample call shows how a production manager can access a resource on a specific site:

        {
          "resourceIdentifier": "/customers/customer1/sites",
          "subjectIdentifier": “/subject/Acme Production Manager",
          "action": "GET"
        }

    The call returns the following policy evaluation result:

        {
        "effect": "PERMIT",
        "subjectAttributes": [
        {
        "issuer": "https://acs.attributes.int",
        "name": "site",
        "value": "site1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "customer",
        "value": "customer1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "role",
        "value": "Production_Manager"
        }
        ],
        "resourceAttributes": [ ]
        }
  • The following sample call shows how a production manager can access a specific resource in a specific site:

        {
          "resourceIdentifier": "/customers/customer1/sites/site1",
          "subjectIdentifier": “/subject/Acme Production Manager",
          "action": "GET"
        }

    The call returns the following policy evaluation result:

        {
        "effect": "PERMIT",
        "subjectAttributes": [
        {
        "issuer": "https://acs.attributes.int",
        "name": "site",
        "value": "site1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "customer",
        "value": "customer1"
        },
        {
        "issuer": "https://acs.attributes.int",
        "name": "role",
        "value": "Production_Manager"
        }
        ],
        "resourceAttributes": [ ]
        }

Example: Access Control Services Hierarchical Attribute Use Case

This use case shows the use of hierarchical subject and resource attributes in Access Control Services (ACS).

Note: To use the hierarchical subject and resource attributes, you must use the ACS instance with Beta plan. To subscribe to this plan, click on the Access Control Service tile in the predix.io catalog and select the Beta plan option.

A company has the following security requirements:

  • Define an Analyst role for all sites in the organization.
  • Define a sub-category of Analyst role as Data Scientist. A data scientist inherits attributes of Analyst role.
  • Tom, who is a Data Scientist at Site 1, should be able to access all the resources at that site.
  • Tom should not have access to resource at site 2.

The following diagram shows the company structure:

To implement this flow, an administrator can use the Policy Management service and Attribute Management service APIs to specify the required policies and hierarchical attributes and Policy Evaluation service to determine the access for web service calls.

Note: ACS service instances cache subject and resource attribute information in memory, as a performance optimization, up to a maximum of one second. This implies that there can be up to a 1 second delay between the time when a update to resource or subject is completed, and the time when the updated value is seen by a subsequent request (if the request goes to a different instance of ACS deployment).

The following sections demonstrate the use of ACS for:

  • Hierarchical Attribute Management
    • Defining role and attributes
      This section shows use of Attribute Management Service APIs to create:
      • Analysts role with an attribute of Data Scientist
      • User (Tom) that inherits all attributes of Analyst
      • Resource site (San Ramon)
      • Resources (engine 9 and engine 11) at the resource sites
    • Policy Management

      This section shows use of Policy Management APIs to define a policy where data scientist can access data at the resource site.

    • Policy evaluation with hierarchical attributes

      This section evaluates policy to permit data scientist (Tom) to access data at a site. In this case, Tom can access both site 1 and site 2.

  • Hierarchical Scope Management

    To limit Tom's access to site 1 (San Ramon) only, an administrator can define scoped attributes.

    • Defining scoped attributes

      This section shows use of Attribute management Service API to define scopes that further qualify access a particular site.

    • Policy Evaluation with hierarchical and scoped attributes

      This section evaluates policy to deny access to resource at site 2 to Tom.

Before You Begin

Review the following resources to understand the concepts, tasks, and reference information needed to demonstrate the use of ACS services for this use case::

Select a REST client (such as Postman) that can execute API requests. For more information about these APIs, see the API Documentation (Predix.io home page – Documentation – Service APIs).

Defining Roles and Attributes Using Attribute Management Service APIs

  • Create an Analyst Role (role-analyst) with an attribute named group with a value of Data Scientist.

    In a REST client, enter the following REST API to create an Analyst role:

    HTTP PUT
    http://<host>/v1/subject/role-analyst

    In the response body, enter the following sample JSON string to create the role of an Analyst, role-analyst. The Analysts has an attribute of Data Scientist.

    {
      "subjectIdentifier" : "role-analyst",
      "attributes" : [
        {
          "issuer" : "https://acs.predix.io",
          "name"   : "role",
          "value"  : "analyst"
        }, 
      {
          "issuer" : "https://acs.predix.io",
          "name"   : "group",
          "value"  : "Data Scientist"
      }
      ]
    }
  • Create a User, Tom, who inherits analyst role and all its attributes (group as Data Scientist).

    In a REST client, enter the following REST API to create a user to inherit the role of an Analyst:

    HTTP PUT
    http://<host>/v1/subject/[email protected]

    In the response body, enter the following sample JSON string to create the subject user:

    {
      "subjectIdentifier" : "[email protected]",
      "parents" : [
        {
          "identifier" : "role-analyst"
        }
      ]
    }
  • Create a resource site, San Ramon.

    In a REST client, enter the following REST API:

    HTTP PUT
    http://<host>/v1/resource/%2fsites%2fsan-ramon

    In the response body, enter the following sample JSON string to create the resource site:

    {
      "resourceIdentifier" : "/sites/san-ramon",
      "attributes" : [
        {
          "issuer" : "https://acs.predix.io",
          "name"   : "site",
          "value"  : "san-ramon"
        }
      ]
    }
  • Create a resource called engine 9 at San Ramon site.

    In a REST client, enter the following REST API:

    HTTP PUT
    http://<host>/v1/resource/engines/9

    In the response body, enter the following sample JSON sample strong to create the resource:

    {
      "resourceIdentifier" : "/engines/9",
      "parents" : [
        {
          "identifier" : "/sites/san-ramon"
        }
      ]
    }
  • Create a resource called engine 11. This resource resides outside of San Ramon site.

    In a REST client, enter the following REST API:

    HTTP PUT
    http://<host>/v1/resource/%2fengines%2f11

    In the response body, enter the following sample JSON string to create the resource:

    {
      "resourceIdentifier" : "/engines/11"
    }

Policy Management

The administrator adds the policies to allow access to resources for analysts that are Data Scientists:
  • In a REST client, enter the following REST API to create an access control policy for a zone:

    HTTP PUT
    /v1/policy-set/default
    Note:

    You must specify the Predix-Zone-Id header when you use the REST APIs.

  • In the response body, enter the following sample JSON string to create the policy:

    {
      "name" : "default",
      "policies" : [
        {
          "name" : "Analysts can access engines if they belong to the same group.",
          "target" : {
            "resource" : {
              "name" : "Engine",
              "uriTemplate" : "/engines/{engine_id}"
            },
            "action" : "GET",
            "subject" : {
              "name" : "Data Scientists Group",
              "attributes" : [
                {
                  "issuer" : "https://acs.predix.io",
                  "name"   : "group",
                  "value"  : "Data Scientist"
                }
              ]
            }
          },
          "conditions" : [
            { 
              "name"      : "is an analyst",
              "condition" : "match.single(subject.attributes('https://acs.predix.io', 'group'), 'Data Scientist')" 
            }
          ],
          "effect" : "PERMIT"
        },
        {
          "name" : "Deny all other requests.",
          "effect" : "DENY"
        }
      ]
    }

Policy Evaluation with Hierarchical Attributes

The Policy Evaluation service performs policy evaluation based on the web service requests. The following samples display web service calls and their corresponding policy evaluation results based on the policies and attributes defined in this use case.

In a REST client, use the following REST API to evaluate an access-control policy:

HTTP POST
/v1/policy-evaluation

In the response body, enter one of the following sample JSON strings to evaluate web service calls and their corresponding policy evaluation results based on the policies and attributes defined in this use case.:

  • The following sample call shows how Tom can access a resource at any of the sites. Tom will be able to access resources at both Site 1 and Site 2.

    {
      "action" : "GET",
      "resourceIdentifier" : "/engines/9",
      "subjectIdentifier" : "[email protected]"
    }

    The call returns the following policy evaluation result:

    {
      "timestamp": 0,
      "resolvedResourceUris": [
        "\/engines\/9"
      ],
      "resourceAttributes": [
        {
          "value": "san-ramon",
          "name": "site",
          "issuer": "https:\/\/acs.predix.io"
        }
      ],
      "subjectAttributes": [
        {
          "value": "analyst",
          "name": "role",
          "issuer": "https:\/\/acs.predix.io"
        }
      ],
      "effect": "PERMIT"
    }
  • The following sample call shows that Tom also has access to a resource at the other site:

    {
      "action" : "GET",
      "resourceIdentifier" : "/engines/11",
      "subjectIdentifier" : "[email protected]"
    }

    The call returns the following policy evaluation result:

    {
      "timestamp": 0,
      "resolvedResourceUris": [
        "\/engines\/11"
      ],
      "resourceAttributes": [],
      "subjectAttributes": [
        {
          "value": "analyst",
          "name": "role",
          "issuer": "https:\/\/acs.predix.io"
        }
      ],
      "effect": "PERMIT"
    }

Defining Scoped Attributes

In this example, the attributes of a subject are defined to meet the access-control requirement.

  • The user Tom inherits analyst role and all its attributes (group as Data Scientist). In addition, Tom has access to resources at the San Ramon Site only.

    In a REST client, use the following REST API to create a user to inherit the role of an Analyst and add scope to limit access to a site:

    HTTP PUT
    http://<host>/v1/subject/[email protected]

    In the response body, enter the following sample JSON string to create the subject user:

    {
      "subjectIdentifier" : "[email protected]",
      "parents" : [
        {
          "identifier" : "role-analyst",
          "scopes" : [
            {
              "issuer" : "https://acs.predix.io",
              "name"   : "site",
              "value"  : "san-ramon"
            }
        }
      ]
    }

Policy Evaluation with Hierarchical and Scoped Attributes

The following samples shows web service calls and their corresponding policy evaluation results based on the policies and attributes defined in this use case.

In a REST client, use the following REST API to evaluate an access-control policy:

HTTP POST
/v1/policy-evaluation

In the response body, enter one of the following sample JSON strings to evaluate web service calls and their corresponding policy evaluation results based on the policies and attributes defined in this use case.:

  • The following sample call shows that Tom who is an analyst at site 1 (San Ramon) cannot access a resource (resource 11) at other site:

    {
      "action" : "GET",
      "resourceIdentifier" : "/engines/11",
      "subjectIdentifier" : "[email protected]"
    }

    The call returns the following policy evaluation result:

    {
      "timestamp": 0,
      "resolvedResourceUris": [
        "\/engines\/11"
      ],
      "resourceAttributes": [],
      "subjectAttributes": [],
      "effect": "DENY"
    }

Example: ACS Attribute Connector Setup

Configure access to subject and resource attributes from external resources for policy evaluation.

Purpose

As a developer, you can extend Access Control Services to access remote attributes from external sources for policy evaluation:

  • Allow ACS policies to reference attributes of a protected resource from an external source (such as Predix Asset service).

  • Allow ACS policies to reference attributes of a currently authenticated user from an external source (such as federated identity management).

Before You Begin

As a developer, you should review the following resources to understand the conceptual, task, and reference information needed to extend Access Control Services to support external attribute resources:

Task Roadmap

The following tasks show how to extend Access Control Services to support external attribute sources.

#TaskInformation
1Create a custom ACS adapter to manage requests for remote attributes from a specific external resource.See acs-using-access-control-services.html#task_06e85f49-b32f-4261-87aa-0604905022c7.
2Create a common ACS connector to manage requests for remote attributes for policy evaluation.See acs-using-access-control-services.html#task_6b9244e0-fb0a-4d26-8387-5ce7c2920a32.

Creating An ACS Attribute Adapter

Create a custom ACS adapter to manage requests for remote attributes from a specific external resource.

Before You Begin

Select a REST client (such as Postman) to create a REST API that can interface with the Attribute Connector Management API to retrieve remote attributes from an external resource. For more information about Attribute Connector Management API, see the API Documentation (Predix.io home page – Documentation – Service APIs).

Note:

You must specify the Predix-Zone-Id header when you use this REST API to communicate with a deployed application about its environment.. For more information, see acs-getting-started.html#task_a2375607-175a-40bc-b53b-2133c16473ad.

About This Task

As a developer, you need to create a REST API that follows a common scheme to retrieve remote attributes from an external resource for evaluation in access-policy conditions. For example:
GET {adapterEndpoint}/v1/attribute?id={id}
where
  • {adapterEndpoint} is the adapter URL to retrieve remote attributes from an external resource.
  • {id} is the identifier to retrieve remote attributes .
Note:

An error will occur if the REST API does not match the /v1/attribute?id={id} syntax.

The response to the GET call would return the value of the remote attributes associated with {id}:. For example:

{
 "attributes": [
 {
 "issuer": "string"
 "name": "string",
 "value": "string"
 }
 ],
 "id": "string"
 }

Creating an ACS Attribute Connector

Create a common ACS connector to manage requests for external attributes for policy evaluation.

Before You Begin

Select a REST client (such as Postman) that can execute API requests for the Attribute Connector Management service. For more information about this API, see the API Documentation (Predix.io home page – Documentation – Service APIs).

Note:

You must specify the Predix-Zone-Id header when you use this REST API to communicate with a deployed application about its environment.. For more information, see acs-getting-started.html#task_a2375607-175a-40bc-b53b-2133c16473ad.

About This Task

The syntax to configure an ACS attribute connector to manage requests for external attributes from an external source is listed:

{
  "adapters": [
   {
    "adapterEndpoint":"string",
    "uaaTokenUrl":"string",
    "uaaClientId":"string",
    "uaaClientSecret":"string"
    }
    ]
    "isActive":"boolean",
    "maxCachedIntervalMinutes":"number",
}
The ACS attribute connector can have the following values:
  • adapterEndpoint: ACS attribute adapter URL to retrieve attribute data from the external source, If an adapter is configured and is active, it will be used as the source for attributes instead of the built-in attribute store managed by the Attribute Management Service (see acs-overview.html#concept_tjm_4p3_mr).
  • uaaTokenUrl UAA URL used to request an access token for the adapter.
  • uaaClientId: OAuth2 client used to obtain an access token for the adapter.
  • uaaClientSecret: OAuth client secret used to obtain an access token for the adapter ,
  • maxCachedIntervalMinutes : Maximum time (in minutes) before external attributes are refreshed.
  • isActive : A flag that either enables or disables the retrieval of external attributes.

Here a sample request body for the PUT /v1/connector/resource API that can be used as a template

{
    "adapters": [
        {
            "adapterEndpoint": "https://<adapter.fully.qualified.domain>/v1/attribute",
            "uaaClientId": "<connector_client_id>",
            "uaaClientSecret": "<connector_client_secret>",
            "uaaTokenUrl": "https://<uaa-instance-guid>.<uaa-service-id>.run.aws-usw02-pr.ice.predix.io/oauth/token"
        }
    ],
    "isActive": true,
    "maxCachedIntervalMinutes": 480
}