передать параметры от одного скрипта другому

Здесь выкладываем скрипты
Правила форума
Уважаемые Пользователи форума, обратите внимание!
Ни при каких обстоятельствах, Администрация форума, не несёт ответственности за какой-либо, прямой или косвенный, ущерб причиненный в результате использования материалов, взятых на этом Сайте или на любом другом сайте, на который имеется гиперссылка с данного Сайта. Возникновение неисправностей, потерю программ или данных в Ваших устройствах, даже если Администрация будет явно поставлена в известность о возможности такого ущерба.
Просим Вас быть предельно осторожными и внимательными, в использовании материалов раздела. Учитывать не только Ваши пожелания, но и границы возможностей вашего оборудования.
Sertik
Сообщения: 1601
Зарегистрирован: 15 сен 2017, 09:03

ПОСТ не для ЧАЙНИКОВ !

Передать параметры от одного скрипта другому - что проще скажете Вы. Сделай это через глобальные переменные или функции.
Но недавно один наш форумчанин обратился ко мне именно с подобным вопросом и я вспомнил, что такое уже делал, когда передавал параметры из Телеграмм скрипту без всяких глобальных переменных вот такой конструкцией двойного парсинга:

[[:parse "[:parse [/system script get $scrName source]] $Var1]"]]

и она реально работает.

Скрипт приемник должен "подхватить" передаваемый параметр(ы). При этом они могут быть именованными и позиционными.
При этом именованные даже не нуждаются в объявлении их имён в скрипте-приёмнике, а позиционные должны быть локализованы.
Проблема в том, что все параметры, какими бы они не были, передаются как строковые (превращаются в тип "str").
Мне удалось обойти и эту проблему - передавать параметры с сохранением их типов без всяких переменных и функций.

Единственно, с чем не удалось справиться - это передать кириллические символы (пока не удалось, может и это возможно).

Поколдовав на досуге, я пришёл в итоге к такой финишной конструкции (на сегодня):

Код: Выделить всё

[[:parse "[:parse [/system script get $scrName source]] Par1=[:to$[:typeof $Var1] $Var1] [:to$[:typeof $Var2] $Var2] [:to$[:typeof $Var3] $Var3] [:to$[:typeof $Var4] $Var4] [:to$[:typeof $Var5] $Var5]"]]
Выглядит страшно, но работает !

Обратить внимание нужно вот на что:

1. Если нужно передать именованный параметр, то его нужно передавать записью вида Par1=[:to$[:typeof $Var1] $Var1] , где Par1 - это его имя, которое будет известно скрипту-приемнику (:local даже делать не нужно)

2. Если нужно передать позиционный параметр, то его нужно передавать записью вида [:to$[:typeof $Var2] $Var2], тогда подхватить в скрипте-приемнике его можно будет через $0, $1 и т.д..

3. Интересна запись [:to$[:typeof $VarX] $VarX]. Что она собственно делает ? Оказалось, что чтобы :parse передал тип переменной, ему нужно его буквально повторить. То есть если Вы передаете, например, время (тип "time"), содержащееся в переменной $X, то нужно в моей конструкции :parse указать это ещё раз явно [:totime $X], хотя [:typeof $X] и так уже ="time". Иначе :parse превратит время в строку. Поскольку неохота писать каждому параметру его тип напрямую типа [:totime $Var1], [:toip 192.168.88.1] и т.д..., я заменил это универсальной конструкцией :to$[:typeof $VarX] $VarX]. Тогда :parse "налету" определяет тип параметра и передает его как нужно !

Пример:

Скрипт источник:

Код: Выделить всё

# передача параметра другому скрипту

:local scrName "BIBLIO_scriptReceiver"

:local Var1 "mamulia"
:local Var2 "12"
:local Var3 14
:local Var4 192.168.0.1
:local Var5 [/system clock get time]

:log info ("$Var1"." $[:typeof $Var1]")
:log info ("$Var2"." $[:typeof $Var2]")
:log info ("$Var3"." $[:typeof $Var3]")
:log info ("$Var4"." $[:typeof $Var4]")
:log info ("$Var5"." $[:typeof $Var5]")

# обе записи ниже правильные, первая выполняет скрипт в параллельном процессе - в фоне

# :execute script="[[:parse \"[:parse [/system script get $scrName source]] $Var1 $Var2 $Var3 $Var4 $Var5\"]]";
# [[:parse "[:parse [/system script get $scrName source]] $Var1 $Var2 $Var3 [:to$[:typeof $Var4] $Var4] [:totime $Var5]"]]


