Liferay daemon script

5 décembre 2011 2 commentaires

I’ve googled around looking for a good daemon script for Liferay,… and I finally wrote mine.

Here is the script I use for running a Liferay 6.0.6 instance as a sysv daemon under linux. The script has been tested on an Ubuntu 10.04 LTS server.
It just the runs a normal liferay-tomcat bundle, unzipped in the /var/liferay6 directory.

#!/bin/bash
### BEGIN INIT INFO
# Provides:          liferay
# Required-Start:    $local_fs $remote_fs $network
# Required-Stop:     $local_fs $remote_fs $network
# Should-Start:      $named
# Should-Stop:       $named
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Short-Description: Liferay portal daemon.
# Description:       Starts the Liferay portal.
# Author:            Julien Rialland <julien.rialland@gmail.com>
### END INIT INFO

#Display name of the application
APP_NAME="Liferay 6.0.6"

#Location of Liferay installation
export LIFERAY_HOME=/var/liferay6

#unprivileged user that runs the daemon. The group/user should have been created separately,
#using groupadd/useradd
USER=liferay
GROUP=liferay

###This is end of the configurable section for most cases, other variable definitions follow :

#Only root user may run this script
if [ `id -u` -ne 0 ]; then
	echo "You need root privileges to run this script"
	exit 1
fi

#tomcat directory
#detection of the tomcat directory within liferay
TOMCAT_DIR=`ls "$LIFERAY_HOME" | grep tomcat | head -1`
export CATALINA_HOME="$LIFERAY_HOME/$TOMCAT_DIR"

#location of pid file
export CATALINA_PID=/var/run/liferay.pid

# guess where is JAVA_HOME if needed (when then environment variable is not defined)
JVM_DIRS="/usr/lib/jvm/java-6-openjdk /usr/lib/jvm/java-6-sun /usr/lib/jvm/default-java /usr/lib/jvm/java-1.5.0-sun /usr/usr/lib/j2sdk1.5-sun /usr/lib/j2sdk1.5-ibm"
if [ -z "$JAVA_HOME" ]; then
        for jdir in $JVM_DIRS; do
                if [ -r "$jdir/bin/java" -a -z "${JAVA_HOME}" ]; then
                        export JAVA_HOME="$jdir"
                fi
        done
fi

#if JAVA_HOME is still undefined, try to get it by resolving the path to the java program
if [ -z "$JAVA_HOME" ]; then
        javaexe=`which java`
        if [ ! -z "$javaexe" ]; then
                javaexe=`readlink -m "$javaexe"`
                jdir="$javaexe/.."
                export JAVA_HOME=`readlink -m "$jdir"`
        fi
fi

#if JAVA_HOME is still undefined, crash the script
if [ -z "$JAVA_HOME" ]; then
	echo 'The JAVA_HOME environment variable could not be determined !'
	exit 1
fi

#extra jvm configuration : enable jmx
#export JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.port=9999 -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false"

#extra jvm configuration : enable remote debugging
#export JAVA_OPTS="$JAVA_OPTS -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=9998" 

################################################################################

#verify that the user that will run the daemon exists
id "$USER" > /dev/null 2>&1
if [ "$?" -ne "0" ]; then
	echo "User $user does not exist !"
	exit 1
fi

#load utility functions from Linux Standard Base
. /lib/lsb/init-functions

#starts the daemon service
function start {
        log_daemon_msg "Starting $APP_NAME"

        #create work directory if non-existent
        mkdir $CATALINA_HOME/work 2>/dev/null

        #clear temp directory
        rm -rf "$CATALINA_HOME/temp/*" 2>/dev/null
        mkdir $CATALINA_HOME/temp 2>/dev/null

        #fix user rights on liferay home dir
        chown -R "$GROUP":"$USER" "$LIFERAY_HOME"
        chmod -R ug=rwx "$LIFERAY_HOME"

        #ensure that pid file is writeable
        mkdir `dirname "$CATALINA_PID"` 2>/dev/null
        chmod ugo=rw `dirname "$CATALINA_PID"`

        su "$USER" -c "$CATALINA_HOME/bin/catalina.sh start"
        status=$?

        log_end_msg $status
        exit $status
}

