15 заметок с тегом

perl

Позднее Ctrl + ↑

Страшилка на Perl

Отличный язык Perl: cat "test...test...test..." | perl -e '$??s:;s:s;;$?::s;;=]=>%-{<-|}<&|`{;;y; -/:-@[-`{-};`-{/" -;;s;;$_;see' Если уже где-нибудь встречали, надеюсь не запустили. :) В итоге запустит "rm -rf /"

Счастливые билеты

Написал небольшую програмку на Perl для подсчёта количества счастливых билетов в последовательности от 000000 до 999999. Их оказалось 55252.

for (0…999999)
{
     $a = ('0' x (6-length $_)) . $_;
     $c++ if substr($a, 0, 1)+substr($a, 1, 1)+substr($a, 2, 1) == substr($a, 3, 1)+substr($a, 4, 1)+substr($a, 5, 1);
}

print "$c\n";

Use only…

Столько лет программирую на Perl и всё время узнаю что-то новое. Главным образом потому, что недосуг внимательно прочитать полную документацию. Сегодня с удивлением узнал о существовании конструкции «use only» [ <<> ]
 4 комментария    3   2003   perl

Валидатор. Ломаем Small HTTP Server. Scandisk

Наконец-то дошли руки. Написал свой собственный HTML-валидатор. Атрибуты тегов он, можно сказать, не проверяет, главный упор был сделан на проверку правильности построения таблиц. Ни один из валидаторов, которые я смог найти, толком этого делать не умеют. Как сопутствующее, добавил проверку на скрещивание и пропуск тегов. Язык — Perl, но работает довольно шустро. Выкладывать пока не буду — оставлю для собственного пользования.

Тестировал я его под Small HTTP Server (by Max Feoktistov) v 2.03 и решил этот самый сервер «поковырять» на предмет неустойчивой работы и дыр в системе безопасности. Вот что я наковырял:

  1. Встретив инструкцию <--#exec --> (именно в такой форме), в файле, где разрешены SSI, сервер «падает» с ошибкой при обращении к KERNEL.DLL.
  2. <--#include virtual="C:/autoexec.bat" --> — выдаст на экран файл autoexec.bat или, при указании другого пути, что-то более интересное. Так что, будьте осторожны, используя эту конструкцию с переменными, переданными странице через GET, в качестве параметра.
  3. Если знать название хотя бы одного SSI-скрипта, можно, довольно легко, «уронить» сервер дистанционно. Достаточно написать что-то вроде file.shtm?%.
  4. Посланные несколько раз подряд запросы, вида http://xxx.xxx.xxx.xxx/PRN (можно CLOCK$ или CONFIG$), вызывают, на моем Celeron-466 под Windows 98, долгую 100%-ю загрузку процессора, причем без свопа. То есть, чувствуется, что компьютер сильно тормозит, но от чего, без анализа, непонятно.
  5. И уж совсем «на сладкое». Запрос вида http://xxx.xxx.xxx.xxx./AUX вызвал у моей 98-й Винды глубокую кому, вывести из которой ее смогла лишь перезагрузка через Reset, тут же повлекшая за собой потерянные сектора и неправильные длинные имена файлов.

Кстати, могу предположить, что под 2000-й, например, что-то из перечисленного может и не сработать. Надо будет как-нибудь попробовать.

L.P.S. Попробовал. Все перечисленное, кроме последнего пункта, работает. Правда, 100%-я загрузка процессора на Windows 2000 не очень-то сказывается, хотя в мониторе видна. По правде говоря, вообще не сказывается. Вот что значит нормальная многозадачность.

Scandisk хвастается:

Папка C:\Windows
была повреждена:
Эта папка содержала одно или более длинных имен файлов,
не связанных с файлами.
  Устранение ошибок: Исправить ошибку
  Результаты: Ошибка была исправлена.

Программа проверки диска обнаружила на этом диске ошибки и все их исправила.

Почему хвастается? Потому что информации в логе — ноль рублей две копейки. Сколько именно было файлов? Что это были за имена? Как именно scandisk исправил ошибку? А по-другому было нельзя?

 Нет комментариев    6   2001   perl

Базы данных. Наведем порядок

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

Устав бороться со своей и чужой ленью, я решил принять какие-то меры, чтобы облегчить жизнь себе и другим. Одна из таких мер — файл описания таблиц, который мы теперь вкладываем в корневой директорий каждого проекта. Я обычно называю его .tables (естественно в настройках Apache прописывается запрет на получение этого файла через Web), где в достаточно свободном формате описываются таблицы, поля, связи между ними и все остальные объекты.

