Skip to content

Latest commit

 

History

History
183 lines (147 loc) · 5.69 KB

README.md

File metadata and controls

183 lines (147 loc) · 5.69 KB

How to demo

Run OPA in server mode

  1. Check the latest OPA release and download it.

  2. Put the binary file in the PATH of your system

  3. Allow its execution with something like

    chmod 755 ~/opa
  4. Run opa in server mode with the sample policies:

    cd examples
    opa run -s data.json app.rego

In this folder (examples) you will find a simple app.py file that contains endpoints to test how you can see some data using OPA. For commodity purposes the user id will be passed in the request using the header Authorization.

Run the app.py file with your IDE. It will run in http://localhost:5000

Try out some http requests

  • Check the home page curl http://localhost:5000

  • Check list of users using a non admin user: Denied

      curl -X GET \
        http://localhost:5000/list \
        -H 'Authorization: paul' \
        -H 'Content-Type: application/json'
  • Check list of users using an admin user: Granted

      curl -X GET \
        http://localhost:5000/list \
        -H 'Authorization: eliux' \
        -H 'Content-Type: application/json'
  • Add a new user (steve) data using an admin user: Granted

    curl -X POST \
      http://localhost:5000/data/steve \
      -H 'Authorization: steve' \
      -H 'Content-Type: application/json' \
      -d '{
        "fullname": "Steve Perez",
        "city": "New York",
        "salary": 3400,
        "biography": "Studied in harvard. Leaves in Miami, Florida"
    }'
  • Get new user's data using another non admin user: Denied

     curl -X GET \
       http://localhost:5000/data/steve \
       -H 'Authorization: paul' \
       -H 'Content-Type: application/json'
  • Get new user's data using an admin user: Granted

     curl -X GET \
       http://localhost:5000/data/steve \
       -H 'Authorization: eliux' \
       -H 'Content-Type: application/json'
  • Get new user's data using same user, yet not a admin one: Granted

     curl -X GET \
       http://localhost:5000/data/steve \
       -H 'Authorization: steve' \
       -H 'Content-Type: application/json'
  • Try to delete a user using the same user but not an admin one: Denied

    curl -X DELETE \
      http://localhost:5000/data/steve \
      -H 'Authorization: steve' \
      -H 'Content-Type: application/json'
  • Try to delete a user using an admin user: Granted

    curl -X DELETE \
      http://localhost:5000/data/steve \
      -H 'Authorization: eliux' \
      -H 'Content-Type: application/json'

Try Policy Enforcement Point on functions

When you try to enforce policies beyond the endpoint layer you may not want to evaluate policies just depending on the data related to the user request, but probably you need to be aware of the parameters of a function. E.g.

Problem

  1. We want to create a function for logging data in a remote server. For this purpose we will create a log dedicated function called log_remotely, which will be used in multiple endpoints.
  2. The log function will be allowed to log only info generated by admin users or if the content to be logged names any admin user.

Solution

  1. As the logging will be used in difference execution points of our app, the input of the corresponding policies should be independent of the request. In such cases its better to use a Policy Enforcement Point to enforce specialized policies for this particular scenario of security.
  2. A new OPA package called logging will be created to enforce this particular set of policies.

In this example project, logging a message will be allowed if:

  • The requesting user is administrator or
  • The logged content contains information about an administrator

You can see the implementation of the PEP in Python in utils.py and the policies in logging.rego.

Follow the following steps to demo this functionality.

  1. Create a valid non admin user
    curl -X POST \
      http://localhost:5000/data/steve \
      -H 'Authorization: eliux' \
      -H 'Content-Type: application/json' \
      -d '{
        "fullname": "Steve Perez",
        "city": "New York",
        "salary": 3400,
        "biography": "Studied in harvard. Leaves in Miami, Florida"
    }'

As the user executing the query is administrator you will see a log that says:

Updated user steve with data {...}

Which means that when the function utils.log_remotely the OPA returned true for the given input and the logging routing was executed successfully.

  1. List the created user data with a non valid user
    curl -X GET \
      http://localhost:5000/data/steve \
      -H 'Authorization: steve' \
      -H 'Content-Type: application/json' \
      -H 'Postman-Token: dba83620-3117-4a57-b330-f1b0efd93c0b' \
      -H 'cache-control: no-cache'

For the previous request the OPA policies of the application (app.rego) will allow steve to see its own data. Nonetheless, as steve is not an administrator and no admin user was referenced in the added content the previous request wont be logged.

  1. Lets try the previous request but this time with an admin user.
    curl -X GET \
      http://localhost:5000/data/steve \
      -H 'Authorization: eliux' \
      -H 'Content-Type: application/json' \
      -H 'Postman-Token: dba83620-3117-4a57-b330-f1b0efd93c0b' \
      -H 'cache-control: no-cache'

You should get something like

  Logged remotely: Queried user steve

Check the logging_test.rego to check other valid and invalid queries.