I have a question regarding an order of operations and to get some feedback on feasibility.
This involves MVC Razor, Javascript and the HTML preload property.
I have a partial view that runs some Javascript. It requires an external JS library to run but I don't want it to run on every page to save load times.
I know I can use MVC "Sections" to have blocks of code render within sections of a page by using the RenderSection function. However, I have a partial view that is part of many templates.
So the structure of my template system (and this is because this is an off the shelf product), that the View structure is as below.
Root.cshtml (is the main layout wrapper)
< Root.Head.cshtml > (Partial view contained within Root.cshtml that has the HTML Head markup)
THEN,
OneColumn.cshtml, TwoColumn.cshtml (Inherit Root.cshtml as their "master" template)
THEN
ProductTemplate1.cshtml,ProductTemplate1.cshtml,ProductTemplate1.cshtml,ProductTemplate1.cshtml (these inherit EITHER "OneColumn" or "TwoColumn" as their "master" template).
THEN each of those "Product" templates can have a partial view of "Calendar.cshtml".
The 'Calendar.cshtml' is the one that requires the external JS library to run some of its functions. I would like to have the external JS library only load if the Calendar.cshtml partial is included in a product template, BUT I want the library to not end up in the body of the HTML layout but instead, like any good formatted HTML, either in the HTML Head OR just before the closing tag of the HTML body.
Since the Calendar.cshtml file 'lives' in the Product template, the product template is actually already two levels deep in its inheritance of layouts.
My thought would be to put in the Calendar.cshtml file this code, BUT I don't know if it would load fast enough to allow the code that calls the external JS file to actually run.
Hence my question about the 'preload' property.
This is what I am thinking of putting in the 'calendar.cshtml' file.
function loadJQUERYUI(){
var importJQUERYUI= document.createElement('script');
importJQUERYUI.src = 'https://code.jquery.com/ui/1.13.0/jquery-ui.min.js';
importJQUERYUI.async = 'true';
importJQUERYUI.rel= 'preload';
document.head.appendChild(importJQUERYUI);
}
loadJQUERYUI();
<!--Code called in the Calendar.csthml partial-->
$('#datepicker').datepicker();
The thing is, would jQuery UI even load before the .datepicker() function fires?
I had looked at wrapping the $('#datepicker').datepicker(); call in a timeout so it gives the external script time to load, but I don't know how long an external responding server will take to respond to the request. That is super hacky, and don't really want to do that.
I tested it without a timeout and the $('#datepicker').datepicker(); function fired before the call to the jQuery UI library loaded. I tried it with a 1 second timeout and the datepicker loaded, but that is not ideal, because I don't know when the external library will respond in what timeframe.
If I were to use the MVC Razor "RenderSection", I have done it where it each section calls a sub section all the way down the line four levels deep, but since I have multiple templates that require this, isolating it so the Calendar.cshtml partial injects the external jQueryUI library is desired without having to next "RenderSections" all throughout my templates.
Is there another way?
Related
I am trying to render a component server-side for the initial page load. The markup gets rendered perfectly using #Html.React("componentName", props). The issue I am having is the component will render without styling. An instant later the styles get loaded through a Webpack bundle and the typical style-loader.
I have tried a couple approaches.
https://github.com/thereactivestack/style-collector-loader does not work because I get an error saying the global is undefined.
https://github.com/kriasoft/isomorphic-style-loader does not work for the same reason
Ideally I would like to get the required CSS from the components and render them into the razor view.
I am trying to fix a bug on an existing project. Webpack and react are relatively new concepts for me so I am not entirely sure what information I should provide. Let me know what additional details will help.
You should call require('your css file') in componentDidMount function when trying to use server-side rendering.
for more info:
https://github.com/webpack/react-starter/issues/37
We are still using asp.net mvc WebForms (legacy code) with a lot of our own frameworks.
one of our features is gathering the static content on run time and creating the min and optimize versions. (we found out it was faster).
Yet Razor rendering pipeline is different then WebForms, so the content is rendered out of order.
For example we have a view to render lets call it Home, Home has several calls to X.Css("css_x");
we gather them into a 'list' Home has partial view to render which inside also has X.Css invocation.
After Home is rendered into the output buffer stack the _Layout is rendered again with X.Css being called. assume that now we need to render all of the css files but the order is wrong.
How is it possible to synchronize view and layout with the order i need (first layout then views and partials)
Any one got an idea.
(if i am not understood please let me know and i'll try to elaborate more)
I ran into this problem multiple times in my career, and never was able to find a elegant solution for it. Imagine you have a simple page, that has a repeater. You populate that repeater on the server-side through the databinding. That's great, works fast and does what it's supposed to. But now you want to add paginator to that repeater, or otherwise change the output. Doing it through Ajax is a preferred way to enable rich client interaction.
So you create a web-service that serves you the data as JSON, but now you are stuck... Either you have to write complicated client-side code to find each field that you need to modify in each repeater-item, or you have to blow away the whole server-side output of the repeater and construct new HTML from the scratch, or, the method that I've been using lately, take the first repeated item, blow away everything else and clone the first item as many time as you need to and modify it's fields.
All of the described methods are not optimal, because no matter what, they require quite a bit of repeated logic on the server-side (i.e. template in repeater) and on the client-side (javascript to display JSON data). There's got to be a better, easier way to do this. First thing that comes to mind, is instead of returning JSON from the web-server, return HTML of the pre-populated repeater. But for something like that, I might as well use ASP.NET AJAX Update panel. The output isn't going to be any smaller with a stand-alone web-service.
Next thing that I thought of, is JavaScript templates. What if there would be some way to take unprocessed repeater template on the server-side, and convert it to JavaScript template that could be either embedded on the page at load, or served as part of the web-service response. However, I couldn't find any existing solutions for something like this. And I can't think of a simple way to do that myself. Any ideas?
P.S. Rendering JavaScript template to the client-side on page load, and using JavaScript to populate it without the initial view being rendered on the server (no repeater and databinding) is out of the question. I care too much about performance.
Firstly, I don't believe that using client template with JSON data even on first load will adversely affect the performance unless we are talking about devices with different form factors such as phones etc.
However, if you must use server side templating/rendering then why not make server return the html for the repeater. This can be done by putting repeater logic into a different user control/page and processing only that page on ajax request. And this is not at all equivalent to using UpdatePanel (as stated by you) - UpdatePanel posts entire page data (including view-state) having more request size. The response size is also larges because it must contain the view-state. On server side also, use of UpdatePanel results in loading complete control tree with state data and post-back event processing. Sending only the requisite html is much better approach and will fit your needs perfectly - only issue is the html would be larger in size as compared to JSON.
Lastly, there are some interesting projects such as Script# - Script# converts C# code into java-script. You may build something similar (using script# itself) to convert the server side templating code into eqivalent JS code. More viable approach on similar lines could be use T4 templating to convert a technology-agnostic template into both server side code (markup + code or pure code) and equivalent JS-code.
After thinking about all pros and cons of different approaches, I stopped on the following method. I created a custom ASP.NET databound control, that can render HTML, however, when the page is requested with query string parameters, instead of just doing standard rendering, it will use Response.Clear() and Response.End() and in between of those two commands output JSON version of data based on the query string parameters. Also on the first rendering of the page, it will also output JavaScript template using reflections to read names of the variables from the control's template area.
This method works great, all I have to do, is drop my control on the page, data bind it, and it works as a true AJAX grid that supports pagination, sorting and filtering. However it does have limitation. In the control's template you can only specify variables, not expressions. Otherwise reflections can't convert it to a JavaScript variable. But I can live with that.
Other possibilities that I considered is a separate web-service that takes a type of the page as parameter and uses reflection to get data bound object as well as create template for the grid. I also though about writting my own version of update panel, that would not use view state and only send in part of the page.
I am working on moving an application from MVC2 ASPX to MVC3 Razor, and is quite stuck moving a baseclass for more MasterPages in old MVC2 application.
The baseclass is used for automate include of css and js on pages in order to ease quickfix and debugging when developing application in local environment, but when running application in production environment it has to update and include single minimized css and js files delivered from a external CDN.
The code needs to know about the View file eg. "~/views/home/index.chtml" and/or the Layout file eg. "~/Views/DefaultNoLogon.Master" in order to include and handle css and js files correct.
I tried to implement own baseclass using the pageBaseType in Razor part of web.config, but it seems like it is executed both for View and Layout file, and I could not find a execution point where information about both View and Layout file is present. I also tried to implement the file logic using a HtmlHelper, but I can only access information about the View file and miss information for Layout file for View.
I don't want this kind of code to be implemented in Route, Controller or ViewModel since it should be related directly to generation of Views.
Any ideas how to get information about View and Layout files in MVC3 Razor app?
Well, never mind my question.
I redesigned my logic for automatic rendering of js and css files, which actually is more simple and works better. My Mvc3 Razor app is now capable to take all js and css files for a view (including css and js for all layoutpages) and render them into single minified files.
Works like a charm, and I guess it's more future proof than my old solution, unless Guthrie make fundamental changes in layoutpages and Html helpers in Mvc4 or later.
Is there a c# command to include another web page - the equivelant of the php require?
I know how to do server side includes but was looking for something code based.
Thanks
Thanks for the answers all. I think I might need to explain further. I have several sub-pages that I will be loading during the use of the site using an xmlhttp request. Initially however, I need to load the starting sub-page before the user has interacted with the site. I could do this with js, but that would require more overhead in server calls from the client for the initial load. I already use master pages, but this is a little different. Since this is done serverside initally but must remain able to be refreshed clientside, I don't think I can make these pages into controls can I? I am pretty new to .Net so I may be making my life harder than I need to.
I think what you may be looking for are MasterPages and UserControls. A MasterPage allows you to define a basic template that is "filled in" by the implementing pages by having the implementing page add it's own content to the ContentPlaceHolders defined on the MasterPage. A UserControl is a re-usable piece of markup and associated code that you can reference from your mark up or add dynamically to the page being rendered in codebehind.
The way ASP.NET is structured, you shouldn't really need to do this. Code is compiled, so all of your classes and functions should be accessible simply by referencing the relevant assembly or namespace, without having to include individual code files.
You might be looking for user controls, which allow you to create fragments of markup with their corresponding code behind, and then reference these in your page.
With ASP.NET MVC it looks like this:
<% Html.RenderPartial("LogOnUserControl"); %>
This way you can put another UserControl on your page.
you can use include in asp.net like php include from below mentioned code
<!--#include file="include/leftmenuscript.inc"-->
You can also use a master page, as someone stated below, which flushes out your basic layout and lets you define content place holders, which other pages can implement and fill in the content. Master pages are a popular approach for defining page elements that are consistent across all pages, like your nav there (also things like headers, footers, common scripts, CSS, etc.).