Автор Тема: Обработка данных из формы и прочая...  (Прочитано 5395 раз)

0 Пользователей и 1 Гость просматривают эту тему.

Оффлайн Phoinix

  • RW
  • Ветеран
  • *****
  • Сообщений: 1097
  • +0/-0
  • 2
    • Просмотр профиля
    • http://phoinix.ucoz.ru
Хочется узнать мнение остальных специалистов о новом "велосипеде" на тему обработки данных из формы (+ URI и Cookies)

Модуль получился на редкость небольшой, но при этом не проиграл в функциональности:

package My::CGI;
use strict;
use IO::File;
our $VERSION = \'1.1.0\';

sub new {
    my ($self, %common) = @_;
    $self = {
             max_upload     => 262144,  # Default 256 Kb
             data           => {},
             cookies        => {},
             tmp            => {},
            };
    $self->{\'max_upload\'} = $common{\'MAX_UPLOAD\'} if $common{\'MAX_UPLOAD\'};
    $self = &_parse_common_data($self);
    bless $self;
    return $self;
}

sub param {
    my ($self, $param) = @_;
    unless ($self->{\'data\'}->{$param}) {return undef}
    my $data = $self->{\'data\'}->{$param};
    return wantarray ? (ref $data ? @$data : ($data)) : (ref $data ? $data->[0] : $data)
}

sub file {
    my ($self, $param) = @_;
    my $data;
    unless ($self->{\'tmp\'}->{$param}) {return undef}
    $data = IO::File->new($self->{\'tmp\'}->{$param});
    return $data
}

sub cookies {
    my ($self, $param) = @_;
    return $self->{\'cookies\'}->{$param} || undef;
}

sub _parse_common_data {
    my $self = shift;
    if ($ENV{\'QUERY_STRING\'}) {$self = &_parse_QUERY_STRING($self, \'GET\')}
    if (uc($ENV{\'REQUEST_METHOD\'}) eq \'POST\') {
        if(exists($ENV{\'CONTENT_TYPE\'}) && $ENV{\'CONTENT_TYPE\'}=~m|^\\s*multipart/form-data|i) {$self = &_parse_MultiPart($self)}
        else {$self = &_parse_QUERY_STRING($self, \'POST\')}
    }
    if ($ENV{\'HTTP_COOKIE\'} || $ENV{\'COOKIE\'}) {$self = &_parse_COOKIES($self)}
   
    return $self
}

sub _parse_QUERY_STRING {
    my ($self, $type) = @_;
    my $data;
    if ($type && $type eq \'POST\') {read(STDIN, $data, $ENV{\'CONTENT_LENGTH\'})}
    else {$data = $ENV{\'QUERY_STRING\'};}
    my @pairs = split(/[\\?\\&]/,$data);
    foreach (@pairs) {
        my ($param, $value) = split(\'=\',$_,2);
        next unless $param && $value;
        $param = URLDecode($param);
        $value = URLDecode($value);
       
        $self = &_include_data($self, $param, $value);
    }
    return $self
}

sub _parse_MultiPart {
    my $self = shift;
    if ($ENV{\'CONTENT_LENGTH\'} > $self->{\'max_upload\'}) {return}
    binmode STDIN; my ($spliter, $end, $data);
    read(STDIN, $data, $ENV{\'CONTENT_LENGTH\'});
    ($spliter, $end, $data) = $data =~m /^([^\\r\\n]+)([\\n\\r]+)(.*?)\\2\\1\\-\\-\\2*$/s;
    srand;
    foreach my $block (split($end.$spliter.$end, $data)) {
        my ($header, $content) = split($end.$end, $block, 2);
        my ($param, $data);
        foreach my $line (split(/($end)|(\\s*\\;\\s*)/,$header)) {
            my ($name, $value) = split(/\\=|\\:\\s/,$line, 2);
            if ($name eq \'name\') {($param) = $value =~/^\\"(.*)\\"$/}
            if ($name eq \'filename\') {($data) = $value =~/^\\"(.*)\\"$/}
        }
        if ($data) {
            $self->{\'data\'}->{$param} = $data;
            my $temp_file = \'./COME_\'.int(rand 100000).\'.tmp\';
            open (UPL, \'>\', $temp_file);
                binmode UPL;
                print UPL $content;
            close UPL;
            $self->{\'tmp\'}->{$param} = $temp_file;
        } else {
            $self = &_include_data($self, $param, $content);
        }
    }
    return $self
}

sub _parse_COOKIES {
    my $self = shift;
    my $cookies = $ENV{\'HTTP_COOKIE\'} || $ENV{\'COOKIE\'};
    foreach my $line (split(/\\;\\s*/,$cookies)) {
        my ($param, $value) = split(\'=\',$line, 2);
        next unless $param && $value;
        $self->{\'cookies\'}->{$param} = $value;
    }
    return $self
}

sub _include_data {
    my ($self, $param, $value) = @_;
   
    $value =~s /(\\x0d\\x0a)|(\\x0a\\x0d)/\\n/sg;
    if (exists $self->{\'data\'}->{$param}) {
        if (ref $self->{\'data\'}->{$param}) {push @{$self->{\'data\'}->{$param}}, $value}
        else {$self->{\'data\'}->{$param} = [$self->{\'data\'}->{$param}, $value]}
    } else {
        $self->{\'data\'}->{$param} = $value
    }
    return $self
}

sub URLDecode {my $s = shift; $s =~tr /+/ /; $s =~s /%([0-9A-Fa-f]{2})/chr(hex($1))/esg; return $s }

sub DESTROY {
    my $self = shift;
    foreach (values %{$self->{\'tmp\'}}) {unlink $_}
    return 1
}

1;


Работа с ним, практически как с CGI:

use My::CGI;
my $query = new CGI;
my $value = $query->param(\'param\');
my $filehandle = $query->file(\'param\');
my $cookies = $query->cookies(\'name\');

Что скажете?
« Последнее редактирование: 11 Марта 2005, 22:29:47 от Phoinix »

Оффлайн arto

  • Ветеран
  • *****
  • Сообщений: 699
  • +0/-0
  • 2
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #1 : 13 Марта 2005, 20:16:58 »
не обработает "http://perlmonks.org/?displaytype=print;node_id=431702".
стандарты, что ли, почитали-бы...

Оффлайн Phoinix

  • RW
  • Ветеран
  • *****
  • Сообщений: 1097
  • +0/-0
  • 2
    • Просмотр профиля
    • http://phoinix.ucoz.ru
Обработка данных из формы и прочая...
« Ответ #2 : 14 Марта 2005, 15:59:26 »
arto
Цитировать
стандарты, что ли, почитали-бы...

Спасибо почитаю, а заодно, что бы долго не искать, подскажите в каком RFC почитать? что в HTTP, QUERY_STRING в URL разделяется не только амперсантом?

P.S. На гугле тоже "самые умные"?

http://www.google.ru/webhp?hl=ru&q=rfc+2068&lr=
http://www.google.ru/webhp?hl=ru;q=rfc+2068;lr=
« Последнее редактирование: 14 Марта 2005, 16:50:53 от Phoinix »

Оффлайн arto

  • Ветеран
  • *****
  • Сообщений: 699
  • +0/-0
  • 2
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #3 : 14 Марта 2005, 19:22:23 »
RFC 2616

Оффлайн ondr

  • Модератор
  • Глобальный модератор
  • Старожил
  • *****
  • Сообщений: 440
  • +0/-0
  • 0
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #4 : 14 Марта 2005, 19:39:12 »
rcf 2616 этого не определяет
а определяет спецификация html относительно форм http://www.w3.org/TR/html401/interact/forms.html
и ";" в роли разделителя там не используется, также как и ни один из популярных броузеров их не использует при обработке форм.
0 OK, 0:1

Оффлайн Phoinix

  • RW
  • Ветеран
  • *****
  • Сообщений: 1097
  • +0/-0
  • 2
    • Просмотр профиля
    • http://phoinix.ucoz.ru
Обработка данных из формы и прочая...
« Ответ #5 : 14 Марта 2005, 19:43:11 »
arto

Мудро... А можно поточнее... в каком разделе искать, ибо я при беглом просмотре в части касающейся, подобного не увидел... :(

Оффлайн arto

  • Ветеран
  • *****
  • Сообщений: 699
  • +0/-0
  • 2
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #6 : 14 Марта 2005, 20:03:05 »
sorry, rfc 2396,
less -p "3. URI Syntactic Components"

Оффлайн ondr

  • Модератор
  • Глобальный модератор
  • Старожил
  • *****
  • Сообщений: 440
  • +0/-0
  • 0
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #7 : 14 Марта 2005, 20:19:33 »
arto
rfc 2396 тоже не определяет то, как должны компоноваться данные из форм. Я уже дал ссылку на документ

Относительно точки с зяпятой: одинственное упоминание есть в "аппендиксе" к html спецификации и носит рекомендательный характер как один из вариантов избежания проблем с амперсандом.

IMHO: Поддерживать ли ";" или нет вопрос спорный и как решит Phoinix так и будет правильно.
0 OK, 0:1

Оффлайн Phoinix

  • RW
  • Ветеран
  • *****
  • Сообщений: 1097
  • +0/-0
  • 2
    • Просмотр профиля
    • http://phoinix.ucoz.ru
Обработка данных из формы и прочая...
« Ответ #8 : 14 Марта 2005, 20:23:50 »
Самое интересное, что в модуле CGI действительно в качестве разделителя используетя как "&" так и ";", причины мне лично так и не известны (В других альтернативных модулях используется только "&", я думаю, они то знали что писали...).

Оффлайн arto

  • Ветеран
  • *****
  • Сообщений: 699
  • +0/-0
  • 2
    • Просмотр профиля
Обработка данных из формы и прочая...
« Ответ #9 : 16 Марта 2005, 12:25:29 »
в 2396 определяются разделители uri, в число коих входит и \';\'

Оффлайн Phoinix

  • RW
  • Ветеран
  • *****
  • Сообщений: 1097
  • +0/-0
  • 2
    • Просмотр профиля
    • http://phoinix.ucoz.ru
Обработка данных из формы и прочая...
« Ответ #10 : 16 Марта 2005, 13:04:50 »
arto
Чеcтно говоря спор на пустом месте:

    my @pairs = split(/[\\?\\&\\;]/,$data);

На этом все изменения заканчиваются...

 

Sitemap 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28