#perl
Вопрос:
Я пытаюсь выполнить сценарий оболочки внутри сценария perl. Я могу выполнить сценарий оболочки, если вручную назначу переменную. Но я хотел бы вызвать переменную вне скрипта, который находится в файле конфигурации.
Как выполнить скрипт? Ниже приведены мои примеры команд.
my $confdir = $ENV{CFG_DIR}; ## Directory where configuration file resides
my $configfile = 'LED.cfg'; ## Configuration file
my $LEDcfg = new Config::Simple( filename => "$confdir/$conffile" ); ## assigning the configuration file to LEDcfg file
my $ApID = $LEDcfg->param(".ApID") ## passing the parameter ApID from configuration file
chomp ${ApID};
my $pwd = `(ApID=$ApID $path/CA.sh)`; ## running shell script by ApID parameterized => Failed
my $pwd = `(ApID=ACF_ERTF_DER $path/CA.sh)`; ## running shell script by ApID hardcoded => Succeeded
Значение ApID=ACF_ERTF_DER
, указанное в строке 7. Это значение вызывается из другого файла конфигурации, из которого я звонил $CFG_DIR/LED.cfg
.
Если я прокомментирую my $ApID
(строка 4) и my $pwd
(строка 6), задание завершится успешно, вызвав ApID напрямую, используя последнюю строку 7, т. Е. my $pwd = (ApID=ACF_ERTF_DER $path/CA.sh);
.
Я вызываю файл ApID
from LED.cfg, чтобы получить пароль из сценария оболочки и подключиться к серверу. Если я запускаю сценарий оболочки вручную, я получаю пароль, который используется для подключения к серверу.
Комментарии:
1. Разве это не…
my $pwd = `(ApID=$ApID $path/CA.sh)`;
?2. @vkk05 — Да. изменил вопрос. Спасибо за это. Но проблема все еще сохраняется.
3. Как только вы
chomp ${ApID};
поймете, в чем ценность${ApID}
? Правильный ли параметр был передан вашему сценарию оболочки? Что происходит, когда вы выполняете сценарий оболочки вручную, передавая необходимые аргументы?4. Это очень огромный сценарий, созданный лидерами моей организации. Сценарий выполняет различные действия. Однако единственная часть, которую я пытаюсь сделать, — это подключиться к серверу базы данных, запустив сценарий оболочки, который берет переменную с именем ApID из другого файла /abcd/efgh/ijkl/LEG.cfg. Я знаю, что делаю что-то не так, присваивая переменной из /abcd/efgh/LEG.cfg значение $ApID. Я подозреваю, что синтаксис неверен в строке 6. т. Е. мой $ApID = $LEDcfg->param(«.ApID»). Здесь я вызываю $LEDcfg и назначаю $ApID. Это правильный способ объявить переменную, взятую из какого-то другого места
5. Вам не нужно пробовать это с помощью «огромного сценария, созданного лидерами моей организации». Выясните, как это сделать в небольшом отдельном скрипте, а затем перенесите его в приложение.
Ответ №1:
Похоже, ваша проблема в том, что вы не читаете файл конфигурации, и, возможно, именно поэтому вы не получаете никаких значений.
Хитрость в программировании заключается в том, чтобы знать, что вы находитесь в хорошем, ожидаемом состоянии на каждом шаге. Вернитесь к своей программе и посмотрите на каждый шаг, чтобы убедиться, что то, чего вы хотели, действительно произошло. Я подозреваю, что ваша проблема возникает очень рано в процессе, и тогда ничто другое не может сработать.
У вас есть имя $configfile
файла , но затем используйте $conffile
:
my $confdir = $ENV{CFG_DIR};
my $configfile = 'LED.cfg';
my $LEDcfg = new Config::Simple( filename => "$confdir/$conffile" );
Затем, после этого, вы ничего не делаете, чтобы проверить, что у вас есть правильная конфигурация.
Начните с использования strict
, которое заставляет вас объявлять переменные, чтобы вы могли отлавливать те досадные случаи, когда вы используете неправильное имя. Затем, как только вы построите путь, посмотрите, существует ли он на самом деле:
use strict;
use warnings;
use File::Spec::Functions;
my $conf_dir = ...;
my $conf_file = ...;
my $conf_path = catfile( $conf_dir, $conf_file );
die "Config path <$conf_path> does not exist!" unless -e $conf_path;
Как только вы узнаете, что у вас есть существующий файл. Обратите внимание, что вы должны правильно вызвать метод. Первый аргумент-это путь, а не filename
. Вы также можете проверить, получили ли вы то, что ожидали:
my $config = Config::Simple->new( $conf_path );
my %vars = $config->vars;
use Data::Dumper;
print "Found config: ", Dumper( %vars );
Кроме того, вы говорите, что хотите получить значение ApID
, но затем пытаетесь получить доступ .ApID
. Может быть, это и правильно, но это выглядит подозрительно, и вы не показали нам пример файла конфигурации. Вы можете добавить туда еще несколько отладочных выходных данных, чтобы проверить, что вы получили значение.
Как только вы разберетесь с этой частью, вы сможете продолжить с остальным. Но также обратите внимание, что Config::Simple 15 лет. Есть много лучших, поддерживаемых в настоящее время модулей, которые могут вам помочь.
Комментарии:
1. Спасибо за твой ответ, Брайан. Я просто пытаюсь распечатать значение ApID из файла LED.cfg. Я попробовал ниже, но получил некоторую ошибку. ` >cat /amex/lcd/LED.cfg ApID=ACF_ERTF_DER >>кот test1.pl #! /usr/bin/perl используйте предупреждения; используйте конфигурацию::Просто; мой $confdir = «/amex/lcd» $conffile = ‘LED.cfg’; мой $LEDcfg = «$configdir/$configfile»; мой $ApID = Конфигурация::Просто->>>($LEDcfg->>>>ApID); печать «$AppID»; >>>>> ./test1.pl Не удается найти Config/Simple.pm в @INC (@INC содержит: /amex/lib/жк-дисплей /amex/lib/ /usr/локальный/lib64/perl5 НАЧАТЬ не удалось—компиляция прервана в test1.pl либ `
2. Обратите внимание, что у вас те же ошибки в этом коде, и вы не попробовали то, что я показал вам в своем ответе. Но вам нужно установить Config::Просто, и в StackOverflow есть множество ответов, которые могут вам помочь.
3. спасибо, Брайан. Я успешно извлек значение с помощью Config::Simple. Я получаю желаемый результат для значения ApID. Однако я получаю ошибку при попытке выполнить команду ниже в другом скрипте perl. Из команды ниже я выполняю CA.sh и проанализируйте вывод до $pwd. Чтобы эта переменная pwd использовалась для дальнейшего подключения к базе данных. Если я запущу CA.pl вне сценария я получаю пароль пользователя базы данных, указанного в CA.pl. Но я получаю ошибку, если добавлю это CA.pl инсайдер огромного скрипта perl. ошибка: ORA-01017: неверное имя пользователя/пароль; вход запрещен.
4. Если у вас есть другой вопрос, задайте новый вопрос о StackOverflow.