Learning about constraints in Alloy - alloy

I'm exploring Alloy for my company hackathon. We have a complicated data model, and my goal is to generate pictures of correct examples so that new employees can see them and learn about our application. I've managed to stumble along and generate some pictures, but I'm having trouble expressing the following idea:
A role can grant access to one or more fields. A user has one or more roles, and can access zero or more fields. A user can access a field if and only if the user has a role which grants access to that field.
Here's one of many attempts with incorrect syntax; hopefully it shows what misconceptions I have about how Alloy works.
sig Role { grantsAccess: some Field }
sig User {
has: some Role,
canAccess: Field
}{
all u: User |
f: Field in u.canAccess iff some r: Role in u.has | f in r.grantsAccess
}
Thank you!

-- A role can grant access to one or more fields.
sig Role { grant : some Field }
sig Field {}
-- A user has one or more roles,
-- and can access zero or more fields.
sig User {
roles : set Role
}
-- A user can access a field
pred User.canAccess[ field : Field ] {
-- if and only if the user has a role
-- which grants access to that field.
some role : this.roles | field in role.grant
// alternative:
// some ( this.roles & grant.field )
}
run ex1 {
some u : User, f : Field {
u.canAccess[f]
}
}

Related

Retrieving properties of relationship through query

I would like to create a query which returns all the Requests (asset) in which the Container's (asset) owner's id is equal to the parameter.
Model file (owner of a container is a Company participant, identified by id):
namespace org.acme.shipping.assets
import org.acme.shipping.participants.*
asset Container identified by number {
o String number
o ContainerType type
o String content
o ContainerStatus status default = "FREE"
--> Company owner
}
enum ContainerType {
o DRY
o REEFER
}
enum ContainerStatus {
o LOCKED
o FREE
}
asset Request identified by id {
o String id
--> Container container
}
Query file
query getRequestsByCompany {
description: "Get requests by company"
statement:
SELECT org.acme.shipping.assets.Request
WHERE (container.owner.id == _$company_id)
}
However, the current query does not seem to work. Is this achievable with a query?
I did a lot of research also to do it using query file, but couldnt find a way, so I think that its not possible at moment.
The alternative way is to use loopback filters:
https://github.com/hyperledger/composer-knowledge-wiki/blob/latest/knowledge.md#information_source--filters-loopback
https://loopback.io/doc/en/lb2/Where-filter.html
Something like:
{"where":{"shipmentId":1000}, "include":"resolve"}
you can go one level in like search by number . I am working on it if get the exact solution .
query getRequestsByCompany {
description: "Get requests by company"
statement:
SELECT org.acme.shipping.assets.Request
WHERE (container == _$container)
}

Accessing Azure Assigned Groups via Razor or Controllers in ASP.NET Core

My ASP.NET Core web app is using an Azure Active Directory tenant and using OpenID Connect to sign-in users. I'm able to login successfully and I'm able to view the full list of Claims on a user with the following code:
return new JsonResult(from c in User.Claims select new { c.Type, c.Value });
My security token includes the following "groups":
{
type: "groups",
value: "e8f1a447-336a-47bb-8c26-79f1183f989f"
},
{
type: "groups",
value: "38421450-61ba-457b-bec2-e908d42d6b92"
}
I'm having trouble trying to determine how to capture these groups to perform logic in my Razor views and controllers. For example, I need to hide/show a button in my Razor view depending on whether a user is in a specific group. In my controllers I may need to allow/deny an action.
What is the standard/preferred method to do this in ASP.NET Core?
When Azure AD adds applicable group claims to the token it issues for users, the value for the group claim will be the Object ID of the security group and not the name of the security group(a group’s name can be changed in the directory so it is not a reliable identifier for the group ) .You could check whether the user’s existence in the security group in controller by :
// Look for the groups claim for the 'Dev/Test' group.
const string devTestGroup = "99dbdfac-91f7-4a0f-8eb0-57bf422abf29";
Claim groupDevTestClaim = User.Claims.FirstOrDefault(
c => c.Type == "groups" &&
c.Value.Equals(devTestGroup, StringComparison.CurrentCultureIgnoreCase));
// If the app has write permissions and the user is in the Dev/Test group...
if (null != groupDevTestClaim)
{
//
// Code to add the resource goes here.
//
ViewBag.inGroup = true;
}
else
{
ViewBag.inGroup = false;
}
Then in view , you could control whether show/hide links/buttons :
#if (ViewBag.inGroup)
{
<div>show/hide button/link goes here</div>
}
In your AppSettings.json, add your group's name and GUID object ID:
"AzureAdAuthorizationGroups": {
"MyGroup": "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee"
}
Next, hook up authorisation in your Startup.cs ConfigureServices method
services.AddAuthorization(options => {
options.AddPolicy("MyGroup", policyBuilder => policyBuilder.RequireClaim("groups", Configuration.GetValue<string>("AzureAdAuthorizationGroups:MyGroup")));
});
Finally in your view:
#if ((await AuthorizationService.AuthorizeAsync(User, "MyGroup")).Succeeded)
{
// ...
}

