Видео смотреть бесплатно

Смотреть домашнее видео

Официальный сайт mixzona 24/7/365

Смотреть видео бесплатно

WeLinux.ru

19.06.09 00:15cppmm

Скрипты на bashПример скрипта с параметрами.

Роясь на просторах винта нашёл один старый скриптик. писался он во времена, когда я не признавал ничего кроме fluxbox и консоли. Основное назначение - запись дисков из консоли. Но это не важно.
Вспомнился мне этот скрипт, когда его у себя нашёл потому, что из-за способа обработки парметров, принимаемых скриптом(т.е. -h - помощь, -d - директория и т.д.) пришлось как-то поковырять документацию. В принципе, ничего сложного и всё максимально упрощено, но может кому и пригодится подход.
В самом скрипе используется два подхода - приём команды и приём опций. Ну и плюс для совсем уж новичков - работа с функциями.
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
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
#!/bin/bash
#
TMPFILE=/home/cppmm/wtmp/cdrom.iso

# Определение действия.

case $1 in
        wr)
                FUNC="f_write"
        ;;
        cp)
                FUNC="f_copy"
        ;;
        cl)
                FUNC="f_clear"
        ;;
        ch)
                FUNC="f_check"
        ;;
        wi)
                FUNC="f_write_iso"
        ;;
        help)
                FUNC="f_help"
        ;;
        *)
                FUNC="f_help"
        ;;
esac
shift

# Определение параметров.
until [ -z $1 ]
do
        if [ "$1" = "-d" ]
        then
                DIR="$2"
                shift
        fi
        if [ "$1" = "-s" ]
        then
                SPEED="$2"
                shift
        fi
        if [ "$1" = "-o" ]
        then
                ODISK="$2"
                shift
        fi
        if [ "$1" = "-i" ]
        then
                IDISK="$2"
                shift
        fi
        if [ "$1" = "-f" ]
        then
                ISO="$2"
                shift
        fi
        shift
done

# Функйия проверки наличия переменных и оповещения.
f_var_check() {
        case "$1" in
                v_help)
                        echo "Для справки: cd.sh help"
                        exit 0
                ;;
                v_dir)
                        if [ -z "$DIR" ]
                        then
                        echo "Нужно указать директорию, подготовленную для записи."
                        f_var_check v_help
                        fi
                ;;
                v_odisk)
                        if [ -z "$ODISK" ]
                        then
                        echo "Нужно указать устройство, производящее запись."
                        f_var_check v_help
                        fi
                ;;
                v_idisk)
                        if [ -z "$IDISK" ]
                        then
                        echo "Нужно указать устройство, с которого производится копирование."
                        f_var_check v_help
                        fi
                ;;
                v_speed)
                        if [ -z "$SPEED" ]
                        then
                                SPEED="4"
                                echo "Скорость записи не установленна. По-умолчанию 4"
                                echo "Продолжить? [Y/n]: "
                                read ANSWER
                                case $ANSWER in
                                        [nN])
                                                f_var_check v_help
                                        ;;
                                        *)
                                        ;;
                                esac
                        fi
                ;;
                v_eject)
                        eject -r /dev/${ODISK}
                        echo "Вставьте записываемый диск и нажмите Enter."
                        read ready
                        eject -t /dev/${ODISK}
                ;;
                v_iso)
                        if [ -z "$ISO" ]
                        then
                        echo "Укажите файл образа."
                        f_var_check v_help
                        fi
                ;;
esac
}

# Функция записи дирректории на диск.
f_write() {
        f_var_check v_odisk
        f_var_check v_dir
        f_var_check v_speed
        mkisofs -V "Disk" -l -J -R -v -o ${TMPFILE} ${DIR}
        f_var_check v_eject
        cdrecord -v -dev=/dev/${ODISK} -speed=${SPEED} ${TMPFILE}
        rm -f ${TMPFILE}
}

