Servlet called from Icefaces webapp creates constantly high CPU usage on client - java

I'm developing a web application (using JBoss and Icefaces) which uses a Servlet to create a Excel or PDF file and sends it to the browser.
But I'm experiencing performance problems after the servlet was called, resulting in a constantly high (~50%) CPU consumption of the browser. Testet in Firefox and Internet Explorer on different machines. The high cpu usage arises with a little delay (half a minute) after the servlet was called and stays high (until I close the browser or reload the page).
Whether I download the created file or open it directly makes no difference.
I'm clueless how this can happen...
Is there a way to analyze/debug the browser to find out, what is causing the cpu consumption?
UPDATE:
I've found out that is definitly related to the Icefaces webapp. When I replace my direct html-link to my servlet with a javascript call which opens the servlet in a new window (with window.open), then I can download the created file without problems.
Also when I logout inside my application, the CPU usage goes back to normal again!
UPDATE:
Ok, now Firebug helped me on: After the servlet was called I can see in the Firebug Console that there are XMLHtppRequests every milliseconds. Now I can understand the CPU usage!
POST http://localhost/webapp/block/receive-updated-views
is coming on and on. Have to check this...
UPDATE:
Ok I found an iceface thread (with the corresponding iceface jira bug) but the bugtracker states this should be fixed already... somehow not for my case!

Have you tried FindBugs or other tools for static code analysis?
http://en.wikipedia.org/wiki/List_of_tools_for_static_code_analysis#Java

If the CPU consumption is really coming from the browser, then you can't do anything about it - it is either the PDF or excel viewer .
If the server is on the same machine, and the cpu load comes from the servlet, then you have to optimize it. Give us code for that.

Browsers doesn't run servlets. Browsers runs/displays the output which is produced by the servlet. It's the output which is causing a high load. Based on the as far given little information, it's hard to tell what's the problem with the output. Firebug can give lot of insights of what's going on in the webbrowser.
Usually, an extraordinary large HTML table or an inefficent piece of JavaScript code can consume a lot of CPU/memory resources. But with a binary file download like XLS/PDF, this should in fact not happen. The cause is then probably deeper. Do you see lot a resource usage when you do a file-to-file copy on the harddisk? If so, then it may probably be a bad harddisk or bad harddisk driver or harddisk DMA is being turned off.
Update: as per your investigation with help of Firebug, it look like that you're using IceFaces' ice:commandButton or ice:commandLink to download the file. Replace them by the normal JSF h:commandButton or h:commandLink so that it doesn't unnecessarily generate JS code which is responsible for that.

