вторник, апреля 21, 2015

Агрегатор статей про Go в рунете

Запилил сайт http://planetgo.ru, который подтягивает и отображает новые статьи про язык Go, написанные в рунете.
Сделано по аналогии с сайтом planetperl.ru.
Пока среди источников только хабр, но уже на подходе пара сайтов, на которых периодически всплывают статьи про Go.

Сам сайт написан на перле с mojo. В отдалённом будущем возможно перепишу на Go

среда, марта 04, 2015

запилил плагин для моджо

Написал плагин для добавления в Mojolicious моделей(Model из MVC), похожих в работе на модели веб-фреймворка Catalyst.
По схеме подключения модели в моджо написал статью в прагматикперл.
Плагин автоматически создаёт папку Model в проекте и автоматом генерит в это папке модуль Base.pm, который будет являться родительским для остальных моделей. Генерация папки, использование базовой модели и имя базовой модели регулируются опциями при подключении плагина.
Сам модуль -  Mojolicious::Plugin::BModel
Имя 'Mojolicious::Plugin::Model' заняли буквально за пару дней до меня. Не зря говорят, что умные идеи приходят разным людям одновременно))

В настоящий момент занимаюсь написанием более внятной доки к модулю и тестами. Пользоваться можно уже сейчас.

среда, октября 22, 2014

.vimrc

Чтобы не искать, буду держать его тут.
runtime! debian.vim
syntax on
set hls
set tabstop=4
set shiftwidth=4
set smarttab
set et
" переносить длинные строки
set wrap
" наследовать отступы предыдущей строки
set autoindent
" умные отступы на основе синтаксиса
set smartindent
"подсветка любых пробелов на конце строки
au BufNewFile,BufRead * let b:mtrailingws=matchadd('ErrorMsg', '\s\+$', -1)
"подсветка табуляций, перед которыми или после которых есть пробелы
au BufNewFile,BufRead * let b:mtabbeforesp=matchadd('ErrorMsg', '\v(\t+)\ze( +)', -1)
au BufNewFile,BufRead * let b:mtabaftersp=matchadd('ErrorMsg', '\v( +)\zs(\t+)', -1)
" не разрешать курсору выходить за последний символ при выделении
set selection=old

if filereadable("/etc/vim/vimrc.local")
  source /etc/vim/vimrc.local
endif
set tabpagemax=15
map <F4> <Esc>:tabnext<CR>
map <F3> <Esc>:tabprevious<CR>
map <F5> <C-W>p
map <F6> <C-W>w

вторник, октября 21, 2014

Смена работы

Сменил место работы. Сегодня был первый день на новом месте.
Теперь на работу приходится как и всем, добираться транспортом. До этого полтора года работал удалённо из дома.
Эти полтора рабочих года были моим лучшим временем работы. Очень хороший и профессиональный коллектив, очень отзывчивые и приветливые коллеги.
"РЕГ.РУ", ты навсегда в моём сердце.

Python. Первое знакомство

Пересилил себя, начал знакомиться с языком программирования Python. Для знакомства выбрал третью версию, т.к. вторая, судя по новостям, хоть и является довольно популярной, но всё-же со временем отомрёт.

Что ж, в сравнении с перлом некоторые вещи даются "сложно". Не в плане сложности для понимания(синтаксис языка довольно простой, если не сказать примитивный), а в плане принятия.

Тем не менее, процесс идёт, некоторые вещи уже даже начали нравиться и приятно удивлять. Например, сумма чисел фибоначчи для 30 на третьем питоне выполняется примерно вдвое быстрее чем на перле 5.18.

Уже есть в уме пара проектов, которые буду писать на пайтоне.

среда, сентября 03, 2014

Perl. Не используйте конструкцию "return $a or $b"

На компе недавно обновился перл до версии 5.20 и в рабочем коде словил варнинг "Possible precedence issue with control flow operator". Гугление показало, то, оказывается, перл код вида
sub mysub {
    my ( $a, $b ) = @_;
    return $a or $b;
}
интерпретатором будет воспринят как
sub mysub {
    my ( $a, $b ) = @_;
    ( return $a ) or $b;
}
т.е. функция/метод всегда будет возвращать $a в не зависимости от того, истиннен он или ложен. Поэтому в данном случае надо использовать оператор || вместо or хотя я всегда считал, что два обозначения одного и того же оператора. И в итоге наша функция будет выглядеть так:
sub mysub {
    my ( $a, $b ) = @_;
    return $a || $b;
}

