I have been working with ASP.NET for a few years and am now working on a project using JSP, Struts, and Java so I am fairly new to this.
I have a for-loop in a JavaScript function that looks something like this:
<% int count=0; %>
for(i = 0; i < arrayCount; i++){
jsArray[i] = <%= myBeanArrayList.get(count) %>;
alert("i = " + i + "count = " + count);
<% count++; %>
}
The count variable doesn't increment even if I use <% count = count + 1 %>. I don't understand why that piece of code doesn't do as I want inside the loop. Does anyone have any suggestions on how I can increment the count for the JSP Bean?
That's because you are mixing things.
Your loop is in javascript and the variable count doesn't exists there (beacuse it's java)
You incremented count once, just in <% count++ %>
So if you change to use the loop inside java, the count can work just fine. For example:
<% for( int i = 0; i < ???; i++ ) { %>
alert('<%= i %>');
<% } %>
But it's better separate your javascript from JSP. This can be a pain to mantain.
I kind of agree with b1naryj, but you could try doing the looping in the jsp, and just write the array assignments in javascript, something like:
<%
for(i = 0; i < arrayCount; i++){
%>jsArray[<%i%>] = <%= myBeanArrayList.get(i) %>;
<%}%>
It is ugly, tho...
No one should be using scriptlet code in JSPs. It's a late 90s idiom that has been found to be ugly, brittle, and hard to maintain. Model-2 MVC has swept the field.
You should concentrate on doing things on the server side. If you must write JSPs, use JSTL.
I think the current best practice is to use HTML, CSS, and JavaScript. Get data from services on the server side using HTTP GET/POST or AJAX calls.
You are only looping on the client, not the server. The server code only gets executed once. So, for every iteration of the JavaScript loop, you are using the same value - myBeanArrayList.get(0). View source to look at the generated HTML code and that will probably help to clarify the problem.
Edit: Instead, use server-side code to build a JavaScript array literal. I don't really know JSP, and my Java is a little rusty, but wouldn't this work?
var jsArray = <%= new JSONArray(myBeanArrayList) %>;
Related
I have a unique problem to solve. I need to dynamically create HTML based reports using a standard template. The contents of the report are created by a Java program so it makes sense to create a new class which uses JSP* to make a static HTML output file.
Here is the gist:
MyObject me = new MyObject();
me.process();
MyJSP jsp = new MyJSP(me);
File output = jsp.renderFrom("templateFile.jsp");
And output is a static, self contained HTML file which I can open in IE/Firefox and see the report.
What pattern/framework should I follow to allow me to best accomplish this?
Some notes: This is actually not a webapp. I am creating HTML based reports, but this won't be used as a webapp. I would also rather not use String.format(".. giant template string .. ", args) as this is very clumsy. I would much rather have a template file like this:
<html>
<head><title>First JSP</title></head>
<body>
<%
double num = Math.random();
if (num > 0.95) {
%>
<h2>You'll have a luck day!</h2><p>(<%= num %>)</p>
<%
} else {
%>
<h2>Well, life goes on ... </h2><p>(<%= num %>)</p>
<%
}
%>
<h3>Try Again</h3>
</body>
</html>
Where the "dynamic" aspects of the template can use MyObject properties, etc.
Lastly, I plan to use Java 7 for this due to some issues I am having with Java 8. If there is some better way to do this in Java 8, let me know...
*After some negative comments against JSP, perhaps JSP is not the right option. Some other library is fine too, as long as it works with Java.
Use a template engine for this!
I would recommend Freemarker, Velocity or StringTemplate. Just google it. Any of these engines will cover your needs.
I have some javascript
<script>
// some java code that doesn't matter right now
localStorage.setItem("myName", "Bob");
alert(localStorage.myName);
<script>
it works just fine (giving an alert message that says Bob). that's fine and dandy but what I really want is to pass a java variable to a javascript variable and have that print out instead.
But when I put these lines into it...
var hi5 = <%= "getMyName();" %>
localStorage.someName = hi5;
It quits. Any javascript before that works fine. but any javascript after it just doesn't show up.
now the <% %> tags might not be in the exact syntax but it doesn't really give me any errors
I'm sure I'm overlooking something but I'm not sure what it would be. What can I do?
Because look at the source code of the page that this line generates
var hi5 = <%= "getMyName();" %>
It would render something this
var hi5 = BOB
Do you have a variable BOB? No. You are missing the quotes which would make it a string.
var hi5 = "<%= getMyName(); %>";
^ ^^
I'm pretty new to Java and I apologize in advance if I'm wording this incorrectly. I've got a small code snippet that has multiple opening and closing delimiters because I've got some HTML mixed with JSP. Without the HTML this can be done in just a few lines of code but I need the HTML to render and it leads to almost double the lines of code. I'm wondering if there is a better way to do this as opposed to having so many opening and closing delimiters. I know I can use a templating library but I'm trying to stay away from that and would like if at all possible to do this inside a JSP (not a separate class). Thanks for the help!
<%
try {
List<Page> children = properties.getPath("getChild", "");
%>
<ul>
<%
for (Page children : e) {
if (children != null) {
%>
<li>Show a link</li>
<%
}//end if statement
}//end for loop
%>
<li>Another link goes here</li>
</ul>
<%
} catch (NullPointerException e){
%>
//show some content here
<% } %>
I think that this kind of problem can really be solved by using templating libraries or the included view convention for a framework.
These libraries were created to solve these kinds of problems and to organize the view as a whole. It will not only clear up the clutter in your view, it will also adhere to the MVC pattern.
In struts, for example, we will do something like this:
<s:textfield name="myParameter" />
and this:
<html:link page="/linkoutput.jsp" paramId="id" paramName="name"/>
For more reasons why you should be using templating or frameworks visit this question. As what Dave Newton said:
Attempting to do it all in jsp is precisely the wrong approach.
Hope this clears it up.
Use JSTL instead of all that Java code you have in your JSP. You can read about JSTL here - http://docs.oracle.com/javaee/5/tutorial/doc/bnakc.html
Never catch NPE just to catch NPE.
Consider using JSTL http://jstl.java.net/getStarted.html It provides plenty of tags for iteration and so on.
You'd be much better of using something like JSF. Just as JSP, this is also included in Java EE.
I am trying to use iText for pdf file generation and I have a question regarding the generation. I would like to serve the PDF to the browser so that the browser displays it, without actually creating a file.
What would be the best approach to achieve this?
One limitation is that I would need to use it from a JSP page - something that would circumvent the "getOutputStream has already been called once" error is what I am looking for.
I would like to serve the PDF to the browser so that the browser displays it, without actually creating a file.
Just pass responsegetOutputStream() instead of new FileOutputStream to PdfWriter.
PdfWriter pdfWriter = PdfWriter.getInstance(document, response.getOutputStream());
// ...
One limitation is that I would need to use it from a JSP page - something that would circumvent the "getOutputStream has already been called once" error is what I am looking for.
Just remove any whitespace outside <% %> in JSP, including newlines. They are implicitly sent to the response by the response writer.
I.e. do NOT
<% page import="foo" %>
<% page import="bar" %>
<%
for (int i = 0; i < 1000; i++) {
out.println("I should not use scriptlets.");
}
%>
(newline here)
but more so
<% page import="foo" %><% page import="bar" %><%
for (int i = 0; i < 1000; i++) {
out.println("I should use servlets.");
}
%>
Or better, don't put Java code in JSP files. JSP files are designed to present template text like HTML, not to do entirely different things. Do that in a normal Java class like a servlet.
Write it to the servlet output stream, remembering to set the encoding to the correct value
This http://onjava.com/onjava/2003/06/18/dynamic_files.html explains how to do it
I have a list of strings on my server which I am trying to get to the client in the form of an array. The code I am attempting to use is the following:
Within the jsp I have a List<String> column
I am attempting the following code:
<%int j = 0; %>
for(var i = 0; i < <%=columns.size()%>; i++)
{
colArray[i] = "<%=columns.get(j++)%>";
}
This code simply returns the first element in the columns list for every element in the colArray.
I have also tried:
colArray = <%=columns.toArray()%>;
which does not work either.
I feel like I am making a little mistake somewhere and am just not seeing it. Is what I am trying to do possible in the way that I am attempting?
Thanks.
You're getting the JSP code that is executed on the server mixed up with the JavaScript code that's executed on the client. The snippet <%=columns.get(j++)%> is executed once, on the server, and the JavaScript loop around it is irrelevant at this point. When it arrives the the client, the loop's body just says colArray[i] = "first entry"; which of course puts the same string into every element of the array.
What you need to do instead is to have a loop execute on the server, like this:
<% for (int i=0; i<columns.size(); i++) { %>
colArray[<%= i %>] = "<%= columns.get(i) %>";
<% } %>
My JSP skills are rusty, and the syntax may be different, but I hope you get the idea.
Edit: As was pointed out in the comments, you need to be VERY careful about escaping anything in those Strings that could cause them to be interpreted as JavaScript code (most prominently quotation marks) - especially if they contain user-generated content. Otherwise you're leaving your app wide open to Cross-site scripting and Cross-site request forgery attacks.
Try using JSON (Javascript object notation) it'd be quite simple to encode the array and decode it on javascript
check it out here
http://www.json.org/java/index.html
Once the JavaScript reaches the client, the server code has stopped executing. The server code does not execute "in parallel" with the client code.
You have to build the entire JavaScript initialization in Java and send it, complete and executable, to the client:
<%
StringBuffer values = new StringBuffer();
for (int i = 0; i < columns.size(); ++i) {
if (values.length() > 0) {
values.append(',');
}
values.append('"').append(columns.get(i)).append('"');
}
%>
<script type="text/javascript">
var colArray = [ <%= values.toString() %> ];
</script>
That is just one way to do it, you can also build the output "on the fly" by embedding the server code inside the [ and ]. I used this example to try to demonstrate the separation between building the string that comprises the client-side JavaScript and outputting that to the browser.
Exp Language:
colArray = ${columns}
For me this solution has worked. First of all You should make a JSONArray and use it's toJSONString() method. This method converts the list to JSON text. The result of it is a JSON array.
<%
List<String> exampleList = new ArrayList<>();
exampleList.add("Apple");
exampleList.add("Orange");
exampleList.add("Lemon");
JSONArray fruitList = new JSONArray();
fruitList.addAll(exampleList);
%>
In your JSP page you should invoke the toJSONString() method of the list, and pass the JSON text to a JavaScript array.
<script type="text/javascript"> var fruitArray = <%= fruitList.toJSONString() %>;</script>
(Optionally You could make a simple getter method for the list. In case if you only instantiate the JAVA class - which has the list field - int the JSP page.)
The solutions posted above didn't work in my case, I needed an extra Javascript variable to do the transference:
var codesJS=new Array();
<% String[] codes=(String[])request.getAttribute("codes");
if(codes!=null){
for(int i=0; i<codes.length; i++){ %>
var code='<%= codes[i] %>'; //--> without this doesnt work
codesJS[<%= i %>]=code;
<%}
}%>