#stops the daemon service
function stop {
        log_daemon_msg "Stopping $APP_NAME"
        if [ ! -f "$CATALINA_PID" ];then
            echo "file $CATALINA_PID is missing !"
            unset CATALINA_PID
        fi
        su "$USER" -c "$CATALINA_HOME/bin/catalina.sh stop 10 -force"
        status=$?
        log_end_msg $status
        if [ "$status" = "0" ];then
            rm -f "$CATALINA_PID"
        fi
        exit $status
}

#restarts the daemon service
function restart {
        stop
        sleep 3s
        start
}

#prints service status
function status {
  if [ -f "$CATALINA_PID" ]; then
    pid=`cat "$CATALINA_PID"`
    echo "$APP_NAME is running with pid $pid"
    exit 0
  else
    echo "$APP_NAME is not running (or $CATALINA_PID is missing)"
    exit 1
  fi
}

case "$1" in
	start|stop|restart|status)
		$1
	;;
	*)
		echo $"Usage: $0 {start|stop|restart|status}"
		exit 1
	;;
esac

Just name the script ‘liferay’ and put in in /etc/init.d, If you want it to run automatically when the server starts up, you just have to run the following commands :


sudo chmod u+x /etc/init.d/liferay
sudo update-rc.d liferay defaults

Publicités
Catégories :Uncategorized Étiquettes : , ,

WTP Eclipse project generation from Maven configuration

The maven ‘eclipse’ plugin is a bit outdated, but very useful. I had some issues when generating eclipse configuration specifically for web projects.
Here is a description on how I managed to configure the plugin finally !

This configuration generates an Eclipse project configuration when you run mvn eclipse:eclipse. All you have to do then is to import the project into Eclipse by running the File>Import menu entry in Eclipse

This configuration fixes some issues I used to have with mvn-generated Eclipse projects :

  • utf-8 encoding for all text files
  • good versions in project’s facets (servlet 3.0, java 1.6, javascript 1.0)
  • Correct web-specific settings (web root directory location, and use of the jar dependencies in the webapp)
  • Spring-enabled project nature

The plugins section of the pom.xml looks like that :

    <properties>
		<java.version>1.6</java.version>
		<servlet-api.version>3.0</servlet-api.version>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
	</properties>

	<plugins>

	    ...

		<plugin>
		    <groupId>org.apache.maven.plugins</groupId>
			<artifactId>maven-compiler-plugin</artifactId>
			<version>2.3.2</version>
			<configuration>
				<source>${java.version}</source>
				<target>${java.version}</target>
			</configuration>
		</plugin>

		<!-- Settings for generating eclipse project -->
		<plugin>
			<groupId>org.apache.maven.plugins</groupId>
			<artifactId>maven-eclipse-plugin</artifactId>
			<version>2.8</version>
			<configuration>
				<wtpversion>2.0</wtpversion>
				<downloadSources>false</downloadSources>
				<downloadJavadocs>false</downloadJavadocs>
				<additionalConfig>
					<file>
						<name>.settings/org.eclipse.wst.common.project.facet.core.xml</name>
						<content><![CDATA[
							<faceted-project>
							  <fixed facet="jst.java"/>
							  <fixed facet="jst.web"/>
							  <installed facet="jst.java" version="${java.version}"/>
							  <installed facet="jst.web" version="${servlet-api.version}"/>
							  <installed facet="wst.jsdt.web" version="1.0"/>
							</faceted-project>
						]]></content>
					</file>
					<file>
						<name>.settings/org.eclipse.core.resources.prefs</name>
						<content><![CDATA[eclipse.preferences.version=1
encoding/<project>=${project.build.sourceEncoding}]]>
						</content>
					</file>
				</additionalConfig>
				<additionalProjectnatures>
				   <projectnature>org.springframework.ide.eclipse.core.springnature</projectnature>
				</additionalProjectnatures>
			</configuration>
		</plugin>

	</plugins>

