Privacy of users/organizations data in the application - node.js

I am currently designing an application with many organizations, and each organization will have many users. My concern is about the data privacy and security of these organizations/users. It should never happen that organization A would see data of organization B and vice versa.
I want to use PostgreSQL and Node.js (Nest.js), but the technology does not play a strong role here.
I wanted to have one PostgreSQL database where each organization has its schema, for example, orgA.organizations, orgB.organizations, etc. Unfortunately, I found that it is not a good solution. With many schemas, there can be a performance problem. Then I was thinking about database per organization, but it seems like a huge overhead to handle ~1000 databases.
Now, I am thinking about having a "flat database structure" - without any schemas and having just one database. Organizations would be just in one table and the same for users.
The concern with data privacy would be solved primarily on the application level - I would check if user A can access the data of organization A. Still, in the database, these data will "live together".
So, my question is - what is the best way/technique to ensure that user A that belongs to organization A, will never see the data of organization B?

Related

DDD - How to ensure aggregate consistency when integrating with third party systems?

This question is really two-fold with emphasis on the most important question.
Aggregates define the consistency and transactional boundaries of a system.
Say your company provides some service through an app and you are about to add a new feature through an integration with a third party. The third party has its own API and you need to create the user in their system when they choose to use the new feature. Now, you're not a monster, so you allow users to toggle off the feature if they had previously started using it. This means you must also be able to delete the user in the third party API.
If we were to design an Aggregate for such a feature (lets say it is a subscription), where should we put the interaction with the third party API?
What if the third party we integrate with allow the users to remove themselves from their system bypassing our app completely? Now our aggregate would be out of sync.
Generally, an aggregate enforces consistency not on a system level, but over some data. The concept was introduced in the DDD blue book, and at a time where most solutions relied on traditional large-scale SQL db's, and it intended to remove responsibility for consistency from the storage layer, and into business logic. It did so because that's what consistency is: business logic. If you have to decrease stock when you sell something, this is a consistency rule, and one which should live in application code, with other business logic instead of being delegated to a stored procedure.
With that in mind, any aggregate you'd have wouldn't (indeed couldn't) enforce consistency with the outside world (it's not data you own and hold internally). However, what you could do is introduce two (or one combined) process managers:
One process manager that would enforce the policy of "when a user asks to get deleted, delete them from the external system". This would observe internal requests and call out to the 3rd party service to delete a user when the user requested to be deleted
One process manager that would enforce the policy of "when a user gets deleted from the third party service, mark them as deleted in our system too" which would do pretty much what the policy says
You may or may not have a subscription aggregate. What would determine that is if you need to enforce some consistency around data you own and are responsible for.

MicroServices separate databased

I'm creating a micro services for example one for user management i.e (roles, credentials, rights, menus etc) related and one for bank account-details, now i have a scenario to getting user roles detail and rights detail from db, is it a good practice to repeat columns of database user management db i.e.(roles, rights) in bank-account db as per requirement or duplicate data in bank-account db ?
Or no need to duplicate data in bank-account db and send a separate call to get user data first from user management db ?
please suggest a best possibility
Waqas,
You're in microservices environment. There is a well-known Domain Driven Design (DDD) with one of a key pattern of Bounded Contexts. That means you should try to avoid mixing the contexts and duplicate the user information in bank-account db (it might be inevitable some time, but I suppose not in your case).
Therefore, it's fine that you have to call user management service in order to gain the required information about your users.
I agree with #Stepan Tsybulski. Also, I suggest you reduce the need for a bounded context to depend on the other to the minimum possible. So, duplication of data is the best option here. However, you do not have to have roles and rights in the Bank Account context / DB. I'd put in the Bank Account context only what's necessary in that context: User details (such as names, birthdates, etc.) + user id.
You get the roles and rights from the session. You manage roles in the User Management context only. It's good for security and consistency, plus it's the reason for using Contexts.
There are many ways to approach a problem, but that's how I'm doing it.

Entity-level access restriction in the microservice architecture based on user or group membership

