Можно ли передавать ассоциативные массивы BASH как argv для PHP-скриптов?
У меня есть сценарий bash, который собирает некоторые переменные в ассоциативный массив bash, подобный этому. После этого мне нужно отправить его в PHP-скрипт:
typeset -A DATA DATA[foo]=$(some_bash_function "param1" "param2") DATA[bar]=$(some_other_bash_function) php script.php --data ${DATA[@]}
Из скрипта PHP мне нужно получить доступ к массиву следующим образом:
<?php $vars = getopt("",array( "data:" )); $data = $vars['data']; foreach ($data as $k=>$v) { echo "$k is $v"; } ?>
Странный синтаксис вокруг параметра --data
следует советам из большой публикации о массивах bash от Norbert Kéri, как принудительно передать передаваемый параметр в виде массива:
Вы не можете сигнализировать функции, что вы передаете массив. Вы получаете N позиционных параметров, без информации о типах данных каждого.
Однако это решение все еще не работает для ассоциативных массивов – только значения передаются функции. Норберт Кери сделал следующую статью об этом, однако его решение на основе eval
не работает для меня, поскольку мне нужно передать фактический массив в качестве параметра.
Является то, что я пытаюсь достичь невозможным или есть какой-то способ? Спасибо!
У меня есть несколько файлов конфигурации PHP следующей структуры:
<?php return array( 'option1' => 'foo', 'option2' => 'bar' )
Мой скрипт bash собирает данные из пользовательского ввода (через функцию read
bash) и сохраняет их в ассоциативный массив bash. Этот массив должен быть позже передан как аргумент PHP-скрипту.
php script.php --file "config/config.php" --data $BASH_ASSOC_ARRAY
Поэтому вместо сложных функций sed
и т. Д. Я могу сделать просто:
<?php $bash_input = getopt('',array('file:,data:')); $data = $bash_input['data']; $config = require($config_file); $config['option1'] = $data['option1']; $config['option2'] = $data['option2']; // or foreach ($data as $k=>$v) { $config[$k] = $v; } // print to config file file_put_contents($file, "<?php \n \n return ".var_export($config,true).";"); ?>
Это используется для настройки конфигурационных файлов Laravel
Разный подход к @ will
Ваш скрипт bash:
typeset -A DATA foo=$(some_bash_function "param1" "param2") bar=$(some_other_bash_function) php script.php "{'data': '$foo', 'data2': '$bar'}"
PHP Script
<?php $vars = json_decode($argv[1]); $data = $vars['data']; foreach ($data as $k=>$v) { echo "$k is $v"; } ?>
EDIT (лучший подход). Кредит @ будет
typeset -A DATA DATA[foo]=$(some_bash_function "param1" "param2") DATA[bar]=$(some_other_bash_function) php script.php echo -n "{"; for key in ${!DATA[@]}; do echo - "'$key'":"'${DATA[$key]}'", | sed 's/ /,/g' ; done; echo -n "}"
это делает то, что вы хотите (я думаю) все в одном сценарии bash. Очевидно, вы можете перенести файл php.
declare -A assoc_array=([key1]=value1 [key2]=value2 [key3]=value3 [key4]=value4) #These don't come out necesarily ordered echo ${assoc_array[@]} #echos values echo ${!assoc_array[@]} #echos keys echo "" > tmp for key in ${!assoc_array[@]} do echo $key:${assoc_array[$key]} >> tmp # Use some delimeter here to split the keys from the values done cat > file.php << EOF <?php \$fileArray = explode("\n", file_get_contents("tmp")); \$data = array(); foreach(\$fileArray as \$line){ \$entry = explode(":", \$line); \$data[\$entry[0]] = \$entry[1]; } var_dump(\$data); ?> EOF php file.php
избегание неизбежно в кошачьем блоке.