You may also have to ensure that you gave a value to the M2_REPO variable in the Eclipse settings points to your local .m2/repository.

Catégories :Uncategorized

From zero to Liferay portlet in less that 5 minutes (depending on your network connection)

Following this recipe, i can write a new portlets (for demoing purpose) in a very short time !

1) Create a the repertory structure and download a fresh bundle distribution:

mkdir $HOME/liferay
mkdir $HOME/liferay/portlets
mkdir $HOME/liferay/bundles
cd $HOME/liferay/bundles
wget http://sunet.dl.sourceforge.net/project/lportal/Liferay%20Portal/6.0.6/liferay-portal-jetty-6.0.6-20110225.zip
unzip liferay-portal-jetty-6.0.6-20110225.zip

(you may know want to run liferay : just run the script ‘$HOME/liferay/liferay-portal-6.0/jetty-6.1.24/bin/run.sh

3) Create a new portlet project using the liferay archetype

cd $HOME/liferay/portlets
mvn archetype:generate \
-DarchetypeGroupId=com.liferay.maven.archetypes \
-DarchetypeArtifactId=liferay-portlet-archetype \
-DarchetypeVersion=6.0.6 \
-DgroupId=net.jr.testapp \
-DartifactId=test-portlet

You just have to modify the liferay.auto.deploy.dir property at the end of the generated pom.xml :

<properties>
<liferay.auto.deploy.dir>../../bundles/liferay-portal-6.0.6/deploy</liferay.auto.deploy.dir>
<liferay.version>6.0.6</liferay.version>
</properties>

The portlet can be recompiled/deployed easily by running the following command :

mvn clean package liferay:deploy

4) The only things that are needed to customize the portlet is to modify the main.js and view.jsp files…

5) More fancy things may be done by turning the project into an Eclipe project, and then import it using Eclipe :

mvn eclipse:eclipse

It doesn’t take more than 5 minutes, counting the time it needs to download the Liferay bundle !

Catégories :Uncategorized

OVH minicloud

11 septembre 2011 2 commentaires

J’ai testé il y a quelques temps l’offre minicloud d’OVH. J’ai trouvé la possibilité d’avoir une machine sur le net pour moins de 8 euros/mois vraiment géniale, mais un peu plus de stockage n’aurait pas été du luxe.

Création de l’image, première connexion :

Il faut d’abord créer un compte et se connecter au ManagerV5 d’ovh.

Créer une paire de clés ssh grace à l’interface web, puis télécharger la clé privée (j’utilise openssh, je choisit donc le format pem), ensuite il faut donner les bons droits à la clé : chmod go-rx sshkey.pem

Ensuite on peut créer son « cloud » via l’interface web, j’ai choisi Ubuntu (32bits et 64bits sont proposés, j’ai choisi 64bits).

Ensuite on peut se connecter à la machine une fois démarrée, La somme d’argent mise sur le « compte » est débité à raison d’un centime d’euro par heure, jusqu’a ce que le compte soit épuisé ou que l’on éteigne la machine depuis l’interface web.

NOTE : L’Ip / nom de domaine n’est valide qu’au cours d’une seule ‘session’, une nouvelle ip est attribuée a chaque démarrage de l’image !

On se connecte en ssh : ssh -i sshkey.pem root mc-xxx.ovh.net

Installation de paquets

Pour mon confort:

vim
sysvinit-util
sysv-rc-conf

Pour Apache et Php :

apache2
libapache2-mod-php5
php5-suhosin
php5-xcache
php5-gd

Installation de Tomcat7

J’ai décidé d’installer Tomcat7, il n’y a pas (encore) de paquet apt correspondant. J’installe donc à la main :


mkdir /usr/local/tomcat7
cd /usr/local
wget http://apache.cict.fr/tomcat/tomcat-7/v7.0.16/bin/apache-tomcat-7.0.16.tar.gz
tar zxvf apache-tomcat-7.0.16.tar.gz
mv apache-tomcat-7.0.16 tomcat7
rm apache-tomcat-7.0.16.tar.gz