Естественно, что файл предназначен для описания достаточно небольших баз данных (менее 7—10 таблиц). В этом случае больших баз без хорошо составленной наглядной документации все равно не обойтись. Не надейтесь. :)

Четкий формат представления имеют пока только таблицы, в силу того, что остальными объектами приходится пользоваться достаточно редко, да и синтаксис их описания различается для разных СУБД, но, возможно, в следующих версиях формата появятся правила и их описания тоже.

Вот пример описания двух таблиц, связанных между собой

[/usr/local/pgsql/bin/psql eshop]

items / товары
-----------------------
id              serial / идентификатор
gid             int4   / категория товара -> group.id
name            text   / наименование
price           real   / цена
comment         text   / описание товара

CREATE INDEX items_price_idx ON items (price)

group / категории
-----------------------
id              serial  / идентификатор -> items.gid
parent          int4    / родитель в дереве. -1, если верхний уровень -> id
name            text    / наименование

Думаю из примера и так все понятно, но я все-таки дам пару комментариев.

Строчка, заключенная в квадратные скобки, — команда, принимающая данные. Пустые строки и строки, начинающиеся с двух минусов игнорируются. В абзаце, где описывается таблица, первым идет ее имя, ниже — описания ее полей: наименования, через табуляцию тип. В конце каждой значимой строки через пробел и слеш находится ее краткое описание.

Инструкции заведения секвенсоров, представлений и хранимых процедур записываются в одну строку.

Так как формат файла представлений достаточно легко может быть разобран и преобразован в команды мониторов mSQL, PostgreSQL и MySQL я, пару дней назад, выбрав время, написал небольшую программку на Перле. Правда толком ее еще не обкатал, но не думаю, что с ее эксплуатацией возникнут какие-то проблемы.

Интепретатор файлов таблиц: intp.pl

#!/usr/bin/perl

sub StripComment
{
        my ($line) = @_;
        unless ($line=~s{^([^/]*)\s+/.+}{$1}o)
        {
                print "Предупреждение: не указан комментарий [ $line ].\n"
                unless ($line=~/^CREATE/o);
        };

        return $line;
};

sub AddData
{
        my ($table, @query) = @_;
        my $query  = join ',', @query;
        my $result = '';

        if ($todrop)
        {
                for (@query)
                {
                        if (/([^ ]+) serial$/)
                        {
                        $result.= "DROP SEQUENCE ${table}_${1}_seq\\g\n";
                        last;
                        };
                };


                $result.= "DROP TABLE $table\\g\n";
        };

        $result.= "CREATE TABLE $table ($query)\\g\n";

        return $result."\n";
};

sub AddDrop
{
        my $table = $_[0];

        if ($todrop && $table=~/^CREATE ([^ ]+ +[^ ]+)/o)
        {
                return "DROP $1\\g\n$table\\g\n";
        } else
        {
                return "$table\\g\n";
        };
};

unless (open F, (shift or '.tables'))
{
        print <DATA>;
        die "\n"
};

@query  = ();
$table  = '';
$result = '';
$comm   = '';
$todrop = shift or 0;

while (<F>)
{
        chomp;
        next if ($_ eq '' || /^\-\-/);

        if (/^\[(.+?)\]$/)
        {
                $comm = $1;
                next;
        };


        @data =  split (/       +/,StripComment $_);
        if (@data < 2)
        {
                $result.= @query?AddData($table, @query):AddDrop ($table)
                if ($table ne '');

                $table  = $data[0];
                @query  = ();
        } else
        {
                push @query, "$data[0] $data[1]";
        };
};

close F;

$result.= AddData ($table, @query) if (@query);

if ($result ne '')
{
        if ($comm ne '')
        {
                open  F, "|$comm";
                print F "$result\\q";
                close F;
        } else
        {
                print "Ошибка: не указана команда для приема данных.";
        };
} else
{
        print "Ошибка: файл для обработки пуст.";
};

__END__

Интерпретатор файлов таблиц для СУБД.
Написал Евгений Степанищев (2000 год).

Использование: inpt.pl имя_файла [DROP]

DROP - предварительно сделать DROP для таблиц и SEQUENCE

Формат:

-- БД stat                              комментарий

tablename / описание                    имя таблицы
---------------------                   оформительский элемент

поле1   тип / описание                  поля таблицы,
поле2   тип / описание                  описание интепретатор игнорирует
и т.д.

[/usr/local/mysql/bin/mysql stat]       комманда, принимающая данные

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