# This file is heavily commented explaining various configuration options.
# The other configuration file examples are uncommented, but their field names
#   should be easily visually mapped to the ones in here.
# All example configuration files evaluate to the same configuration.
# The uncommented.toml file is the exact same is this but without
#   empty newlines and comments.

# DefaultUsername specifies the default username to use for
#   authenticating to tunnelbroker.net.
# It is optional, as the username can be specified for each Tunnel,
#   but at least one or the other *must* be provided.
# This makes it easier if you have multiple tunnels under the same account
#   (as possible in higher levels of HE IPv6 certification).
# If a username is specified in Tunnel.Username, it will be used.
# If not (and, of course, DefaultUsername is specified), then
#   DefaultUsername will be used for that Tunnel.
DefaultUsername = 'default_user'

# Frequency specifies the check frequency in daemon mode.
# (Not used in single-run mode.)
# If not specified, it defaults to 5 minutes.
# Note that this does not specify how often the client IP is set/updated
#   upstream, it specifies how often to *check* if it needs to be updated.
# It will always attempt to be updated if there is a mismatch, this just
#   controls how often that check runs.
# It must be a string compatible with Golang's time.ParseDuration.
#   (https://pkg.go.dev/time#ParseDuration)
# Note that there may be some "drift" from this; the timer is restarted
#   after a check/update *completes* to avoid duplicate job duplication.
# Likewise, if SingleTunnel (below) is true, each run may take even
#   longer than expected.
Frequency = '5m'

# If SingleTunnel is true, each Tunnel below will be run in order instead of
#   concurrently.
# If there is any concern about race conditions (e.g. the same service being
#   restarted by multiple tunnels, etc.), then it is HIGHLY RECOMMENDED
#   you set this to true.
SingleTunnel = true


#############
## Tunnels ##
#############

