I was tasked to create a javascript library.
The role of this library is to create a complex form with multiple choices/steps on any website. (It means that we don't have access to the website where the form is deployed.)
The code to use the library is the following :
<body>
<div id="container"><!-- Here should be inserted my HTML form --></div>
</body>
<script src="http://wwww.example.com/path/to/myLibrary.js"></script>
<script>
(function() {
var dom = document.getElementById('container');
var mb = new MLibrary(dom);
mb.initialize();
})();
</script>
Once filled, this form is finally sent to our API endpoint where it is treated.
Because of the complexity of the form, I need to create a huge amount of element using javascript. The HTML source code of the form is ~600 lines of HTML
Having this much HTML inside a .js file has proved to be ridiculously hard to maintain and horrible to read.
Because of performance purpose, I was required to avoid AJAX request as much as possible which means that I should avoid to store the HTML on the server and get it through AJAX.
If you can't use AJAX to get HTML, how can you handle a large amount of HTML inside a javascript library in order for it to be maintainable ?
I've created a very basic version of this library using JSFiddle :
https://jsfiddle.net/xd4ojka2/
I faced the same problem awhile back. Basically, I had to bundle my html with my js with Webpack. In development, all code lives in it's own file: html inside .html, js in .js, less or sass in their respective files. Then Webpack will build the app by combining all these files, giving me a build.js file (the name is configurable).
That file might be bigger than your average JS file, but it has all the stuff your app needs, meaning no AJAX to fetch HTML, or other parts of the app. Since this file will be kept in browser's cache, you need to implement a cache busting (outside of the scope of this question).
You could programmatically create HTML tags using JSON input on the fly. The JSON input for generating the markup can be retrieved using AJAX calls or stored in LocalStorage on app initialization or be lazy loaded.
Related
I am developing a Google App Script project that will be used right from within a Google Sheet, with HTML files as dialogs. My project will be a mix of .gs files as well as HTML files for data entry, etc. I am trying to use the methodology explained here:
https://developers.google.com/apps-script/guides/html/best-practices#separate_html_css_and_javascript
to create global JavaScript and CSS modules that I can include in my HTML files rather than cutting and pasting inline code all over the place. This will be mainly useful for the data-saving routines which capture form data, serialize it, then save it to Sheets via the methodology outlined here (and many other places): http://railsrescue.com/blog/2015-05-28-step-by-step-setup-to-send-form-data-to-google-sheets/.
The problem I am having is with trying to call the "include" statement from my HTML files, namely, lines like:
<?!= include('JavaScript'); ?>
It doesn't work when I create a menu on the spreadsheet to display my HTML file as a dialog -- the text of the include line just shows up as literal output on the dialog, and code does not appear to be getting included (not in scope).
I know the Google example is primarily for pages delpoyed via a web app, but I'd like to use my HTML files as dialogs right inside the spreadsheet (e.g. from a menu or sidebar) -- that feels nice and tidy to me. But if I can't get includes to work, my code base is going to be a nightmare and it will be really, really hard to standardize CSS across the whole app. I don't want to be cutting and pasting all the time.
So, what is the secret behind this <?! tag, and why won't it work in my HTML files when they are called as dialogs? It is clear those lines are different from the get-go (maybe not in a bad way, but they don't work), as the Google Scripting console displays those lines oddly, as depicted in the screenshot below:
Please try adding:
<?xml-stylesheet href="chrome://global/skin/" type="text/css"?>
More information can be found in Adding Style Sheets.
Figured it out. I was not properly understanding the way the HTML was being served up as a dialog. I was using this behind a custom menu option:
var html = HtmlService.createHtmlOutputFromFile(htmlFileName);
when I should have been using the more dynamic:
var html = HtmlService.createTemplateFromFile(htmlFileName).evaluate();
The latter generates a user interface object where the server-side script is executed and everything is included properly when I display the object with showModalDialog() (or showSidebar()).
I just had a complete misunderstanding of how the user interface object was being created, so now all scripting works inside my HTML files.
I'm writing a Django app and while somewhat familiar with Django I'm pretty unfamiliar with JavaScript. I'm adding a few lines of JavaScript into one of my pages in order to include a map.
The script simply encompasses initializing the map and then adding markers according to information saved in my database.
Given that there is so little code, would it still be considered bad practice to leave the script in the HTML template and pass information from my database using {{info}}?
If so, what method would you consider to be better?
I assume what you're suggesting is putting both the JS script and its required data into the template (the data being injected into the JS script through string interpolation)
You can see how this can get quickly out of hand. Below I provide levels of code organization, in approximate ascending order (the further you go to better, in general)
1. Include your JS using a script tag, not embedded into the HTML
First: putting the JS into its own .js file and including it via <script> tag is easy. So let's do that. Moreover, modern browsers can load files in parallel, so it's a plus to load the HTML and JS files simultaneously.
2. Avoid feeding the data into the JS using a Django template
Now the other problem I've seen people do is pass the data into the JS using a <script>data = {"info": "something"}</script> before including their JS code.
Which isn't ideal either for many reasons, stemming from the fact that the data is being string-interpolated in the Django template:
3. Make JS pull the data through a Django (REST) API
However since you said you are familiar with Django, I'd like to suggest you create a view that returns the data that your client side JS needs in JSON format. E.g. something that returns {"info": "something"} on /api/info.
There's lots of ways to achieve this, here's a start (albeit might be outdated)
Then I'd have the script.js file read the data with a simple HTTP GET call. Lots of JS libraries can do this for you easily.
Some advantages of this approach
Your code (the JS part) is independent from the data part (the JSON data)
You can easily view/test what's being fed into your JSON, since it's just a HTTP GET request away
Your HTML/JS part is completely static and hence cachable which improves the performance of loading the page.
The Python data conversion to JSON is pretty straightforward (no interpolation kung-fu)
Yep that's bad practice.
Consider defining static folder for your app as described on official django documentation page: Managing static files and upload your js via static template tag.
You could get data which in {{ info }} variable by creating separate django view which would return JsonResponse and then perform AJAX Request to fetch desired data from newly createdd js file.
In my Django projects, if I am using a "base" template that every other template extends, I just put a block called "extrahead" inside of the <head></head> in the HTML.
<html>
<head>
........ other header stuff
........ include other scripts
{% block extrahead %}
{% endblock %}
</head>
.............
</html>
... and then use that block just in the template you want the map on. That is assuming that it is just static js code?
We have some widgets developed using Dojo and Javascript. The dojo code invokes some application services using io script mechanism to overcome cross browser issues. Currently the action for the io script is hard coded as follows.
var host="myhost.com";
var url = "http://"+host+"/context/service";
Every time we need to create WAR, we have to change host details. Is there a way in JS we can configure this ie., some thing like reading it from properties.
I found this s:url struts tag. I assume we can use this tag inside javascript code in a JSP. Can i use it in plain JS out side of JSP?
Sure, if you have your container set up to process *.js files as JSP files.
IMO this is a bit brittle.
You can also do things like hide data in the DOM via hidden elements or <script> tags with reasonable type attributes (e.g., not "text/javascript", the default).
You can also put the data into JavaScript variables in the JSP and access them from external JS files.
Currently I am creating a website which is completely JS driven. I don't use any HTML pages at all (except index page). Every query returns JSON and then I generate HTML inside JavaScript and insert into the DOM. Are there any disadvantages of doing this instead of creating HTML file with layout structure, then loading this file into the DOM and changing elements with new data from JSON?
EDIT:
All of my pages are loaded with AJAX calls. But I have a structure like this:
<nav></nav>
<div id="content"></div>
<footer></footer>
Basically, I never change nav or footer elements, they are only loaded once, when loading index.html file. Then on every page click I send an AJAX call to the server, it returns data in JSON and I generate HTML code with jQuery and insert like this $('#content').html(content);
Creating separate HTML files, and then for example using $('#someID').html(newContent) to change every element with JSON data, will use even more code and I will need 1 more request to server to load this file, so I thought I could just generate it in browser.
EDIT2:
SEO is not very important, because my website requires logging in so I will create all meta tags in index.html file.
In general, it's a nice way of doing things. I assume that you're updating the page with AJAX each time (although you didn't say that).
There are some things to look out for. If you always have the same URL, then your users can't come back to the same page. And they can't send links to their friends. To deal with this, you can use history.pushState() to update the URL without reloading the page.
Also, if you're sending more than one request per page and you don't have an HTML structure waiting for them, you may get them back in a different order each time. It's not a problem, just something to be aware of.
Returning HTML from the AJAX is a bad idea. It means that when you want to change the layout of the page, you need to edit all of your files. If you're returning JSON, it's much easier to make changes in one place.
One thing that definitly matters :
How long will it take you to develop a new system that will send data as JSON + code the JS required to inject it as HTML into the page ?
How long will it take to just return HTML ? And how long if you can re-use some of your already existing server-side code ?
and check how much is the server side interrection of your pages...
also some advantages of creating pure HTML :
1) It's simple markup, and often just as compact or actually more compact than JSON.
2) It's less error prone cause all you're getting is markup, and no code.
3) It will be faster to program in most cases cause you won't have to write code separately for the client end.
4) The HTML is the content, the JavaScript is the behavior. You're mixing both for absolutely no compelling reason.
in javascript or nay other scripting language .. if you encountered a problem in between the rest of the code will not work
and also it is easier to debug in pure html pages
my opinion ... use scriptiong code wherever necessary .. rest of the code you can do in html ...
it will save the triptime of going to server then fetch the data and then displaying it again.
Keep point No. 4 in your mind while coding.
I think that you can consider 3 methods:
Sending only JSON to the client and rendering according to a template (i.e.
handlerbar.js)
Creating the pages from the server-side, usually faster rendering also you can cache the page.
Or a mixture of this would be to generate partial views from the server and sending them to the client, for example it's like having a handlebar template on the client and applying the data from the JSON, but only having the same template on the server-side and rendering it on the server and sending it to the client in the final format, on the client you can just replace the partial views.
Also some things to think about determined by the use case of the applicaton, is that if you are targeting SEO you should consider ColBeseder advice, of if you are targeting mobile users, probably you would better go with the JSON only response, as this is a more lightweight response.
EDIT:
According to what you said you are creating a single page application, if this is correct, then probably you can go with either the JSON or a partial views like AngularJS has. But if your server-side logic is written to handle only JSON response, then probably you could better use a template engine on the client like handlerbar.js, underscore, or jquery templates, and you can define reusable portions of your HTML and apply to it the data from the JSON.
If you cared about SEO you'd want the HTML there at page load, which is closer to your second strategy than your first.
Update May 2014: Google claims to be getting better at executing Javascript: http://googlewebmastercentral.blogspot.com/2014/05/understanding-web-pages-better.html Still unclear what works and what does not.
Further updates probably belong here: Do Google or other search engines execute JavaScript?
I'm pretty new to web development. What is the best practice in keeping the same sidebar and other elements across web pages on one's site? Do you store the sidebar html and call that? If so, how would one go about doing something like that?
There're many options to handle this problem but I've found easy one using jQuery. Use this if it suits your requirements.
Add the jQuery CDN in your HTML file.
Create a JS file as sidebar.js.
Copy all your HTML code of the sidebar and store as a string variable in a function of the JS file. as
function loadNavbarDiv() {
String navbar_code_str = '<nav><div>...</div></nav>
$('body').append(navbar_code_str);
}
Then in the HTML file, you want to add navigation bar, add folowing code in your <head>
<script src="sidebar.js"></script>
<script>
$(document).ready(function(){
loadNavDiv();
});
</script>
It's working fine for me.
Happy coding!
Here's one way to do it: use "include" files. No JavaScript required. The server does the work, instead of requiring the client to add the content.
SSI, or Server Side Includes, were first developed to allow Web
developers to "include" HTML documents inside other pages. If your Web
server supports SSI, it's easy to create templates for your Web site.
Save the HTML for the common elements of your site as separate files.
For example, your navigation section might be saved as navigation.html
or navigation.ssi.
Use the following SSI tag to include that HTML in each page.
<!--#include virtual="path to file/include-file.html" -->
Use that same code on every page that you want to include the file.
That page also describes some other approaches. But if you know this is called using include files, you can search for it more easily. For example, this article describes includes and how to call them from JavaScript if you must.
As long as you're only coding in html, you will need to copy your html into every page. You can store the css for the sidebar in one and the same file and call that on every page though.
Other scripting languages and frameworks might contain templates (php) or master pages (asp.net) for example which make it possible to use the same code in different pages.