Thanks,
Iain
<%@ language="javascript"%>
<script type="text/javascript" language="JScript" runat="server">
function myFunction() {return 'Hello Functional World'};
var myVariable = 'Hello Variable World';
</script>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://
www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en">
<head>
<title>Test</title>
</head>
<body>
<% Response.Write('Test 1: ' + myFunction());%>
<br />
<% Response.Write('Test 2: ' + myVariable);%>
</body>
</html>
> Hi, throw the following example into a text file, save with an ASP
> extension, and execute it in IIS6/7. Can anyone explain why Test 1
> works fine, and Test 2 doesn't? Is it something to do with variable
> scope?
>
> <%@ language="javascript"%>
> <script type="text/javascript" language="JScript" runat="server">
> function myFunction() {return 'Hello Functional World'};
>
> var myVariable = 'Hello Variable World';
> </script>
> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://
> www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
> <html xmlns="http://www.w3.org/1999/xhtml" lang="en">
> <head>
> <title>Test</title>
> </head>
> <body>
> <% Response.Write('Test 1: ' + myFunction());%>
> <br />
> <% Response.Write('Test 2: ' + myVariable);%>
> </body>
> </html>
Let's first get the crap out:
<%@ language='javascript'%>
<script language='javascript' runat='server'>
function myFunction() {return 'Hello Functional World'};
var myVariable = 'Hello Variable World';
</script>
<% Response.Write('Test 1: ' + myFunction());%><br>
<% Response.Write('Test 2: ' + myVariable);%>
Because of the order of things, as I believe they are:
1 the functions are build
2 runats of the non globally declared language are run
3 the global code is run
4 runats of the globally declared language are run.
so the var is not jet executed when needed by the response write.
--
Evertjan.
The Netherlands.
(Please change the x'es to dots in my emailaddress)
I am very keen to include parts of the prototype library on the server
side, and to declare objects ( var object = Class.create({...}); )
in an external .js file that I can then include on both the server and
client. This would, for example, allow me to use the same object to
write html to the page before it's sent to the client, and then
rewrite that html on the client-side.
Given your understanding of the order of execution, can you say
whether this is possible? For example, might there be a way to say,
'once the global code is run, do xyz'?
Thanks again,
Iain
[please always quote on usenet, this is not email. others should be able
to follow the thread, and not all newsservers are getting postings in
reasonable chronological order to switch back. NEtiquette is sensible.]
Serverside you could just include the script file as a text include:
<%@ language='javascript'%>
<%
<!--#include virtual ="/libs/myJs.js"-->
%>
There is no advantage of calling libraries as done clientside, because
caching them is not usefull IMHO.
I had wondered why we always had all this quoting cluttering up the
page - I will leave it from now on.
>
> > Evertjan, many thanks for cleaning up my example and offering an
> > explanation.
>
> > I am very keen to include parts of the prototype library on the server
> > side, and to declare objects ( var object = Class.create({...}); )
> > in an external .js file that I can then include on both the server and
> > client. This would, for example, allow me to use the same object to
> > write html to the page before it's sent to the client, and then
> > rewrite that html on the client-side.
>
> > Given your understanding of the order of execution, can you say
> > whether this is possible? For example, might there be a way to say,
> > 'once the global code is run, do xyz'?
>
> Serverside you could just include the script file as a text include:
>
> <%@ language='javascript'%>
>
> <%
> <!--#include virtual ="/libs/myJs.js"-->
> %>
>
> There is no advantage of calling libraries as done clientside, because
> caching them is not usefull IMHO.
>
> --
> Evertjan.
> The Netherlands.
> (Please change the x'es to dots in my emailaddress)
No doubt I'm making a mistake here. However, I don't appear to be
able to use the include syntax within <% %> brackets. Assuming
test.js consists of the single line Response.Write('test');, the first
of the following examples yeilds 'Response.Write('test');' on the page
as text, and the second yeilds a blank page.
<%@ language="javascript"%>
<!--#include virtual="/test.js"-->
<%@ language="javascript"%>
<%
<!--#include virtual="/test.js"-->
%>
Are you sure this is possible?
[please do not quote signatures on usenet, and quote only the bare
essential, skipping the rest]
>
> No doubt I'm making a mistake here. However, I don't appear to be
> able to use the include syntax within <% %> brackets. Assuming
> test.js consists of the single line Response.Write('test');, the first
> of the following examples yeilds 'Response.Write('test');' on the page
> as text, and the second yeilds a blank page.
>
> <%@ language="javascript"%>
> <!--#include virtual="/test.js"-->
this works if test.js contains:
<%
Response.Write('2')
%>
==========================================
> <%@ language="javascript"%>
> <%
> <!--#include virtual="/test.js"-->
> %>
This does NOT work if test.js contains:
Response.Write('3')
But why not??????????
Ok, please forgive any future netiquette faux-pas!
> > <%@ language="javascript"%>
> > <!--#include virtual="/test.js"-->
>
> this works if test.js contains:
>
> <%
> Response.Write('2')
> %>
>
> ==========================================
>
> > <%@ language="javascript"%>
> > <%
> > <!--#include virtual="/test.js"-->
> > %>
>
> This does NOT work if test.js contains:
>
> Response.Write('3')
>
> But why not??????????
I think your example may confuse the issue - in the first, you the
include outside <% %> brackets, AND <% %> brackets in the .js file.
In the second, you have the include INSIDE <% %> brackers, BUT NO <%
%> in the .js file.
My tests show that regardless of contents of the .js file, the include
only works if outside angle brackets.
Let me share another example. Consider a javascript file 'test.js'
containing:
---------------------------
var myVariable = 'test'
Response.Write('-' + myVariable);
and an ASP file containing:
--------------------------------------------------------------------
<%@ language="javascript"%>
<script src="test.js" language="javascript" runat="server"></script>
<%
Response.Write('-' + myVariable);
%>
I would expect this would output '-test-test', but it outputs '-
undefined-test'.
Any further thoughts?
Thanks,
Iain
Another example:
-----------------------------------------------------
<%@ language="javascript"%>
<script language="javascript" runat="server">
var global = 'global';
Response.Write('1' + global);
function function1() {
Response.Write('2:' + global);
}
function function2() {
var local = 'local';
Response.Write('3:' + local);
}
</script>
<%
Response.Write('4:' + global);
Response.Write(function1());
Response.Write(function2());
%>
This produces the output:
-------------------------------------
4:undefined2:undefined3:local1global
Execution order of .asp files is not that obvious - particularly
blocks in <% %> and in <script runat="server"> execute at different
times - and not in source order.
See http://classicasp.aspfaq.com/general/does-order-matter-when-using-different-languages-in-asp.html
for details, but basically it's
1. scripts in non-default language
2. scripts using <% %>
3. scripts in default language
You can include code in two ways, using <!-- #include --> and
specifying a src for <script runat="server">
#include must be outside of a <% %> block (the SSI processor seems not
to see them there, even though they are processed first before any
script executes), so either in the HTML body or within a <script
runat="server"> block.
If the #include is in the body, your js code just gets output to the
client. No good.
Using #include in the <script> is exactly equivalent to using a src
attribute on the <script>, either way it is executed after any <% %>
blocks.
So the only way you'll get this to work is to ONLY use <script> blocks
and eschew any <% %>, even for quick document.writes.
You could possibly set <%@ language="vbscript"%> and use vbscript to
write to the client (it'll see your js objects just fine, you just
need to change the syntax), whereupon your <script> blocks will have
executed already.
That said, I've no idea if prototype.js will work serverside - it's
bad enough within a browser, no idea what will happen to it if it
suddenly finds itself in an environment that doesn't have a DOM.
Altering the script ever so slightly (and yes I've deliberately left
out some semicolons for reasons that will become clear:
<%@ language="javascript"%>
<script language="javascript" runat="server">
var globalvar = 'global';
Response.Write('1' + globalvar);
function function1() {
Response.Write('2:' + globalvar);
}
function function2() {
var local = 'local';
Response.Write('3:' + local);
}
</script>
<%
Response.Write("4:" + globalvar)
Response.Write(function1())
Response.Write(function2())
%>
You do indeed get 4:undefined2:undefined3:local1global
Note the execution order - the function calls in the <% %> block take
place before those in the <script> block. I hadn't expected the
functions (or their local vars) to be defined at all, but clearly they
are.
Now change the first line to
<%@ language="vbscript"%>
You will get 1global4:global2:global3:local
because the script block is nolonger in the default language, it
executes first, defining the global vars, but also executing the first
response.write as a sideeffect.
Now you see how mixing <% %> blocks and <script> blocks can lead to
madness and nasty side-effects.
The only way I can think of to achieve what you want to do is to use
#include to insert the files server-side, put <% and %> around all
your javascript and then write a filter for your webserver that strips
them when the files are requested over HTTP by a client
I've recreated the Prototype v1.6 on the server and it comes in very
handy. Gives you OOP properties in classic ASP.
First, within the script runat="server", the methods are processed
first, but in-line code (to include variable declaration) is not
executed until the end.
Try the following
<script language="javascript" runat="server">
var globalvar = 'global';
Response.Write('1' + globalvar);
function initVars(){
globalvar = 'G.L.O.B.A.L.';
}
function function1() {
Response.Write('2:' + globalvar);
}
function function2() {
var local = 'local';
Response.Write('3:' + local);
}
</script>
<%
initVars()
What the authors of Prototype and you failed to observe is that J(ava)Script
is by default an object-oriented programming language. It just uses
prototype-based instead of classed-based inheritance.
http://javascript.crockford.com/javascript.html
Furthermore, with ASP .NET server-side you already have a class-based
object-oriented programming language available, JScript .NET (JScript 7.0+),
which implements features of Netscape's latest proposal for Edition 4 of the
ECMAScript Specification.
Your misguided attempt to port an already faulty approach and error-prone
junk code to the server side is not going to do any good. Search the
archives for discussions about Prototype.js.
PointedEars
--
Use any version of Microsoft Frontpage to create your site.
(This won't prevent people from viewing your source, but no one
will want to steal it.)
-- from <http://www.vortex-webdesign.com/help/hidesource.htm>