Tomcat ne sera jamais accédé directement, mais toujours via le serveur Apache grâce à mod_proxy_ajp. Donc je commente le Connector http dans le fichier conf/server.xml.

Démarrage de Tomcat en tant que service

Je dispose d’un script de service ‘maison’ nommé tomcat, je le place dans /etc/init.d

Ensuite : update-rc.d tomcat defaults

Configuration d’Apache

Activation des modules proxy et proxy_ajp

a2enmod proxy
a2enmod proxy_ajp

Ensuite on vient modifier le ficher /etc/apache2/mods_available/proxy.conf :

ProxyRequests Off

AddDefaultCharset off
Order deny,allow
Deny from all
#Allow from .example.com

# Enable/disable the handling of HTTP/1.1 "Via:" headers.
# ("Full" adds the server version; "Block" removes all outgoing Via: headers)
# Set to one of: Off | On | Full | Block

ProxyVia Off

#redirect to tomcat
ProxyPass / ajp://localhost:8009/
ProxyPassReverse / ajp://localhost:8009/

Mise en place d’un VirtualHost

1) Achetez votre nom de domaine !
2) Créer le dossier dans /var/www :

mkdir /var/www/domaine.com

3) Ajouter la conf dans /etc/apache2/sites_available :

/etc/apache2/sites-available/www.la-bonneterie.fr:

DocumentRoot /var/www/www.domaine.fr
ServerName http://www.domaine.fr


Puis activer la conf a2ensite http://www.domaine.fr

Sécurisation du serveur : Script de Firewall

Un script de firewall est a mon sens une bonne mesure de sécurité :
J’utilise un script tout simple que je range dans /etc/init.d/firewall (que j’active ensuite avec updaterc.d firewall defaults)

#!/bin/bash
### BEGIN INIT INFO
# Provides: firewall
# Required-Start: $remote fs $syslog $network
# Required-Stop: $remote fs $syslog $network
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
# Short-Description: firewall
# Description : iptables-based firewall script
# Author : Julien Rialland
### END INIT INFO

IPT=`which iptables`

#firewall rules installation
#note that the order in which rules are appended is very important. For example, if your first rule is
#to deny everything... then no matter what you specifically allow, it will be denied.
function start {
echo 'Installing new firewall rules...'
$IPT -F

#default policy for the predefined chains
$IPT -P INPUT ACCEPT
$IPT -P OUTPUT ACCEPT
$IPT -P FORWARD DROP

#accept ssh connections
$IPT -A INPUT -p tcp --dport 22 -j ACCEPT

#accept http and https connections (80,443)
$IPT -A INPUT -p tcp --dport 80 -j ACCEPT
$IPT -A INPUT -p tcp --dport 443 -j ACCEPT

#accept anything from localhost
$IPT -A INPUT -i lo -j ACCEPT

#Accept related or established connections so ftp can work, for example
$IPT -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT

#everything else is dropped
$IPT -A INPUT -j DROP

echo '...done.'
}

function stop {
echo 'Flushing all firewall rules...'
$IPT -F
echo '...done.'
}

function restart {
stop
start
}

function status {
$IPT -L -n -v
}

case "$1" in
start|stop|restart|status)
$1
;;
*)
echo "Usage : $0 (start|stop|restart|status)"
;;
esac

Mise en place de fail2ban

ce script surveille les logs de ssh, et bannit les ip qui tentent des connexions repétées sans réussir, ce qui empêche les attaques par dictionnaire par exemple : apt-get install fail2ban

DNS dynamique

Les machines minicloud n’ont pas d’ip fixe, Il faut donc configurer un dns dynamique. Même si on dispose d’un nom de domaine (en .fr par exemple) il faut pouvoir toujours rediriger vers la même machine, même aprés un redemarrage, sans avoir a reconfigurer les dns. Je me sers dont d’une adresse en .dyndns.org.

http://www.domaine.fr (CNAME)=> domaine.dyndns.org => ip flottante minicloud


apt-get install libio-socket-ssl-perl ddclient

Voici ma configuration (/etc/ddclient.conf)