# Функция копирования диска.
f_copy() {
                f_var_check v_odisk
                f_var_check v_idisk
                f_var_check v_speed
                dd if=/dev/${IDISK} of=${TMPFILE} bs=2048
                f_var_check v_eject
                cdrecord -v -dev=/dev/${ODISK} -speed=${SPEED} ${TMPFILE}
                rm -f ${TMPFILE}
}

# Функция очистки диска.
f_clear() {
        f_var_check v_odisk
        cdrecord dev=/dev/${ODISK} -blank=all
}

# Функция проверки размера будующего образа.
f_check() {
        f_var_check v_dir
        echo "Размерв байтах:"
        expr `mkisofs -print-size -quiet $DIR` \* 2084
       
}

# Функция записи iso-образа.
f_write_iso() {
        f_var_check v_odisk
        f_var_check v_iso
        f_var_check v_speed
        cdrecord -v -dev=/dev/${ODISK} -speed=${SPEED} ${ISO}
}

# Функция помощи.
f_help() {
        echo "  Использование: cd.sh ДЕЙСТВИЕ ОПЦИИ"
        echo "          Действия:"
        echo "          wr      запись директории на диск."
        echo "          cp      копирование с диска на диск."
        echo "          cl      очистка диска."
        echo "          ch      проверка размера будущего образа диска из директории."
        echo "          wi      запись на диск образа."
        echo "          Опции:"
        echo "          -d      Директория, подготовленная для записи."
        echo "          -f      Файл ISO."
        echo "          -i      Исходный диск."
        echo "          -o      Диск, подготовленный для записи."
        echo "          -s      Скорость записи."
}

$FUNC
 


P.S. Если вдруг кто захочет использовать этот скрипт в реальной жизни, он не умеет писать dvd(man cdrecord). Просто у меня в те времена не было пишущего dvd. :)
+11
Kraplax19.06.09 00:21# +0
ай-ай-ай!
Каты в таких постах не забываем! Поправил.
NucleoFag19.06.09 00:22# +-1
А я тока тоже хотел добавить! Оперативно!
Kraplax19.06.09 00:25# +0
Случайное совпадение просто :P
cppmm19.06.09 00:23# +0
За каты извиняюсь. Форумный я человек. Никак не привыкну. :)
xT19.06.09 01:03# +0
Еще в блог "Скрипты на bash" перенести бы =)
Kraplax19.06.09 01:10# +0
о! точно :) проглядели как-то. Думаю у автора нет веских причин, по которым этот пост нужно было бы оставить в персональном блоге.
cppmm19.06.09 07:48# +0
хм... Вот честно, выбирал же блок "Скрипты на bash", когда постил. Странно, почему не выбралось.
Kraplax19.06.09 19:20# +0
Да ничего, со всяким бывает. Нам перенести несложно, а вам продолжать писать =)
Kraplax19.06.09 20:57# +0
Кажется, я понял почему так вышло - наверняка вы действительно запостили изначально именно в блог "Скрипты на bash", вот только когда я правил с катом я сам не состоял в этом блоге. Система попыталась честно выставить правильный блог, и выставила что попало, потому что того что надо не было.
Так что тут моя вина.
cppmm19.06.09 23:48# +0
Если так, думаю, это стоит запостить багрепортом разработчикам.
NucleoFag19.06.09 00:21# +0
Клево! А почему не getopts например?
cppmm19.06.09 00:24# +0
Вернуться бы на несколько лет назад, спросить, почему не getopts, было бы интересно. :) Я же говорю, что здесь просто один из вариантов. Просто тогда, помню, недели две над этим бился.
NucleoFag19.06.09 00:27# +3
Я кстати за то чтобы выкладывать сюда всякие скрипты, с их обсуждением и допиливанием. Соглась, прогресс бы сразу бы виден был! =)
А у нас тоже лабы были по СПО в универе, с подобными скриптами...
Kraplax19.06.09 00:29# +0
Кстати да, очень полезно было бы.
Вот тут нехватает, например, задания утилиты записи через переменную - по опыту знаю, что не у всех wodim слинкован на cdrecord. Так что было бы интересно добавить какую-то опцию, что ли. Или, может быть даже проверку.
NucleoFag19.06.09 00:32# +0
Вот вот! Жаль я совсем уж дрянной кодер, я даже баш весьма посредственно знаю, но насмотревшись на обсуждения я бы полюбому бы научился полезному, что есть мэйнтаргет одна из главных целей ресурса.
cppmm19.06.09 00:48# +0
Проверку добавить можно. Это довольно легко. Если нужно, могу сделать пример, но в Debian даже в те времена в этом не было надобности.
cppmm19.06.09 00:46# +0
Возможно, было бы полезно. Но лично мне сложно понять, что стоит выкладывания, а что нет. Ведь всё здесь очень просто и понятно. :)
Kraplax19.06.09 00:27# +0
Скрипт хорош. Было бы неплохо пояснить некоторые аспекты, например что значит
until [ -z $1 ]

