Skip to content

Commit d1c8682

Browse files
committed
make configurable
1 parent 116b392 commit d1c8682

File tree

2 files changed

+68
-5
lines changed

2 files changed

+68
-5
lines changed

lib/dns_cluster.ex

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,8 @@ defmodule DNSCluster do
9292
`"myapp.internal"` or `["foo.internal", "bar.internal"]`. If the basename
9393
differs between nodes, a tuple of `{basename, query}` can be provided as well.
9494
The value `:ignore` can be used to ignore starting the DNSCluster.
95+
* `:dns_rr_types` - the resource records types that are used for node discovery.
96+
Defaults to `[:a, :aaaa, :srv]` which are all currently supported types.
9597
* `:interval` - the millisec interval between DNS queries. Defaults to `5000`.
9698
* `:connect_timeout` - the millisec timeout to allow discovered nodes to connect.
9799
Defaults to `10_000`.
@@ -108,21 +110,29 @@ defmodule DNSCluster do
108110
GenServer.start_link(__MODULE__, opts, name: Keyword.get(opts, :name, __MODULE__))
109111
end
110112

113+
@valid_rr_types [:a, :aaaa, :srv]
114+
111115
@impl true
112116
def init(opts) do
117+
dns_rr_types = Keyword.get(opts, :dns_rr_types, @valid_rr_types)
118+
113119
case Keyword.fetch(opts, :query) do
114120
{:ok, :ignore} ->
115121
:ignore
116122

117123
{:ok, query} ->
118-
if valid_query?(query) do
124+
with(
125+
{:valid_query?, true} <- {:valid_query?, valid_query?(query)},
126+
{:valid_rr_types?, true} <- {:valid_rr_types?, valid_rr_types?(dns_rr_types)}
127+
) do
119128
warn_on_invalid_dist()
120129
resolver = Keyword.get(opts, :resolver, Resolver)
121130

122131
state = %{
123132
interval: Keyword.get(opts, :interval, 5_000),
124133
basename: resolver.basename(node()),
125134
query: List.wrap(query),
135+
dns_rr_types: dns_rr_types,
126136
log: Keyword.get(opts, :log, false),
127137
poll_timer: nil,
128138
connect_timeout: Keyword.get(opts, :connect_timeout, 10_000),
@@ -131,8 +141,13 @@ defmodule DNSCluster do
131141

132142
{:ok, state, {:continue, :discover_ips}}
133143
else
134-
raise ArgumentError,
135-
"expected :query to be a string, {basename, query}, or list, got: #{inspect(query)}"
144+
{:valid_query?, false} ->
145+
raise ArgumentError,
146+
"expected :query to be a string, {basename, query}, or list, got: #{inspect(query)}"
147+
148+
{:valid_rr_types?, false} ->
149+
raise ArgumentError,
150+
"expected :dns_rr_types to be a subset of [:a, :aaaa, :srv], got: #{inspect(dns_rr_types)}"
136151
end
137152

138153
:error ->
@@ -186,8 +201,8 @@ defmodule DNSCluster do
186201
%{state | poll_timer: Process.send_after(self(), :discover_ips, state.interval)}
187202
end
188203

189-
defp discover_ips(%{resolver: resolver, query: queries} = state) do
190-
[:a, :aaaa, :srv]
204+
defp discover_ips(%{resolver: resolver, query: queries, dns_rr_types: dns_rr_types} = state) do
205+
dns_rr_types
191206
|> Enum.flat_map(fn type ->
192207
Enum.flat_map(queries, fn query ->
193208
{basename, query} =
@@ -220,6 +235,13 @@ defmodule DNSCluster do
220235
end)
221236
end
222237

238+
defp valid_rr_types?([]), do: false
239+
240+
defp valid_rr_types?(dns_rr_types) do
241+
MapSet.new(dns_rr_types)
242+
|> MapSet.subset?(MapSet.new(@valid_rr_types))
243+
end
244+
223245
defp warn_on_invalid_dist do
224246
release? = is_binary(System.get_env("RELEASE_NAME"))
225247
net_state = if function_exported?(:net_kernel, :get_state, 0), do: :net_kernel.get_state()

test/dns_cluster_test.exs

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -139,4 +139,45 @@ defmodule DNSClusterTest do
139139
end
140140
end
141141
end
142+
143+
describe "dns_rr_types" do
144+
test "dns_rr_types can be a subset of [:a, :aaaa, :srv]", config do
145+
assert {:ok, _cluster} =
146+
start_supervised(
147+
{DNSCluster,
148+
name: config.test,
149+
query: "app.internal",
150+
dns_rr_types: [:a, :srv],
151+
resolver: __MODULE__}
152+
)
153+
end
154+
155+
test "dns_rr_types can't be outside of [:a, :aaaa, :srv]", config do
156+
assert_raise RuntimeError,
157+
~r/expected :dns_rr_types to be a subset of \[:a, :aaaa, :srv\]/,
158+
fn ->
159+
start_supervised!(
160+
{DNSCluster,
161+
name: config.test,
162+
query: "app.internal",
163+
dns_rr_types: [],
164+
resolver: __MODULE__}
165+
)
166+
end
167+
end
168+
169+
test "dns_rr_types can't be empty", config do
170+
assert_raise RuntimeError,
171+
~r/expected :dns_rr_types to be a subset of \[:a, :aaaa, :srv\]/,
172+
fn ->
173+
start_supervised!(
174+
{DNSCluster,
175+
name: config.test,
176+
query: "app.internal",
177+
dns_rr_types: [],
178+
resolver: __MODULE__}
179+
)
180+
end
181+
end
182+
end
142183
end

0 commit comments

Comments
 (0)