воскресенье, июля 06, 2014

Next Gen PBX

Возвращаюсь к теме создания софта для ip-телефонии. Тема для меня не перестала быть интересной даже спустя год после смены деятельности с администрирования на программирование.
Уже больше года вынашиваю идею создания платформы для ip-телефонии с реализацией виртуализации на уровне самой платформы. Т.е., например, есть оператор связи мелкой или средней руки, который получил лицензию на телематические услуги и взял у ФАС пул городских номеров. И вот хочется этому оператору со своих клиентов стричь деньги не только за предоставление городского номера и телефонных линий, а, например, за услугу виртуальной АТС. Это чтобы клиент вообще не заморачивался с оборудованием, а только купил/взял в аренду телефонные аппараты.
И вот тут выходит на сцену платформа для предоставления услуг виртуальных АТС. Таких решений на рынке пока немного и все они, как правило, платные и очень(просто космически) дорогие или топорно сделанные(или и то и другое). Я хочу создать опенсорсную систему на базе IP PBX FreeSWITCH. Выбор данной pbx(а не того же астериска) обусловлен некоторыми факторами, главными из которых являются более серьёзный подход к разработке системы(этой мой взгляд со стороны), использование в качестве SIP-модуля библиотеки sofia, возможность(вроде как неиллюзорная) использовать платы расширения digium|sangoma|openvox, ну и вообще, за 8 лет астериск уже как-то поприелся, хочется чего-то свежего.
В настоящий момент пилю систему для аудио-конференций, планирую в будущем включить данную систему в состав телефонной платформы. Сейчас же просто, как проба пера, чтобы сформировать окончательный образ будущей системы и понабивать себе руку в написании кода асинхронного приложения.

среда, июля 02, 2014

Perl. Добавляем инкапсуляцию методам класса

Перл - замечательный язык с очень простой и понятной ООП-парадигмой. Из коробки мы имеем полиморфизм и наследование, но, к сожалению, не можем похвастаться инкапсуляцией.
Инкапсуляция, для тех кто не знаком с терминами, это сокрытие методов класса от посторонних лиц. Другими словами, мы в классе создаём различные методы, часть из которых доступна для вызова другими модулями/скриптами. Другая часть не должна быть вызвана нигде, кроме как в самом классе(private-метод) или в классе, который наследуется от данного класса(protected-метод).
В перле, как и в питоне, нельзя штатными средствами перекрыть доступ к методам класса. Применяется негласное соглашение, по которому методы(или функции), имена которых начинаются с нижнего подчёркивания, считаются приватными.

С этим в принципе можно мириться и ваять код на pure-перл, не прибегая к ООП-фреймворкам типа Moose, что я в принципе всегда и делал - меня слегка пугает перспектива тянуть в своё приложение 100500 модулей ради одного функционала.
К счастью, благодаря статье в журнале pragmaticperl я узнал о модуле Attribute::Protected. Данный модуль написал Tatsuhiko Miyagawa, очень известный разработчик в мире Perl.
Модуль достаточно легковесный и имеет в зависимостях только Attribute::Handlers, который давно является модулем ядра perl.
Рассмотрим на примере, как можно с помощью указанного модуля добавить в наш класс инкапсуляцию.
Для наглядности создадим 2 модуля и один скрипт, который будет вызывать оба модуля. Один модуль будет наследоваться от другого.

MyModuleParent.pm :
package MyModuleParent;

use strict;
use warnings;
use Attribute::Protected;

sub new {
    my $class = shift;

    return bless {}, $class;
}

sub _private_method : Private {
    print "This is private method in package " . __PACKAGE__ . "\n";
}

sub _protected_method : Protected {
    print "This is protected method in package " . __PACKAGE__ . "\n";
}

sub public_method {
    print "This is public method in package " . __PACKAGE__ . "\n";
}