Почему здесь указан "первый параметр" (я не силен в скриптах, может быть $1 значит не совсем первый параметр, а что-то другое), и зачем там -z?
cppmm19.06.09 00:45# +2
[ -z $var ] проверяет, присутствует ли параметр $var. Если подробнее, то конструкция until [ -z $var ] означает по-русски "пока есть параметр $var, делать". Если параметра нет, цикл завершается.
А $1 используется так, как надо. Смотреть надо на команду shift. Она сдвигает принимаемые скриптом параметры командной строки. Т.е. если я скажу ./script.sh var1 var2, то по умолчанию, var1 - это $1, а var2 - $2. Но если в скрипте после приёма $1, дать команду shift, то для него $1 станет равен var2. Проще говоря, идёт сдвиг вправо, а самый левый параметр отбрасывается.

P.S. Не уверен, что я могу объяснить лучше, чем ABS Guide. :)
Kraplax19.06.09 00:58# +0
Вроде все правильно сам осилил :)
Kraplax19.06.09 00:56# +0
Не читая манов интуитивно вроде бы начинаю понимать, что опция -z проверяет "на вшивость" параметр, и если параметр задан неверно (то есть если такого файла нет или параметра просто не задано), то возвращает положительный результат (1, true или что там еще). При этом $1 это первый (а может просто единственный?) параметр, который есть на входе и он постоянно передвигается командой shift.
А вот в функции f_write_iso() - там первые три строчки проверяют заданы ли параметры. Мне интересно - если они не заданы, то проверка ведь просто выдаст предупреждение, тогда как при заданном параметре v_help функция должна наткнуться на exit 0 и выйти. Так вот - если не задать устройство записи, например, то что будет? cdrecord будет-таки вызван или скрипт сам прервется?
cppmm19.06.09 07:43# +0
Если не задать какой-нибудь из параметров, функция f_var_check() выведет справку(v_help()) и выйдет из программы(exit 0 в v_help()). Т.е. при нехватки любого из параметров(кроме скорости записи, для которого существует значение по умолчанию) скрипт не вызывает cdrecord и выходит.
Kraplax19.06.09 00:48# +0
И зачем там в конце добавлена $FUNC?
cppmm19.06.09 00:52# +0
Это собственно то, что будет делать скрипт. Проще говоря, вызов одной из функций, описанных в самом первом case.
Kraplax19.06.09 00:59# +0
А, теперь понял =) Спасибо =)
xT19.06.09 01:14# +0
Познавательно +)
xT19.06.09 01:20# +0
А чем обусловлено использование case в #Определении действия и "тысячи" if`ов в #Определение параметров?
Разве нельзя использовать case и в определении параметров? Там же только $1 проверяется
Kraplax19.06.09 02:41# +0
Даже если бы было одинаково в обоих вариантах ценность данного скрипта в освещении различных подходов. Конечно, скорее всего автор просто по незнанию (на тот момент) или из-за определенного положения звезд использовал именно такую комбинацию, но все же этот скрипт в качестве учебного пособия, некоего стартапа для новичка будет лучше именно в таком виде.

