OrientDB - How To - Record Level Security with ODocument

akagixxer

I'm trying to get Record Level Security working using the Document database (Java) API for OrientDB. I like the idea of restricting access for certain records in the database to particular roles; however, I could not find how to do this in the documentation. I'm new to OrientDB so I'm sure I'm just missing something.

Here is what I have so far.

// Create database.
ODatabaseDocumentTx db = new ODatabaseDocumentTx(path);
db.create();

// Create role with no permissions.
db.command(new OCommandSQL("INSERT INTO orole SET name = 'foobar', mode = 0;")).execute();

// Create a user with the new role.
OSecurity sm = db.getMetadata().getSecurity();
OUser user = sm.createUser("user", "user", "foobar");
ORole foobarRole = sm.getRole("foobar");

// Insert 2 records, one restricted, one is not.
OClass restricted = db.getMetadata().getSchema().getClass("ORestricted");
OClass docClass = db.getMetadata().getSchema().getOrCreateClass(TABLE_NAME, restricted);

ODocument doc1 = new ODocument(docClass);
ODocument doc2 = new ODocument(docClass);

// The restricted record...
doc1.field("name", TABLE_NAME);
doc1.field("Id", 1, OType.INTEGER);
doc1.field("Message", "Hello 1", OType.STRING);
doc1.save();

// The unrestricted record...
doc2.field("name", TABLE_NAME);
doc2.field("Id", 2, OType.INTEGER);
doc2.field("Message", "Hello 2", OType.STRING);
doc2.save();

// Allow "user" with "foobar" role to read record doc2.
String sql = String.format(
  "UPDATE %s ADD _allowRead = %s",
  doc2.getIdentity().toString(),
  foobarRole.getDocument().getIdentity().toString());

db.command(new OCommandSQL(sql)).execute();

// Give foobar role permission to read from table.
db.command(new OCommandSQL(String.format("GRANT READ ON database.class.%s TO foobar", TABLE_NAME))).execute();

db.close();

// Open connection for "user".
ODatabaseDocumentTx userDb = new ODatabaseDocumentTx(path);
userDb.open("user", "user");

// Here I would expect to see the message from doc2 but not doc1.
// Nothing gets printed...
for (ODocument odoc : userDb.browseClass(TABLE_NAME))
{
  System.out.println(odoc.field("Message"));
}

The documentation says that records that are not accessible to a role are skipped during a READ. In my case, the user cannot read anything.

Any ideas of how can I get this behavior working?

akagixxer

After a couple days of fiddling with it, this is how I got it to work.

// Create database.
ODatabaseDocumentTx db = new ODatabaseDocumentTx(path);
db.create();

// Create users/roles.
OSecurity sm = db.getMetadata().getSecurity();

restrictedRole = sm.createRole("foobar", OSecurityRole.ALLOW_MODES.DENY_ALL_BUT);
restrictedRole.addRule(ORule.ResourceGeneric.CLASS, TABLE_NAME, ORole.PERMISSION_READ);
restrictedRole.addRule(ORule.ResourceGeneric.DATABASE, TABLE_NAME, ORole.PERMISSION_READ);
restrictedRole.addRule(ORule.ResourceGeneric.CLUSTER, TABLE_NAME, ORole.PERMISSION_READ);
restrictedRole.save();
restrictedRole.reload();

admin = sm.getUser("admin");
user2 = sm.createUser("user2", "user2", "foobar");

// Insert 2 records, one restricted, one is not.
OClass restricted = db.getMetadata().getSchema().getClass("ORestricted");
OClass docClass = db.getMetadata().getSchema().getOrCreateClass(TABLE_NAME, restricted);

ODocument doc1 = new ODocument(docClass);
ODocument doc2 = new ODocument(docClass);

// The restricted record...
doc1.field("name", TABLE_NAME);
doc1.field("Id", 1, OType.INTEGER);
doc1.field("Message", "Hello 1", OType.STRING);
doc1.save();

// The unrestricted record...
doc2.field("name", TABLE_NAME);
doc2.field("Id", 2, OType.INTEGER);
doc2.field("Message", "Hello 2", OType.STRING);
db.getMetadata().getSecurity().allowRole(doc2, OSecurityShared.ALLOW_READ_FIELD, "foobar");
doc2.save();

//
// PRINT RESTRICTED
//
db.close();
db = new ODatabaseDocumentTx(path);
db.open("user2", "user2");

// Prints:
// Hello 2
for (ODocument doc : db.browseClass(TABLE_NAME))
{
  System.out.println(doc.field("Message"));
}

