23 июля 2011 г.

Баг kdesu в openSUSE 11.4

Столкнулся в openSUSE 11.4 с тем, что мои замечательные скрипты выбора конфигурации сети, вдруг перестали нормально работать. Довольно быстро мне стало понятно, что сердце неприятности заключается в программе kdesu. Здравствуй, новый KDE! Суть проблемы была в том, что после ввода в диалоговом окне пароля суперпользователя ничего не происходило, а должен был запуститься скрипт с соответствующими правами. Я перекопал весь интернет и не нашел ничего лучше, чем удалить (а точнее просто переименовать на всякий случай) файл /usr/lib/kde4/libexec/kdesud. После этого всё вроде бы заработало, но теперь kdesu стал ругаться, что не может найти своего друга-демона и что это вроде как небезопасно. Ну и хрен с ним, пусть боится.

22 июля 2011 г.

Instant Messenger'ы в Linux. Сборка qutIM 0.3 beta в openSUSE 11.4

По моему сугубо личному мнению, в Linux, если рассматривать его как систему для десктопного использования, существует две бросающихся в глаза проблемы: отсутствие приятных в использовании мультимедиа проигрывателей и отсутствие таких же приятных Instant Messenger'ов. В этой статье я хочу поговорить о последних.

Не знаю кому как, но мне всем известные Kopete и Pidgin кажутся страшненькими и неудобными. Хочется что-то попроще, но симпатичное. Что-то вроде того, чем раньше был QIP, только многопротокольное. И достаточно давно я открыл для себя qutIM. Думаю, что сегодня у него уже достаточно много пользователей. Первая версия, которую я себе поставил была 0.1 (то ли альфа то ли бета). Когда я её увидел, то сразу понял, что это то, чего мне так не хватало для счастья. Конечно, глючило это создание прилично, но мне было всё равно, главное, что глаз радовало.

Потом была версия 0.2, её я и использую до сих пор. Глючит вроде поменьше и в целом стало лучше. Хочется сказать огромное спасибо ребятам, которые в своё свободное время продолжают развивать этот проект.

Несколько дней назад я решил попробовать 0.3 beta, и тут меня поджидало разочарование. Внешне всё сильно изменилось, и для меня не в лучшую сторону. Вдобавок появилось очень много новеньких глюков. Понятно, конечно, что это бета-версия, но дело даже не в глюках. Я по-прежнему готов с ними мириться. Такое чувство, что проект пошел в ту же сторону, где сидят Kopete и Pidgin. Я говорю, главным образом, о простоте и органичности интерфейса, а также о понятности настроек. Пока что я решил остаться на версии 0.2, но продолжу следить за проектом, вдруг снова станет лучше. А пока расскажу, как собрать 0.3b в openSUSE 11.4, и делается это довольно просто, что приятно.

21 апреля 2011 г.

Как узнать полный путь до запущенного bash-скрипта

Иногда нужно знать, в каком каталоге находится запущенный скрипт. Ну, например, в этом же каталоге лежат другие скрипты, которые должны быть запущены текущим выполняющемся скриптом. Для того, чтобы он их запустил, ему было бы неплохо знать, где их искать, потому что вы могли запустить скрипт находясь в совершенно произвольной директории, или воспользоваться для запуска не самим файлом скрипта, а символической ссылкой, лежащей в другом каталоге, которая указывает на файл скрипта.

Можно, конечно, поступить просто и в самом скрипте в переменной жёстко прописать полный путь до каталога, в котором этот скрипт лежит. Получится что-то вроде этого:
#!/bin/bash

DIRECTORY="/home/user/my_scripts"
cd $DIRECTORY

# запуск "соседних" скриптов
./script1.sh
./script2.sh
Вполне рабочий вариант и две обозначенные выше проблемы будут решены, но если надо будет переместить скрипт в другой каталог, то и значение переменной придётся руками поменять в самом скрипте. Не очень удобно.

