WebLogic: use a startup and/or a shutdown class in a WAR
Abstract
WebLogic offers you to specify a startup and/or a shutdown class for an application. Anyway, this feature is restrained to EARs, and is not available for applications deployed as WARs. For EARs, Oracle WebLogic Server’s documentation is complete and gives basic examples: Programming Application Life Cycle Events
Yet, sometimes you need such a class even for a WebApp. You have two ways to handle this case.
Solutions
Full Weblogic!
Base
The first solution is not elegant. Open WebLogic console, go to Startup And Shutdown Classes
, then add the classes names of which main()
methods will be run on startup and shutdown, let’s say JonathanWeblogicStartup
. These classes must be available in WebLogic classpath, which is surely different from your application classpath, eg in a library $DOMAIN_HOME/lib/customized-weblogic.jar
.
Advantage of this means: if your startup/shutdown class does not evoluate often, then write it once and forget, it will be OK. Unlike, you will have to manage different versions of the JAR on each release… I assume your exploitation team may get angry at playing with classpaths and lib folders 😀
Suggestion
To improve the basic solution (and avoid your exploitation guy burst in your office), I had the following idea, that I did not experiment, but that should work:
- Keep
JonathanWeblogicStartup
- Create another class
JonathanConcreteStartup
, locate as a source in your application code. - In
JonathanStartup.main()
, callJonathanConcreteStartup
This way,
- You keep a unique JAR in classpath that you do not need to update and you can forget.
- You can add, update or remove features in your very source code.
- The exploitation teams does not become hateful at you.
Add a Listener
The second one requires a bit more work.
- Create a class implementing
javax.servlet.ServletContextListener
interface, let’s sayMyLifecycleListener
. - Implement methods
contextInitialized()
andcontextDestroyed()
. - Edit your web.xml, add the following block:
[xml]
<listener>
<listener-class>lalou.jonathan.MyLifecycleListener</listener-class>
</listener>[/xml] - Rebuild and deploy. It should be OK
WebLogic: Unresolved Webapp Library references for … coherence-web-spi
Case
I have to integrate Oracle Coherence, or more accurately Coherence*Web, within an application deployed as a WAR in WebLogic 10.3.
Since Oracle bought both BEA and Tangosol, increasing their integration, using Coherence jars implicitely is allowed. Anyway I decided to add the following block in weblogic.xml
[xml] <library-ref>
<library-name>coherence-web-spi</library-name>
<specification-version>1.0.0.0</specification-version>
<implementation-version>1.0.0.0</implementation-version>
<exact-match>false</exact-match>
</library-ref>
[/xml]
Then I get this error:
[java]Caused By: weblogic.management.DeploymentException: Error: Unresolved Webapp Library references for
""ServletContext@25681165[app:risklayer-web module:jonathan-lalou.war path:/jonathan-lalou spec-version:null]"", defined in weblogic.xml [Extension-Name: coherence-web-spi, Specification-Version: 1, Implementation-Version: 1.0.0.0, exact-match: false][/java]
Fix
Indeed, I had to deploy Coherence*Web WAR in WebLogic, in the console:
Deployments > Install > select Coherence WAR, eg: C:\jonathan\bea\coherence_3.5\lib\coherence-web-spi.war
> Next> Install this deployment as a library > Next > Target your server > Finish
Jasypt / java.lang.NoClassDefFoundError: com/ibm/icu/text/Normalizer
Context
Ippon, a French company, published a job offer as an challenge / enigma / eliminating heat / project hosted by Git:
https://github.com/ippontech/IpponRecrute
Solving this “enigma”, I get the following error:
[java]org.jasypt.exceptions.EncryptionInitializationException: java.lang.NoClassDefFoundError: com/ibm/icu/text/Normalizer[/java]
Fix
This issue appears only with Java versions prior to 6. To fix it, you can upgrade your JRE ;-), or add the following dependency:
[xml]<dependency>
<groupId>com.ibm.icu</groupId>
<artifactId>icu4j</artifactId>
<version>3.4.4</version>
</dependency>[/xml]
By the way, the project displays the following page:
Venez travailler dans un monde post-J2EE
Marre d’être un matricule qu’on assigne sans ménagement sur de la TMA ou des projets sans grand intérêt? Alors venez vous éclater dans mon équipe Conseil chez Ippon.
Nos technos: Spring, Java EE, Portail, ESB, GWT, BI, Android… Vous participerez aux projets les plus innovants en terme d’environnements technologiques, le tout rythmé en mode agile.
Sans parler des collègues sympas et de l’équipe de Direction à l’écoute de vos envies et de vos ambitions. N’attendez plus, rejoignez mon Pôle Conseil!
Compétences requises:
avoir réussi à lire ce texte
bon niveau de babyfoot
Pour me faire parvenir votre candidature, envoyez votre cv à
recrutement@ippon.fr
(précisez qu’il s’agit d’une candidature pour le Pôle Conseil) ou postulez en ligne.
A très bientôt!
Julien.
Equivalent of ‘ps’ in MS-DOS
What is the equivalent of Unix’ ps
in MS-DOS, to be used in a .BAT
script?
Let’s use %tasklist%
.
eg:
[java]tasklist /fi "IMAGENAME eq java.exe" /FI "MEMUSAGE gt 100000"
Image Name PID Session Name Session# Mem Usage
========================= ====== ================ ======== ============
java.exe 9972 Console 0 212,932 K
java.exe 9640 Console 0 219,328 K
java.exe 11040 Console 0 213,432 K
java.exe 11144 Console 0 214,232 K\[/java]
Start Mule ESB as an NT service under a Windows server
Case
You would like to start a Mule ESB instance as an NT service, under a Windows server. You would also like to give a specific name and description
Fix
- add an environment variable
MULE_HOME
, with value the path of Mule install, for instance:C:\jonathan\mule-standalone-3.0.1
- edit the file
%MULE_HOME%\conf\wrapper.conf
- replace the following properties default values:
[java]wrapper.ntservice.name=%MULE_APP%
wrapper.ntservice.displayname=%MULE_APP_LONG%
wrapper.ntservice.description=%MULE_APP_LONG%[/java] - (you can also set other properties related to NT service configuration)
- launch the command:
- then you can see in the administration services that the service has started
- to remove the service, only launch the following command
[java]%MULE_HOME%\bin\mule.bat install -config %MULE_HOME%\bin\mule-conf.xml[/java]
[java]%MULE_HOME%\bin\mule.bat remove[/java]
Known issue:
On certain installations (among them the servers on which CygWin is installed), a conflict may happen between the files %MULE_HOME%\bin\mule
(standard launcher for Unix and Linux) and %MULE_HOME%\bin\mule.bat
(standard launcher for Windows). In this case, rename %MULE_HOME%\bin\mule
as %MULE_HOME%\bin\mule.OLD
How to access global variables in Mule 3?
Case
In Mule 2.2.1, getting the global variables was allowed. Therefore, such a block worked:
[xml]
<add-message-property key="jonathanProperty"
value="#[groovy:MULE_ORIGINATING_ENDPOINT]" />[/xml]
In Mule 3, this is no more possible. Therefore, how to access -former- global variables within a Mule 3 config file?
Fix
Access the global variables owing to their scope, such as Invocation, Inbound, Outbound, Session
, thanks to the methods MuleMessage.get<Scope>Property()
, eg:
[xml]<add-message-property key="jonathanProperty"
value="#[groovy:message.getInboundProperty("MULE_ORIGINATING_ENDPOINT")]" />[/xml]
BEA / JMSExceptions 045101
Case
I used a RuntimeTest to send a JMS message on a WebLogic application, with native WebLogic hosting of the queues, distributed queues to me more accurate. The test was OK.
I clustered the application. When I execute the same test, I get the following error:
[java][JMSExceptions:045101]The destination name passed to createTopic or createQueue "JONATHAN_LALOU_JMS_DISTRIBUTED_QUEUE" is invalid. If the destination name does not contain a "/" character then it must be the name of a distributed destination that is available in the cluster to which the client is attached. If it does contain a "/" character then the string before the "/" must be the name of a JMSServer or a ".". The string after the "/" is the name of a the desired destination. If the "./" version of the string is used then any destination with the given name on the local WLS server will be returned.[/java]
Fix
Since the message error is rather explicit, I tried to add a slash ('/'
) or a dot ('.'
) or both ('./'
), but none worked.
To fix the issue, you have to prefix the queue name with the JMS module name and an exclamation mark ('!'
), in the RuntimeTest configuration file, eg replace:
[xml]<property name="defaultDestinationName" value="JONATHAN_LALOU_JMS_DISTRIBUTED_QUEUE"/>[/xml]
with:
[xml]<property name="defaultDestinationName" value="JmsWeblogicNatureModule!JONATHAN_LALOU_JMS_DISTRIBUTED_QUEUE"/>[/xml]
Presentation on Mule and the ESBs
On December 13th, I led a presentation about the ESBs and especially Mule.
Here is the presentation file, available under licence Creative Commons CC-by-cc, hosted by Google Docs.
Crash of Eclipse 3.6.1 on Linux x86 64 bits, because of OSGi file locking
Case:
On launching Eclipse 3.6.1 under Linux 64bits, I get the following error:
[java]Locking is not possible in the directory "/opt/eclipse/configuration/org.eclipse.osgi". A common reason is that the file system or Runtime Environment does not support file locking for that location. Please choose a different location, or disable file locking passing "-Dosgi.locking=none" as a VM argument. /opt/eclipse/configuration/org.eclipse.osgi/.manager/.fileTableLock (Permission denied)[/java]
Fix:
Edit /opt/eclipse/eclipse.ini, add or move the line:
[java]-Dosgi.locking=none[/java]
at the end of the file, or at least after the argument -vmargs
Filter too large files in Mule ESB
Case
You use a filter connector in Mule ESB 2.2.1, to perform any operation (let’s say: to send them on JMS, but this does not matter). You would like to filter files owing to their size, ie stop the handling of files larger than 10,000,000 bytes for instance.
We assume the files you handle are text files (not binary).
Solution
In your Mule XML config file, add the following block, using a short Groovy script:
[xml]<message-properties-transformer name="add-properties">
<add-message-property key="fileSizeOK"
value="#[groovy:message.getPayload().size() < 10000000]" />
</message-properties-transformer>[/xml]
In the tag <file:inbound-endpoint>
, add the attribute: transformer-refs="add-properties"
Now, add a tag <message-property-filter pattern="fileSizeOK=true"/>
. Your outbound should then be similar to:[xml] <outbound>
<filtering-router>
<jms:outbound-endpoint queue="lalou.jonathan.jms.queue"
connector-ref="jmsConnector"/>
<message-property-filter pattern="fileSizeOK=true"/>
</filtering-router>
<forwarding-catch-all-strategy>
<file:outbound-endpoint path="/my/folder/"
connector-ref="fileConnector" outputPattern="error/#[header:originalFilename].too_big.#[function:dateStamp:yyyyMMdd_HHmmss_SSSSS].KO" />
</forwarding-catch-all-strategy>
</outbound>[/xml]
Many thanks to Vincent N. for his help.