Posted on March 6th, 2010 by Reiner.
Categories: Hibernate, Grails, English.
As outlined at Grails - How to Use Native Server Logging Configuration (e.g. Tomcat GlassFish JBoss), it may be advisable to remove any conflicting logging implementation when deploying a Grails application into a production environment. I’ll give a full source example on how to achieve this and how to work-around an issue which prevents a Grails 1.2.0 and 1.2.1 applications from starting.
Unfortunately, each server provides a distinct set of logging frameworks. Still worse, servers can be reconfigured to use alternate logging frameworks (e.g. JBoss can be configured to use Java Logging instead of its default Log4J implementation and Tomcat 6 can be configured to use Log4J instead of its default Java Logging implementation).
Thus you either have to prepare a war which has been set-up for a specific target environment or completely remove any logging implementation from your Grails war and add missing jars to the lib directory of your target server instead. Which one to choose may depend on whether access to the server configuration is permitted (e.g. its lib directory), how many different servers your application is to be deployed to and how hard it is for your build process to reliably produce variants specifically tailored for a particular deployment site.
Before presenting the code for a deployment to JBoss 5.1.0GA, let’s have a look at Grails’ logging architecture. In its infancy Grails just used Apache Commons Logging (JCL) to provide an abstraction level and Log4J to implement the actual logging. Although even now, all log instances injected into Grails applications still implement org.appache.commons.logging.Log, Grails no longer uses JCL, but meanwhile has moved on to SLF4J:
Starting with Grails 1.2, an additional bridge jul-to-slf4j which delegates Java Logging (Jul) to Slf4j is enabled by setting grails.logging.jul.usebridge = true. Be warned though, that for performance reasons this bridge should not be used when expecting heavy logging.
Now for the good news: With JBoss 5, all of the above (but excluding jul-to-slf4j) has already been integrated into the server configuration and libraries. In order to deploy a Grails application to JBoss 5, we’ll just need to get rid of the jars within your war and prevent Grails from trying to configure the logging. How to achieve this?
Within grails-app/conf/BuildConfig.groovy we’ll remove offending jars when building the war:
// TODO JBOSS - Remove own log4j and use the one supplied by JBoss instead
grails.war.resources = {stagingDir ->
def toRemove = [
"$stagingDir/WEB-INF/lib/log4j-1.2.14.jar", // log4j supplied by JBoss
"$stagingDir/WEB-INF/lib/log4j-1.2.15.jar", // log4j supplied by JBoss
"$stagingDir/WEB-INF/classes/log4j.properties", // logging conf done in JBoss only
"$stagingDir/WEB-INF/lib/slf4j-api-1.5.6.jar", // slf4j supplied by JBoss 5+
"$stagingDir/WEB-INF/lib/slf4j-api-1.5.8.jar", // slf4j supplied by JBoss 5+
"$stagingDir/WEB-INF/lib/slf4j-log4j12-1.5.6.jar", // slf4j supplied by JBoss 5+
"$stagingDir/WEB-INF/lib/slf4j-log4j12-1.5.8.jar", // slf4j supplied by JBoss 5+
"$stagingDir/WEB-INF/lib/jcl-over-slf4j-1.5.6.jar", // jcl supplied by JBoss as well
"$stagingDir/WEB-INF/lib/jcl-over-slf4j-1.5.8.jar", // jcl supplied by JBoss as well
// see also Config.grails.logging.jul.usebridge - shouldn't be used
// http://www.slf4j.org/legacy.html#jul-to-slf4j
// "$stagingDir/WEB-INF/lib/jul-to-slf4j-1.5.6.jar",
// "$stagingDir/WEB-INF/lib/jul-to-slf4j-1.5.8.jar",
// you might want to remove JDBC drivers when using server supplied JNDI...
// "$stagingDir/WEB-INF/lib/hsqldb-1.8.0.5.jar",
].each {
delete(file: it)
}
}
Within scripts/_Events.groovy we’ll disable Grails logging configuration components:
import groovy.xml.StreamingMarkupBuilder
/**
* TODO JBOSS - Remove log4j configuration stuff (when running with JBoss or GlassFish a.s.o)
*/
eventWebXmlEnd = {String tmpfile ->
def root = new XmlSlurper().parse(webXmlFile)
// When running with JBoss (or GlassFish a.s.o) remove log4j configuration stuff
def log4j = root.listener.findAll {node ->
node.'listener-class'.text() == 'org.codehaus.groovy.grails.web.util.Log4jConfigListener'
}
log4j.replaceNode {}
def log4jFile = root.'context-param'.findAll {node ->
node.'param-name'.text() == 'log4jConfigLocation'
}
log4jFile.replaceNode {}
webXmlFile.text = new StreamingMarkupBuilder().bind {
mkp.declareNamespace("": "http://java.sun.com/xml/ns/j2ee")
mkp.yield(root)
}
}
You are now set to control logging within JBoss jboss-log4j.xml.
If you’re using Grails 1.2.0 or 1.2.1, JBoss still refuses to deploy your war. This is caused by version conflicts within Hibernate jars (used to be work-arounded by deleting all Hibernate jars from JBoss lib directory) and they have been fixed by GRAILS-5606 for (not yet released) Grails 1.2.2.
Graeme Rocher as well supplies a work-around for 1.2.x:
Fixed in latest hibernate plugin 1.3.0.BUILD-SNAPSHOT
It seems in order to use the latest version of Hibernate on JBoss you must include Hibernate validator otherwise you run into this classloading error. This means the hibernate plugin is forced to include hibernate-validator as a dependency even if we don’t use it which is a pretty annoying.
Anyway you can fix this yourselves in 1.2.x by adding the following dependency to BuildConfig.groovy:
runtime('org.hibernate:hibernate-validator:3.1.0.GA') { excludes 'sl4j-api', 'hibernate.core', 'hibernate-commons-annotations', 'hibernate-entitymanager' }Be sure to uncomment the jboss maven repository so the dependency resolvers
This work-around is included within sample sources. Just search for TODO tags.
Links:
Posted on March 15th, 2009 by Reiner.
Categories: J2ME, English, Computers.
Wondering about best practices on how to use HttpConnection with J2ME, I had a peek at the sources and to my surprise, I found out, that HttpConnection should offer both keep-alive and chunking without any additional application code (e.g. adding http headers).
The implementation of HttpConnection uses an internal connection cache, so your application code can happily create - Connector.open(”http://…”, …) - and close connections and still transparently re-use the underlying TCP-connections as per HTTP/1.1 Keep-Alive specs, provided the operations being performed on those connections do not preclude Keep-Alives (e.g. by using the request property “Connection Close”, forcing HTTP/1.0, encountering any errors, or just the server plainly rejecting keep-alives).
It is a common misconception, that in order to use Keep-Alive, the HttpConnection object should be kept open. Just don’t do that! Instead always tidy-up resources you’re fed up with, as is the case with HttpConnection that is best used for a single transaction (request-reply) only. HttpConnection will transparently take care of caching the underlying TCP socket connection for you.
HttpConnection appears to be far more powerful than most J2ME programmers suspect. My advice: If you are not completely sure whether a particular option, header or application code is required, just leave it out and see what happens. For instance, HttpConnection will either add a Content-Length header (provided the content does not exceed its output buffer) or enable chunking (again adding the appropriate header) on its own and in a way completely transparent to your application code.
I myself had to learn it the hard way after having set up an implementation for chunking of my own. Not before trying to find out about how to properly interface my implementation to HttpConnection (and peeking at its sources), I realized that it’s all there already - ready to be used for free without even having asked for it
I was able to verify this behavior using a Nokia 6131 NFC mobile device (CLDC-1.1 + MIDP-2.0) and GlassFish v2ur2. It works like a charm!
The automatic keep-alive may not be what you want when your mobile pays for each second of online access. Keep-Alive can easily be disabled by calling conn.setRequestProperty( “Connection”, “close” );.
Your actual mileage may vary
The behavior of the implementation on your phone might be inferior to the one I dealt with (Nokia with lots of implementation code from Sun - judgement derived just from looking at package names) . Nick reports about some of his amazing experiences in his post Using HTTP-Over-Socket and HTTP Proxy in J2ME Applications.
My test responder is implemented in Grails and it succeeds in chunking but fails the keep-alive test (i.e. multiple socket connections are being established) when being run in developer mode from Grails built-in Jetty-Container (i.e. grails run-app). Don’t know (and don’t care), whether this is due to Jetty or Grails running in development mode.
I would have liked to post this as a comment to Codepimps’ article at http://codepimpsdotorg.blogspot.com/2008/12/every-byte-counts.html, however I did not succeed in talking Blogger into accepting my WordPress.com account ![]()
Posted on October 11th, 2008 by Reiner.
Categories: Grails, English, Computers.
Never before in my life I had the opportunity to learn a new technology and put it into productive use within just a couple of days. Grailswill changeis changing the Java and framework landscape right now. Using Grails, within less than 3 weeks, an application has been developed that accepts NFC-scans from mobile devices (i.e. Nokia 6131 NFC), sends notifications by email and by SMS, and renders a live view of scans as well. None of the staff involved had any previous experience with Grails whatsoever (I started implementing the domain classes and services, a colleague of mine then took over to implement the GUI while I was on vacation on the Canary Islands). Our work was targeted towards NetBeans, GlassFish and PostgreSQL.
Listed here are the links that helped us jump on the track to wealth, glory and wisdom
Pet stores, sort of:
The web service side:
Still more advanced:
Slightly off topic:
Tiddlers:
Deutsche Ecke (German corner, don’t hold your breath yet):
Posted on March 15th, 2008 by Reiner.
Categories: English, Computers.
Deutsche Fassung bei Debuggen von Java Anwendungen - auf der Überholspur!
When instrumenting your Java application for remote debugging, a commonly used set of VM parameters brings your application to a crawl, as it disables just-in-time compiliation and enforces interpeter-only mode, e.g.:
-Xdebug
-Xnoagent
-Xrunjdwp:transport=dt_socket,address=8787,server=y,suspend=n
-Djava.compiler=NONE
Starting with Java 1.4, it is neither required nor advisable to disable the Java just-in-time compiler,
so just remove the -Djava.compiler=NONE:
-Xdebug
-Xnoagent
-Xrunjdwp:transport=dt_socket,address=8787,server=y,suspend=n
Thus, you are able to prepare your application (e.g. JBoss) for debugging, and there will be no perceivable overhead unless you actually connect your debugger to the debuggee (using remote debugging). And even while debugging, the Java just-in-time compiler will speed up your application. That may be handy for test (or even production) environments that are supposed to both deliver full speed and still supply a back door for debugging once the need arises.
Even recent posts still promote the -Djava.compiler=NONE antipattern, as in See how maven works inside - remote debugging plugins or Debugging your Maven Project in Eclipse.
And the bad -Djava.compiler=NONE habit may still be hidden within numerous configuration files or tools, as it even made its way into Sun’s Java 6 itself. See -Djava.compiler=NONE and -Xdebug anachronisms unanachronistically disable full-speed debugging at Sun’s Bug Database.
Posted on February 19th, 2007 by Reiner.
Categories: English, Computers.
After upgrading to WordPress 2.1 Search Everything often returns the same pages multiple times.
22-Feb-07 Update: The information below has been superceeded, as Dan has just released version 3.01 of the plugin that includes code to prevent duplicate hits.
One of a my friends runs a property management agency, where WordPress is used as an internal knowledge base to document internal procedures and the like. Quite often, valuable information is not contained within the main post, but added later as a comment. Search Everything makes sure that this information can be searched and retrieved.
After upgrading to WordPress 2.1 and installing Search Everything Version 2.6, searches will quite often return the very same pages multiple times.
I had a look at both Search Everything and WordPress Code and found that WordPress 2.1 does not use the distinct option when querying the databse, but provides a filter instead that may, at its discretion, return the magic ‘DISTINCT’ to cancel duplicate entries. The distinct option may need additional resources within the database, so I believe, it’s off by default for performance reasons.
Here’s my fix (the bolded lines below), which will cause WordPress to cancel duplicate results. It should be applied to the search_everything2.php file and requires WordPress 2.1+ to work (but won’t harm older WordPress releases) :
if ("true" == get_option('SE2_use_metadata_search')) {
add_filter('posts_where', 'SE2_search_metadata');
add_filter('posts_join', 'SE2_search_metadata_join');
SE2_log("searching metadata");
}
// http://blog.saddey.net/?p=167
add_filter(’posts_distinct’, SE2_search_distinct);
// http://blog.saddey.net/?p=167
function SE2_search_distinct($distinct) {
if($distinct == ”) {
return ‘DISTINCT’;
}
return $distinct;
}
//search pages
function SE2_search_pages($where) {
global $wp_query;
The fix is very basic and may apply the distinct clause, even when it might not be required as dictated by your Search Everything options. But I don’t think, there’ll be any problem with this and would like to leave the final inclusion to the author of Search Everything. Thanks to Dan Cameron for this great plugin!
After having implemented the fix, I found, that the concept for the fix has already been outlined at WordPress Hackers - Getting double/triple posts listed on some blogs ten days ago.
Aditya has posted a fix as well, which was taken from Google Code, but I believe that my version more closely adheres to WordPress 2.1 standards (the ‘posts_distinct’ just returns a keyword for the tasks it’s supposed to instead of modifying the whole query).
Posted on February 18th, 2007 by Reiner.
Categories: English, Computers.
After upgrading to WP 2.1, Kelson had to downgrade WP-Cache 2.1 to a tweaked 2.0.17, because with RSS feeds WP-Cache 2.1 would, when serving a request from its cache, always return Content-Type text/html instead of Content-Type text/xml.
Why does WP-Cache not reproduce the original Content-Type text/xml?
I had a look at wp_cache_shutdown_callback within wp-cache-phase2.php and found that all and everything should work perfectly.
Disabling WP-Cache’s code that forcibly sends a Content-Type text/html header if there is none, led me to the mazes ob flush(), ob_flush(), ob_end_flush(), headers_sent() and the like. And to the interesting fact, that…
WP-Cache does not see at least some of the http response headers, that have been output by WordPress code. Why?
If WP-Cache misses some headers, the reason must be located somewhere in the way it tries to retrieve them. wp_cache_get_response_headers() first interrogates apache_response_headers() and, if this function does not exist, reverts to headers_list().
headers_list() docs clearly state, that it returns both, headers that have already been sent and those that have not yet been sent, i.e. are about to be sent. That might be the ones, that WP-Cache is missing after all. headers_list() requires PHP >= 5, but even then, headers_list() may not work at all due to Bug #29683 headers_list() func. return empty array.
apache_response_headers() requires PHP >= 4.3 (>= 4.3.3 with NSAPI) and its docs are a little bit vague on platform requirements. There are some hints on how to have it “working good”.
Fix for wp_cache_get_response_headers within wp-cache-phase2.php:
function wp_cache_get_response_headers() {
if(function_exists('apache_response_headers')) {
flush(); // fix text/html on feeds
$headers = apache_response_headers();
} else if(function_exists(’headers_list’)) {
$headers = array();
foreach(headers_list() as $hdr) {
list($header_name, $header_value) = explode(’: ‘, $hdr, 2);
$headers[$header_name] = $header_value;
}
} else
$headers = null;
return $headers;
}
Last-not-least an honorable mention of ieHTTPHeaders , that made it possible to spy on both the actual http request and response headers and much more. Thanks to Jonas!
There’s another interesting area as to when a page needs refreshing. It’s the If-Modified-Since header. Do WordPress and WP-Cache support this technique, and why not? I’ll try to cope with that one in a future post…
Posted on February 15th, 2007 by Reiner.
Categories: English, Computers.
WP-Cache and Spam Karma both implement strategies that are contradictory by their very nature. Let’s see why.
In the past, I got along with a remarkably short comment blacklist (hand**b, pi**ing, tran****ual, b**bs) , that was able to block over 5000 spam attempts during the last year, but still allowed too many false nagatives to slip through for manual approval to be avoided. Personally, I don’t like having to approve - or being approved, for that matter
When upgrading to WordPress 2.1, I was looking for a better way to prevent spam. I soon ruled out Akismet, because Akismet requires a key and I was unable to find the right kind of key within a reasonable amount of time. My blog is both a private one and non-commercial, but still runs on my own server (10 feet from my bed, see Small is beautiful - WordPress in a Handbag).
When leaving a comment at Kelson’s Updated to WordPress 2.1, I was quite impressed by a challenge popup, that I could trace back to Spam Karma 2.2. Wow, that’s cool - I must have this.
Within minutes, I downloaded, installed - and donated to - Spam Karma 2.2.
Due to my CPU’s inferior processing power, I’m using WP-Cache (with expire time set to 60 days) in order to speed up page display. To my dismay, WP-Cache caused new comments not to be displayed at all. Everton’s article at How To Fix WP-Cache And Spam Karma 2 (SK2) Issues led me to Priv’s SK2-WP-Cache-Compatibility plugin which sucessfully fixed the case of the missing comments. So far, so good.
Everything ought to be in perfect harmony by now.
But is it really?The answer may be no, and here’s why:
WP-Cache works very much like a camera. It lets WordPress generate the HTML for a page, which is then captured and resent by WP-Cache on all subsequent request for the same page. That’s the secret to its stunning performance. A page, once cached, is returned just as fast as if it were plain static HTML. WP-Cache is quite smart about building the key for a cached page. Keys include your WordPress cookies so as to avoid disclosure of private pages. There’s even a hack that enables WP-Cache to properly snapshot gzipped pages as well, thus avoiding the computational expense of compressing identical contents more than once (see WP-Cache 2.1 revisited: Compression)
Spam Karma contains quite a number of advanced features, some of which can easily be revealed by looking the HTML of a page. Three of those may not work as designed when used in conjunction with WP-Cache:
These two techniques very much rely on Spam Karma being able to prepare individual output for each and every particular page request. This is defeated by WP-Cache returning static content that may have been prepared hours or days ago in response to another request for the same page, eventually causing Spam Karma to no longer accept or misinterpret the values returned.
It’ll be an interesting challenge as to how these conflicting goals can be met at the same time:
Posted on February 11th, 2007 by Reiner.
Categories: English, Computers.
Speeding up WordPress appears to be the play of the month, see 5 Ways to Speed Up Your Site. I ran into an interesting post from Nick Georgakis in which he presents both an in-depth discussion and working code to properly enable compression with WP-Cache. The main idea is, that in order to support compression, WP-Cache must keep compressed cached files separate from uncompressed ones. This is achieved by appending the compression method to the url when allocating and retrieving cache entries. That way, browsers will always be returned a version of the content they will be able to handle - depending on whether they requested compressed contents or not in the first place.
I’ve adopted Nick’s code to the current 2.1 version of the WP-Cache and applied some minor amendments, e.g. replaced the somewhat complicated gzcompress call with the more up-to-date gzencode. Be warned though, that it requires at least PHP 4.2.
What it comes down to: WP-Cache is a very effective plugin that lets WordPress serve content just as if it were plain static html. Why not have WP-Cache take a snapshot of the compressed image as well?
Posted on February 10th, 2007 by Reiner.
Categories: English, Computers.
After having added some wallpapers to Vistered Little, I learnt that they will all be downloaded, regardless whether they are actually shown or not. That sums up quite a bit… The reason is, that the background selection does not display real thumbnails, but just tiny squares taken from the center of the wallpaper images instead.
That was easy - I thought. Thus I modified Vistered Little so that the menu would fetch its images from a separate directory (wallpapers/thumbs) and then prepared real tiny thumbnails (20×20 px). All and everything appeared to be great, even my Nokia E61 now showed the site without a glitch (it used to choke on the multi megabytes before), but… IE 6 would no longer refresh its background on a selection change
The problem only occurs with Internet Explorer 6. IE 7 is ok, as is Firefox. I’m currently working on this bug… In the meantime, press F5 to refresh.
It appears as though programming real world browsers is a preview of living hell. IE 6 completely refuses to load images when requested by setting document.style.background, but happilly displays them if - by chance - they have been loaded at least once before. Changing the background image within the onload event of an Image object did not work with Firefox 1.5, but works as advertised with both IE 6 & 7.
So here’s a code snippet that appears to work for FireFox (1.5), IE (6&7) and the Nokia E61 alike - the background is set both, immediately and within the onload event, if required
function setBackgroundWP(bgNumber,bgUrl) {
var im = new Image();
im.bgSty = "url('" + bgUrl + "') top center fixed";
im.setBackgroundWPOnLoad = function() {
if (document.body.style.background != this.bgSty) {
document.body.style.background = this.bgSty;
};
};
im.onload = im.setBackgroundWPOnLoad;
im.src = bgUrl;
document.body.style.background = im.bgSty;
createCookie('wpcookie',bgNumber,7);
}
Disabling JavaScript reveals a tiny bug within Vistered Little: The initial background style refers to the wrong directory within functions.php.spitOutWallpaperCSS() :
// nono print "/images/" . $wallpaper . "') top center fixed; }n";
print "/wallpapers/" . $wallpaper . "') top center fixed; }n";
Posted on February 8th, 2007 by Reiner.
Categories: Deutsch, Computers.

Wie kann ich Text aus der Zwischenablage ohne Formatierung einfügen? Wie kann ich eine Formatierung löschen? Dies und noch mehr ist gut im Advanced Toolbar des Editors versteckt, der sich mit <Alt>+v oder <Alt>+<Umsch>+v (je nach Browser) ein- und auschalten lässt.
Gefunden bei WordPress 2.1 - More Editor Options.