Fluent NHibernate - Multiple collections in the same table

Im working on rebuilding a clients software and they want to keep their database as unmodified as possible.
I got a table where they collect users and orders for different companies, no biggie there but the twist is they do it for multiple entities.
for example the table looks like this:
ID
UserID
Index
CompanyID
Type
lets say they got entities like Project and Workflow, then the Type column would be 'P' for projects and 'W' for workflows. So on a ID is the ID of a Project or Workflow Identity. UserID is always a foreign key to a User entity and Index is the order that the user is used when this Project/Workflow is used. And CompanyID is what company owns project or workflow entity.
I have tried to search google for this but i came up with nothing.
What i want is on a Template entity map two collections say StandardProjectUsers and StandardWorkflowUsers and they should collect them from correct entities with a user and index for current company.
Is this at all possible with fluent nhibernate ?
A nice article on how to do it: http://www.philliphaydon.com/2011/08/fluent-nhibernate-table-inheritance-discriminators/
You are looking at a table-per-hierarchy strategy.
In a nutshell you use:
public class BaseClassMap : ClassMap<BaseClass>
{
public BaseClassMap()
{
DiscriminateSubClassesOnColumn("Type");
...
}
}
public class WorkflowMap : SubclassMap<Workflow>
{
public WorkflowMap()
{
DiscriminatorValue("W");
...
}
}
public class ProjectMap : SubclassMap<Project>
{
public ProjectMap()
{
DiscriminatorValue("P");
...
}
}

Symfony 2 ACL vs Voters

I want to use isGranted('EDIT', $userObject) for allow edit given user data by all administrators and managers and that one user.
Should I use ACL for control edit $userObject?
I have written extra Voter which check if logged user and given object are the same or user is manager or admin.
In acl I must add ACE for userObject for all administrators, managers and that one user.
Wchich way is recommended?
I am new in Symfony..
below is voter's code:
function vote(TokenInterface $token, $object, array $attributes)
{
$intersect=array_intersect(array('EDIT','VIEW' ), $attributes);
if (!empty($intersect))
{
//intersect is not empty, it seems to edit or view are in $attributes
//voter grants privileges for [user->granted object]
//manager->every customer, child-manager
//admin->every customer and manager
if ($token->getUser()->isAdmin())
{
return VoterInterface::ACCESS_GRANTED;
}
elseif ($token->getUser()->isCustomer())
{
//voter not want to think about customer grants, because customer grants currently are held in ACL
return VoterInterface::ACCESS_ABSTAIN;
}
/* #var $object \PSB\StoreBundle\Entity\Customer */
if (is_a($object, '\PSB\StoreBundle\Entity\Customer'))
{
if ($token->getUser()->isManager())
{
//managers also edit customers
return VoterInterface::ACCESS_GRANTED;
}
}
elseif (is_a($object, '\PSB\StoreBundle\Entity\Manager'))
{
/* #var $object \PSB\StoreBundle\Entity\Manager */
if ($token->getUser()->isManager())
{
//manager can edit own children
if ($token->getUser() == $object->getParent())
{
return VoterInterface::ACCESS_GRANTED;
}
}
}
}
return VoterInterface::ACCESS_ABSTAIN;
}
When your model already stores the data required to know if an action should be granted or not, it's really annoying to keep the ACL in sync with your real data.
So you should obviously implement your own voters for this.
PS: You should use $object instanceof Class instead of is_a($object, 'Class')