Для красивого решения проблемы нужно знать всего три вещи:
  1. Путь до выполняющегося скрипта можно узнать с помощью $0, но проблема в том, что он относительный, т.е. если вы запустите скрипт как ./script.sh, то и $0 будет содержать ./script.sh
  2. Команда readlink с параметром -e решит сразу две проблемы: во-первых она вернет полный путь до файла скрипта, если вы воспользовались для запуска символической ссылкой (даже если это была цепочка симлинков), а во-вторых преобразует относительный путь, если такой получен с помощью $0, в абсолютный
  3. Чтобы избавиться от имени файла скрипта в конце абсолютного пути, нужно воспользоваться командой dirname
    Пример:
    #!/bin/bash
    
    # полный путь до скрипта
    ABSOLUTE_FILENAME=`readlink -e "$0"`
    # каталог в котором лежит скрипт
    DIRECTORY=`dirname "$ABSOLUTE_FILENAME"`
    
    # запуск "соседних" скриптов
    $DIRECTORY/script1.sh
    $DIRECTORY/script2.sh
    

    4 апреля 2011 г.

    Прикручиваем кнопки "Поделиться" от Яндекса к www.blogger.com

    Захотелось мне прикрутить к блогу эти самые кнопочки. Напишу пару слов о том, как я это сделал.

    Сначала идём по адресу http://api.yandex.ru/share/, настраиваем вид блока "Поделиться" и выбираем сервисы, в которые хочется постить с его помощью. Получаем код, вроде этого:

    Теперь заходим в Панель инструментов -> Дизайн -> Изменить HTML. Ставим галку рядом с "Расширить шаблоны виджета".

    Между тегами <head> и </head> где-нибудь втыкаем первую строку из листинга выше. Короче эту:

    Дальше надо выбрать место, где хочется разместить эти кнопки. Я решил вставить их под сообщением, ниже автора и времени создания сообщения. Если вас устраивает это место, то ищите в шаблоне строку <span class="post-icons"> и над ней вставляйте оставшуюся часть полученного кода:

    Если вы сохраните шаблон и зайдёте на блог, то кнопочки должны будут появиться и будут даже работать, только не всегда правильно. Например, если отдельно открыть страницу с конкретным сообщением блога и там нажать на какую-либо из кнопок "поделиться", то всё отработает правильно. А вот если нажать на одну из этих кнопок под каким-либо сообщением на главной странице, то делёжка будет осуществляться не ссылкой на это сообщение, а ссылкой на главную страницу блога. Для того, чтобы такого безобразия не происходило, нужно элементу DIV добавить атрибуты data-yashareLink и data-yashareTitle, которые позволяют установить ссылку, которой нужно поделиться и заголовок сообщения, соответственно. Но для того, чтобы динамически получать ссылку и заголовок нужно использовать хитрые выражения, которые понимает движок блоггера.

    Вот как это выглядит:

    В процессе генерации страниц блога выражение expr:data-yashareLink='data:post.url' будет заменено блоггером на data-yashareLink='http://myblog.blogspot.com/путь_до_сообщения', а expr:yashareTitle='data:post.title' на yashareTitle='Заголовок_сообщения'.

    Кстати, контейнером для кнопок может быть не обязательно элемент DIV, я использую SPAN. Вот код, который я добавил себе в шаблон:


    25 марта 2011 г.

    Красивое использование косвенной адресации в bash-скриптах

    Косвенная адресация это когда, грубо говоря, одна переменная ссылается на какое-либо значение через другую переменную. Если говорить точнее и применительно к bash'у, то это когда одна переменная хранит имя другой переменной, которая в свою очередь содержит, например, какое-либо значение. С помощью косвенной адресации можно, используя первую переменную, сразу получить доступ к значению, которое содержит вторая переменная. Как это работает вроде бы ясно, но, возможно, не сразу понятна нужность всего этого.

    Итак, допустим у нас есть переменная X, которая содержит строку "значение". Так же есть переменная Y, которая в качестве значения содержит имя переменной X. Красивость заключается в том, что с помощью прямой и косвенной адресации, используя переменную Y, можно получить соответственно имя и значение переменной X.

    Простой пример:
    X="значение"
    Y=X
    echo "$Y: ${!Y}"
    
    В этом примере с помощью прямой адресации $Y мы получаем доступ к имени переменной X, а с помощью косвенной ${!Y} - к её значению. В старых версиях bash косвенная адресация могла использоваться только так eval Z=\$$Y, а начиная со 2 версии она стала выглядеть проще, хотя старый вариант так же может использоваться.

    Теперь приведу более жизненный пример. У меня есть скрипт, который настраивает iptables. Косвенная адресация в нем используется для того, чтобы сделать проще изменение настроек скрипта и создать красивый вывод. Приведу пример поясняющий основную суть.
    #!/bin/bash
    
    # список сервисов и их портов
    SSH=22
    HTTP=80
    HTTPS=443
    SAMBA="137 138 139 445"
    
    # локальные сервисы на которые разрешен доступ снаружи
    INPUT_PORTS_ACCEPT="SSH SAMBA HTTP HTTPS"
    
    echo "Удаленный доступ к сервисам хоста:"
    # открываем доступ на разрешенные сервисы
    for SERVICE_NAME in $INPUT_PORTS_ACCEPT
    do
        # для каждого порта сервиса добавляем разрешающие правила в iptables
        PORTS=${!SERVICE_NAME} # устаревший вариант: eval PORTS=\$$SERVICE_NAME
        for PORT in $PORTS
        do
            iptables -t filter -A INPUT -i eth0 -p tcp --dport $PORT -j ACCEPT
            iptables -t filter -A INPUT -i eth0 -p udp --dport $PORT -j ACCEPT
        done
    
        # выводим имя и порты сервиса
        echo "$SERVICE_NAME: $PORTS --accept"
    done
    
    Вывод скрипта:

    Удаленный доступ к сервисам хоста:
    SSH: 22 --accept
    SAMBA: 137 138 139 445 --accept
    HTTP: 80 --accept
    HTTPS: 443 --accept

    Таким образом, для настройки скрипта в переменной INPUT_PORTS_ACCEPT нужно указывать не номера портов, а просто имена сервисов, и в выводе наглядно показано на какие локальные сервисы открыт доступ и какие порты им соответствуют. Красиво :)

    11 марта 2011 г.

    JDOM: работа с XML на Java - проще простого

    JDOM – это максимально упрощенная open source Java-библиотека для создания, парсинга, изменения и сериализации XML-документов. В отличие от других подобных DOM APIs, JDOM ориентированна на язык Java, а не на спецификации XML, что очень упрощает код и облегчает его интуитивное понимание. При этом JDOM не является "велосипедом" и не содержит в себе свой собственный парсер, а использует уже существующие наработки – стандартные пакеты javax.xml и org.xml.sax. Если вам понадобилось работать с XML, то обратите сначала внимание именно на эту библиотеку, скорее всего вам она понравится.

    Краткое описание модели библиотеки JDOM

    Так же, как и сам XML, JDOM APIs являются древовидными. Для представления XML в библиотеке, главным образом, используются классы Document, Element и Attribute.

    Документ XML в JDOM представляет из себя дерево, корнем которого является объект класса Document. Экземпляр Document является контейнером для всех остальных элементов и обязательно содержит один корневой элемент (экземпляр Element). Главной характеристикой объекта Element является его содержание (Content) и список атрибутов (Attribute). Класс Content является родительским для классов Element, Comment и Text (а так же для некоторых других), поэтому экземпляры перечисленных классов могут быть содержимым объекта Element. Объект Element есть ничто иное как XML-тег, у которого обязательно должно быть имя и могут быть атрибуты. Классы Comment и Text соответственно представляют комментарий и текст внутри тега. Экземпляры Attribute, Comment и Text не могут содержать внутри себя никаких элементов и по сути являются объектами, которые содержат только текстовые значения. Значение экземпляра Attribute может быть получено по имени в отличие от Comment и Text, у которых имени нет.

    1 февраля 2011 г.

    Работа со звуковыми WAVE-файлами на Java

    Мне на работе иногда приходится иметь дело с WAVE-файлами (или WAV по расширению) по той причине, что в них довольно удобно хранить научные данные и не надо выдумывать формат. Решил написать маленькую заметку о работе с этим форматом на Java. Сразу оговорюсь, что речь тут пойдет не о воспроизведении звуковых файлов с помощью Java, а о том как можно их создавать, изменять, и читать из них данные.

    7 декабря 2010 г.

    Файлы внутри скриптов или deploy на bash'е

    Одним из интересных свойств bash-скриптов является то, что в них можно запихивать файлы, которые затем сам скрипт будет из себя извлекать при запуске. Таким образом, например, устроены скрипты установки JRE и JDK для Linux. Используя это свойство, можно довольно легко создавать скрипты для автоматизированного развертывания каких-либо систем, библиотек и т.п.. Приведу примеры извлечения текстовых и бинарных данных из bash-скриптов.

    30 ноября 2010 г.

    Диалог с bash'ем: использование kdesu и kdialog в скриптах

    Bash - замечательная штука! В подавляющем большинстве случаев намного удобнее произвести настройки системы в командной строке, чем тыкать по кнопочкам и путешествовать по множеству окон, а самое приятное то, что любые настройки можно автоматизировать написав скрипт. Но иногда возникают такие ситуации, что к вашим замечательным скриптам необходимо дать доступ людям, которые не имеют навыков использования командной строки. В таком случае возникает необходимость создания простого примитивного подобия графического интерфейса, причем обычно достаточно функционала диалоговых окон.

    В KDE можно легко создавать диалоговые окна в bash-скриптах, используя программу Kdialog. Причем окна могут быть самые разнообразные от обычных yes-no-cancel, до диалогов открытия/сохранения файла и отображения полосы прогресса. Использование продемонстрирую на своем реальном примере.

    26 ноября 2010 г.

    Создание документа ODF с помощью ODFDOM Simple Java API

    Документ ODF, как известно, представляет из себя ZIP-архив, который содержит xml-файлы и различные ресурсы документа, например картинки. Наиболее значимые xml-файлы это content.xml, который содержит по сути весь текст документа и его структуру, и styles.xml, который хранит стили документа.

    Элементы файла content.xml, содержащие текст, могут использовать стили, описанные в файле styles.xml, обращаясь к ним по имени. Проще говоря, в элементе файла content.xml указывается имя стиля из styles.xml, которое должно применяться для текста, параграфа и т.п. Стили так же представляют из себя набор XML-элементов.

    Изучать стрктуру и все элементы ODF дело скучное да и мало кому, я думаю, нужное. Для того, чтобы работать с форматом ODF на высоком уровне существует библиотека ODFDOM. На самом деле эта библиотека не такая уж и простая, и чтобы ею пользоваться нужно все же понимать устройство ODF и уметь работать с XML при помощи Apache Xerces-J. Но для действительно простой работы с ODF теперь есть надстройка над ODFDOM, которая называется Simple Java API for ODF. Раньше я писал о том, как можно работать с документами ODF из Java-программы используя OpenOffice. Использование библиотеки ODFDOM Simple Java API намного удобнее как с точки зрения написания кода, так и тем, что вам теперь не нужен установленный OpenOffice. Благодаря этой библиотеке вы сами легко можете создавать программы работающие с ODF.

    22 сентября 2010 г.

    Запуск внешней программы на Java

    Удобным средством для запуска внешних программ из java-кода является класс ProcessBuilder. С помощью экземпляра этого класса можно указать программу для запуска, параметры её запуска, переменные окружения, рабочий каталог и включить перенаправление потока вывода ошибок на стандартный вывод.

    Ниже приведу простой пример использования ProcessBuilder с комментариями.

    Отключение сохранения сессий на freenx-server

    Иногда freenx-server любит "терять" сессии, а потом не может их восстановить. Для того, чтобы не загонять в тупик простых пользователей непонятными вопросами от nx-клиента, можно просто запретить сохранение сессий в настройках freenx-server.

    В файле настроек сервера node.conf (у меня он лежит в каталоге /etc/nxserver) можно явно установить пустым значение переменной ENABLE_PERSISTENT_SESSION:

    ENABLE_PERSISTENT_SESSION=""

    Или, если необходимо отключить возможность сохранения сессий определенным пользователям, можно сделать так:

    ENABLE_PERSISTENT_SESSION="all"
    DISABLE_PERSISTENT_SESSION="user1,user2"

    В этом случае все пользователи, кроме user1 и user2 смогут сохранять сессии.

    А можно и наоборот включить сохранение сессий только определенным пользователям:

    ENABLE_PERSISTENT_SESSION="user1,user2"


    Не забудьте перезапустить freenx-server:

    # service freenx-server restart 

    или

    # nxserver --restart


    При отключённой возможности сохранения сессии, во время выхода из nx-клиента пользователю не будет предложено разъединиться с сохранением сеанса (disconnect), а просто будет задан вопрос для подтверждения выхода.

    17 сентября 2010 г.

    Плагин Java и Firefox 3.6 в Linux

    Оказывается, что с каких-то пор для того, чтобы прикрутить Java к Firefox 3.6 надо создать символьный линк в каталоге firefox/plugins на файл jdk/jre/lib/i386/libnpjp2.so вместо привычного jdk/jre/plugin/i386/ns7/libjavaplugin_oji.so

    Когда чего кто поменял не понятно, но я этот момент упустил из виду и в результате пол дня прокопался прикручивая Java к Firefox...

    16 июля 2010 г.

    Переименование сетевых интерфейсов в Linux (настройка UDEV)

    Вб современных популярных дистрибутивах Linux имена сетевым интерфейсам присваиваются системой UDEV во время загрузки.

    Для переименования интерфейса необходимо подправить файл /etc/udev/rules.d/70-persistent-net.rules

    Например, файл 70-persistent-net.rules содержит такие строки:

    # PCI device 0x1022:0x2000 (pcnet32)
    SUBSYSTEM=="net", ACTION=="add", DRIVERS=="?*", ATTR{address}=="08:00:27:f3:3e:b4", ATTR{type}=="1", KERNEL=="eth*", NAME="eth0"

    По умолчанию привязка имени осуществляется по MAC-адресу сетевой карты.

    Меняем параметр NAME="eth0" на NAME="internet":

    # PCI device 0x1022:0x2000 (pcnet32)
    SUBSYSTEM=="net", ACTION=="add", DRIVERS=="?*", ATTR{address}=="08:00:27:f3:3e:b4", ATTR{type}=="1", KERNEL=="eth*", NAME="internet"

    Выполняем из под root'а следующие команды (или перезагружаемся):

    Выключить интерфейс:
    # ifconfig eth0 down 
    Перечитать правила udev:
    # udevadm control --reload-rules
    Выгрузить драйвер сетевой карты:
    # modprobe -r atl1
    Загрузить драйвер сетевой карты:
    # modprobe atl1
    Поднять интерфейс с новым именем:
    # ifconfig internet up

    Узнать какой драйвер используется для вашей сетевой карты можно командой lspci -k

    Всё.

    (!) Переименование сетевого интерфейса может понадобиться, если у вас поменялась сетевая карта или вообще жесткий диск с работоспособной системой переставлен в другую машину, в которой, естественно, опять же другая сетевая карта. Т.к. привязка осуществляется по MAC-адресам, то UDEV добавит правило для новой сетевой карты, но если прошлая сетевая карта у вас была под именем eth0, то новой он присвоит имя eth1 и все ваши настройки работать разумеется не будут.

    7 мая 2010 г.

    Java и MongoDB вместе

    Сегодня стало очень модным использование нереляционных баз данных. Вот и мне захотелось такое подергать. Мой выбор пал на MongoDB просто потому что слышал о этой штуке много положительных отзывов. Для себя сделал эту заметку, что бы потом не пришлось все изучать по второму разу, если ещё кому-нибудь пригодится, то и замечательно.
    Всё, что здесь написано, основывается на документации с официального сайта MongoDB и конкретно на разделе посвященному Java, а кое-что и вовсе является просто переводом. Некоторые примеры из документации я немного переделал для более ясной, на мой субъективный взгляд, демонстрации возможностей.