1

I'm working on designing a system for reporting/storing information on hardware devices (IoT-like), and trying to figure out how that would best be structured in Azure's Cosmos DB.

Every device will have a unique string identifier, and several groups of properties we need to record. I don't have the structure finalized yet, but it will be something like:

{
    "deviceIdentifier": "model-serial0123",
    "summaryInformation": {
        "isActive": true,
        "purchaseDate": "2020-02-11T20:31:47.6450853Z",
        ...
    },
    "configurationSettings": {
        "setting1": "value1",
        "setting2": "value2",
        ...
    },
    "checksums": {
        "fileA.xyz": "ABCD1234",
        "fileB.xyz": "EF567890",
        ...
    }
}

Each of the various blocks can have a large number of key/value entries, and will not necessarily need to be retrieved at the same time.

In a standard relational database, I would have the deviceIdentifier as a natural key, and then the other three blocks would be separate tables with a foreign key to the list of device identifiers. My instinct here is to set teh deviceIdentifier field as a partition, and to split the three sub-blocks into separate documents in the same partition. That might be my prior experience leading me astray, though.

In NoSQL (and Cosmos in specific), does it still make sense to split this up into separate documents? Or is it reasonable to have a single document per partition? Am I even choosing the right type of field to partition on?

If I do split it up, how do I do a search for something like "devices with setting1 of value AND checksum of fileA.xyz of ABCD1234"? Or does the fact that I'll sometimes need to reassemble this information imply that I should keep it all together even if it will usually result in returning more data than necessary?

Basically, I'm struggling at wrapping my mind around how to best model this data in an unstructured manner, and even knowing what questions to ask myself.

1

It's OK to have sparse documents in a document database, in fact it's probably one of the better reasons to use one. Let the indexer deal with it. If you later discover your access patterns have changed, you can provision an indexing policy for specific properties

You'd want the deviceIdentifier as an unique key so the database can help enforce it's uniqueness

Defining a partition key is kind of a chance to have one query parameter optimized for you ("Candidates for partition keys might include properties that appear frequently as a filter in your queries."). Looks for another property that's always present but I would not sweat it too much if your design just doesn't have one that's also a good statistical distribution (i.e. not "Manufacturer").

| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.