[[:parse "[:parse [/system script get $scrName source]] Par1=[:to$[:typeof $Var1] $Var1] [:to$[:typeof $Var2] $Var2] [:to$[:typeof $Var3] $Var3] [:to$[:typeof $Var4] $Var4] [:to$[:typeof $Var5] $Var5]"]]
Скрипт-приемник BIBLIO_scriptReceiver:

Код: Выделить всё

:log warning ("$Par1"." $[:typeof $Par1]")
:log warning ("$Par2"." $[:typeof $Par2]")

:local Par3 $0
:local Par4 $1
:local Par5 $2
:log error ("$Par3"." $[:typeof $Par3]")
:log error ("$Par4"." $[:typeof $Par4]")
:log error ("$Par5"." $[:typeof $Par5]")
Можете сами попробовать !

Если кому удастся передать в качестве параметра кириллицу или сделать это другим способом (более изящно) - сигнализируйте !
Последний раз редактировалось Sertik 12 дек 2023, 10:09, всего редактировалось 1 раз.


фрагменты скриптов, готовые работы, статьи, полезные приемы, ссылки
viewtopic.php?f=14&t=13947
Sertik
Сообщения: 1601
Зарегистрирован: 15 сен 2017, 09:03

Оказывается можно передать и кириллические символы и другие напрямую не передаваемые моей конструкцией.

Просто если такие есть в передаваемом параметре нужно весь параметр дополнительно экранировать:

:local Var1 "\"privet Мамочка !\""

Всё ! можно передавать любые параметры скриптам без глобальных переменных и функций !


фрагменты скриптов, готовые работы, статьи, полезные приемы, ссылки
viewtopic.php?f=14&t=13947
-13-
Сообщения: 125
Зарегистрирован: 18 мар 2021, 12:45

как вариант, [[:parse "[:parse [/system script get $scrName source]] $Var1]"]] можно объявить глобальной, чтобы не писать каждый раз страшный код))

:global fnParse [[:parse "[:parse [/system script get $scrName source]] $Var]"]]

и уже в другом скрипте

:global fnParse
:local Var1 [$fnParse scrName="script1" Var="Var1"]
:local VarN [$fnParse scrName="scriptN" Var="VarN"]


Sertik
Сообщения: 1601
Зарегистрирован: 15 сен 2017, 09:03

Да, можно. Единственно, что меня напрягает, это то, что количество передаваемых параметров как бы "оговорено" моей конструкцией и нельзя передать МЕНЬШЕ, иначе не сработает.

То есть, если:

Код: Выделить всё

