Редактировать гиперссылки во вложенных тегах, которые не находятся в отдельных строках - PullRequest
0 голосов
/ 31 марта 2010

У меня интересная проблема. Я написал следующий Perl-скрипт для рекурсивного цикла по каталогу, и во всех html файлах для img/script/a тегов выполните следующее:

  • Преобразовать весь URL в нижний регистр
  • Заменить пробелы и% 20 подчеркиванием

Сценарий прекрасно работает, кроме случаев, когда тег изображения обернут тегом привязки. Есть ли способ изменить текущий скрипт, чтобы также иметь возможность манипулировать ссылками на вложенные теги, которые не находятся в отдельных строках? В основном, если у меня есть <a href="..."><img src="..."></a>, скрипт только изменит ссылку в теге привязки, но пропустит тег img.


#!/usr/bin/perl

use File::Find;

$input="/var/www/tecnew/";

sub process {
        if (-T and m/.+\.(htm|html)/i) {
                #print "htm/html: $_\n";

                open(FILE,"+<$_") or die "couldn't open file $!\n";
                $out = '';
                while(<FILE>) {
                        $cur_line = $_;
                        if($cur_line =~ m/<a.*>/i) {
                                print "cur_line (unaltered) $cur_line\n";
                                $cur_line =~ /(^.* href=\")(.+?)(\".*$)/i;
                                $beg = $1;
                                $link = html_clean($2);
                                $end = $3;
                                $cur_line = $beg.$link.$end;
                                print "cur_line (altered) $cur_line\n";

                        }
                        if($cur_line =~ m/(<img.*>|<script.*>)/i) {
                                print "cur_line (unaltered) $cur_line\n";
                                $cur_line =~ /(^.* src=\")(.+?)(\".*$)/i;
                                $beg = $1;
                                $link = html_clean($2);
                                $end = $3;
                                $cur_line = $beg.$link.$end;
                                print "cur_line (altered) $cur_line\n";
                        }
                        $out .= $cur_line;

                }
                seek(FILE, 0, 0) or die "can't seek to start of file: $!";
                print FILE $out or die "can't print to file: $1";
                truncate(FILE, tell(FILE)) or die "can't truncate file: $!";
                close(FILE) or die "can't close file: $!";
        } } find(\&process, $input);

sub html_clean {
        my($input_string) = @_;
        $input_string = lc($input_string);
        $input_string =~ s/%20|\s/_/g;
        return $input_string; 
}

Ответы [ 2 ]

3 голосов
/ 31 марта 2010

Рассматривали ли вы использование настоящего парсера вместо регулярных выражений? Регулярные выражения не подходят для анализа HTML! Попробуйте использовать такой синтаксический анализатор, как HTML :: Parser .

0 голосов
/ 31 марта 2010

Я бы фактически предложил поместить весь текст HTML в память, выполнить многострочный поиск и заменить на полный тег RE, соответствующий:

text =~ s/(<a[^>]+href=")([^"]+)("[^>]+>.*?</a>)/$1 . &html_clean($2) . $3/ge
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...