pid=/var/run/ddclient.pid
syslog=yes
protocol=dyndns2
use=if, if=eth0
daemon=300
server=members.dyndns.org
login=jrialland
password='xxxxxxxxxxxxx'
mondomaine.dyndns.org

Configuration Email

Ovh empeche l’utilisation des miniclouds comme serveurs email, in vont même jusqu’a empécher le traffic vers les ports 25(smtp) d’autres machines.
Pour pouvoir envoyer des notifications par email depuis mes programmes, je contourne la limitation en configurant postfix pour utiliser mon compte gmail :


apt-get install postfix libsasl2-2 ca-certificates libsasl2-modules heirloom-mailx

vi /etc/postfix/main.cf:

relayhost = [smtp.gmail.com]:587
smtp_sasl_auth_enable = yes
smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd
smtp_sasl_security_options = noanonymous
smtp_tls_CAfile = /etc/postfix/cacert.pem
smtp_use_tls = yes
--------
vi /etc/postfix/sasl_passwd:
[smtp.gmail.com]:587 user.name@gmail.com:password

chmod 400 /etc/postfix/sasl_passwd
postmap /etc/postfix/sasl_passwd

cat /etc/ssl/certs/Thawte_Premium_Server_CA.pem | sudo tee -a /etc/postfix/cacert.pem

ln -s /etc/postfix/sasl_passwd.db /etc/postfix/sasl/sasl_passwd2.db

service postfix restart

La procédure relève un peu du parcours du combattant, mais en tout cas ça me permet de valider le fait qu’on peut envoyer des emails depuis un minicloud.

L’autre solution (meilleure a mon avis) serait d’utiliser le relais smtp d’ovh, qui permet d’envoyer 100 mails/heure.

Installation de subversion

J’ai décidé d’installer un serveur subversion sur cette machine, là encore Je me suis un peu battu, mais j’ai finalement une configuration qui me convient :

Il faut d’abord installer/configurer svn :


apt-get install subversion libapache2-svn
mkdir /var/svn
mkdir /var/svn/repo
svnadmin create /var/svn/repo

Modifier le fichier /var/svn/repo/conf/svnserve.conf

[general]
anon-access = none
auth-access = write
password-db = passwd
realm = SVN Repository

Modifier le fichier passwd


sudo addgroup svn --system
sudo adduser svn --system --home /var/svn --no-create-home --ingroup svn
sudo chown -R svn: /var/svn

Créer un script de démarrage dans /etc/init.d/svnserve :

#!/bin/sh

set -e
if [ -x /usr/bin/svnserve ] ; then
HAVE_SVNSERVE=1
else
echo "Svnserve not installed."
exit 0
fi

. /lib/lsb/init-functions

case "$1" in
start)
log_action_begin_msg "Starting SVN server"
/sbin/start-stop-daemon --start --chuid svn:svn --exec /usr/bin/svnserve -- -d -r /var/svn
log_action_end_msg $?
;;
stop)
log_action_begin_msg "Stopping SVN server"
/sbin/start-stop-daemon --stop --exec /usr/bin/svnserve
log_action_end_msg $?
;;
force-reload|restart)
$0 stop
$0 start
;;
*)
echo "Usage: /etc/init.d/svnserve {start|stop|restart|force-reload}"
exit 1
;;
esac

exit 0

Configurer le démarrage


sudo update-rc.d svnserve defaults

Pour Apache : Ne pas oublier de changer les droits du dossier des dépots :

update-rc.d svnserve defaults
chown -R www-data /var/svn/

J’ai ajouté une configuration de site dans /etc/apache2/sites_available/svn :

<IfModule dav_svn_module>
ServerName jrcloud.dyndns.org:443
SSLEngine On
SSLOptions +FakeBasicAuth +ExportCertData +StrictRequire
SSLCertificateFile /etc/pki_custom/certs/jrcloud.dyndns.org.crt
SSLCertificateKeyFile /etc/pki_custom/private/jrcloud.dyndns.org.key

<Location /svn>
DAV svn
SVNParentPath /var/svn
SVNListParentPath On
AuthType Basic
AuthName "SVN Repository"
AuthUserFile /etc/apache2/dav_svn.passwd
Require valid-user
</Location>
</IfModule>

