понедельник, 6 мая 2013 г.

Использование разных значений CATALINA_HOME и CATALINA_BASE в Tomcat

По умолчанию в свежеустановленном Tomcat переменные окружения CATALINA_HOME и CATALINA_BASE равны между собой - и указывают на ту директорию, где установлен tomcat (в нашем случае это директория /opt/tomcat). Во 2-й главе Tomcat: The Definitive Guide от О'Рейли описан пример использования разных значений этих переменных. При этом CATALINA_HOME указывает на местоположение неизменяемых "глобальных" директорий (bin и lib), а CATALINA_BASE - локальных (conf, logs, temp, webapps и work). В книге подробно рассматривается использование такой конфигурации для запуска нескольких экземпляров tomcat на одном сервере, но лишь вскользь упомянуто гораздо более практически полезное применение: конфигурация, позволяющая обновлять tomcat простым обновлением символической ссылки. Ниже приводится пошаговая инструкция, как это сделать. Опыты проводились на Debian sid, версии tomcat: 7.0.32  и 7.0.37, установленные простой распаковкой архивов, скачанных с http://tomcat.apache.org в директорию /opt (предполагается, что в первоначальной конфигурации /opt/tomcat является симлинком на /opt/apache-tomcat-7.0.32).

1. Создаем файл-пускач /etc/init.d/tomcat (если он еще не создан). Минимальный пример взят из 1-й главы вышеупомянутой книги:

#!/bin/sh

export CATALINA_HOME=/opt/tomcat
export CATALINA_BASE=/opt/catalina

$CATALINA_HOME/bin/catalina.sh $*


2. при остановленном томкате переносим в /opt/catalina директории с изменяемой частью сервера:

$ cd /opt/tomcat
$ mv conf logs temp webapps work ../catalina

Подразумевается, что пользователь, под которым запускается томкат, должен иметь права на чтение и запись в эти директории (для conf достаточно чтения, для webapps - если не используется autoDeploy - тоже).

3. теперь для установки новой версии томката достаточно, распаковав дистрибутив в /opt, удалить ссылку (иначе ln -sf, имеющий последним аргументом директорию - в полном соответсвии с мануалом - создаст ссылку внутри нее):

$ rm -f /opt/tomcat

и создать заново:

$ ln -s /opt/apache-tomcat-7.0.37 /opt/tomcat

и перезапустить томкат. Поддиректории в /opt/catalina будут использоваться вместо поддиректорий в /opt/tomcat с теми же именами. Для достижения большей прозрачности конфигурации можно удалить из /opt/tomcat все лишнее, но строгой необходимости в этом шаге нет. Откат на старую версию в случае проблем с новой выполняется так же легко - обратной заменой ссылки.

среда, 13 марта 2013 г.

X11 Forwarding in Solaris 11

В Solaris 11 Express из коробки X11 forwarding разрешен в /etc/sshd/sshd_config - однако не работает (о чем и сообщает при каждой попытке захода на сервер с помощью ssh -X). Для того, чтобы увидеть, в чем проблема, достаточно добавить в командную строку ssh ключ -v В составе системы просто-напросто нет программы xauth.
Поправить беду - как ни странно - можно вполне стандарным способом:
# pkg install xauth
Если после этого перезайти на серевер, сообщение об ошибке больше не выводится, но первая же X-программа, которую я попытался запустить (это была groovyConsole) умерла, сообщив об отсутствии в системе libXrender.so
Но мы уже знаем, что делать:
# pkg install libxrender
После этого groovyConsole запустилась. В процессе поиска в сети решения проблемы достаточно часто мне встречался совет, который и приведу ниже (хотя в моем случае заработало и без этого). Утверждается, что X11 forwarding работает лучше, если явно потребовать от sshd использовать IPv4. Делается это добавлением строки:
ListenAddress 0.0.0.0
в файл /etc/sshd/sshd_config. Применяемая для этой же цели в Linux инструкция:
AddressFamily inet
sshd из поставки Solaris 11 неизвестна.

P.S.: в Solaris 10 аналогичная проблема решается установкой пакетов SUNWxwplt и SUNWxwice (также нужно убедиться, что  /usr/openwin/bin входит в PATH).

вторник, 5 февраля 2013 г.

Pseudo-targets in Groovy AntBuilder


К моему удивлению, ни в 700-страничном фолианте "Groovy in Action", ни в достаточно неплохой документации на сайте языка  не приводится пример создания с помощью AntBuilder полнофункционального проекта (т.е. не просто последовательности выполняемых задач (tasks), а совокупности взаимозависимых целей (target). Анализ имеющихся в сети исходников и сниппетов не дал ничего интереснее, чем псевдо-цели с использованием замыканий (closures). Например, такой код принимает имена задач из командной строки (почти как настоящий ant):

#!/usr/bin/env groovy
DEFAULT = 'jar'
DEST = 'target'
JAR = "$DEST/myapp.jar"
SRC = 'src'
ant = new groovy.util.AntBuilder()
ant.taskdef(name: 'groovyc', classname: 'org.codehaus.groovy.ant.Groovyc')
compile = {
    println '\ncompile:'
    ant.mkdir(dir: DEST)
    ant.groovyc(destdir: DEST, srcdir: SRC, includes: '*.groovy')
}
jar = {
    compile()
    println '\njar:'
    ant.jar(destfile: JAR, basedir: DEST, includes: '*.class')
}  
if (args) for (t in args) this[t]() else this[DEFAULT]()

Самое обидное в том, что в groovy вполне можно написать в таком стиле:

ant.target(name: 'clean') {delete(dir: DEST)}

но паче чаяния такая цель будет выполнена немедленно после объявления - а это совсем не то поведение, которое нам нужно. А из этого unresolved issue в джире кодехауза следует, что путей борьбы с данной странностью разработчики пока не придумали.