1;

MyModule.pm :
package MyModule;

use strict;
use warnings;

use parent 'MyModuleParent';

sub mymethod {
    print "This is simple method in package " . __PACKAGE__ . "\n";
}

sub call_protect_method {
    my $self = shift;
    $self->_protected_method;
}

sub call_private_method {
    my $self = shift;
    $self->_private_method;
}

1;

script.pl :
#!/usr/bin/perl

use strict;
use warnings;

use MyModule;
use MyModuleParent;

my $parent_object = MyModuleParent->new;
my $object = MyModule->new;

$object->public_method;         # OK
$object->mymethod;              # OK
$object->call_protect_method;   # OK
$object->call_private_method;   # NOT OK

$parent_object->public_method;       # OK
$parent_object->_protected_method;   # NOT OK
$parent_object->_private_method;     # NOT OK
Объект "$object" может вызвать публичный метод класса "MyModuleParent", т.к. от него наследуется класс "MyModule". Также, данный объект вызывает методы "call_protect_method" и "call_private_method", вызывающие в свою очередь protect и private методы класса "MyModuleParent" соответственно. Вызов метода "call_private_method" завершится с ошибкой _private_method() is a private method of MyModuleParent!, вызов метода "call_protect_method" завершится успешно. Прямой вызов из скрипта private и protected методов класса "MyModuleParent"(через объект $parent_object) завершится с ошибкой.

Таким образом, мы получаем малой кровью(а оверхед там действительно ничтожный, проверенно в дебаггере) надёжную инкапсуляцию методов, очень похожую на сишную и явовску, да к тому же сделанную почти полностью на базовых средствах языка. Модулю Attribute::Protected уже 13 лет, удивитильно, что его так мало используют.

воскресенье, июня 29, 2014

yet another conference server

Начал пилить демона для управления аудио-конференциями на базе ip-pbx FreeSWITCH. Сам демон будет выступать прослойкой между пользователями и сервером PBX.
В бытность свою работы с ip-телефонией вцелом и астериском в частности, не раз собирался заняться фрисвичом, да всё как-то руки не доходили и задач соответствующих не было. Зато теперь, в чине разработчика, полёт фантазий в плане приложений для телефонии уносит меня за дальние горизонты)) Специально для этих целей даже c++ начал изучать.
Но пока что пишу на перле и anyevent. Проект ещё в начальной стадии, готово процентов 20.
Думаю, что к осени будет готова хотя бы альфа-версия.

суббота, июня 28, 2014

Perl. Получить в модуле полный путь до файла модуля

Возник давеча такой вопрос: надо было в модуле, в не зависимости от того, кто и откуда его запускает, получать текущий PATH данного модуля.
Инструменты типа FindBin и Cwd не работали, т.к. они показывали путь до скрипта, который использовал данный модуль. Недолгое гугление выдало вот такое решение:
use File::Spec;

my $mod_dir = (File::Spec->splitpath( __FILE__ ))[1];
Вызов
File::Spec->splitpath( __FILE__ )
возвращает массив, в котором первым аргументом является имя файла, а вторым как раз будет полный путь от "/" до модуля.

среда, мая 28, 2014

perl 5.20

Сегодня релизнулся. В perlbrew себе собрал, играюсь.
На ЛОР новость ожидаемо вызвала срач адептов, неосилянтов и простомимопроходящих ))

суббота, апреля 19, 2014

*sh: перевод списка пакетов из стобца в строку

Иногда требуется удалить и вычистить определённый список пакетов, притом, хочется получить и список пакетов по-быстрому и без лишних тыканий мышкой. Например, потребовалось удалить все пакеты, относящиеся к libreoffice. Если делать долго, то сначала надо получить список пакетов командой
dpkg -l | grep libreoffice
потом вручную из списка выбрать пакеты и вставить их в команду удаления. Но есть способ ускорить эту операцию переведя список пакетов, относящихся к libreoffice(или к нужному вам пакету) из столбца в строку воспользовавшись командой
dpkg -l | grep libreoffice | awk '{print $2}' | tr '\n' ' '
данная команда переведёт список пакетов из столбца в строку, которую затем можно вставить в команду aptitude purge