Problem solved (actually it's more a workaround).
It's a Iceface Prob, which should be fixed according to the bugtracker.
But as it is actually still present I could only fix it by calling the servlet in a new windows, created by javascript. (As already mentioned in my edited question).
It's really not a nice solution and has the drawback, that browser must not block popups.
But it's also a solution I've seen several times in the net (like here).
public void exportToExcel(ActionEvent e) {
JavascriptContext.addJavascriptCall(FacesContext.getCurrentInstance(), "window.open (\"downloadServlet.dl?contentType=excel\",\"report\")");
}

Related

CPU gets pegged - Problem with java.util.zip.ZStreamRef

We are seeing this intermittent issue in production. The CPU gets pegged at 50% (2 core CPU) randomly and it never comes back. Only option is to restart the server.
This is how CPU appears from Dynatrace
This is how the thread dump looks when we analyzed through dynatrace.
Through my research, it appears there was a jdk defect
Calling 'java.util.zip.Deflater.finish()' prematurely hangs the application.
The application is spinning consuming one cpu
https://bugs.openjdk.java.net/browse/JDK-8060193
Only happens randomly when for some multiple filters are involved.
I was able to reproduce this using test class in above jira on CentOs vm which has JDK "1.8.0_201"
That was surprising because as per the docs and ticket, this has been fixed.
On further research, find similar defect opened again in jdk.
https://bugs.openjdk.java.net/browse/JDK-8193682
Now the team is not willing to work on it unless someone could reproduce it.
Since it is happening randomly in production, I am not sure how to reproduce it. The test class from https://bugs.openjdk.java.net/browse/JDK-8060193 still has issues. IS this even a valid test case?
If this is valid then there will be problems every time we send compressed data.
Our run time JRE is Jdk 1.8
Compression is at tomcat, not at load balancer.
Any pointers as to why is this happening and how we can solve this?
Update:
In one of the libraries we are using, it was throwing an exception
Malformed UTF-8 character (unexpected non-continuation byte 0x00, immediately after start byte 0xfd)
LastName, First’Name
As we can see, this is not a regular apostrophe.We can have this by copy pasting from word which auto corrects a regular apostrophe to this funky character.
Our reproducer did threw an error but CPU was not getting stuck. I think it happens under high volume and traffic.
EDIT 4 Oct 2022
It seems that the problem has been fixed and applied to OpenJDK 11 and 17: https://bugs.openjdk.org/browse/JDK-8193682
Original answer
As I said in a comment before, we are facing this problem when we try to generate Zip files which are being written in the OutputStream of the HttpServletResponse through a ZipOutputStream.
The reason for the cores running at 100% is because of three (under certain conditions)infinite loops in ZipOutputStream(closeEntry()) and DeflaterOutputStream(write() and finish()).
These infinite loops look like this:
while (!def.finished()) {
deflate();
}
Where def is a java.util.zip.Deflater.
If I understand right, this is the problem in JDK-8193682. There is a workaround class there which overwrites the deflate method of ZipOutputStream.
I am going to try to use a class based on that workaround, which accepts a timeout to be checked in the deflate method. I hope not to produce resource leaks with this approach.
Related question: Thread locking when flushing jsp file
I want to post an update to this problem that has bugged us for years. We had an inititiave to migrate static content to CDN underway. After CDN was implemented and all static resources was served from a different server, the ZipStream problem was resolved. Although the research showed that the problem was more for dynamic content and not static, I am not sure how the problem got solved. Maybe someone who is reading this answer can explain me how this has got fixed.

How to know the Memory Usage of specific functionlity?

I wanted to know the how much memory is utilized by specific functionality of application.
I am running the Java based web application in Chrome browser (or any browser), It consist the form approve functionality like this,
Step
Select the record/records.
select the status as approved.
click on submit button form gets successfully approved.
This works fine for number of records are less than 50, but for 500 form is shown as memory issue.
Now my question is, how to find the memory usage of submit functionality. so that can i show the exact understandable figures.
Why not use Java profiler(jvisualvm). It exist in the bin directory of Java installation folder.
You can start your application, same time start monitoring main tread through this profiling tool. Then take Heap snapshot when ever you want, this will not just tell you about memory usage by individual classes, it even help you identify memory leaks too.

java gwt a script is causing the browser to run slowly

I have a web application written in java gwt. When opening the website in IE8 there always popups the message that says 'A script on this page is causing your web browser to run slowly'
The message only appears in IE8 no higher version and not in FF or Chrome!
Since the application is written in java gwt its pretty difficult to debug the javascript code , is there another possibility to determine the problem?
The application also has many asynchronous calls a database might that be the problem?
This message means that JavaScript blocks browser thread for quite a long time.
Its implementation in IE8 is really silly. It counts number of JavaScript lines of code (instructions) it executes and if it reaches certain threshold this message is shown.
Actually this limit is configured in Windows registry, by default it is 5000000 or something like that. It could be increased, which is not a recommended solution of course.
One of the ways to avoid this message is to use GWT DeferredCommand. If you could split the work being done to chunks small enough not to trigger IE8 guard constraint you will be fine. Also try to merge multiple asynchronous requests into as few as possible and improve rendering logic, potentially shifting from Widgets to UI Binder or plain DOM.
This is related question (Disabling the long-running-script message in Internet Explorer)
I would slightly disagree on - "java gwt its pretty difficult to debug the javascript code"
MSDN article for disabling slow script warning only hides the problem.
The slow script warning occurs when you have a heavy for loop or deep recursive call. This can happen in 2 scenarios -
1) Poorly coded client side processing logic - example tree navigation
2) Deep object graph in rpc.
You can quickly isolate the trouble spot if you familiarize yourself with
1) Using Speed Tracer - https://developers.google.com/web-toolkit/speedtracer/
2) Using GWT logging - https://developers.google.com/web-toolkit/doc/latest/DevGuideLogging
3) Using Chrome Dev Tools & Firebug to capture timeline, profiling etc
4) IE8 has profiling , but it is darn slow and cumbersome.
5) Use GWT Pretty mode instead OBF mode when profiling.
Once you are sure which part of the code is causing the slow script warning Just FIX it.
Because some scripts may take an excessive amount of time to run, Internet Explorer prompts the user to decide whether they would like to continue running the slow script.
If the Generated Cache.js Javascript file is some what in big size that message may come .
So The message box for Internet Explorer versions 4.0, 5.0, 6, 7, and 8 come with a message
Read this article on MS blog
And refer the below question
a script on this page is causing ie to run slowly

