Парсер структурного имени файла. { Linux; Bash }

Главные вкладки

Аватар пользователя starmark starmark 22 апреля 2016 в 11:57
1

В ходе построения небольшой библиотеки учебников и размещении их на сайте пришлось придумать структурное название книг.

В названии содержится вся информация, необходимая для базы данных и автоматического заполнения полей новой записи.
Книги в формате PDF, или каком другом, лежат в папке с книгами.
А ссылки на них и все характеристики - в базе под MySQL

PHP достанется работа по возне с размещением книг и поиск.

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

Потом все аккуратненько повторил на PHP и внедрил на сайт.

А теперь - техническое описание.
(Не знаю, может это и велосипед, но изобретать никто не запретил...)


Как распарсерить сложное название файла

Постановка задачи:

Необходим скрипт для парсера имен файлов в каталоге

Пусть в каталоге находятся однотипные файлы с шаблонным названием типа:
cmn-zdorovie-1-uchebnik-rus-Boichenko_Savchenko-Kiev-2012.pdf

Результат должен быть примерно такой для каждого имени файла:

-------------------------------------------------------------------------------------------
full: cmn-zdorovie-1-uchebnik-rus-Boichenko_Savchenko-Kiev-2012.pdf
book: cmn-zdorovie-1-uchebnik-rus-Boichenko_Savchenko-Kiev-2012
ext : pdf
<<< ------------------------- Script parsitem working ------------------------- >>>
category= cmn
subcateg= zdorovie
numclass= 1
format = uchebnik
strana = rus
authors = Boichenko_Savchenko
author[1]= Boichenko
author[2]= Savchenko
sity = Kiev
year = 2012
------------------------------------------------------------------------------------------

Укрупненно - план действий

Открываем терминал (Ctrl+Alt+T) и выполняем с правами администратора:

user@user-comp:~$ sudo gedit ~/prg/scripts/parslist #{напишем скрипт считывания однотипных файлов из каталога}
user@user-comp:~$ sudo gedit ~/prg/scripts/parsitem #{напишем скрипт парсера полного имени файла}
user@user-comp:~$ sudo gedit ~/prg/scripts/parslist #{редактируем parslist и добавляем в него вызов parsitem}
user@user-comp:~$ sudo chmod 755 ~/prg/scripts/parslist #{делаем скрипт исполняемым: parslist}
user@user-comp:~$ sudo chmod 755 ~/prg/scripts/parsitem #{делаем скрипт исполняемым: parsitem}

Скрипт для считывания названий файлов из каталога и вызов парсера строки

#!/bin/bash

script_name=$0
directory=/mnt/virt/common_host/
varls=`ls $directory`

num=0
for item in $varls
do
        echo " "
        echo "[$num] -------------- Script "$script_name" working -------------- [$num]"

        ./parsitem $item

        echo "--------------------------------------------------------------"

  let "num=num+1"
done  

exit 0                         

Скрипт для парсера строки на элементы-слова

#!/bin/bash
#
# Задача: например, эту строку побъем на части
# isc-isobriskusstvo-1-uchebnik-ukr-Kalinichenko_Sergienko_Mironenko_Bakst-Kiev-2012.pdf
#

line=$1         # присваиваем переменной line значение первого параметра скрипта
script_name=$0  # присваиваем переменной script_name значение имени скрипта

echo "<<< --------------- Script $0 working --------------- >>>"
echo "full: $line"

# ----------------------------------------------------------------
# точка - разделитель
IFS="."
set -- $line
bookname=$1
extname=$2
echo "book: $bookname"
echo "ext : $extname"
echo "<<< -------------------------------------------------------- >>>"
# ----------------------------------------------------------------
v=$bookname
# дадим имена полей
arrname=("category" "subcateg" "numclass" "format  " "strana  " "authors " "sity    " "year    ")

# дефис - разделитель
IFS="-"

# Организуем цикл

k=0
ind=0
for i in $v
do
    # 5-й элемент в строке состоит из нескольких имен авторов
        # не забудем про это, используя условный оператор
        if [ $k = "5" ]
        then
                let "k=k+1"
                let "ind=k-1"
                echo "[$k] ${arrname[$ind]}= $i"

                # подчеркивание - разделитель
                IFS="_"
                vv=$i
                n=0
                for j in $vv
                do
                        let "n=n+1"
                        echo "        Author[$n]= $j"
                done
        else
                let "k=k+1"
                let "ind=k-1"
                echo "[$k] ${arrname[$ind]}= $i"
        fi
done

exit 0

Запуск скрипта как обычно: ./parslist

Комментарии

Аватар пользователя dashiwa dashiwa 22 апреля 2016 в 12:49

Баш конечно быстрее намного пхп. Если вам важна скорость смотрите в этом направлении. Я бы мог посоветовать конечно php.
Тут вам нужно смотреть в регулярнуе выражения.Это обширная тема довольно.

Аватар пользователя starmark starmark 22 апреля 2016 в 13:12

Применил Bash только ради скорейшего макетирования алгоритма.
В дело пошел скрипт на PHP, естественно.

Можно вспомнить первые персоналки с DOS. Там был встроенный Бейсик.
Пользовались им для быстро-что-то-сделать.
На черном экране в режиме интерпретатора.
Потом сохраняли в виде программы как положено.

А в линуксе побогаче возможностей будет...
Вот цель, собственно, статейки - обратить внимание людей на эффективные средства работы.
Лежат прямо под ногами Smile