вторник, декабря 10, 2013

Git-шпаргалка


1. Переключиться на удалённую ветку минуя master:
1.1. Для начала обновим список веток на удалённом сервере:
git remote update origin --prune
1.2. Затем переключимся на ветку
git checkout --track origin/<имя ветки>
или для старых версий Git
git checkout -b <имя ветки> origin/<имя ветки>
или так
git checkout master
git pull
git checkout <имя ветки>

2. Убрать файл/папку из индексации
git rm -r --cached FILE
git commit -m "delete file from index"
git push origin master
3. Посмотреть файл командой blame до указанного коммита
git blame commitID~1 filename
4. Удалить ветку на сервере
git push -d origin [имя ветки]
5. Посмотреть историю между коммитами
git log --oneline commitID1..commitID2

вторник, мая 07, 2013

Gnome shell

После очередного обновления дебьяна на ноуте перестал запускаться gdm3. Вместо стартового окна наблюдаю картинку о том, что произошла ошибка. Ну да ладно, мы не пальцем деланные - переключился в консоль, погасил gdm3, стартанул иксы через startx.
Вместо привычного fallback-режима запустился стандартный Gnome Shell. После некоторого времени плевания и матюгов вдруг ощутил, что пользоваться им можно и даже с удовольствием. Да, непривычно устроено расположение элементов, до тех, что раньше запускались с одного щелчка, приходится щёлкать дополнительные разы. Но к этому привыкаешь.
Поставил себе несколько расширений с сайта https://extensions.gnome.org и моё рабочее окружение заиграло новыми красками)
Само оформление мне очень нравится, всё такое плавное и изящное, выглядит гораздо удобнее, нежели compiz в своё время.
В общем, для себя решил, что даже когда починят баг с gdm, на fallback-режим уже не вернусь. Надо идти в ногу со временем)

четверг, апреля 18, 2013

Perl. Сортировка ключей хеш-массива по значениям этих ключей



В процессе выполнения тестовых заданий для новой работы столкнулся с задачей вывода сортированных данных.
Итак, имеем структуру:
$VAR1 = bless( {
                 'DOMAINS' => {
                                'yandex.ru' => 1,
                                'INVALID' => 5,
                                'rambler.ru' => 1,
                                'vk.com' => 1,
                                'mail.ru' => 2
                              }, 
               }, 'MyModule' );
необходимо выводить данные хеш-массива DOMAINS, отсортированные по значениям(values) данного массива.
Недолго думая обратился за ответом к замечательной книге Perl: изучаем глубже, в которой было найдено решение:
foreach my $domain (sort { $self->{DOMAINS}->{$b} cmp $self->{DOMAINS}->{$a} } 
                keys $self->{DOMAINS}) {
        print $domain . "\t" . $self->{DOMAINS}->{$domain} . "\n";
    }
В результате получаем то, что требовалось:
INVALID 5
mail.ru 2
yandex.ru 1
rambler.ru 1
vk.com 1

Perl. Перехват warn'ов и carp'ов



Сейчас немного про перл.
В перле есть замечательная функция eval, которая умеет перехватывать критические ошибки, которые были вызваны die и/или croak. Но эта функция не умеет работать с предупреждениями, которые генерируются с помощью функций warn и carp. Ну и что такого, спросите вы, предупреждения для того и существуют, чтобы информировать пользователя/разработчика о некорректной работе скрипта или модуля. Но порой всё-же требуется, чтобы наш скрипт, написанный на перле, умел перехватывать подобные сообщения, сгенерированные модулями или функциями, чтобы, например, обрабатывать подобные сообщения особым образом.

Отображение киррилицы(cp1251/win1251) в Sublime Text 2


Файлы в редакторе Sublime Text 2 по умолчанию открываются в кодировке UTF8, но иногда требуется работать с файлами, которые были созданы в кодировке cp1251(кодировка, используемая по умолчанию в операционных системах семейства Windows).
Для этих целей вы можете переназначить fallback-кодировку, которую будет использовать сублим текст, если файл не в кодировке UTF8.
Для этой цели откройте меню Preferences -> Settings - Default. В открывшемся окне воспользуйтесь поиском(ctrl-f), найдите строку
"fallback_encoding": "Western (Windows 1252)",
и замените её на
"fallback_encoding": "Cyrillic (Windows 1251)", (запятая в конце строки обязательна!).
Сохраните файл. Отлично! Теперь сублим текст умеет открывать файлы в кодировке cp1251 корректно и ваша жизнь станет чуточку проще)