А если вы попытались как раз обратиться к проблеме оптимизации и доработки скриптов, о которой говорилось выше - то вопрос интересный. Возможно, с case скрипт выглядел бы действительно элегантнее и читался бы удобнее.
xT19.06.09 09:34# +0
Конечно, скорее всего автор просто по незнанию (на тот момент) или из-за определенного положения звезд использовал именно такую комбинацию

Это вряд ли (даже без ответа автора ниже), ибо в двух других случаях использовался case =)

А пособие хорошее)
cppmm19.06.09 07:47# +0
case выбирает одно из значений и продолжает выполнение скрипта дальше после esac. Мне же надо было проверить все заданные параметры командной строки, используя shift. Поэтому было выбрано некрасивое решение с тысячью if'ами.
Честно говоря, даже сейчас этот способ видится простейшим выбором для меня. )
xT19.06.09 09:33# +0
Понял =) познал магию shift`а
aonick19.06.09 19:09# +-1
Есть еще команда getopt для использования в подобных скриптах.

а скрипт хороший :)
cppmm19.06.09 23:52# +0
Выше я говорил, что тогда я не знал про getopt и изобретал велосипед. :)
Спасибо за "хорошесть". :)
aonick20.06.09 00:02# +0
Точно - комментарии по диагонали смотрел.
А велосипед замечательная штука, чем чаще изобретаешь, тем больше потом понимания и удовольствия от узнавания уже существующих решений.
aonick20.06.09 21:38# +0
Кстати похожий по назначению код, но слегка элегантней (взято без изменений из /etc/init.d/network в SUSE):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
while [ $# -gt 0 ]; do
        case $1 in
                boot|onboot) MODE=onboot ;;
                hotplug)     MODE=hotplug ;;
                manual)      MODE=manual ;;
                check)       CHECK=check ;;
                quiet)       be_quiet_has_gone ;;
                debug)       DEBUG=yes ;;
                type=*)      TYPE=${1#type=} ;;
                fake)        FAKE=echo ;;
                skip=*)      SKIP=${1#skip=} ;;
                nm)          NETWORKMANAGER=yes ;;
                netcontrol)  NETWORKMANAGER=no ;;
                localfs)     FS_FILTER=localfs  ;;
                remotefs)    FS_FILTER=remotefs ;;
                *)           mesg "Unknown option '$1'"
                             mesg "options: {[on]boot,hotplug,manual,check,debug,type=<typelist>,fake,localfs)"
                             exit 1 ;;
        esac
        shift
done
Kraplax20.06.09 21:51# +0
куски кода вставляются с помощью тега code, а не color. Поправил, но будьте внимательнее в следующий раз
Kraplax20.06.09 21:57# +0
кстати, что-то было не так в тексте скрипта строке в 17 - заканчивалось на угловую скобку. Уверен что правильно было бы дописать там еще какие-то значения, да вот незнаю какие, поэтому просто закрыл скобку и кавычки - без них скрипт оставался красным из-за битого синтаксиса.
predator20.06.09 22:07# +0
да и сейчас тут не все ок выглядит

Top блогов (все)
Топ пользователей Топ блогов
Топ пользователей Топ блогов
Top пользователей (все)
Топ пользователей Топ блогов
В сети: monolith, Axell

Новенькие: iken, ice, shtopor, rosko, necrotigr
welinux.ru
Идея сайта exelens; Движок 0byte, разработчик nvbn; Дизайн - Astramak

В хорошем качестве hd видео

Онлайн видео бесплатно


Смотреть русское с разговорами видео

Online video HD

Видео скачать на телефон

Русские фильмы бесплатно

Full HD video online

Смотреть видео онлайн

Смотреть HD видео бесплатно

School смотреть онлайн