:global fnParse do={
  :do {
[[:parse "[:parse [/system script get $scrName source]] Par1=[:to$[:typeof $Var1] $Var1] [:to$[:typeof $Var2] $Var2] [:to$[:typeof $Var3] $Var3] [:to$[:typeof $Var4] $Var4] [:to$[:typeof $Var5] $Var5]"]]
 on-error={:return "Error $0 Var`s not send"}
:return Done}
Но тогда при:

:local Answer [$fnParse "\"Привет mother!\"" 192.168.0.1 [/system clock get time] 0x0F 23]

все пять параметров должны быть указаны. Массивы, кстати, не передаются.
Да и смысл тогда - раз используется :global ?

Или я не допонял ?


фрагменты скриптов, готовые работы, статьи, полезные приемы, ссылки
viewtopic.php?f=14&t=13947
-13-
Сообщения: 125
Зарегистрирован: 18 мар 2021, 12:45

из массивов я дергаю вот так
 переменные

Код: Выделить всё

:global fnParse

:set $dbCmd [[$fnParse script="dbCmd"]]
:set $syName ($dbCmd->"syName")
:set $cuDate ($dbCmd->"syClock"->"date")
:set $cuTime ($dbCmd->"syClock"->"time")
:set $cuUptime ($dbCmd->"syRes"->"uptime")
:set $cuHealth ($dbCmd->"cuHealth")
:set $cuWAN ($dbCmd->"cuWAN"->"comment")
 массив в скрипте dbCmd

Код: Выделить всё

:set $dbCmd [:toarray ""]
:set $dbCmd {
    "apiTg"="https://api.telegram.org/bot"
    "botID"=$botID
    "myChat"=$myChat
    "myAlarmChat"=$myAlarmChat
    "syName"=[/system identity get name]
    "syClock"=[/system clock get]
    "syRes"=[/system resource get]
    "syRB"=[/system routerboard get]
    "cuHealth"=(([/system health get 0]->"value" . "V") . "; " . ([/system health get 1]->"value" . "\E2\84\83"))
    "cuVoltage"=([/system health get 0]->"value")
    "cuWAN"=[/ip route get [find active dst-address="0.0.0.0/0" routing-table="main"]]
}


Sertik
Сообщения: 1601
Зарегистрирован: 15 сен 2017, 09:03

Ну то есть по одному элементу ... Или опять не понял ? Поясните стратегию.

Что Вас делает эта строка ?

:set $dbCmd [[$fnParse script="dbCmd"]]

Она по идее дергает целый массив из скрипта dbCmd. Но в виде чего ? и КАК это удается ?
Вы же имеете ввиду что под fnParse стоит наша конструкция ?

Код: Выделить всё

:global fnParse [[:parse "[:parse [/system script get $scrName source]] $Var]"]]

:set $dbCmd [[$fnParse script="dbCmd"]]
:set $syName ($dbCmd->"syName")
:set $cuDate ($dbCmd->"syClock"->"date")
:set $cuTime ($dbCmd->"syClock"->"time")
:set $cuUptime ($dbCmd->"syRes"->"uptime")
:set $cuHealth ($dbCmd->"cuHealth")
:set $cuWAN ($dbCmd->"cuWAN"->"comment")
Получается, что после этого .... в $dbCmd как в массив попадает куча элементов ?
Чё то у меня крыша не выносит ... Надо попробовать.


фрагменты скриптов, готовые работы, статьи, полезные приемы, ссылки
viewtopic.php?f=14&t=13947
Sertik
Сообщения: 1601
Зарегистрирован: 15 сен 2017, 09:03

Нет, что-то вообще не пойму что Вы имеете ввиду
У меня массив $dbCmd получается пустым ...

Кроме того, Вы опять по своей старой привычке не объявляете переменные, а сразу делаете :set
Это категорически не рекомендуют даже супер гуру на оф. форуме, типа Rextended.


фрагменты скриптов, готовые работы, статьи, полезные приемы, ссылки
viewtopic.php?f=14&t=13947
-13-
Сообщения: 125
Зарегистрирован: 18 мар 2021, 12:45

в шедуле стоит вот такой скрипт при запуске
 startUp

Код: Выделить всё

:delay 10s

:global fnExe do={:execute [/system script get $script source]}
:global fnParse do={:parse [/system script get $script source]}
:global tgSend [:parse [/system script get "tgSend" source]]

[$fnParse script="-Check Firmware"]

:delay 10s

:retry {[$fnParse script="-Startup RB"]} delay=20 on-error={}

$fnExe script="-Check botChat"
в нем объявлены все глобальные переменные которые я использую чаще остальных

далее в каждом скрипте объявляю что есть массив :set $dbCmd [[$fnParse script="dbCmd"]], и забираю уже нужные параметры

давно пришел к этому, т.к. содержу целый зоопарк с типовыми ботами, удобно кода меняешь только в одном месте ключевые параметры
целиком dbCmd выглядит так
 

Код: Выделить всё

:set $botID "xxx***yy"
:set $myChat "-xxx0000xxxx"
:set $myAlarmChat "-yyyyyyy"

:set $dbCmd [:toarray ""]
:set $dbCmd {
    "apiTg"="https://api.telegram.org/bot"
    "botID"=$botID
    "myChat"=$myChat
    "myAlarmChat"=$myAlarmChat
    "syName"=($syMark . "   \"" . [/system identity get name] . "\"")
    "syClock"=[/system clock get]
    "syRes"=[/system resource get]
    "syRB"=[/system routerboard get]
    "cuHealth"=(([/system health get 0]->"value" . "V") . "; " . ([/system health get 1]->"value" . "\E2\84\83"))
    "cuVoltage"=([/system health get 0]->"value")
    "cuWAN"=[/ip route get [find active dst-address="0.0.0.0/0" routing-table="main"]]
}

:return $dbCmd


-13-
Сообщения: 125
Зарегистрирован: 18 мар 2021, 12:45

Sertik писал(а): 07 дек 2023, 18:17 Кроме того, Вы опять по своей старой привычке не объявляете переменные, а сразу делаете :set
Это категорически не рекомендуют даже супер гуру на оф. форуме, типа Rextended.
ну у меня пока все работает, не понимаю почему нет?)) set короче чем local, сокращаю так сказать кол-во символов


-13-
Сообщения: 125
Зарегистрирован: 18 мар 2021, 12:45

наврал, меняю еще system identity и название главного скрипта которое привязано system identity ну и botID ессено :-):


Ответить