воскресенье, апреля 14, 2013

Добавление в Sublime Text 2 горячих клавиш для работы с языком Perl


В повседневной работе использую этот замечательный редактор. Всем он хорош - подсветка синтаксиса, скорость работы, автоподстановка. Только сильно не хватало мне горячих клавиш для проверки синтаксиса и запуска скрипта на perl. Sublime Text 2 позволяет в данном случае забиндить на стандартную комбинацию(ctrl-b) только одно действие.
После недолгого гугления было найдено решение, написанное для языка Go и без проблем адаптированное для Perl.
Для начала необходимо создать свой плагин. Для этого открываете Tool->New Plugin. Вводите следующий код:
import sublime, sublime_plugin 
   
class RunBuildCommand(sublime_plugin.WindowCommand): 
    def run(self, build_system): 
        self.window.run_command( "set_build_system", {"file": build_system } )
        self.window.run_command( "build" )

Сохраняете данный плагин под именем RunBuild.py
После этого в папке ~/.config/sublime-text-2/Packages/User создаёте два файла следующего содержания:
~/.config/sublime-text-2/Packages/User/Perl-build.sublime-build :
{
    "cmd": ["/usr/bin/perl", "$file"],
    "file_regex": ".* at (.) line ([0-9])",
    "selector": "source.perl"
}

~/.config/sublime-text-2/Packages/User/Perl-check.sublime-build :
{
    "cmd": ["/usr/bin/perl", "-c", "$file"],
    "file_regex": ".* at (.) line ([0-9])",
    "selector": "source.perl"
}

После этого открываете Preferences->Key Binding - User и добавляете следующие строчки:
[
    {
        "keys": ["alt+c"],
        "command": "run_build",
        "args": {
                "build_system": "Packages/User/Perl-check.sublime-build"
        }
    },
    {
        "keys": ["alt+b"],
        "command": "run_build",
        "args": {
                "build_system": "Packages/User/Perl-build.sublime-build"
        }
    }
]
После этого у вас на комбинациях alt-c и alt-b появляются проверка синтаксиса и выполнение скрипта соответственно.

среда, апреля 10, 2013

Меняю направление деятельности


Решил поменять сферу деятельности, переквалифицироваться в программиста.
Если честно, давно уже думал соскочить с админства, т.к. всё это обслуживание телефонного парка порядком приелось, хочется чего-то нового.
Сегодня(уже вчера, получается) было небольшое собеседование по телефону. Отныне буду перловым разработчиком в одной крупной компании. Для того, чтобы меня окончательно взяли на работу необходимо выполнить 2 тестовых задания. Одно уже сделал, со вторым разбираюсь, курю мануалы по фреймворку catalyst. Но с телефонией я не прощаюсь, хочу лишь подойти к ней с другой стороны, с позиции разработчика. Для этого сейчас активно прокачиваю свои навыки в программировании, в частности, читаю умные книги по C/C++. В общем, посмотрим, что будет дальше. Удачи мне.

понедельник, апреля 08, 2013

Проблема с работой Mantis после обновления Postgresql


Столкнулся на работе с такой неприятностью - после обновления СУБД Postgresql с версии 8.4 до версии 9.1 перестали подгружаться прикреплённые файлы в тикетах мантиса. После того, как спала паника начался судорожный поиск решения проблемы. Был даже запилен трабл-тикет на багтрекере мантиса. Но в итоге всё оказалось проще.
В 9-й версии поменяли формат вывода данных типа bytea. Для того, чтобы решить проблему потребовалось ввести в базе мантиса следующий запрос:
ALTER DATABASE bugtracker SET bytea_output='escape'
Данный запрос устанавливает формат вывода bytea таким же, какой был в версии 8.4. После проделанной процедуры всё успешно заработало.