Last active
February 28, 2021 19:57
-
-
Save fakuivan/de7da6158c8913d05ebc51de6a0868fa to your computer and use it in GitHub Desktop.
Sets flow rules on a zerotier controller from a capabilities and rules file, abuses jq <3
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
eval_on_ztncui () { | |
# shellcheck disable=1090 | |
(source ~/containers/ztncui.sh && ztncui-compose exec -T ztncui bash -c "$1"); return $? | |
} | |
# Arguments are escaped, last argument gets the address of the server prepended, auth token is added to the header | |
curl_on_ztncui () { | |
# shellcheck disable=2016 | |
eval_on_ztncui 'curl -s --header "X-ZT1-Auth: $ZT_TOKEN" '"$(printf "%q " "${@:1:$#-1}")"'"$ZT_ADDR"/'"$(printf "%q " "${@: -1}")" | |
} | |
NETWORKS="$(curl_on_ztncui -X GET controller/network)" | |
for rules_file in ./rules/*.ztrules; do | |
nwid="$(python3 -c "import pathlib, sys; print(pathlib.Path(sys.argv[1]).stem)" "$rules_file")" && | |
# Check if network id matches any network on the controller | |
{ [[ "$(echo "$NETWORKS" | jq --arg nwid "$nwid" 'any(. == $nwid)')" == "true" ]] || continue; } && | |
config="$(curl_on_ztncui -X GET controller/network/"$nwid")" && | |
#npm install -g zerotier-rule-compiler | |
rules_compiled="$(node /usr/local/lib/node_modules/zerotier-rule-compiler/cli.js "$rules_file")" && | |
config_merged="$(jq -s '.[1] * .[0].config' <(echo "$rules_compiled") <(echo "$config"))" && | |
echo Writing final config | |
final_config="$(echo "$config_merged" | curl_on_ztncui -X POST -d @- controller/network/"$nwid")" && | |
# jd could be used instead | |
diff -u <(echo "$config" | jq .) <(echo "$final_config" | jq .) --color && | |
rules_file="./rules/$nwid.caps.json" | |
if [[ ! -r "$rules_file" ]]; then | |
echo Skipping rules for network "$nwid" | |
continue | |
fi | |
members="$(curl_on_ztncui -X GET controller/network/"$nwid"/member)" | |
caps="$(jq -s '.[0] as $members | | |
.[1].capabilitiesByName as $caps | | |
.[2] | | |
with_entries(select(.key | in($members))) | | |
with_entries(.value |= map(select(. | in($caps)) | $caps[.]))' \ | |
<(echo "$members") <(echo "$rules_compiled") "$rules_file")" | |
i=0; while [[ "$i" < "$(echo "$caps" | jq 'keys | length')" ]]; do | |
member="$(echo "$caps" | jq -r --arg iter "$i" 'keys | .[$iter | tonumber]')" | |
member_config="$(curl_on_ztncui -X GET controller/network/"$nwid"/member/"$member")" | |
member_caps="$(echo "$caps" | jq --arg member "$member" '.[$member]')" | |
member_config_merged="$(jq -s --arg member "$member" '.[0] * {"capabilities": .[1][$member]}' <(echo "$member_config") <(echo "$caps"))" | |
member_final_config="$(echo "$member_config_merged" | curl_on_ztncui -X POST -d @- controller/network/"$nwid"/member/"$member")" | |
diff -u <(echo "$member_config" | jq .) <(echo "$member_final_config" | jq .) --color | |
i=$(("$i" + 1)) | |
done | |
done | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment