Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use Ext JS for role based application

I am planning to use Ext JS for a large application. The application's features are role based. When user login, they only see menu and screen features related to them. My server side technology will be Java & JSP.

To solve this I have two ideas..
1. Create Ext JS related javascript dynamically after the user login using server side technology. The servlet / JSP will create the necessary est js code according to user roles.

2. Have Js variables that are set in view JSPs that will be used to ensure only the right features are available to users.

What is the best way to ensure security and provide role based UI in Ext Js application.
Thanks in advance for you ideas..

Abdel Olakara

like image 762
Abdel Raoof Olakara Avatar asked Nov 21 '09 14:11

Abdel Raoof Olakara


People also ask

What is Ext JS used for?

Ext JS is a popular JavaScript framework which provides rich UI for building web applications with cross-browser functionality. Ext JS is basically used for creating desktop applications. It supports all the modern browsers such as IE6+, FF, Chrome, Safari 6+, Opera 12+, etc.

Is Ext JS outdated?

For being over a decade old, Ext JS is still a good platform to develop many enterprise-grade (think intranet) applications.

Is Ext JS a framework?

Ext JS. Ext JS is a JavaScript framework that enables developers to build web apps for any modern device. It includes 140+ fully supported components that easily integrate with React and Angular.


1 Answers

I had to solve a similar problem in an application that I currently developed, but permissions are based on user country.

I know you already are, but just to reiterate for the benefit of anyone reading, permissions should always be implemented on the server side and JavaScript security is always secondary. This is because anyone with half a brain can use either a bookmarklet or Firebug to execute arbitrary JavaScript and circumvent your client-side security.

I've found that there are several ways to do this, but there are two approaches in particular that are the most sane. Regardless of the approach, there are two things to consider: 1) what JavaScript to server and how to avoid serving unnecessary logic, and 2) how to avoid executing logic that is not available to the user.

Lazy loading and permissions configuration:

  1. All widgets in my application are lazy loaded via dojo.require, so there was no need to worry about the unnecessary inclusion of JavaScript that wasn't applicable to the user. I am not deeply familiar with the ExtJs library, but as far as I have seen, it doesn't supply a comparable method; however, it is essential a synchronous ajax call followed by an eval. In any case, in this method it is important that component functionality doesn't cross-cut through different files (also, this is generally good design). Each file should be its own class that controls a specific widget or other UI element.

  2. I then set permissions in a server generated JavaScript config class. This class can then be referenced throughout the application for what is and what is not allowed.

For example, the following method controlled access to most of the widgets that were available from global controls.

com.project.frontController.prototype.init = function(widgets) {
   var permissions = com.project.config.permissions;

   // For each widget in the controller
   for ( var i=0, l=widgets.length; i<l; ++i ) {
       // If access is restricted to the widget (by id), then disable it.
       if ( !permissions[ widgets[i].id ] {
           com.project.util.disable(widgets[i].btnAccessNode);
       }
       // Otherwise, leave it enabled and connect the necessary event handlers.
       else {
           // connect an onclick handler or whatever is required for the widget
       }
   }
};

And the config looked something like:

com.project.config.permissions = {
    "widgetAbc": {
        btnAccessNode:     "#some-css-selector",
        otherWidgetConfig: "etc"
    },
    "widgetXyz": {
        btnAccessNode:     "div.some-css-selector"
    }
};

Compile and functionality check:

  1. Some applications will compile all of its JavaScript into one file, and then serve it to the client. If your application does such a thing, and you can manage to do this dynamically, all necessary JS can be determined on the server-side before it is served. Of course, this will accrue some overhead; however, you can cache compiled versions by role. If the roles are few, then this cache can be easily primed and it's just a matter of including one specific script.

  2. Since only the allowed JavaScript will be available, simply detecting if the required class/function is available before attempting to execute it is all you need to do for your permissions check.

For example, you script inclusion may look like this:

<script type="text/javascript" src="/js/compiler.php?role=moderator"></script>

And your functionality check would be something like this:

com.project.frontController.prototype.init = function(widgets) {
   // For each widget in the controller
   for ( var i=0, l=widgets.length; i<l; ++i ) {
       // If the widget controller doesn't exist, disable it.
       if ( !com.project.util.widgetExists[ widgets[i].id ] {
           com.project.util.disable(widgets[i].btnAccessNode);
       }
       // Otherwise, leave it enabled and connect the necessary event handlers.
       else {
           // connect an onclick handler or whatever is required for the widget
       }
   }
};

or

com.project.someWidget.prototype.launchOtherWidget = function() {
    if ( typeof otherWidget != "undefined" ) {
        (new otherWidget()).open();
    }
};

Notice that both methods are very similar in implementation. I would say the best way to make a determination between the two is to consider the size of your codebase, the tools available to you for compiling on the fly, and caching those role-based, compiled packages. For my project, not only was a compiler not available in the environment, but the code base was large (1.3mb inflated/296kb defaulted plus the dojo library), which wasn't acceptable as the client was more interested in maintaining low application load times.

like image 160
Justin Johnson Avatar answered Oct 24 '22 22:10

Justin Johnson