Хранение файлов внутри скриптов BASH
есть ли способ хранить двоичные данные внутри скрипта BASH, чтобы его можно было передать в программу позже в этом скрипте?
на данный момент (на Mac OS X) я делаю
play sound.m4a
# do stuff
Я хотел бы иметь возможность сделать что-то вроде:
SOUND <<< the m4a data, encoded somehow?
END
echo $SOUND | play
#do stuff
есть ли способ сделать это?
7 ответов
Base64 кодирует его. Например:
$ openssl base64 < sound.m4a
а потом в скрипт:
S=<<SOUND
YOURBASE64GOESHERE
SOUND
echo $S | openssl base64 -d | play
Я знаю, что это похоже на езду на мертвой лошади, так как этот пост довольно старый, но я хотел бы улучшить ответ Sionide21, поскольку его решение хранит двоичные данные в переменной, которая не нужна.
openssl base64 -d <<SOUND | play
YOURBASE64DATAHERE
SOUND
Примечание: синтаксис HereDoc требует, чтобы вы не отступали последний "звук" и декодирование base64 иногда не удавалось мне, когда я отступал, что Раздел "YOURBASE64DATAHERE". Так что лучше всего сохранить Base64 Данные, а также конечный токен unindented.
Я ищу более элегантный способ хранения двоичных данных в Shell-скриптах, но я уже решил его, как описано здесь. Единственная разница в том, что я перевозил некоторые файлы tar-bzipped таким образом. Моя платформа знает отдельный двоичный файл base64, поэтому мне не нужно использовать openssl.
base64 -d <<EOF | tar xj
BASE64ENCODEDTBZ
EOF
существует формат Unix под названием Шарья (Shell archive), который позволяет хранить двоичные данные в сценарии оболочки. Вы создаете файл shar с помощью .
когда я это сделал, я использовал оболочку здесь документ, пропущенный через atob
.
function emit_binary {
cat << 'EOF' | atob
--junk emitted by btoa here
EOF
}
одинарные кавычки вокруг 'EOF'
запретить расширение параметров в теле документа here.
atob
и btoa
are очень старые программы, и по какой-то причине они часто отсутствуют в современных дистрибутивах Unix. Несколько менее эффективной, но более вездесущей альтернативой является использование mimencode -b
вместо btoa
. mimencode
будет кодировать в кодировке base64 кодировке ASCII. Соответствующая команда декодирования -mimencode -b -u
вместо atob
. The openssl
команда также будет выполнять кодировку base64.
вот код, который я написал давно, который упаковывает исполняемый файл выбора в скрипт bash. Я не могу точно вспомнить, как это работает, но подозреваю, что вы могли бы довольно легко изменить его, чтобы сделать то, что вы хотите.
#!/usr/bin/perl
use strict;
print "Stub Creator 1.0\n";
unless($#ARGV == 1)
{
print "Invalid argument count, usage: ./makestub.pl InputExecutable OutputCompressedExecutable\n";
exit;
}
unless(-r $ARGV[0])
{
die "Unable to read input file $ARGV[0]: $!\n";
}
my $OUTFILE;
open(OUTFILE, ">$ARGV[1]") or die "Unable to create $ARGV[1]: $!\n";
print "\nCreating stub script...";
print OUTFILE "#!/bin/bash\n";
print OUTFILE "a=/tmp/\`date +%s%N\`;tail -n+3 $0 | zcat > $a;chmod 700 $a;$a ${*};rm -f $a;exit;\n";
close(OUTFILE);
print "done.\nCompressing input executable and appending...";
`gzip $ARGV[0] -n --best -c >> $ARGV[1]`;
`chmod +x $ARGV[1]`;
my $OrigSize;
$OrigSize = -s $ARGV[0];
my $NewSize;
$NewSize = -s $ARGV[1];
my $Temp;
if($OrigSize == 0)
{
$NewSize = 1;
}
$Temp = ($NewSize / $OrigSize) * 100;
$Temp *= 1000;
$Temp = int($Temp);
$Temp /= 1000;
print "done.\nStub successfully composed!\n\n";
print <<THEEND;
Original size: $OrigSize
New size: $NewSize
Compression: $Temp\%
THEEND
поскольку Python доступен в OS X по умолчанию, вы можете сделать следующее:
ENCODED=$(python -m base64 foo.m4a)
затем расшифровать его, как показано ниже:
echo $ENCODED | python -m base64 -d | play
Если это один блок данных для использования, трюк, который я использовал, заключается в том, чтобы поместить маркер "начало данных" в конце файла, а затем использовать sed в скрипте для фильтрации ведущих материалов. Например, создайте следующее Как"play-sound.bash"
:
#!/bin/bash
sed '1,/^START OF DATA/d' | play
exit 0
START OF DATA
затем, вы можете просто добавить данные в конец этого файла:
cat sound.m4a >> play-sound.bash
и теперь, выполнение сценария должно воспроизводить звук напрямую.