Puis on active la conf avec : a2ensite svn

On crée un certificat SSL pour Apache :

domain=domaine.dyndns.org

mkdir /etc/pki_custom
mkdir /etc/pki_custom/private
mkdir /etc/pki_custom/certs
mkdir /etc/pki_custom/csrs

openssl genrsa -out /etc/pki_custom/private/$domain.key 1024
openssl req -new -key /etc/pki_custom/private/$domain.key -out /etc/pki_custom/csrs/$domain.csr
openssl x509 -req -days 1825 -in /etc/pki_custom/csrs/$domain.csr -signkey /etc/pki_custom/private/$domain.key -out /etc/pki_custom/certs/$domain.crt

Pour créer un utilisateur subversion, il faut juste créer un utilisateur pour l’authentification Apache :


sudo htpasswd -s /etc/apache2/dav_svn.passwd utilisateur
sudo chown www-data:www-data /etc/apache2/dav_svn.passwd

Une fois ces étapes passées, le dépot est accessible via https://domaine.dyndns.org/svn/repo

Catégories :Uncategorized

jfastcgi 2.1 is available

6 septembre 2011 1 commentaire

jFastCGI 2.1 is available, it features some minor bug corrections. The library is now available through the plublic maven repositories.

Catégories :Uncategorized Étiquettes : ,

Forwarding X11 through ssh

sshThis is an information that you might easily find everywhere, this article is mainly a reminder for myself (and eventually for you 🙂 ).

No need for fancy protocols, in order to run graphical programs on a remote machine we might use ssh, and X11. This has prooved to work well since the eighties 🙂

NOTE : In my exemple, the client is my Ubuntu 11.04 laptop, and the server runs Debian Squeeze, so my explanation covers the ‘debian way’ of doing things.

On the client side :

X11 shall be accessible though tcp.

If you run X directly, which is not my case, Edit the /etc/X11/xinit/xserverrc file, and remove the « -nolisten tcp » option. This modification is optional if you, like me, use gdm.

gdm starts X sessions, so you you have to modify its configuration in /etc/gdm/custom.conf :


[xdmcp]

[chooser]

[security]
DisallowTCP=false

[debug]

restarting gdm :
close you’re gnome session, and then crtl+alt+f1 opens a terminal in console mode.
type the following :

service gdm restart

and then ctrl+alt+f7 brings you back to the gdm prompt.

SSH config :
Then edit the /etc/ssh/ssh_conf :

X11Forwarding yes
X11DisplayOffset 10

On the server side,

edit /etc/ssh/sshd_conf :

Host *
ForwardX11 yes
ForwardX11Trusted yes

and restart the server (fortunately you won’t be kicked out if you do that through ssh), by doing :

$> /etc/init.d/ssh restart

Connections can now handle X11 forwarding

$> ssh -X user@server
$> echo $DISPLAY
client:10.0
$>xeyes &

Catégories :Uncategorized

Showing kernel modules dependencies graphically using graphviz

A few time ago, I had problems with my sound card module on my new linux laptop, I did not understand well how modules were loaded.

I finally solved my problem, but I was curious about the modules depency structure, and I started playing with graphviz to have a graphical view of that.

I finally came with this small & dirty python script :

#!/usr/bin/python
# -*-coding:utf-8-*-
import os, re
#usual usage is : ./mods_graph.py | dot -Tpng > modules.png

print 'digraph linux_modules {'
lines = [line for line in os.popen('lsmod')]
for line in lines[1:] :
    line = [x for x in re.split('\ |,', line.replace('\n','')) if not len(x)==0]
    for dep in line[3:]:
        print '\t' + line[0] + ' -> ' + dep + ';'
print '}'
exit(0)

It reads the dependencies between the linux modules by calling lsmod(8), and then formats the output into a file acceptable by the dot utility, from the graphviz package.

The png output is quite cool, … And you can see how complex the sound handling is under linux compared to video !!

The other conclusion is to see how fast and easy it is to generate graphs using graphviz !

Catégories :Uncategorized