In the systems, there may be data that is restricted in nature.
Sometimes access to specific entities should be easily restricted or granted based on user or group membership.
What is the best way to implement this in the microservice architecture?
#1
Should access control, managing permissions etc. be the responsibility of the microserive itself? Developers will have to implement access control, store, and update permissions for every service. Seems like not very robust and error-prone approach.
#2
Create dedicated microservice handling permission management? This service will be called by other microserives to check access permissions for each entity and filtering entities before returning results. Centralized permissions storage and management is an advantage but microservice will have to make a call to "Permission Service" for each entity to check access rights what may have a negative influence on performance. And developers still have to integrate access checks into their services what leaves space for an error.
#3
Make access control responsibility of the API Gateway or Service Mesh. It is possible to think of an implementation that will automatically filter responses of all services. But in the case when the microservice returns list of entities permissions should be checked for each entity. Still a potential performance problem.
Example
Consider the following synthetic example.
Healthcare system dealing with test results, X-Ray images etc. Health information is very sensitive and should not be disclosed.
Test results should be available only to:
patient
doctor
laboratory
Attending doctor may send the patient to another specialist. A new doctor should have access to test results too. So access can be granted dynamically.
So each entity (e.g. test results, X-Ray image) has a set of rules what users and groups are allowed to access it.
Imagine there is a microservice called "Test Results Service" dealing with test results. Should it be responsible for access control, manage permissions etc.? Or permissions management should be extracted to separate microservice?
Healthcare system may also handle visits to a doctor. Information about patient's visit to the doctor should be available to:
patient
doctor
clinic receptionist
This is the example of a different entity type that requires entity level access restriction based on user or group membership.
It is easy to imagine even more examples when entity level access control is required.
I came to the following generic solution.
ACL security model is used. Each object in the system has associated set of permissions. Permissions defines who and what actions can perform on the object.
Microservices are responsible for entity-level authorization and filter objects in responses based on permissions of the objects.
Central Access Control Service is responsible for the creation, update, and deletion of permissions for all objects in the system. Access Control Service database is the primary store of objects' permissions.
Permissions stored in microservices databases are synchronized with Access Control Service database using event-carried state transfer. Every time, permissions are changed an event is sent to the message broker. Microservices can subscribe to these events to synchronize permissions.
API Gateway can be used as the additional protection layer. API Gateway can call Access Control Service directly (RPC) to check response objects' permissions or load recently revoked permissions.
Design features:
A way to uniquely identify each object in the system is required (e.g. UUID).
Permissions synchronization in microservices are eventual consistent. In case of partitioning between message broker and microservice permissions will not be synchronized. It may be a problem with revocation of the permissions. The solution to this problem is a separate topic.
Looks like security is a part of business logic here. In both examples.
Then security could be a part of data scheme.
For example,
Patient can see his tests:
select * from test_result where patient_id=*patient_id*
Doctor can see all test from his medical department:
select * from test_result where branch_id=*doctor_branch*
I believe that to have separate MS for access control is a really bad idea and could lead serious performance problems. Just imagine situation that somebody with zero entity access tries to fetch all entities each time :) You will always need to handle larger result sets than actually needed.
Firstly, this is very bad idea to have a separate (per microservice) security model. It should be single always cross-cutting all application, because it can lead to a hell with access management, permissions granting and mapping between entities in different microservices.
In second, I assume that you are wrong with understanding how to organize microservices..? You should dedicate the principle of splitting functionality into microservices: by features, by domain, etc. Look at Single Responsibility, DDD and other approaches which helps you to achieve clear behavior of your MS.
So, in best case, you should have to:
Choose right security model ABAC or RBAC - there are a lot of other options, but looking at your example I guess the ABAC is the best one
Create separate MS for access management - the main responsibility of this MS is a CRUD and assignment of groups/roles/permissions/attributes to the people accounts.
Create separate MS for providing only permitted health information.
In third, how it works?:
With ABAC you can setup hierarchical roles/permissions (based on groups/attributes) - it helps you to resolve a delegation path of who is permitted to the data
Setup authorization (via auth-MS) and store the list of permissions (in session, cookies, etc)
Check access for a given user for a needed data in health-info-MS. Here we have several options how to do this:
If you use memory-grids (hazelcast, coherence), you can easily create filters with predicates based on security attributes.
If you're using SQL (hibernate, plain SQL, etc.) you should generate queries to return only permitted data - add security specific criteria to the where clause
Few more details about SQL queries with security check in where: before the SQL execution (if hibernate & spring is easy to do with spring-method-auth hook) you should resolve all permissions assigned to a user - you can do this with call to auth-MS.
Example
We created CRUD permissions for TestResult entity - VIEW, EDIT, DELETE.
The role DOCTOR can see any TestResults - so, it has VIEW permission
The role PATIENT can see only his/her TestResults
So, you create a business rules which provide the correct where clause for each business role (DOCTOR, PATIENT, LAB, etc.) and at the end the SQL request would be like:
For patient who has assigned VIEW permission:
select * from test_result where id=*patient_id* and 1=1
For patient who hasn't assigned VIEW permission:
select * from test_result where id=*patient_id* and 1!=1
NOTE: In business rules we can add 1=1 or 1!=1 to permit/restrict query result

SSAS security: is one role per user practical?

We have to authorize hundreds of users for a cube, and the users must be restricted to individual dimension members. Two dimensions are relevant for the permissioning, a datatype permission (with only 10 members) and a customer dimension (with 2000+ members).
Since one user can be permissioned for any number of datatypes and customers, we could build one role per datatype and one role per customer... ending up with 2010+ roles. The datatype roles are not authorized for any customers and vice versa, therefore we could enable users for any combination of datatypes and customers.
On the other hand, if we create one role per user, we end up with only hundreds of roles. I therefore do not see the benefit of roles in our scenario. We will probably use AMO to maintain the roles.
My question is, if there is a penalty when using one role per user or it this is a tested method. Of course I am also interested in any alternative approach.
Problem in this case is that you don't have any data that would help you automate the roles.
So in order to make use of suggestions by mmarie you will need to further develop your cube and to maintain the user-customer relationship somehow (more horrible admin work).
Technically your scenario seems simple enough to be handled by http://easyroles.com which was made specifically to help out in these situations.
Disclaimer: I am involved with eR tool, but there is no other way I can answer this question since there are no other tools that are made for this.

How can I enforce security or permissions on a bound dataset?

Using a strongly typed dataset and its related table Adapters, normally when I want the changes to pass back, just pass it the table and let it do all the work.
What are some easy ways to enforce security roles on the application user as to which fields they can insert/update/delete when the database is using an application ID instead of user level security?
Do I have to go row by row and check each row against what this particular user is allowed to do (by checking the current version of every field against it's proposed version against their role's permissions?
I believe the first level of security would be locking down the columns on the UI a particular user is not supposed to modify, but what about at the data level? Is there a nice way to do this?
Is this easier in linq-to-sql?
First, are you asking about actual security or just control/saftey/fool-proofing (ie stopping users from doing something dumb)?
If you are trying to enforce security try to answer some questions like who is allowed to connect to the database? where is the actual enforcement (eg, application vs connection to the database)?
For example if your application is where enforcement is placed then what if your application is compromised? Can it then connect to the database and do whatever?
For role separation I would suggest different application that are running/assigned different roles. Each role has to authenticate against the database in some way and only have access to necessary data.
In summary, ask who is doing what to whom and what if they were compromised.

Resources