Вопрос или проблема
Предположим, что некоторые любимые утилиты foo
имеют полезный переключатель -n bar
, который почти, но не совсем соответствует требованиям. Чтобы получить то, что нужно, можно:
- Отредактировать исходный код, чтобы добавить необходимое. (Обычно не переносимо, если только автор верхнего уровня не оценит правку).
- Создать оболочку-скрипт или функцию, чтобы добавить необходимое — но если синтаксис
foo
не очень простой, то парсить новый или расширенный переключатель может быть сложно. Не потому, что функция сложная, а потому, что сложным может быть парсинг.
Существует ли какой-нибудь инструмент, который работает как псевдоним или оболочная функция для одиночных переключателей утилит? Что-то, что работало бы так:
myfunction() { новый код здесь... }
wrap '-n=myfunction bar' foo ... -n 3 ...
Или если переключатель -n
будет использоваться часто:
myfunction() { новый код здесь... }
foo() { wrap '-n=myfunction bar' foo ... -n 3 ... ; }
Или предположим, что -n bar
позволяет bar быть только целым числом, и нам нужно немного изменить, чтобы обработать число с плавающей точкой, но не нужно заменять -n
если только это не число с плавающей точкой:
wrap '-n=myfunction bar==fp_only' foo ... -n 3.2 ...
Еще одно применение для wrap
может заключаться во временной обработке неустраненной ошибки:
wrap '-n=myfunction bar==x' foo ... -n x ...
…где x
— это какое-то значение (или набор значений), которое, несомненно, вызовет проблемы без предварительного парсинга и переформатирования.
Еще одно применение заключается в добавлении переключателя, где его нет (при условии, что он составлен из существующих функций переключателей, или только влияет на вывод):
newswitchcode() { ...код... }
wrap '-p=newswitchcode bar' foo ... -p 3 ...
Обратите внимание, что wrap
будет осуществим только для утилит с простым выводом. Утилиты со сложными внутренними данными, такие как find
, не подойдут.
Возможно, один из этих (из более длинного списка) может помочь. Хотя и не просто.
3) getopt, улучшенный getopts, часть util-linux, позволяет GNU "--"
Примеры: /usr/share/doc/util-linux/examples, 2016.03.27
4) argp.sh, оболочка для getopt, создает man и help (текст, XML) и т. д.
Позволяет использовать смешанные опции и аргументы.
Скомпилированный argp.c -> argp для более быстрого выполнения.
https://sourceforge.net/projects/argpsh/, 2016.03.27
5) shflags, оболочка для getopt, создает помощь, позволяет смешанные опции
и аргументы
https://github.com/kward/shflags, 2016.08.01
С наилучшими пожеланиями… удачи, drl
Ответ или решение
Для решения задачи перегрузки параметров команд с использованием специфичных возможностей утилиты в Linux, таких как обрабатывание необязательных опций или создание новых функционалов, существует несколько подходов. Давайте рассмотрим, как выполнить это с помощью различных инструментов, таких как getopt
, argp.sh
и shflags
, а также альтернативного подхода через обёртки (wrap).
Текущие Вызовы
Представим, что у вас есть утилита foo
, которая принимает параметр -n bar
. Однако вам нужно расширить функциональность, например, добавив возможность обработки дополнительных типов данных или исправления ошибок в аргументах. Так, перед нами стоит задача создания максимально удобного способа применения новых возможностей.
Подход через обёртки
Обёртка (wrap) — это один из наиболее эффективных способов создания новых функциональных возможностей для существующих команд, не изменяя их физическую реализацию. Основная идея заключается в том, чтобы создать функцию, которая обрабатывает дополнительные параметры и затем вызывает оригинальную утилиту с модифицированными данными.
Пример создания обёртки:
myfunction() {
# Ваша логика обработки аргументов
echo "Обрабатываю аргумент: $1"
}
wrap() {
local option="$1"
shift
# Обработка дополнительных параметров
"$@" $option
}
# Использование обёртки с утилитой foo
wrap '-n=myfunction bar' foo ... -n 3 ...
Это позволяет вам обрабатывать входные параметры и выполнять необходимую логику.
Использование getopt
getopt
— это стандартный инструмент для обработки командных аргументов, который может помочь при создании обёрток. Он позволяет задавать различные форматы и типы принимаемых параметров, что упрощает дальнейшую их обработку.
Пример использования getopt
:
#!/bin/bash
PARSED_OPTIONS=$(getopt -o n: -- "$@")
eval set -- "$PARSED_OPTIONS"
while true; do
case "$1" in
-n)
myfunction "$2"
shift 2
;;
--)
shift
break
;;
*)
break
;;
esac
done
# Активируем оригинальную команду с обработанными параметрами
foo "$@"
Таким образом, вы сможете обрабатывать аргументы более гибким способом.
Использование argp.sh
и shflags
Эти инструменты также представляют вариант формализации работы с параметрами. argp.sh
обрабатывает параметры и создаёт помощь (man) для вашего скрипта, что может быть полезно для документации функционала:
argp.sh
: обеспечивает простоту работы с различными типами параметров.shflags
: облегчает задачу создания флага и автоматической генерации описаний.
Заключение
Альтернативные методы, такие как использование простых оболочек или созданные внешние скрипты, требуют дополнительных усилий, но позволяют более гибко управлять аргументами команд. Решение проблемы перегрузки опций в утилитах Linux можно реализовать через создание обёрток, применение getopt
, argp.sh
, или shflags
, что обеспечит нужную функциональность без необходимости изменения исходного кода утилит.
Ваша задача — выбрать наиболее подходящий метод в зависимости от требований проекта и структуры утилиты. Понимание особенностей каждого из рассматриваемых способов позволит вам обеспечить надежность и расширяемость создаваемых вами решений.
Совершенствуйте свои навыки работы с командной строкой и администрированием Linux — это откроет множество новых возможностей для автоматизации и оптимизации ваших задач.