Do Cities Dream of Cubicle Workers?

A New York Times article in March of 2021 discussed the rapid decline in commercial office space occupancy in Manhattan due to COVID, speculating how the city will never be the same. If we’re lucky…

Smartphone

独家优惠奖金 100% 高达 1 BTC + 180 免费旋转




How to manage user permissions in Aurelia

Awesome CASL and Aurelia

Now lets define who can do what:

CASL allows to translate such permissions into DSL with help of AbilityBuilder class:

First of all, lets add our abilities in src/config/abilities.js file:

Now I need an instance of currently logged in User. To get a reference to that object, I need somehow to hook into session management logic. As Session was defined as js-data Mapper, I can use DataStore to listen to Session management events.

As you can see from the code above I listen to 3 events of DataStore that allows me to understand when Session is created, destroyed or found and update user abilities accordingly.

Now everything seems ok, but if you try to check abilities on models, you will always receive false because CASL can’t detect model’s type. We need to teach it by specifying subjectName option:

Now all good! Lets move on to actual integration with Aurelia templates.

There are 2 ways of how we can add ability checks into Aurelia templates:

I’m going to implement both and later you will understand why. It’s easy to generate binding behavior and value converter using aurelia cli (specify can as a name for both):

Generated classes I’m going to move into single src/pipes/can.js because all this is basically a one thing.

In value converter, we just need to inject Ability instance and use its can method:

Now lets make this converter to be global. To do this I just need to add a line of code into src/main.js :

This allows me to bind ability checks in any template with help of if binding:

But when you test it, it doesn’t work, why? Because Aurelia tracks changes based on used expressions in the binding. The current if binding has 2 static strings and has no knowledge about rules array of Ability instance. Thus don’t know that binding needs to be updated when rules are changed.

It also requires a change in src/config/abilities.js file:

Now everything works as expected but it’s a bit tedious to write signal: ability-changed in every binding where we use can. It’d better to write custom can binding behavior which hides this complexity. To do that I will injectSignalBindingBehavior which re-evaluates binding automatically when ability-changed signal is received. Also I need automatically wrap all expression in can value converter:

Using this binding behavior, templates looks simpler:

That’s it! 🙂

If you like this article, please consider recommending it. 👏

CASL has complementary packages for major frontend frameworks, check the articles below:

Add a comment

Related posts:

Mind Switch Flips for Weight Loss

Over emphasized because without action, mindset is useless for getting results. Under, because people think it won’t do anything and is an excuse not to take action — The “just do it” crowd. So they…

Can we justify taxation?

Those of an economically right-wing bend, libertarians by definition, will often argue against taxation. They argue that the very idea of taxation is robbery. Not just robbery. But robbery under the…

Shattering my dream of being a novelist

I have wanted to write novels for as long as I can remember. Books have always been a monumental part of my life as a reader, a collector, and an aspiring author. I read Steinbeck and am in awe of…