I have several websites and these website share several components. It was quite easy with classic ASP.NET WebControls ascx. I created several such controls, put into one dll library and I reference these libraries from these websites via namespace.elements runat=server...
But I don't know how to do it after I have upgraded to ASP.NET MVC. I can put model and cotroller class into dll.
But how should I put and reuse Views into dll?
I suppose that Views are not compiled into dll, if I can change the View without recompiling the dll.
EDITS:
I would prefer some standard solution over third party. The last solution for me is to use StringBuilder instead of ViewEngine.
I've been using Razor Generator for several years to store reusable MVC views and helpers in separate .dll.
Razor Generator "is a Custom Tool for Visual Studio that allows processing Razor files at design time instead of runtime, allowing them to be built into an assembly for simpler reuse and distribution."
Installation instructions
It’s on the VS extension gallery, so install
it from there. It’s called “Razor Generator” (not to be confused with
“Razor Single File Generator for MVC”).
It is quite simple to use:
Usage in an MVC app
Install the 'RazorGenerator.Mvc' package, which registers a special
view engine
Go to an MVC Razor view's property and set the Custom tool to RazorGenerator
Optionally specify a value for Custom Tool Namespace to specify a namespace for the generated file. The project namespace is used by
default.
Optionally specify one of the generators in the first line of your Razor file. A generator declaration line looks like this: #*
Generator: MvcHelper *# . If you don't specify this, a generator is
picked based on convention (e.g. files under Views are treated as
MvcViews)
You'll see a generated .cs file under the .cshtml file, which will be used at runtime instead of the .cshtml file
You can also go to the nuget Package Manager Console and run 'Enable-RazorGenerator' to enable the Custom Tool on all the views.
And to cause all the views to be regenerated, go to the nuget Package Manager Console and run 'Redo-RazorGenerator'. This is
useful when you update the generator package and it needs to
generate different code.
MVC project should be chosen for class library in order to support intellisense and other useful features.
Usage in a View Library
If you need to create a separate library for your precompiled MVC
views, the best approach is to actually create an MVC project for
that library, instead of a library project. You'll never actually run
it as an Mvc app, but the fact that it comes with the right set of
config files allows intellisense and other things to work a lot
better than in a library project.
You can then add a reference to that 'MVC View project' from your real
MVC app.
And note that you need to install the 'RazorGenerator.Mvc' package
into the library, not the main MVC app.
Programming ASP.NET MVC 4 written by Jess Chadwick tells that
In the ASP.NET Web Forms world, you can achieve this by creating user
controls or custom controls that can be compiled into standalone
assemblies. These assemblies can be distributed across projects,
thereby enabling their reuse across projects.
The Web Forms view
engine offers the ViewUserControl class, which can be leveraged to
create such components for the MVC framework. The Razor view engine in
ASP.NET MVC, however, does not offer any such method out of the box.
and suggests using Razor Single File Generator visual studio extension, another one but the similar to Razor Generator approach.
Related
Visual Studio 2015 + all updates.
Asp .Net Web application (MVC).
I start off by adding a few class libraries and separating the Asp .Net WA into layers i.e. DataAccess, Business Logic and the web project itself.
Once separated I add relevant references and everything is working as I expect it to be (i.e. the application functions as it did before I separated it into layers).
In my BL (Controllers are found here). I don't have the option to Add a Controller, like you would when right clicking the Controllers folder in the default project, so add the below line
<ProjectTypeGuids>{349c5851-65df-11da-9384-00065b846f21};{fae04ec0-301f-11d3-bf4b-00c04f79efbc}</ProjectTypeGuids>
to the csproj file for my class library and the Add Controller option now appears. Create a controller but throws an error which was due to not having a web.config file - add this file and all works (although it would be nice to have this library working without a web.config file).
The problem I've hit is, when the Controller is created it also adds a View template within the class library but my Views folder is located in my web project.
Have I done this wrong? Is there a workaround so when a controller is created, it also creates the Views into the correct project? Or another approach for this?
This is just a guess, but it seems like you are try to use a UI-based architectural pattern to build your business layer.
Typically, your models, views, and controllers are all maintained in the main web-app project. Any supporting functions (like your BL and DL) are added via class libraries. The Visual Studio MVC templates are built around that concept, which is why you had to manually add support with the GUID - and why it automatically creates the view.
If I may ask, why are you trying to build controllers into your BL? If you are trying to decouple your UI from your server code, perhaps WebAPI would be a better option.
UPDATE - A few helpful links
ProDinner - ASP.NET MVC Sample App
N Layered App with Entity Framework, Autofac, ASP.NET MVC and Unit Testing
Architecture Guide: ASP.NET MVC Framework + N-tier + Entity Framework and Many More
Most of your issues boil down to using the scaffold. The scaffold is great when you're just starting out or for extremely simple projects, but it quickly falls down beyond that. Specifically, adding a controller via scaffold is designed for an MVC project, so it expects to find things you'd find in an MVC project. Additionally, it creates scaffolded views in an appropriate directory in Views because, again, that's what it's designed to do.
The simplest solution, then, is to just not use the scaffolds. A controller is just a class that inherits from Controller. Nothing special there. Then, you can create the views where you want to create them.
I am reasonably familiar with C# desktop development and am very familiar with Rails, so ASP.NET MVC makes sense to me. However, I have a more lightweight site that I want to build in a manner more akin to dropping a bunch of .php files into a hierarchy of directories and having them be served up as just HTML files run through a pre-processor. (A full MVC stack and architecture seems like overkill for what is basically a brochure site.)
I believe it is possible to do this in ASP.NET (I remember the single .aspx pages approach from back in the day), but I'm not sure what this programming model is called in order to search for info on it--I can only find references to MVC and "web forms" in newer documentation.
I also would like to use pieces that are more popularly used in MVC, but in this more simple page-based model. For example, I would like to use Razor templates (with layouts and partials) and to access a single Model object that is shared across a number of templates.
I would appreciate any advice, or info on how to find documentation on using ASP.NET in this way.
The ASP.NET Web Pages framework supports web applications built using the Web Site project type* as well as Razor layouts and partials. It does not support strongly type models in the same way as MVC. However. that doesn't prevent you from taking a strongly typed approach to Web Pages development. The mechanism for passing data to partials is via the dynamic Page property (similar to ViewBag) which requires casting to get Intellisense support. Web Pages also lacks any kind of Model Binding support.
*This is the ASP.NET project type that does not require pre-compilation before deployment (as opposed to the Web Application project type). Web Forms apps can be built using either project type, but ASP.NET MVC apps can only be built using the Web Applications project type.
I have an ASP.Net MVC Portable Area project containing pure C# code, Razor views (cshtml), javascript and CSS. It's all being embedded into the output DLL for the area project.
I want to create a #helper function that can be accessed across the cshtml views in the area, and I followed Scott Gu's blog post to set this up. According to the Visual Studio intellisense and the compiler, everything was OK when I tried to access the helper like this:
#Helpers.MyMethod("myInput");
But when I tried running the application I got a runtime error stating that
"The name 'Helpers' does not exist in the current context"
I have put my Helpers.cshtml file in an App_Code folder in the root of my MVC portable area project, and set the build action to "Embedded resource" (as I need to do with the rest of my cshtml files).
I tested putting the Helpers.cshtml file in the App_Code folder of my ASP.Net MVC application project instead, and then it worked just fine, but it is not an option to have the helper in the application project, because I do not want dependencies from the area to the application.
It also works to rewrite the #helper to a #function and put it inside each of the CSHTML views, but I would like to avoid having this duplicated for each view.
So my question is why the application cannot seem to find the Helpers class when placed in the portable area project, and what I can do to be able to have razor helper functions inside my area that can be used across razor views.
When an ASP.NET application is published using the publish option in Visual Studio a series of DLLs are produced in the BIN folder on the web server. What is the difference between the DLLs generated by Visual Studio specifically for ASP.NET and a standard Class Library?
I am wanting to reuse code in classes that are contained in an ASP.NET application.
One option for me is to convert the ASP.NET classes into a class library and hence the reason for this question. The other option is to use a web service to expose the functionality required by other applications.
There is no difference between DLL's generated by ASP.NET and a standard class library. Although the web application project produces a DLL, which can't really be reused (well it could, but it contains the code-behind of your pages and user controls, but not the markup), every other DLL can be reused.
Using services and implementing Service Oriented Architecture (SOA) is another option too, so it really depends on what your requirements are, and what you are trying to reuse.
The main reason for choosing a class library over built in classes is so they can be shared with other projects, or the DLL could be distributed for further use.
The benefits of a class library that I can think of are:
Tidier project structures
Quicker Project build time
Different versions of your library can be referenced, hence resilient to upgrades
I generally use web services for projects that require communication between applications/servers, rather than wrapping common code.
You should extract the code you want to reuse in a separate assembly and reference it in the web project and in the other project. Don't use the assemblies with the web pages and other application specific code in another application.
Has anyone been able to create an Asp.Net Mvc plug-in implementation using MEF (or some other IoC tools) that does NOT require the Razor views to be compiled into dll's? Ideally, I'd like to be able to deploy Razor view changes by simply dropping new files in a folder rather than having to recompile and drop new dll's. Any ideas?
By default views are not compiled so you should be able to do this without any extra work.