How to test your website against multiple users(extended)

There is similar question on this topic I participated in it, but it doesn't really answer what I need at this moment.
How to rigorously test a site?
I noticed java.util.ConcurrentModificationException in my server log, so I fixed that one, but I still don't know if this or some other concurrency will ever occur without testing it.
I've tried to create test in jmeter which just does simple GET and simulates 100 users.
The problem :
I retrieve some information from server when page is done loading, so I'm interested in that part(because that part cause this exception before).
But jmeter gets only the page when its loaded, and all ajax pending requests if any are not displayed in the logs. Actually I can't see anything in logs because, jmeter never reaches these ajax calls when document is ready, it exits just before that.
Naturally when I refresh page from browser I can see logs, what exactly is going on on the server side. Is there a some kind of tool, that waits for all pending requests or can stay on the website for n amount of time, or is there a smarter way to test this to avoid further concurrency exceptions.
AJAX requests are simple GET requests as well, so you just need to configure JMeter to directly call the servlets which serve them.
If you use Selenium instead of JMeter for your tests, you will spawn real browsers that will perform AJAX request exactly like the real application. Simply because it is the real application that is being run.
The problem is... Selenium is for regression testing and compatibility with browsers, not for raw performance. You can't run more than a few browser per computer. Some companies provide cluster of browserd (up to 5000 and up to 500 000 virtual user for browsermob) that you can rent for your performance campain.
You can also use the desktop computer in your office, let say the night to perform your tests.
I know this might be a little complicated and not be the best solution.

Java Applet starts up very slowly for some users?

[UPDATE: I forgot to add that this 30 sec. freezing problem only happens the first time I try to load a file from the server. Subsequent loads are very quick. Maybe some strange reverse DNS lookup? I am hosting on Google's appengine.]
I started a little project recently called http://www.chartle.net which is build around an applet.
Startup time is an important factor in the user's experience of an applet. I collect statistics and am shocked that I find often very long startup times (factor 50 to 100 higher then necessary)
The applet starts in 1-3 seconds depending on the speed of your computer and connection. Still for some users it takes up to 100 sec.
I have mixed results from my own tests. Mostly it is very fast but sometimes freezes the browser for a long time and the Java console doesn't tell me why. Best guess is, that it stalls when loading a saved chart.
Please help me figuring this out - best test by opening an already saved chart (click on one of the 'create' links at http://www.chartle.net/gallery)
Cheers,
Dieter
This is generic help rather than specific for your demo (which loaded fine for me in a few attempts).
Freezing applets
In the JDK bin directory there is a very handy programme called jstack. Refresh your browser window until it crashes and then run:
jstack *process_id*
This will give you the stack trace of any frozen Java process. If Java is not a separate process then you can use the browser's process (eg for Opera).
The following few problems were/are common for me:
I reccommend you use invokeLater rather than invokeAndWait on the init method (although you can't do this if you use start/stop methods)
Opera's custom java plugin acts very poorly...
Deadlocks caused by synch blocks and invokeAndWait's
Slow applets
Possibly the browser is fetching resources from the server, unable to use the jar file?
It may be that only the old plugin causes these problems. That means basically all people running on OSX and other users with Java prior to 1.6_update_10.
So, I would really appreciate people with such setups to watch their Java console and describe the first startup behaviour.
Cheers,
Dieter

Categories

Resources