Creating Separate UI for different Roles - angularjs

I have two roles in my application say Customer and Provider and I want to create separate UI for them after they are authenticated, keeping login screen same and have a radio button that says "I'm a Customer" and "I'm a Provider", this also be same during registration.
I'm looking for a better approach, I have no Idea how to start with.
I already have a an existing UI interface for customers, but now requirement is for "Provider" Interface. So that customer can interact , send requirements, do query directly with provider. currently Customer application send these request by email.

First of all you should detect and define which components are going to be shown for both and which components are only for one or other. After you know exactly how your app will be, angularjs provides a lot of native directives for managing different cases.
Take a look at:
ng-if
ng-switch
ng-hide
ng-show
Those will be of great help for you. But always remember to manage security server side, web apps can be easily manipulated and if you are working with roles and different permissions take this as a must have.
BTW, consider using angularjs $routeProvider in some of the following ways for managing permissions:
$routeProvider.when('/admin/users', {
controller: 'userListCtrl',
templateUrl: 'js/modules/admin/html/users.tmpl.html',
access: {
requiresLogin: true,
requiredPermissions: ['Admin', 'UserManager'],
permissionType: 'AtLeastOne'
});
OR
$routeProvider.
when('/admin', {
templateUrl: 'Your template url',
controller: 'AdminController',
permission: 'AccessAdministration',
resolve: {
permissionList: function (permissionService) { return permissionService.getPermissions(); }
}
})

Related

creating external links to my angularJS app

so i'm trying to create a public/external link that can be generated and shared to anyone for people to get to a specific state of my angularJS app.
I am using $stateProvider to manage states on the app. but i need a part of the app to be open to the public. i.e a particular state open to the public such that as soon as they hit that the url e.g mydoamin/post it gives them access to that state alone. for example
.state("post", {
url: "/post",
controller: "postController",
templateUrl: "templates/post.html",
})
My app currently user $stateChangeStart to check between state transitions but is setup to block any unauthenticated user. so if anyone that is not logged in tries to get to a state it kicks them back to the login state which is the default '/'.
.state("login", {
url: "/",
controller: "LoginController",
templateUrl: "templates/login.html",
})
I know i could just give each state a value probably 'authenticated' and set it to true or false for each state and check the toState on $stateChangeStart if 'authenticated' is false and grant access based on that but i need to know if its a good idea and how to securely implement it.
How would you do this?. thanks in advance for any reply/suggestion.
For 'securing' the UI, i.e. hide some pages from unauthorized users, use ui-state router's resolve parameter. See this question for more info. Put a 'resolve' on the states that need authentication, and leave it out for the public pages.
However it is important to understand that any security measure that is implemented client-side, is never fully secure. Anyone can have access to any page, including the ones that require authentication. All it takes for them is to open dev tools and alter the JavaScript. That's why you should properly handle authorization at API level. This way, even if a malicious user can see a hidden page (i.e. he can browse to it and see the html), he won't be able to see any data that was fetched from the API.

SaaS app with angularjs and nodejs, how do i organize different clients?

I’m trying to decide what to do I this scenario:
I want to create a product that I want to sell in a SaaS business model, I already have the backend more or less thought out and some code in place in nodejs. It handles oAuth, sessions, and controls the roles of the users when accessing a certain endpoint.
The doubt is in the frontend architecture:
Each client will share the same functionality, but the design of their page will be completely different from one another.
I want to put as much of the app logic that I can in services, so I can reuse it, my idea is to only change controllers/templates/directives from client to client, is this ok?
Should I have different folders and serve the static files for each client from nodejs?
ex:
in nodejs I would know the url for client1 was called so I would serve client1-index.html?
should I put each client in their own nodejs server and their own host?
what other ways are there?
I would like to be able to easily reuse the services as I’ll be introducing changes to the features or adding more, and I want to do this upgrades easily.
There will also be an admin panel that will be exactly the same for all of them, the part that will change is the one my client's users see.
Think of it as having many clients and giving each of them a store, so they can sell their stuff. They want an admin page and a public page. The admin page will the same for all, but the public page has to change.
So, and app that shares the same functionality across users but looks completely different for each one of them, how would you do it?
Since You seem to be using Angular, have you thought of using the routing service? See more about it Here : https://docs.angularjs.org/api/ngRoute/provider/$routeProvider
Basically what it does is it based on the url loads a html page and a controller (JS file). For example if your user would just be move to url.com/client1 and angular would load client1.html and client1CTRL.
A Simple Structure would be the following:
Index.Html- References to any dependencies, and in the body only a ng-view tag
Templates (The Html Templates for each of the users)
Login
Admin
Client 1 etc...
Scripts (JS)
External Scripts (Jquery, Angular ETC)
Index.js ( This is where you would have all your js controllers for each page)
Stylesheets
CSS FILES GO HERE
Example Angular Routing: Tutorial
var App = angular.module('saasApp', []);
App.config(['$routeProvider',
function($routeProvider) {
$routeProvider.
when('/admin', {
templateUrl: 'templates/admin.html',
controller: 'AdminController'
}).
when('/client1', {
templateUrl: 'templates/client1.html',
controller: 'client1Controller'
}).
when('/login', {
templateUrl: 'templates/login.html',
controller: 'loginController'
}).
otherwise({
redirectTo: '/login'
});
}]);
Hope this works for what you are trying to do.
I guess your question is about Architecture. If I were to do same back-end and different front ends I would've implemented virtual template structure.
Permissions
I would have:
a super user that has rights to setup multiple stores.
an admin user that can manage a particular store
Super User template management.
I would have base templates in /admin/templates and when I create a new store I would copy them and stick them in database
I would create a menu with all the templates on the left hand side and have wysiwyg editor that allows me to modify those template for particular customer and upload additional assets (images, pdfs etc)
Template would support swig syntax
I would create a server route /get/tempalte/:id and dynamically parse those templates on server using swig engine
I hope this helps. The key here is to be able to update templates via browser and distribute them to new shops/customers via web panel.

How to bring role based view with UI Router in Angular JS?

I am developing a SPA (Single Page Application) with Angular JS and using "UI Router" for routing and using Spring MVC framework for back-end.
I would like to bring the user role based view in the application as we have different user roles in application.
What is the best way to do this?
Is there any way to retrieve the user role from server check it in the ui route before state changes?
You could pass roles through the data attribute and the check the user access on the $stateChangeStart event. This would off course require you to implement users with user roles.
Pass the role restriction as custom data to state object (https://github.com/angular-ui/ui-router/wiki#user-content-attach-custom-data-to-state-objects)
$stateProvider
.state('admin', {
url: '/admin',
data: {
roles: ['ROLE_ADMIN']
}
})
Then in the .run function do a check on the $stateChangeStart event if current user has said role and if so allow the route change, if not send user to some kinda access denied page (or just prevent state change).
.run(function($rootScope, $state) {
$rootScope.$on('$stateChangeStart', function (event, toState, toStateParams) {
// Check if current user has group access
if(!AuthService.userHasRole(toStateParams.roles)) {
$state.go('accessdenied');
}
})
})
There would be quite a bit of work off course to get this working. Setting up users/roles/auth etc. Will leave that to you. JHipster (https://jhipster.github.io/) has a pretty solid auth, access, user with user roles implementation. The backend is in Java though. But the Angular implementation is rock solid.
One way I am exploring is simply putting the various views on the page wrapped in ng-if's and checking the userRole.role(a global value) to determine which state to view.
However, there has to be(or should) be a way to do it relatively easily in UI-Router I would think...
Then again, I wam building this on a sharepoint site, so I don't have to worry about top level access rights as we set those on Sharepoint itself. Anyone who can actualy view the page will be 1 of 5 types of userRoles, I simply have to get the role and then show the proper view based on that role

AngularJS: Best practices for routes and controllers

on our company, we're currently working on a single page web application. Users can login and fill their profiles with data and share those with other subscribers (it's a social network-ish application).
Now, I've imagined this schema:
the users data are provided by a UserService, using REST APIs to recover profiles information;
the profiles related pages are managed by a unique controller (ProfileController);
my question is: what's the best way to associate a route (let's say "view-profile") to a specific controller method (ProfileController.viewProfile)? Is this a right pattern in AngularJS?
Thanks!
Investigating further I've found that the best way to achieve the result I want is by using the resolve in the state configuration, as explained in this article: https://scotch.io/tutorials/making-skinny-angularjs-controllers.
EDIT:
I'll try to explain it a little bit. What I'm trying to achieve is to route a specific application state to a controller method, in order to avoid preloading a huge subset of data everytime I access the controller. Let's say I've this situation in my ui-router
.state('view-profile', {
url: '/view-profile',
templateUrl: 'components/profile/profile.html',
controller: 'ProfileController'
})
[...]
.state('edit-profile', {
url: '/edit-profile',
templateUrl: 'components/profile/edit-profile.html',
controller: 'ProfileController'
})
Since the ProfileController could potentially do a lot of stuff, not necessary related to edit/view, I'd like to set a specific controller method to be called when I navigate to these urls.
In other MVC frameworks you can associate a route to a specific controller method, so you'll have
route: /edit-profile -> resolvesAs: ProfileController.editProfile(args)
Unfortunately, there's no really a way to do this in AngularJS 1.4, at least not using the ui-router.
But fortunately enough, we can use the resolve attribute on the ui-router configuration to avoid preloading useless data for a specific route.

How i can maintain angular-fullstack client and admin different template

I want to use different different types of template in client side and admin side using angular-fullstack.
Can you please let us know how i can achieve this. My routes look like Ex:
www.sitename.com - main site with theme1 (http://demo2.jlvextension.com/probusiness/)
www.sitename.com/administrator - administrator dashboard with theme2 (http://www.theme-guys.com/materialism/angular/)
It seems to me like you're trying to create two very different front ends. I recommend building two different angular applications that utilize the same api's and domain. You could put an entire admin angular application at www.[sitename]/admin.
We also had a requirement like this and initially we had both in one SPA, where we distinguished each page by URL. The URL 'admin/login' loaded admin login page while '/login' loaded the login page for others. The $routeProvider config is given below.
$routeProvider.when("/admin/login", {
templateUrl: "app/admin/login.html",
controller: "AdminCtrl"
}).
when("/login", {
templateUrl: "app/user/login.html",
controller: "LoginCtrl"
}).
Later when the application became big and difficult to maintain, we ported the admin part to a separate application like Gabriel suggested above.
you can resolve this problem with creating a directive with different
templates,This plunker should demonstrate what needs to be done,
but basically:(you should just change the value of isAdmin property
to simulate ). good luck

Resources