Defining Views Based On Selection - asp.net

Well the title isn't very descriptive but I'm not exactly sure how to explain but here goes!
I have a web application (can use either MVC or standard web forms) which a user signs in to. If the user has signed up for more than one product they will have the option to switch between them. For the sakes of this example lets say User1 signs in and has access to Product1, Product2 and Product3.
Now, each product will be very different and offer different functionally. What I want is the main view to be focused around the product they have selected and not redirected to a sub domain.
What I don't want to have to do is get them to go to www.mysite.com/product1 or www.mysite.com/product2 but simply www.mysite.com regardless of the product they have selected and have the site render the views etc for that product.
Wow does any of that make any sense? I was thinking mabe the use of sessions or something and URL rewriting? Are there any sample apps out there that make use of the same kind of functionallity that I could take a look at?
Thanks for any help I appreciate it!

To keep the product ID out of the URL, you can post your product selection page to the server with a hidden control that contains the desired product ID.
<input type="hidden">
Once you have the value in your codebehind or controller method, you can then set a Session variable with the product id to maintain persistence, and then perform a redirect to the appropriate product page.
This will work in both ASP.NET and ASP.NET MVC.

If you could elaborate more, that would be helpful.
Here is my shot at the answer from what I understood:
What you could do is redirect to the user to a specific page after they login.
public ActionResult Login()
{
//Login Logic
if(UserLoggedIn)
{
User MembershipUser = GetUser(User.Identity.Name);
if(MembershipUser.HasProduct1)
return View("Product1");
else if(MembershipUser.HasProduct2)
return View("Product2");
else if(MembershipUser.HasProduct3)
return View("Product3");
}
}
It would be just a simple redirect to a specific view depending on the user's product.
If you could elaborate more, I could give a better answer.

I think I am going to go with a custom ViewEngine in ASP.NET MVC. I can render different views depending on the product chosen that way. Thanks to everyone for their suggestions.

Related

ASP.NET Core - Fill a form inside a View with bound ViewModel

my question is more logical than practical. So I have notifications system and everytime a notification is clicked it reroutes me to a page where I should give feedback to a user.Example
I need the UserId inside my Feedback Page, this way I can add the new Feedback to that user.
So what I am asking is: How do I tackle this problem? Will ViewData[] solve my problem or is flawed this way.
Since you are rerouting to a new page, and want to pass in the user's ID, I believe you would be well off to use a Query String
From the link that takes you to the Feedback Page, you can use a URL like this:
https://example.com/feedback?userId=123456
or add it to however you are building your links
From the Feedback Page, you can then capture that query from the URL

The best solution to customize page controls based on some roles and settings

I have several pages in asp.net each with lots of controls. I Also have some roles in my application that each has some setting options. Now I want to prepare my page based on these settings. Maybe it’s not too clear, so please take a look at my example.
Example: There are some buttons, some textboxes, some datetime picker, and a chart in a page, now what I want is when a user sees this page, the controls appear and disappear based on the users role. An important thing is that I don’t want to have only visible and invisible controls, in some scenarios I need to show controls with some customizations. For example change chart data source, limit selecting date time and so on.
The first solution that I can think of, is saving the settings in database and after visiting the page by user, the settings fetch from database and based on those, I can customize the controls with conditional phrases (if and else). But I suppose it is not a good approach and my page will get very messy.
Please help me with any better solutions and if you know good references about it, please let me know.
Please see this link...use of ControlAdapters may help you...
Role-based enabling/disabling of controls in asp.net
You must use Thread.CurrentPrincipal.
A. When user login to your application, you attach his identity to thread, for example
string[] rolesArray = .....; //Get roles from dataBase by identity.
Thread.CurrentPrincipal = new YourCustomPrincipal(new YourCustomIdentity("YouName", "..."), rolesArray);
B. And when you navige about your application you test Thread.CurrentPrincipal
IPrincipal threadPrincipal = Thread.CurrentPrincipal;
if(threadPrincipal.Roles.Contains("roleTest"))
{
//Adjust your control
}

Go back to a search page without losing search criteria

I need some help on this problem. It is about ASP.NET MVC3. I have a page with at the top some search criteria and at the bottom the resulting data. The user can type some criteria and use a submit button to retieve data. In my controller, I have an ActionResult function for managing these criteria and return to the same page with a ViewModel class filled.
The problem: the user can click on a line in the resulting table for viewing a detail page. On the detail page, he can navigate to an edit page for editing data. On this page (edit data) I would like to able the user to go back to the search result page (in fact: navigate back two times). What is the best way to proceed? If I "simply" use an ActionLink (without posting data) to my search result page, it will simply display an empty result page with empty search criteria. Maybe I need to keep my search criteria in a session variable? I don't like this kind of thing...
Any help will be highly appreciated.
Why not place the data in the Session, as you say?
public ActionResult Search(string searchCriteria)
{
Session["searchCriteria"] = searchCriteria;
// do more stuff
}
This way you have the search criteria available no matter how many "back clicks" the user does.
You could make it much more complicated but I do not think it is necessary in this case. If you want to pass it as route data in an action link you'll have to defensively add a searchCriteria parameter to every ActionLink of the pages the user might navigate to from the Search page. That makes it a lot more cumbersome in my opinion.
Good enough is sometimes good enough. Refactor later as needed. :)

