Not sure if this is possible or even if I should do it, but I think it's quite interesting.
I have a javascript file which I'm referencing in a flat HTML page. I'd like to pass in a parameter or two via the path to the script. Like this;
<script src="/scripts/myJavascriptFile.js?config1=true" type="text/javascript"></script>
Not really sure if it can work but it would make my solution a little easier for others to take my script and implement (arguable).
Cheers,
Mike
I don't think that passing in variables via the src attribute is possible out of the box without some extra coding on your part (there is an article here if you are interested!). You could do the following though, which should provide the same functionality as you are looking for:
Define your "config" variables in a single script block on your HTML page:
<script type="text/javascript">
var config1 = true;
</script>
Reference your external JS file in a second script block:
<script src="/scripts/myJavascriptFile.js" type="text/javascript"></script>
Add this code to your external JS file to reference the "local" variable in your HTML:
var conf1 = window.config1;
if (conf1) {
// Do stuff
}
This is a variation on Matt's answer. I have a similar case where I need a jQuery file to use a value that is generated in the HTML (by Razor in this case). I write the value to a meta tag, generated as it is from the controller:
<meta name="sessionId" content="#ViewBag.SessionId">
and then read it in the jQuery file:
var sessionId = $("meta[name=sessionId]").attr("content");
It's not quite the same as passing it in by querystring, but useful if that information is considered "meta-information" of the HTML page.
Related
I have a JavaScript function that runs in an HTML file, but in order to avoid "angular is not defined", I put the following before my HTML script
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.1/angular.js">
Is there a way to do this in a actual JavaScript file? I want to write my function in a JavaScript file not HTML so I can't use src HTML code.
I tried copying all the code and putting it in a file and referencing the file in the JavaScript but it doesn't work.
Any workarounds?
A simple technique that I use to load dependencies is to dynamically append them to the document head and use a load EventListener to run my code after the external script has finished loading.
let s = document.createElement('script');
s.src = 'https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.1/angular.js';
s.addEventListener('load', init);
document.head.appendChild(s);
function init() {
// your code here
}
Source: I build a lot of plugins/widgets.
There are a variety of solutions to this problem and you should review how scripts load and the onready events for an html document. One simple solution would be coding your custom function to be called in an approach something like this:
<script onload="myCustomFunction();"
src ="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.1/angular.js" >
</script>`
Of course, there are really many different approaches and I would consider this one only to use in a quick and dirty situation.
Something like:
const libname = require("https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.6.1/angular.js")
Should import the .js file into your project.
I have an app that uses HTML, and Coffeescript in the frontend. I recently made it possible to change the language thanks to i18next.
Now I have some buttons that change my window.userLang to the different languages, but the user has to refresh some elements of the app to see it translated.
My problem comes because I need the translations made without refreshing the HTML.
In the app, I use Craftyjs, so what I need to know is how can (if possible) from HTML file, call a function that it's defined in Craftyjs.
The function I want to call is: Crafty.scene("main").
Thanks all!
Create a global name space defined above where your scripts are included. Then in your javascript you can define the functions you need as fields on that namespace.
<script>
var MySweetWebApp = {};
</script>
<script src="..."></script>
... Inside JS file ....
MySweetWebApp.Crafty = { ... }
... From Anywhere ...
MySweetWebApp.Crafty.scene('main');
I need to include a JavaScript object (JSON) in my HTML page.
JSON is rendered at the same time page HTML is rendered on server. Data is not retrieved using AJAX call.
I can think of two ways of doing this, and looking for feedback and recommendations.
What are good practices for passing JavaScript (JSON) blob with a page?
Option 1
HTML:
<script type='text/javascript'>
var model = { <JSON> };
</script>
.js:
function doSomething() { <use this.model here> }
Option 2
HTML:
<script type='text/javascript'>
loadModel({<JSON>});
</script>
.js (included at the top of the html file):
var model = null;
function loadModel(model) { this.model = model; }
function doSomething() { <use this.model here> }
Variation
Instead of including JSON in HTML, JSON can be stored in a separate .js file. Any comments on doing so?
Option 1 lets you include .js file anywhere, and including it at the bottom of the page makes it render faster (good thing), but since JavaScript renders the model on the page, this makes it a moot point. Still not depending on the location of the .js inclusion makes it less error prone.
Also R# complains (reasonably) about model being uninitialized.
Option 2 feels better (it encapsulate details better, for one), but .js must be included before call to loadModel.
I have seen and done both ways, but didn't notice any significant advantages of one way over the other.
Server platform should be irrelevant, but it is IIS 7.5/ASP.NET MVC 3/Razor
Forget your two suggestions - both are extremely vulnerable to XSS. NEVER PUT UNTRUSTED TEXT IN A SCRIPT TAG.
Instead, use the owasp recommendation.
Stick your (HTML encoded) JSON in the DOM like so:
<div id="init_data" hidden>
<%= html_escape(data.to_json) %>
</div>
Then read it in JavaScript like so:
// external js file
var dataElement = document.getElementById('init_data');
// decode and parse the content of the div
var initData = JSON.parse(dataElement.textContent);
There would be ever so slightly more overhead with option two. As you have the overhead of a function call, and an extra variable (your parameter), which will be allocated and deallocated.
As you said, there is little advantage/disadvantage to either way.
Can you use jQuery? Then you can use the DOM ready event instead of including javascript in your HTML.
EDIT:
Hmm, in that case you could include the JSON inside a hidden element when the page is generated. Then inside the DOM ready event you could read and parse it from the page using jQuery.
Another alternative might be to use HTML 5 data attributes and including the data in one of those.
If it were me I'd probably just use an ajax call since it is easier and seems a little cleaner.
I am trying to load the statcounter script from my custom js file. The original script looks like this:
<html>
<head>...</head>
<body>
...
<script type="text/javascript">
var sc_project=11111111;
var sc_invisible=1;
var sc_partition=11111111;
var sc_click_stat=1;
var sc_security="11111111";
</script><script type="text/javascript" src="http://www.statcounter.com/counter/counter_xhtml.js"></script>
...
</body></html>
The code seems to set the variables, then loads the counter script which reads the values of the variables and does its job.
I'm trying to call the counter script like this:
// file: counters.js
function CounterFromStatCounter() {
sc_project=11111111;
sc_invisible=1;
sc_partition=11111111;
sc_click_stat=1;
sc_security="11111111";
var oHead = document.getElementsByTagName('HEAD').item(0);
var oScript= document.createElement("script");
oScript.type = "text/javascript";
oScript.src="http://www.statcounter.com/counter/counter_xhtml.js";
oHead.appendChild( oScript);
}
// main page
<html>
<head>
...
<script type="text/javascript" src="counters.js"></script>
...
</head>
<body>
...
<script type="text/javascript">
CounterFromStatCounter();
</script>
...
</body></html>
The code seems to work: the script element that references the statcounter script appears in the head section as it should, but no visits are recorded - this means that the variables set in my script cannot be accesed by the counter script.
What am I doing wrong?
You are doing a couple of things wrong.
1) You likely have not validated your code. Go to http://jslint.com and validate your JavaScript.
2) Do not write JavaScript into your HTML. That has a tendency to force all code bits into the global namespace, which is very likely to produce collisions with any other JavaScript code.
3) Only reference external JavaScript files directly prior to the closing body tag. Script interpretation blocks parallel downloads in IE.
Accomplish those three and then come back for more help.
var CounterFromStatCounter = function () {
var sc_project = 11111111,
sc_invisible = 1,
sc_partition = 11111111,
sc_click_stat = 1,
sc_security = "11111111",
oHead = document.getElementsByTagName('head').item(0),
oScript= document.createElement("script");
oScript.setAttribute("type", "text/javascript");
oScript.setAttribute("src", "http://www.statcounter.com/counter/counter_xhtml.js");
oHead.appendChild(oScript);
}
I have looked at the above code more closely and here are my thoughts:
1) That is how the code should look once beautified and reduced to a single var command in your function without any implied globals, except for the function name itself.
2) Dynamically created content from client-side code is destroyed each time the page loads at each user. So you will likely not want to write output using JavaScript as any means of providing a data reference point. I recommend doing this completely on the server side to be more efficient. If you must use JavaScript you will need to write to some intermediate data store, like a JSON, file that you connect to using the xmlHttpRequest object.
3) I would not recommend writing anything to the head of the document dynamically from the client-side due to different interpretations of the DOM between browsers and also once the head is loaded the browser has no reason to read it again for new information.
4) To be most efficient scripts should be in external files that referenced just before the closing body tag, because script interpretation blocks parallel downloads in IE. Putting scripts in the head is results in dramatically slower page loads in IE as a result.
5) I changed "HEAD" to "head" because JavaScript and XHTML are both case sensitive.
6) I also changed the way attributes are appended to your dynamically created script tag to use DOM methods. I don't know if this is the more correct method, but it is certainly more inline to the standards.
Define the variables globaly and write some js like below.
window.attachEvent('onload', function() {
document.write('<script type=text\/javascript src=blabla.com\/counter.js><\/sc' + 'ript>');
});
this should work in IE. For other other browsers implement addEventListener...
I've got some JavaScript in an ASP.NET page that looks like this:
var list = $get('<%=Topics.ClientID %>');
I have many functions written now where this syntax is used, and I would like to centralize my JavaScript and move this into an external JavaScript file. This breaks however, since 'Topics' cannot be found.
What is the best strategy for getting this to work? I assume I should pass the control/control information as a parameter to the function, but I can't seem to get the syntax to work. Any suggestions?
It's a common problem for ASP.NET JS development. As for me, I'm using same approach each time and it looks fine.
I'm used to OOP in Javascript, so most my JS external files look like:
function CouponManager()
{
}
And in .aspx code i do:
<script language="javascript">
var couponManager = new CouponManager();
</script>
If I need to pass some parameters I change the declaration of class to:
function CouponManager(params)
{
// .. stuff here
this.initialize = function(initParams)
{
// .. accessing initParams variable for server control IDs
};
this.initialize(params);
}
And from .aspx code I do the following:
<script language="javascript">
var couponManager = new CouponManager
({
txtCouponNameId = '<%= txtCouponName.ClientID %>',
txtCouponDescriptionId = '<%= txtCouponDescription.ClientID %>'
});
</script>
This approach allows me to separate JS from .aspx page and have all server control dependencies in a single tag.
You should create a javascript method from inside the usercontol which returns the client side element. Then in your other page/control, just access that method
In User Control
<script language="javascript">
function GetTopics() {
return = $get('<%=Topics.ClientID %>');
}
</script>
In other page/control
<script language="javascript">
var list = GetTopics();
</script>
Edit - The problem you are facing is you need Topics.ClientID where it doesn't exist. So the only real way to bridge that gap is to put it in a common place. If you really don't want to do that, you can try and select your element by some other criteria. If you are using jQuery, you could mark an element with a class of Topics then find it with $(".Topics").
if you know that you only have one server control called "Topics" per page, and you use naming conventions you can inherit from whatever the control Topics is (maybe it's a HiddenField? you don't specify) and override its ClientId getter to return its server id like this:
http://andreascode.wordpress.com/2009/04/27/tiny-drips-of-aspnet-juice/
then you can know in your javascript files that there will be a hidden field in the page with the id set to "Topics" and use that directly.
depending on your domain/situation this could either save you a lot of time or screw you over big time.