How to design a User Object Model using MS Roles & Membership

I would like to build a ‘User’ Object model for a somewhat typical web application…however I cannot decide how best to design the object model & role system.
Basically I plan to have about 4 user types…which will correspond to user ‘roles’ in the membership provider.
These types will be:
• Worker
• Employer
• Guest
• Admin
The super type is:
• User
In addition – a User could be both a ‘Worker’ & an ‘Employer’ at times.
I would like to use the MS Roles & Membership provider & have navigation UI set to respond to User Role.
My question is:
How can I best design these Users to be flexible (User can be Worker & Employer).
How do I handle the Login / Roles Procedure?
(I am thinking about a User with a Factory for ‘Behavior’ objects (worker behavior, Employer Behavior ) )
For Login-User logins in … finds its role and Casts to its subtype.
Is this how it should be done?
Using just the concept of role by itself has always proven to be in adequate for me. It doesn't provide low enough granularity to control permissions. AS an example you may have a worker role and and an admin role and then in code you use principal.IsInRole("Admin") to check their role to determine if they can modify some value (say salary). Then someone changes their mind and says that supervisors can change salaries but still aren't admins. Now you have to go change you access check to add in another role check. Painful and routine.
So what I do is make a list of all the features in the application and then allow them to be associated in to a role all in the database. The my access checks look like principal.HasPermission("CHANGESALARY"). I load up the users permissions based on the role they are attached to when they log in. This way the business can create as many groups of features they want and name them. They can then be applied to any user.
I create a custom principal object and attach it to the thread so that I can use it in any code throughout the page life cycle. This object has the code for loading the permissions from the database and the methods for checking permissions.
I generally find that the "providers" in the framework are good for a small class of applications and come up short for most needs. By the time you are done bending them to your will, it would have been easier to just write it from scratch.
To be honest, this is probably not a very good solution, but it might help to generate some other ideas.
My Roles are all of the possible combinations of permissions:
Worker, Employee, Guest, Admin, WorkerEmployee, etc
In my code I have an enum for the individual permissions
[Flags]
public enum RolePermissions
{
Guest = 1,
Worker = 2,
Employee = 4,
Admin = 8
}
and I have an enum that corresponds to the Roles in the database. The integer values are the bitwise OR of permissions:
public enum AvailableRoles
{
None = 0,
Guest = RolePermissions.Guest, //1
Worker = RolePermissions.Worker, // 2
Employee = RolePermissions.Employee, // 4
WorkerEmployee = RolePermissions.Worker | RolePermissions.Employee, // 6
Admin = RolePermissions.Admin, // 8
}
Then there's a set of methods I can use to look up permissions and whatnot:
// Used to determine if the currently logged in user has a particular permission (Guest, Worker, Employee, Admin)
public static bool UserHasPermission( RolePermissions rolePermssion )
{
foreach( string role in Roles.GetRolesForUser() )
{
AvailableRoles availableRole = Parse( role );
if( ( (RolePermissions)availableRole & rolePermssion ) == rolePermssion )
return true;
}
return false;
}
// Used to determine whether the currently logged in user is in a specific role
public static bool UserIsInRole( AvailableRoles requestedRole )
{
return UserIsInRole( Membership.GetUser().UserName, requestedRole );
}
// Used to determine whether a specific user is in a specific role
public static bool UserIsInRole( string username, AvailableRoles requestedRole )
{
foreach( string role in Roles.GetRolesForUser( username ) )
{
AvailableRoles actualRole = Parse( role );
if( actualRole == requestedRole )
return true;
}
return false;
}
// Helper method to parse enum
private static AvailableRoles Parse( string role )
{
return (AvailableRoles)Enum.Parse( typeof( AvailableRoles ), role );
}
If you come up with a better method or make improvements, please let me know so I can incorporate it back into my own code. :-)

Resources