ASP.NET MVC partial views and redirecting

I have a partial view called Login.ascx that has my login boxes that I include on a number of pages throughout my site. It works fine when the information is correct but I'm trying to do validation so if the login info is incorrect, I want to redirect the user back to the view they were in before to show them the login errors. What is the correct way of saying, return to the view you came from?
If a login fails from any page, I think I would direct them to a login view for the errors instead of the previous page. A dedicated login page is likely to have more UI space to display errors, etc. than a login control on another page. Having said that, you may want to include a returnUrl parameter to the Login action so that when the login is actually successful, the user is directed back to the place they were (or were attempting to get to).
Sounds like instead of asking how I do this, you should be asking yourself WHY am I doing it this way. Maybe it's a design decision rather than a technical question.
Though if you're really going to have one controller actions for multiple login pages you can try...
return Redirect(Request.UrlReferrer.ToString());
Or keep the route name in TempData and just use a RedirectToRoute(TempData["LoginRoute"]);
Both solutions have a bad code smell though.
Note that if you're not checking for cross-site injections that is just going to refer back to the other site. You may want to do some validation on the referring URL.
For the built-in Login method of the AccountController there is a parameter named returnUrl which you can use like so:
Return Redirect(returnUrl);
or
Return RedirectToAction(returnUrl);
if you specify the returnUrl parameter as a valid actionlink.
I recently had similar problems - you might be able to find something here...

How can I create a view that has different displays according to the role the user is in?

I want to create a view that has different displays according to the role the user is in.
Should I create a different view for different roles or should I check the roles on the Veiw page itself rather than in the actions?
How would I check the role on the view page?
Or should i use check the roles on the
Veiw page its self rather than on
actions, if so can someone plz show me
how do check that on view page
You need to do both. Check roles on actions as a security measure and check roles on views to enable/disable specific controls.
Within your view page the long form of checking a role is
HttpContext.Current.User.IsInRole("Administrator")
many developers will create page helper methods so you can end up with something more concise for your application like
public static bool IsAdmin(this ViewUserControl pg)
{
return pg.Page.User.IsInRole("Administrator")
}
then in your view you can just use this.IsAdmin()
To keep your view clutter down look into using partial views
<% if (IsAdmin())
{
Html.RenderPartial("AdminPanel");
}
else
{
Html.RenderPartial("UserPanel");
}
%>
If the display changes based on the role -- and the change is small -- then I would do the check in the view. If certain views are restricted based on the role, then I would do the check in the controller. If the views are completely different (this would be hard to imagine), then separate views per role may be appropriate.
You may want to abstract out certain role-specific view components into partial views to simplify your view logic -- basically you only have to check to include the partial or not based on the role.
Also, other than to check for "IsAuthenticated", I would move the role checking logic to the controller and pass (as data) to the view information on which elements to include/exclude based on role. This keeps the actual business logic from bleeding into your view.
If you are using MVC the whole point of development is to keep the logic out of the view and in the controller. It seems to me like you'd be better off on a WebForms development track than an MVC track.
All that being said, I do an Admin check on a lot of my pages by using a check like this:
<% if ((bool)ViewData["Admin"]) { %>
<!-- Show admin controls here -->
<% } %>
But if you are attempting to build actual logic into the View then you need to figure out what you can push back to the controller to do the work and have the view be as dumb as possible, acting on flags sent to it.
without researching the exact mechanism asp.net mvc uses for roles i would scream no for putting any of your business logic in the view which is what you are doing if you are checking roles in the view
Yeah that was something that was bothering me as well ... but at the same time it seems ridiculous to load whole different view for such a small change.
btw
how did you set this up in your controller.
Right now, my controller looks something like the code below, which I don't think is correct.
[Authorize(Roles = "Admin, Member")]
public ActionResult RegistrationInformation()
{
return View();
}
I'm not that familiar with ASP.NET MVC (yet) but can't you do some kind of conditional filter in the View? If the Controller passes the role to the View, then you should be able to do a conditional filter and display a certain block of code if the user is an admin. If you want to display a totally separate page, then you'd have a multiple Views, otherwise you can use one and do some conditional.
In Ruby on Rails it would be something like (sorry, I don't know ASP.NET MVC really yet):
<% if #user.admin? # is the user an admin %>
<h3>Admin Tools</h3>
<% end %>
<p>Regular site content</p>
In Rails you would load the extra content from partials; ASP.NET MVC has something similar but I forget what it's called. Maybe look into that?
Sorry I can't be of more help -- like I said I haven't really gotten to play with ASP.NET MVC.
I have base model which from all others models extend. In this model i have loaded the user's roles. Its based on httpcontext.user.isinrole() method. All views are strong typed expecting the base model type.
So i can always check in all views something like Model.CurrentUser.IsInRoles(Role1 | Role2). Not only in views of course, but in hole application.
I like to have full control over this in the view, and I find that:
<% if (User.IsInRole("Super User")) { %>
<h1>Hello world!</h1>
<% } %>
Works for most scenarios. It also allows you to easily do conditional formatting for other roles, e.g "Content Manager", "Registered", etc.
I do like Todd Smith's answer, because you might change the name of the Admin role, and that will require only one change, whereas, if you put the "Super User" or "Administrator" string directly in the view, you will have to change it wherever you've used the value.

Resources