ASP.NET MVC 3 Razor View Restrictions - c#

I apologize in advance for the generic nature of my question, but I was unable to find any helpful advice from people trying to do the same thing as me on the web. Let me describe my scenario:
I am providing end users/designers of a website the ability to customize their views by storing the views (using Razor) in the database. I have all of this working, but my question is the following; From a security standpoint, how can I ensure and enforce that unwanted code doesn't get executed in the user-defined view? There are two basic approaches that I think will work conceptually, but am not sure which one is more possible or feasible.
Option 1: Create a validation method in the administration tool that allows the user to input the view code. This would need to either take a whitelist or blacklist approach to what is allowable or not.
Option 2: Prevent unwanted code from being able to execute when rendering of the view occurs.
As a quick example of something that would need to be blocked, we wouldn't want to allow access to read or write files, access any data access functions, or even access configuration settings, etc. in the web.config. There will likely be a decently-sized list of things that probably shouldn't be allowable, but I'll need to sit down and try to think of as many security-related concerns as possible.
My question then is, which method would be the best bet? Also, can any direction be provided on how to go about either? I thought I might be able to make trust-level based change which would be Option 2, but couldn't find any way to make that work in a per-view based manor (the administration code is allowed to execute whatever it wants). I'm thinking Option 1 will end up being the best bet and I'll have to check for the input of certain framework functions that shouldn't be allowed. Does anyone have any experience doing anything like what I'm trying to do? ANY feedback is much appreciated!

This would be extremely difficult.
You could run the the template through the Razor preprocessor, then use Roslyn (still in early beta) to parse the generated file and look through all method calls (or constructors) and return an error if it calls something you don't like.
I strongly recommend that you use a whitelist for that, since the .Net framework is big enough that you are bound to overlook something in a blacklist.
However, I would instead recommend that you not use Razor at all and instead use a templating engine that does not allow real C# code.

Related

C# Resources: display resource string names instead of localized values