# Each Tunnel represents a single tunnelbroker.net tunnel configuration.
# Note that each Tunnel is run concurrently. If this is undesired due to
#   potential race conditions, set the root-level directive SingleTunnel
#   to true.
# IMPORTANT: *DO NOT* define multiple tunnels with the same TunnelID.
#   It makes no sense to do so, and GoBroke assumes that there are no
#      duplicates.
[[Tunnel]]
	# The TunnelID can be found by logging into https://tunnelbroker.net/ and,
	#   at the "Main Page" that loads when logging in, clicking on the desired
	#   tunnel name.
	# The tunnel ID is then displayed in both the URL bar:
	#   https://tunnelbroker.net/tunnel_detail.php?tid=<TunnelID>
	# And as the first line on the first tab ("IPv6 Tunnel" tab),
	#   labeled "Tunnel ID".
	TunnelID = 123
	# If you wish to use a different or explicit "Client IPv4 address",
	#   this can be specified via ExplicitClientIP.
	# If it is empty or is not specified, the public IP of this host will be determined
	#   via an external service.
	# This *must* be an IPv4 address (if specified).
	ExplicitClientIP = '203.0.113.1'
	# If you have specified a custom MTU under the "Advanced" tab for this tunnel,
	#   you can set this value here.
	# If you have not set a custom one, leave this option unspecified;
	#   the default (and maximum allowed), 1480 MTU, will be used in that case.
	# This is not used by anything directly in GoBroke, but is contained here
	#   to assist in templating that may be configured.
	MTU = 1450
	# The Username field is optional IF DefaultUsername was specified.
	# This also allows you to specify tunnels from different accounts
	#   by providing a tunnel-specific username.
	Username = "specific_user"
	# The UpdateKey can be found under the "Advanced" tab on your tunnelbroker.net
	#   tunnel's page, labeled "Update Key".
	# Your real token is likely to be a bit longer and more random.
	# This token is used to not only update the client-side tunnel IP but also to
	#   query the HE Tunnelbroker "API" (it's really just a single endpoint)
	#   to get the tunnel configuration.
	UpdateKey = "abcdef"


	######################
	## Config Templates ##
	######################

	# Each ConfigTemplate consists of a path to a template file and a destination
	#   file at the bere minimum. In addition, Commands may be provided.
	# Any paths leading up to Destination that don't exist will (attempt to be)
	#   created.
	# The template is always rendered in memory, but the destination is only written
	#   if:
	#       * The Destination doesn't exist
	#       * The Destination differs from the buffered rendering of the template
	[[Tunnel.ConfigTemplate]]
		# Template points to where the template file can be found.
		# It must be in a Golang text/template syntax/format; see:
		#   https://pkg.go.dev/text/template
		# Refer to this library's definition of the runner.TunnelResult struct;
		#    this is the object that is passed to the template.
		Template = "/etc/gobroke/tpl/dnsmasq/ra_dhcpv6.conf.tpl"
		# Destination is the file to write to.
		# It will only be written to if:
		#   * The path does not exist
		#   * The path exists but is different from the in-memory rendered buffer
		# An attempt will be made to create any leading components that are not
		#   present.
		# It is recommended to enforce permissions/ownership of these via the
		#   Commands.
		Destination = "/etc/dnsmasq.d/ra_dhcpv6.conf"


		#################################
		## Config Template Permissions ##
		#################################

		# Permissions can be defined for the Destination file.
		# They are completely optional, in which case the default umask, user,
		#   group, etc. for the runtime user will be used, and permissions/ownership
		#   will not be enforced for existing Destination files.
		# If the file exists and permissions are defined, they will
        #   be enforced.
        # If the file exists but no permissions are defined, they
        #   will be left as-is.
		[[Tunnel.ConfigTemplate.Permissions]]
			# Permissions are/may be defined for both the file being written
			#   and the parent directory (see below).
			[[Tunnel.ConfigTemplate.Permissions.File]]
				# The User is optional.
				# If specified as '-1', the owner will not be modified/enforced.
				# If specified as an empty string (the default), the runtime EUID is enforced.
				# Otherwise, it may be a username or a UID (checked in that order).
				# (For new files/directories, the OS default behavior is used.)
				User = ""
				# Group is also optional, and follows the same exact logic as User except
				#   for EGID/groupnames/GIDs.
				Group = ""
				# Mode is optional also.
				# It *must* be equal to the octal mode bits (e.g. it must be an
				#   unsigned integer 0-4095), but may be represented in multiple ways.
				# e.g.:
				#   Mode = 0o0600
				#   Mode = 0o600
				#   Mode = 0x0180
				#   Mode = 0x180
				#   Mode = 0b110000000
				#   Mode = 384
				# All evaluate to the exact same value in TOML:
				#   https://toml.io/en/v1.0.0#integer
				# For consistency with `chmod(1)`, it is recommended to use the
				#   octal representation (0o0600 or 0o600 above).
				# If you need help determining what number you should actually use,
				#   you can use the calculator here:
				#       https://rubendougall.co.uk/projects/permissions-calculator/
				#       (source: https://github.com/Ruben9922/permissions-calculator )
				#       (Supports/includes "special" bits)
				#   or here:
				#       https://wintelguy.com/permissions-calc.pl
				#       (beware of ads)
				#       (provides an explanation of the bits)
				# Or see https://en.wikipedia.org/wiki/Chmod
				# Note that this does, technically, work on Windows but only read vs. read-write
				#   for the User is used (https://pkg.go.dev/os?GOOS=windows#Chmod).
				# If not specified, the default is 0o0600 for files and 0o0700 for directories.
				Mode = 0o0600
			# Dir permissions specifiy permissions/ownership of the parent directory of File.
			# The same rules, logic, behavior, etc. as in File apply here.
			[[Tunnel.ConfigTemplate.Permissions.Dir]]
				User = ""
				Group = ""
				Mode = 0o0700


		##############################
		## Config Template Commands ##
		##############################

		# Commands are am optional collection of commands to run as part of this template
		#   run.
		# Multiple Commands may be specified; they will be run in the order specified.
		# The below Command would be equivalent to:
		#   SOMEENV=SOMEVAL /usr/local/bin/somecmd -f foo
		# on the shell.
		[[Tunnel.ConfigTemplate.Command]]
			# ProgramPath should be the absolute path to the binary to run.
			# It behaves as an (os/)exec.Cmd.Path (https://pkg.go.dev/os/exec#Cmd),
			# It is recommended to use an absolute path.
			ProgramPath = '/usr/local/bin/somecmd'
			# Args are optional for a Command.
			# They should conform to the rules for (os/)exec.Cmd.Args.
			Args = [
				'-f', 'foo',
			]
			# If IsolatedEnv is false (the default), the runtime environment variables
			#   will be applied to the command.
			# If true, *only* the EnvVars, if specified, will be used for the spawned
			#   command (an empty environment will be used if IsolateEnv is true and
			#   no EnvVars are specified).
			IsolatedEnv = false
			# If provided, EnvVars can be used to add/replace environment variables.
			# They should conform to the rules for (os/)exec.Cmd.Env.
			# Whether they are added to/selectively replace or completely replace
			#   the current runtime environment variables depends on how IsolateEnv
			#   is configured.
			EnvVars = [
				'SOMEENV=SOMEVAL',
			]
			# If OnChange is true, this Command will run *only if SOMETHING CHANGED*.
			#   (e.g. a /48 was added to the tunnel, the client IP is different, etc.)
			# If false, this Command will run *only if NOTHING CHANGED*.
			# If unspecified, the default is to always run this command regardless
			#   of change status.
			# Writing out this template to disk as a new file counts as a "change".
			OnChange = true
			# By default, this Command will be run literally/as-is.
			# However, in some cases it may be useful to dynamically template out
			#   commands to run.
			# If IsTemplate is set to true, then this Command.ProgramPath, each
			#   of the Command.Args, and each of the Command.EnvVars will be
			#   treated as Golang text/template strings as well, and will also
			#   be passed a runner.TunnelResult.
			# Note that if IsolateEnv is false, runtime/inherited environment
			#   variables will *not* be templated.
			# It is recommended to not enable this unless necessary as it can add
			#   a non-negligible amount of resource overhead/execution time.
			IsTemplate = false

		#######################################################################

	# Multiple ConfigTemplates may be specified.
	[[Tunnel.ConfigTemplate]]
		Template = "/etc/gobroke/tpl/stat.tpl"
		Destination = "/tmp/gobroke.dump"


	#####################
	## Tunnel Commands ##
	#####################

	# Each Tunnel also supports its own commands. The syntax, spcification,
	#   behavior, etc. is the same as the Tunnel.ConfigTemplate.Command.
	# These are executed after all Tunnel.ConfigTemplate (if any) are executed.
	# This is particularly useful for consolidating service restarts.
	[[Tunnel.Command]]
		ProgramPath = 'systemctl'
		Args = [
			'restart',
			'someservice',
		]
		# OnChange in a Tunnel.Command is scoped to any updates of the tunnel
		#   and any changes in ANY of the Tunnel.ConfigTemplate specified
		#   for this Tunnel (if true and ConfigTemplate were specified).
		OnChange = true

###############################################################################

# Multiple tunnel configurations are supported as well.
[[Tunnel]]
	TunnelID = 456
	Username = "specific_user"
	UpdateKey = "defghi"


######################
## General Commands ##
######################

# Command items may be specified at the root level as well.
# The syntax is like all other Commands items, with two exceptions:
#   * There is no templating performed...
#   * As such, there is no IsTemplate directive for these.
# A root-level Command is run after all tunnels complete.
# The OnChange directive is true if any Tunnels result in any changes.
[[Command]]
	ProgramPath = "/usr/local/bin/alltunpsrogram"