The first challenge was Modelling a set of Tables with Relationships to a Graph. After studying the Tables and Their Relationships I came up with the following Design.
This design can be improved but I stuck with this because the intention was to increase performance not to win a Design competition. Furthermore this design covers the Domain of Spring Security ACL concisely so I stuck with this. Naming of the relationships could be improved but I like these.
In order to successfully provide a Neo4j back-end for Spring Security ACL we must implement three interfaces with Neo4j specific implementation.
- LookupStrategy - Used to Read Acls based on Class Name and Instance Id
- AclService - Non Mutable Acl related Services
- MutableAclService - Mutable Acl related Services
Implementation Decisions
I used Spring-Data-Neo4j project which is an abstraction layer on top of the Neo4j Graph Database which allows annotated classes to be represented as Nodes and Edges, which is convenient for Rapid Development. Furthermore it allows Repositories to do CRUD operations also but in this project I opted not to use them and instead used Neo4jTemplate because I knew I would need to write alot of Dynamic Cypher queries.
Development
The full source of the development is available at https://github.com/shazin/spring-security-acl-neo4j
Testing
The biggest question is "Will it be faster than RDBMS based implementations?". If not the whole project was a failure. Test coverage was done on both Mutable and Non Mutable Acl Services. Testing Non Mutable Acl Service will cover Lookup Strategy as it is used underneath.
Neo4j In-memory Test Database was used to Test. This is a JVM based, Production Not Ready, Single Database instance. Assuming Production ready Neo4j Embedded or Neo4j Server Databases will increase performance (It ideally should) I decided to test using this.
The RDBMS I used to Test against was H2, which is also a JVM based, but Production Ready In-memory Database.
Both being in-memory implementations and being JVM based somewhat testifies that the underlying Storage hardware has no input in performance (SATA, SSD, doesn't matter) and no latency due to Network congestion.
And I was using the Ubuntu 14.04 LTS 64-bit Operating system with Intel Core i7 Processor, 4 Gb RAM and Sun JDK 8.
Test Data comprised of 200 ACL Entries (2 for each Object Identity), 3 Sids (Including logged in User Sid), 100 Classes and 100 Object Identities.
Testing was mainly focused on Retrieval and for to retrieve 50 non following Object Identities with ACL Entries (2 for each Object Identity) while running four random times with an Empty Cache, following were the results.
The results are in Nanoseconds and Neo4j based Spring Security Acl implementation is a clear winner!
Conclusion
Neo4j clearly stands up for its claims and with this implementation Spring Security ACL could also reach its fullest potential. Can clearly say that this is one of the fastest backend implementations for Spring Security ACL. Even though the difference is in Nanoseconds, the performance will matter with higher volume of Users, Object Identities, Sids and ACL Entries.
The code base could be improved, specially in Cypher queries thus increasing performance even more. Anyone who likes to contribute is welcome.
This doesn't mean that RDBMS are now obsolete. I personally think that RDBMS will be here for at least another 20 years if not more!
And constructive criticism is always welcome.
References
- http://neo4j.com/docs/stable/introduction.html - Cypher Language
- http://www.h2database.com/html/main.html - H2 Database