Как сделать так, чтобы wget переименовал загруженные файлы, чтобы не включать строку запроса?

23683
Keith Twombley

Я загружаю сайт с помощью wget, и ко многим ссылкам прикреплены запросы, поэтому, когда я делаю это:

wget -nv -c -r -H -A mp3 -nd http://url.to.old.podcasts.com/ 

Я получаю много таких файлов:

1.mp3?foo=bar 2.mp3?blatz=pow 3.mp3?fizz=buzz 

Что я хотел бы закончить это:

1.mp3 2.mp3 3.mp3 

Все это происходит в Ubuntu Linux, и у меня есть wget 1.10.2.

Я знаю, что могу сделать это после того, как получу все через скрипт, чтобы переименовать все. Однако мне бы очень хотелось найти решение изнутри wget, чтобы я мог видеть правильные имена во время загрузки.

Может кто-нибудь помочь мне разгадать это?

22
Отправьте свой вопрос на www.stackoverflow.com. Deniz Zoeteman 14 лет назад 0
@TutorialPoint почему? Вопрос в том, чтобы найти способ сделать это, так что SO просто перенесет его сюда. quack quixote 14 лет назад 2
Ну, нет никакого способа сделать это ayrnieu 14 лет назад 0
@ayrnieu: не в одной команде, нет. и не без помощника. но вы, безусловно, можете сделать это с помощью всего лишь n + 1 команд `wget` (если не меньше). quack quixote 14 лет назад 1

7 ответов на вопрос

21
Filox

Если сервер добрый, он может прикрепить заголовок Content-Disposition к загрузке, сообщая вашему клиенту правильное имя файла. Чтобы заставить wget прослушать этот заголовок для окончательного имени файла, достаточно просто:

wget --content-disposition 

Вам понадобится новая версия Wget, чтобы использовать эту функцию.

Я понятия не имею, насколько хорошо он обрабатывает сервер, требующий имя файла '/ etc / passwd'.

14
Gregory Wolf

После обработки большого пакета я понял, что должен был wgetигнорировать строки запроса. Я не хотел делать это снова, поэтому я сделал этот скрипт, который работал для меня:

# /bin/bash for i in `find $1 -type f` do mv $i `echo $i | cut -d? -f1` done 

Поместите это в файл вроде rmqstrи chmod +x rmqstr Синтаксис:./rmqstr <directory (defaults to .)>

Он будет рекурсивно удалять строки запроса из всех имен файлов.

4
quack quixote

Я думаю, wgetчтобы сохранить как имя файла, отличное от указанного в URL, вам нужно использовать -O filenameаргумент. Это только то, что вы хотите, когда вы даете ему один URL - с несколькими URL, весь загруженный контент заканчивается в filename.

Но это действительно ответ. Вместо того, чтобы пытаться сделать все это одной wgetкомандой, используйте несколько команд. Теперь ваш рабочий процесс становится:

  1. Запустите, wgetчтобы получить базовый HTML-файл (ы), содержащий ваши ссылки;
  2. Парсинг по URL;
  3. URL-адрес Foreach, заканчивающийся на mp3,
    1. URL процесса, чтобы получить имя файла (например, превратить http://foo/bar/baz.mp3?gargle=blasterвbaz.mp3
    2. (необязательно) проверьте, что имя файла не существует
    3. бежать wget <URL> -O <filename>

Это решает вашу проблему, но теперь вам нужно выяснить, как получить базовые файлы, чтобы найти ваши mp3URL.

Вы имеете в виду конкретный сайт / базовый URL? С шагами 1 и 3 будет легче справиться с конкретным примером.

1
ayrnieu

так что я могу видеть правильные имена во время загрузки.

ХОРОШО. Используйте wget как обычно; используйте скрипт post-wget, который вы обычно используете, но обработайте вывод wget так, чтобы это было проще для глаз:

#! /bin/sh exec wget --progress=bar:force $* 2>&1 | \ perl -pe 'BEGIN { $| = 1 } s,(?<=`)([^\x27?]+),\e[36;1m$1\e[0m, if /^Saving/' cgi-cut # rename files 

Это все равно будет отображаться при ?foo=barзагрузке, но остальная часть имени будет отображаться ярко-голубым цветом.

Это несколько решает проблему отображаемых имен файлов, но OP также хочет, чтобы в окончательном имени файла не было строки запроса. Michael Mior 9 лет назад 0
1
KittMedia

У меня такой же подход, как у @Gregory Wolf, потому что его код всегда создавал сообщения об ошибках вроде этого:

mv: «./file» и «./file» - это один и тот же файл

Таким образом, я сначала проверяю, есть ли строка запроса в имени файла перед перемещением файла:

for f in $(find $1 -type f); do if [ $f = $ ]; then continue; fi mv "$" "$" done 

Это рекурсивно проверит каждый файл и удалит все строки запроса в их именах файлов, если они доступны.

0
Vijay Padhariya

Посмотрите на эти две команды, которые я создал для клонирования сайта, и после завершения клонирования вы можете выполнить вторую команду.

Вторая команда просматривает весь клон, ищет имена шаблонов файлов « ? » И удаляет строку запроса из имени файла.

# Clone entire site. wget --content-disposition --execute robots=off --recursive --no-parent --continue --no-clobber http://example.com  # Remove query string from a static resource. for i in `find $1 -type f -name "*\?*"`; do mv $i `echo $i | cut -d? -f1`; done 

(Смотрите это в GitHub Gist .)

-2
robcore

Even easier is this: https://unix.stackexchange.com/questions/196253/how-do-you-rename-files-specifically-in-a-list-that-wget-will-use

This suggests a method that essentially uses wget's rename function (can be altered to include directory) for multiple files. See the second version proposed.

Не могли бы вы процитировать соответствующую информацию по ссылке, чтобы мы знали, какой материал, по вашему мнению, отвечает на этот вопрос. Ramhound 8 лет назад 2