How to limit an Authorized user, using Entra Id, to only retrieve records that the user owns, while using a Static Web App, Data API builder for ComosDB, and ownership is determined by a deviceID (a mac address) in the Body (IoT) data.

Adrian Wreyford 45 Reputation points
2024-04-13T15:28:24.48+00:00

I have created a Static Web App, that is up and running, with a Database Connection to a Cosmos DB database.

I have the necessary schema.gql, and config.json set up.

The user needs to be able to connect to the Database using the /data-api/graphql endpoint.

The data in the CosmosDb database is ingested through IoT Hub, and then routed to different containers.

I require an Authenticated user (EntraId), to be able to only see for example all records in the activity container,
that he owns the device for.

There is a user container, that has an entry for all the deviceId's that the user owns.

User1, has access to 3 devices, with Mac's "EDEDEDEDED", "EFEFEFEFEF", "ABAEABAEAB".

An activity item is structured as follows:

{
    "id": "a352212e-ada7-4a11-aba1-acff41a344e60",
    "Properties": {
        "action": "addActivity"
       },
    "SystemProperties": {
        "iothub-connection-device-id": "ABAEABAEAB",
        "iothub-connection-auth-method": "{\"scope\":\"device\",\"type\":\"sas\",\"issuer\":\"iothub\"}",
        "iothub-connection-auth-generation-id": "6222229588333403",
        "iothub-content-type": "application/json",
        "iothub-content-encoding": "utf-8",
        "iothub-enqueuedtime": "2024-04-13T11:31:22.111Z",
        "iothub-message-source": "Telemetry"
    },
    "iothub-name": "La",
    "Body": {
        "la_activity_device_mac_date": "ABAEABAEAB-2024-04-13",
        "action": "addActivity",
        "la_activity_device_mac": "ABAEABAEAB",
        "la_activity_index": 56,
        "la_activity_dev_ref": "12",
        "la_activity_block": "",
        "la_activity_activity": "",
        "la_activity_mode": 100,
        "la_activity_tag": "FFAAB3D2AA0",
        "la_activity_date": "2024-04-13",
        "la_activity_time": "13:31:21",
        "la_activity_timestamp": 1713007881,
        "la_activity_quantity": 1
    },
    "_rid": "ACDEAA8RtGQAAAAAAAA==",
    "_self": "dbs/UCQTAA==/colls/ACDEAA8Rt=/docs/"ACDEAAA8RtGQAAAAAAAA==/"",
    "_etag": "\"06447cac-0000-2000-0011-621f6da00000\"",
    "_attachments": "attachments/",
    "_ts": 1713007882
}

So this client User1 is only allowed to see the above record, as he owns "ABAEABAEA"

There is an Entity section to the config.json, that one can define roles, activities, policies and database.
I'm thinking that his may be the solution, but has no apparent effect on the data returned.

Config as follows:

{
  "$schema": "https://github.com/Azure/data-api-builder/releases/download/v0.10.23/dab.draft.schema.json",
  "data-source": {
    "database-type": "cosmosdb_nosql",
    "connection-string": "@env('my-connection-string')",
    "options": {
      "database": "loadassist-agri",
      "container": null,
      "schema": "schema.gql"
    }
  },
  "runtime": {
    "rest": {
      "enabled": false,
      "path": "/api",
      "request-body-strict": true
    },
    "graphql": {
      "enabled": true,
      "path": "/graphql",
      "allow-introspection": true
    },
    "host": {
      "cors": {
        "origins": [],
        "allow-credentials": false
      },
      "authentication": {
        "provider": "StaticWebApps"
      },
      "mode": "development"
    }
  },
  "entities": {
    "Activity": {
      "source": {
        "object": "activity"
      },
      "graphql": {
        "enabled": true,
        "type": {
          "singular": "Activity",
          "plural": "Activities"
        }
      },
      "rest": {
        "enabled": false
      },
      "permissions": [
        {
          "role": "anonymous",
          "actions": [
            {
              "action": "read",
              "policy": {
                "database": "@item.Body.la_activity_device_mac eq \"ABAEABAEA\""
              }
            }
          ]
        }
      ]
    },
}

This

"policy": {
                "database": "@item.Body.la_activity_device_mac eq \"ABAEABAEA\""
              }

does not appear to work, and doesn't look like the correct approach. Please note that I'm testing as anonymous, and not authenticated above in the config.

I've searched a lot but cannot find any pointers as to how to implement a secure way to limit a user to only see their own data, through the graphql api endpoint to cosmosdb.

Cross partition queries are also not available to Data API builder for CosmosDB.

Currently all items are visible to all users.

Thank you

Azure Cosmos DB
Azure Cosmos DB
An Azure NoSQL database service for app development.
1,633 questions
0 comments No comments
{count} votes

Accepted answer
  1. Sajeetharan 2,261 Reputation points Microsoft Employee
    2024-04-14T18:07:05.5866667+00:00

    Hi,

    Thanks for asking the question. I am the PM for the Data API Builder, currently we do not support database policy for Azure Cosmos DB, we are working on adding the support which will be available in couple of months. It works only with relational databases as of now

    You can open up a issue or discussion item here

    1 person found this answer helpful.

0 additional answers

Sort by: Most helpful

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.