Having rather large project using Resources for internationalization (following this guide: ASP.NET MVC 2 Localization complete guide, using things like data attributes, and so on) we run into the need of translating the resource files. In the beggining of project I selected approach to have lot of small resource files - for each view, viewmodel, controller, ... So I ended up having hundreds of resources. During the translations (which is done by our partners using ResXManager tool we run into trouble identifying the context of the string (where is it displayed, to find out the correct form of translation to make sense when displayed).
So I was asked to make the mutation of application which do not display the localized values, but the keys (or string names). E.g. having string in resources TBL_NAME used somewhere in the view like #ResX.TBL_NAME and translated into english as "Name", I would like to show it in this special mutation as "TBL_NAME", so the translator may see the context - where exactly this string is used.
The best would be, if this is not special build of application, but rather the another "language" of the application available for translators, so he can switch between english and this "unlocalized" languages.
I'm looking some easy ideas of doing this. So far I was thinking of these approaches:
Override ResourceManager.GetString - cannot use, because we use generated Designer classes to access strings massively and so far I haven't find a way to change created ResourceManager (see this answer). Did I miss something?
Create resources for some unused language, which will contain pairs string name/translated value as TBL_NAME/TBL_NAME - viable, but very exhausting since we have hundreds of resources. Also the addition of new resource will require us to remeber that we need to add also this unused language resource will exact same strings name. You also have to do twice much work when adding single string to application.
At the moment, it seems for me, that using resources and current approach it is impossible to solve this task, so I decided to ask this as question (and I'm aware it is rather discussion than question) here, hoping, someone will give me some hint about other approach to solve this problem.
My preferred option would be to give the translators an environment where they can see what they are translating. Rigi requires a bit of setup (basically you need to add an additional UI language), but once you have done that translators can work within the live website - or in a test instance, which is what we did.
They can also work in screenshots, which is convenient when translators would have to access admin or other role specific pages but you do not want to bother giving them all kinds of user rights. These screenshots can be generated as part of automated UI tests or during manual UI testing.
I am afraid I can't say anything about the cost of the solution, but our translators are really happy with it. I am not sure if this is what you are looking for since you asked for an easy solution, but it definitely solves the issue of giving translators the context they need to do their job - better than displaying resource IDs.

Stand-alone Error Page with translated text?

I'm working on a website that will deployed internationally. Very big site, but for the sake of simplicity, all we're concerned about is my Error.aspx with c# code behind. I'd like to make this custom error page as dynamic as possible. There's at least a handful of languages we need to read this page in right now, and more to come. This page needs to work independently and without a database to reference.
I'd like to have some text, and have the appropriate translation appear based on the language appropriate for that domain... e.g. ".com" = English, ".ca/fr" = French, ".mx" = Spanish... you get the idea.
What's the best way to do this?
I've looked into API's, but the decent ones have a cost threshold, and while it might look really helpful, this is just pretty standard error message text, that's unlikely to change, so that seems like overkill to have a dynamic translator. It might help with scalability, but it's extra money indefinitely, when it will only save vs hard-coding on the handful of occasions where we add another language/country/domain.
The other idea I had was to simply hardcode it in the c#. parse out Request.URL and get the domain, and make a ever-growing switch statement which would assign the appropriate text. (As an aside, I'm also trying to find a better way to do this, but is the country code something that would be an available piece of information from either the request object or server?) This way would be independent, precise, and the only drawback on a concrete level would be the cost of adding new languages, or changing every string (probably not that many, at least at first) if the content of the error message needed to be adjusted. But this feels like bad practice.
I've been researching this for a day now, but I haven't found any alternatives to these 2 options. What are the best practices for handling small amounts of text for translation, without the use of a CMS?
There is an easy built-in way to handle localization in ASP.NET Web Forms. It uses the Language Preference settings in the client's browser to select the language. Posting the steps of setting it up would be redundant since there's lots of information on this subject available online. Here is a good tutorial.
EDIT:
It might be a good idea to read up on HTML resource files. That is the HTML standard for handling different languages (referred to as localization). And it is what ASP.NET uses in the background when creating a local resource for a server control.

Pre-process MVC Razor File For Multi-Lingual Language Strings?

In my application we have multi-lingual language strings which are stored in custom tables, as the user can edit, delete, import new languages etc... via a UI
Currently, what I'm doing is at the beginning of each request is. I'm going off and getting all the language strings (From our database) for the currently selected language and sticking them in a dictionary.
I then have a Html Helper extension method which I use in the razor views (See below), which fishes in the dictionary I got at the beginning of the request to pull out the correct language based on the key supplied in the helper.
Html.LanguageString("MyLanguage.KeyHere")
Now this works fine. However, as the application is getting bigger. We are getting more and more language strings. It's not an issue right now, as its still very fast as there are only around 200 strings to get.
But this also means I'm getting all of them, even if a page has say one on it. I'd ideally like a way of processing the LanguageString("")'s before hand and doing a query to just get those that are needed at the beginning of the request? Or maybe my own linq based language that can be processed and product a more efficient call.
I'm looking for some advice on how to do this. As I'd like the application to be as efficient as possible. Any advice, help, tips are greatly received. Thanks.
I'd suggest caching language strings on the application basis rather than fetching them for every request. For example, this can be done by maintaining a static dictionary and invalidating the cache only when the user makes changes to these strings. This will make your application more responsive as well as save you from implementing (imho) rather more complex and not necessarily efficient technique of loading this data on-demand.
As a side note I'd add the following: it's usually a good practice to address these kinds of problems when they arise (rather than fixing something that is not broken) and focus on more important things. I totally agree that performance implications of a given solution must always be taken into consideration, I'm just saying that premature optimizations are not always a good idea.

Applicable design patterns

I must develop a simple web application to produce reports. I have a single table "contract" and i must return very simple aggregated values : number of documents produced in a time range, average number of pages for documents and so on . The table gets filled by a batch application, users will have roles that will allow them to see only a part of the reports (if they may be called so ).
My purpose is :
develop a class, which generates the so called reports, opened to future extension (adding new methods to generate new reports for different roles must be easy )
decouple the web graphic interface from the database access
I'm evaluating various patterns : decorator, visitor, ... but being the return data so simple i cannot evaluate which apply or even if its the case to use one. Moreover i must do it i less than 5 days. It can be done if i make a so called "smart gui" but as told at point 1, i don't want to get troubles when new roles or method will be added.
thank you for your answers.
I'm sorry, i realize i haven't provided too much infos. I live in a Dilbert world. at the moment i've got the following info : db will be oracle (the concrete db doesn't exist yet) , so no EF, maybe linqtodataset (but i'm new to linq). About new features of the application,due to pravious experiences, the only thing i wish is not to be obliged to propagate changes over the whole application, even if it's simple. that are the reasons i've thougth to design patterns (note i've said "if it's the case" in my question) .
I'll KISS it and then will refactor it if needed , as suggested by ladislav mrnka, but i still appreciate any suggestion on how to keep opened to extension the data gathering class
KISS - keep it simple and stupid. You have five days. Create working application and if you have time refactor it to some better solution.
The road to good code is not paved with design patterns.
Good code is code that is readable, maintainable, robust, compatible and future-proof.
Don’t get me wrong: Design patterns are a great thing because they help categorise, and thus teach, the experience that earlier generations of programmers have accrued. Each design pattern once solved a problem in a way that was not only novel and creative, but also good. The corrolary is not that a design pattern is necessarily good code when applied to any other problem.
Good code requires experience and insight. This includes experience with design patterns, and insight into their applicability and their downsides and pitfalls.
That said, my recommendation in your specific case is to learn about the recommended practice regarding web interfaces, database access, etc. Most C# programmers write web applications in ASP.NET; tend to use LINQ-to-Entities or LINQ-to-SQL for database access; and use Windows Forms or WPF for a desktop GUI. Each of these may or may not fulfill the requirements of your particular project. Only you can tell.
How about you use strategy pattern for the retrieving data? And use interfaces like following to keep it extendable at all times.
IReportFilter: Report filter/criteria set
IReportParams: Gets report parameters
IReportData: Gets the report data in a result set
IReportFormat: Report formatting
IReportRender: Renders the report
Just thinking out loud.

How to make maintainable code with minimal duplicate code?

I am making a web application in asp.net mvc C# with jquery that will have different pricing plans.
Of course the more you pay the more features you get.
So I was planning to use roles. So if someone buys plan 1 then they get a role of plan 1. Then on the page use an if statement to check if they are in certain roles. If they are allowed to use the feature generate it. If not do nothing.
It could be very well be that the entire page might be shared among all the roles except maybe one feature on that page.
Now someone was telling me that I should not do the way I am thinking of it since if I add more features then my page will get more cluttered with if statements and it will be hard to maintain.
They said I should treat each plan as a separate application. So if I have 2 plans have 2 different links going to different files.
I agree with the person that it probably will be better in the long run since I won't have to keep tacking on if statements but the thing that gets me is say in this scenario.
In the future versions of my site I will have SMS and Email alerts.
Right now I have a Html table with a set of tasks the user has to do. In future versions of the site I will give the option to get alerted by email OR SMS. If they choose say to be alerted by email in a table column an envelope will appear.
Now this might only be for people who are on Plan 2 and not Plan 1. So the solution of the person was just copy and paste all the code for the table code stick in a file called Plan2.aspx. Then add the new row for the icons to the newly pasted code for Plan 2.
Now I would have a Plan1 file that has everything the same except for this extra row that is in the Plan2 file.
So I am not too crazy about that idea because of duplicate code if something is wrong with the table I now have to change it into 2 locations not one. If I add a 3rd plan now I need to keep track of 3 sets of the same code with some varying differences.
My original way would have been that row in the table that is only for plan2 would be surrounded by an if statement checking their role.
Like in some cases I probably will be able to put all the common code into one partial control and all the different code in another partial control but its situations like this that I am not sure about.
There will be many more of these situations this just one example.
So what is the best way to make your code maintainable but also have minimal amounts of duplicate code.
Sorry for the post its kinda hard to describe what I am trying to achieve and situations that are that are could be possible areas of trouble.
Edit
So I am still kinda confused by the examples people have given and would love to see little full examples of them and not just stubs.
I was also thinking but I am not sure if this would be good practice or what and might look pretty strange and some parts.
Is to have everything in common in a partial view even if it is just like one line. Then have 2 separate links and just put the partial views together depending on their role.
I am thinking about the 2 seperate links because of the jquery stuff. Like for instance if I had this
<textbox code>
<textbox code> // this textbox code is only for plan 2 ppl. This textbox needs to go here
<textbox code>
Each of these textboxes tags would be in its own partial view(so 3 in this case)
so I would have 2 aspx pages.
1st
<render partialView 1>
<render partialView 2>
<render partialView 3>
2nd
<render partialView 1>
<render partialView 3>
Then in each of these 2 aspx pages would have different javascript files linked up.
The thing what I was thinking of if I just have like one javascript file with my jquery someone can just go and add the missing html ones and have access to all those features.
So I am not sure how I would write it if I am using the "if statement" way.
But at the same time have everything in partialView will look very funny. Like if I am making a table or something.
One partial view would have the start tag and some rows then X partial views down the road would have the closing tag.
Will look very weird and hard to see the whole picture since you will have to open up X amount of files to see the whole picture.
So there is got to be a better way.
How well abstracted are the components?
My naive approach would be to create a separate layer that dishes the components out to the UI. Something like a repository pattern, with a method like this:
public IEnumerable<PlanRestrictedFeature> GetFeaturesForPlan(Role r)
{
//return all features that the user has access to based on role
//this forces all this logic to exist in one place for maintainability
}
Of course, the method could also take in a string, enum, or Plan object, if you have one. Internally, this may use some type of map to make things simpler.
Then, the View can simply call the Render method of each component. Make sure the repository passes them back in the correct order for rendering, and rely on CSS for placement.
Whilst it's not the best practice to have a view littered with if statements (see Rob Conery's blog post on the matter), some rudimentary logic, is in my opinion, acceptable. If you do this though, you should try to use partials to keep the view as uncluttered as possible. This, as you pointed out is what you think is the best solution.
Your view logic really should be as simple as possible though and your models would benefit from inheriting your price plan information to save duplicating the code itself.
Removed the other code, as you pointed out that you would just use the User class.
Regarding the textbox, this could be trickier. One thought is that you could have your scripts folders which contain global JS, and then subfolders that have JS specifically for other roles (Role 2 and 3 for example). These could be protected by a custom route constraint which prevents users from accessing the file/folder without the relevant level of authentication. You should also use a web.config to provide a similar level of protection. That, or just use the web.config file.
Take a look at the tutorials and sample projects on http://www.asp.net/mvc.
These all follow certain principles which would help you.

Categories