//
// PRINT ADMIN
//
db.close();
db = new ODatabaseDocumentTx(path);
db.open("admin", "admin");

// Prints:
// Hello 1
// Hello 2
for (ODocument doc : db.browseClass(TABLE_NAME))
{
  System.out.println(doc.field("Message"));
}

The addRule method on the role allows users with that role to read from the class. The second document has an extra line with allowRole which allows users with that role to read that particular document, this was left out of the first document on purpose. The result is that users with the "foobar" role only get the second document while reading. The admin role can read both documents.

Also, note the document class inheritance from "ORestricted".

OClass restricted = db.getMetadata().getSchema().getClass("ORestricted");
OClass docClass = db.getMetadata().getSchema().getOrCreateClass(TABLE_NAME, restricted);

The document needs to inherit from ORestricted in order for the record level security to work. Personally I found no explanation of how to do this in code anywhere (maybe I did not look in the right places) and there is no document class in Java that directly inherits from an ORestricted class. So we have to use the schema class metadata to tell the driver that the documents we are creating need to inherit from ORestricted.

Collected from the Internet

Please contact [email protected] to delete if infringement.

edited at
0

Comments

0 comments
Login to comment

Related

From Dev

MS Access - record level security

From Dev

How to save ODocument in map field in Vertex with Java

From Dev

OrientDB, how to retrieve previous record version

From Dev

How add embedded map to record with sql in OrientDb

From Dev

OrientDB graph: How to use Java API to create a new Record?

From Dev

How do I get all the versions of a record in orientdb

From Dev

How do I find references to a given record for a specific field in the referencing record in OrientDB?

From Dev

How do I change the Java Security level?

From Dev

How to know the social networking websites security level

From Dev

How do I query OrientDB Vertex graph object by Record ID in Java?

From Dev

How do you find a mongodb record that is two level deep

From Dev

How to stay always logged in with Level 3 Perforce security (ticket based)?

From Dev

How to know if field is masked due to field level security?

From Dev

How to implement user-level security in Access 2007

From Dev

Ubuntu 20.04 - how to set lower SSL security level?

From Dev

Ubuntu 20.04 - how to set lower SSL security level?

From Dev

How to implement Field Level Security in Microsoft Dynamics CRM 2011

From Dev

How to implement user-level security in Access 2007

From Dev

How to know if field is masked due to field level security?

From Dev

How to disable the OrientDb in Moqui

From Dev

Is it possible to update the class for a record in OrientDB after creating the record?

From Dev

Collection with record level locking?

From Dev

record level access in cakephp

From Dev

User level security?

From Dev

How to apply Distinct Query in OrientDB?

From Dev

How to populate an OrientDB Time Series?

From Dev

How to use OrientDB in a SailsJS App

From Dev

How to insert embedded document in orientdb

From Dev

How to view linked data in OrientDB

Related Related

  1. 1

    MS Access - record level security

  2. 2

    How to save ODocument in map field in Vertex with Java

  3. 3

    OrientDB, how to retrieve previous record version

  4. 4

    How add embedded map to record with sql in OrientDb

  5. 5

    OrientDB graph: How to use Java API to create a new Record?

  6. 6

    How do I get all the versions of a record in orientdb

  7. 7

    How do I find references to a given record for a specific field in the referencing record in OrientDB?

  8. 8

    How do I change the Java Security level?

  9. 9

    How to know the social networking websites security level

  10. 10

    How do I query OrientDB Vertex graph object by Record ID in Java?

  11. 11

    How do you find a mongodb record that is two level deep

  12. 12

    How to stay always logged in with Level 3 Perforce security (ticket based)?

  13. 13

    How to know if field is masked due to field level security?

  14. 14

    How to implement user-level security in Access 2007

  15. 15

    Ubuntu 20.04 - how to set lower SSL security level?

  16. 16

    Ubuntu 20.04 - how to set lower SSL security level?

  17. 17

    How to implement Field Level Security in Microsoft Dynamics CRM 2011

  18. 18

    How to implement user-level security in Access 2007

  19. 19

    How to know if field is masked due to field level security?

  20. 20

    How to disable the OrientDb in Moqui

  21. 21

    Is it possible to update the class for a record in OrientDB after creating the record?

  22. 22

    Collection with record level locking?

  23. 23

    record level access in cakephp

  24. 24

    User level security?

  25. 25

    How to apply Distinct Query in OrientDB?

  26. 26

    How to populate an OrientDB Time Series?

  27. 27

    How to use OrientDB in a SailsJS App

  28. 28

    How to insert embedded document in orientdb

  29. 29

    How to view linked data in OrientDB

HotTag

Archive