Обходной путь для сохранения значений массива в переменной среды с последующим вызовом из сценария Bash

Да, конфигурация OpenVPN клиент-сервер выглядит как ваша вторая диаграмма. Туннели находятся между сервером OpenVPN и клиентами OpenVPN. Сервер OpenVPN расшифровывает данные, поступающие из одного туннеля, и шифрует их в другом туннеле.

Вы можете реализовать первую схему с OpenVPN, используя архитектуру peer-to-peer вместо клиент-серверной. Вам нужно настроить VPN-туннель для каждой пары машин в вашей сети: каждый узел имеет n VPN-туннелей, итого n² туннелей (что не очень удобно).

Ваш анализ происходящего в основном верен, за исключением одной части. Открытые/закрытые ключи не используются (напрямую) для шифрования/дешифрования пакетов в/из туннеля. Вместо этого они используются для аутентификации туннеля и создания симметричных сеансовых ключей, используемых для фактического шифрования/дешифрования (и MAC).

3
23.05.2017, 15:40
2 ответа

Вы можете столкнуться с обычными проблемами: разделение и подстановка файлов.

У вас не может быть строк с пробелами, так как они будут разделены на отдельные элементы массива, и все, что напоминает глобальный символ ( *? [] ), будет расширено до совпадающих имен файлов. Вероятно, это не проблема с именами хостов, но в целом это так.

Это общая проблема, которая неоднократно обсуждалась, см., Например, Расширение переменной оболочки и влияние glob и разбиение на нее и Последствия для безопасности, если забыть указать переменную в кавычках в bash / POSIX shells


Чтобы обойти это, вам нужно: а) установить IFS на что-то другое, кроме пробелов, и разделить им строки, и б) отключить подстановку с помощью set -f .

Это будет использовать | в качестве разделителя и разделить строку. Вы можете использовать любой символ, который не нужен в значениях, возможно, даже какой-нибудь управляющий символ, например \ 001 (для его создания используйте $ '\ 001' в Bash).

#!/bin/bash
string='foo|bar'
IFS='|'; set -f
array=($string)        # split it

IFS='|'
string="${array[*]}"   # merge it back together

Кроме того, как говорится в комментариях, если ваша переменная имеет только имена хостов и вы не против разбиения на пробелы, вам не понадобится awk для ее разделения. Оболочка сделает это при назначении массиву или запуске цикла:

SRVR_ARRAY=( $HOST_NAMES )
for x in $HOST_NAMES ; do ...

(Опять же, у вас возникнут проблемы, если HOST_NAMES содержит символы glob.)

Собственно, это произойдет даже в вашем примере: awk что-то печатает, оболочка улавливает это, разбивает на слова, поскольку $ () не находится внутри двойных кавычек, а затем сохраняет слова отдельно в множество.

5
27.01.2020, 21:21

Вы можете сохранить вывод declare -p в переменной окружения:

array=(foo 'bar baz'); array[12]=sparse
export ARRAY_definition="$(declare -p array)"

Затем, в выполненном bash скрипте:

eval "$ARRAY_definition"

Обратите внимание, что важно, чтобы eval выполнялся в той же локали, что и declare (и желательно в той же версии bash)

Если eval выполняется не в глобальной области видимости, массив будет объявлен local.

В zsh вы можете использовать кавычки, чтобы избежать необходимости использовать этот опасный eval:

export ARRAY_definition=${(j: :)${(q)array}}

import with:

array=(${(Q)${(z)ARRAY_definition}})

В качестве альтернативы вы можете использовать оболочки типа rc, es или fish, которые поддерживают экспорт массивов нативно (используя свою собственную кодировку).

1
27.01.2020, 21:21

Теги

Похожие вопросы