Skip to content

Commit da41ae5

Browse files
authored
Allow to configure where to send notifications (#14)
1 parent 36c8828 commit da41ae5

File tree

2 files changed

+99
-13
lines changed

2 files changed

+99
-13
lines changed

codecov.yml

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
codecov:
2+
require_ci_to_pass: false
3+
4+
comment:
5+
layout: "header, diff, files, footer"
6+
behavior: default
7+
8+
coverage:
9+
status:
10+
project:
11+
default:
12+
informational: true
13+
patch:
14+
default:
15+
informational: true
16+
17+
github_checks:
18+
annotations: false

lib/ice_agent.ex

Lines changed: 81 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -66,16 +66,26 @@ defmodule ExICE.ICEAgent do
6666

6767
@typedoc """
6868
ICE Agent configuration options.
69+
All notifications are by default sent to a process that spawns `ExICE`.
70+
This behavior can be overwritten using the following options.
6971
7072
* `ip_filter` - filter applied when gathering local candidates
7173
* `stun_servers` - list of STUN servers
74+
* `on_gathering_state_change` - where to send gathering state change notifications. Defaults to a process that spawns `ExICE`.
75+
* `on_connection_state_change` - where to send connection state change notifications. Defaults to a process that spawns `ExICE`.
76+
* `on_data` - where to send data. Defaults to a process that spawns `ExICE`.
77+
* `on_new_candidate` - where to send new candidates. Defaults to a process that spawns `ExICE`.
7278
7379
Currently, there is no support for local relay (TURN) candidates
7480
however, remote relay candidates work correctly.
7581
"""
7682
@type opts() :: [
7783
ip_filter: (:inet.ip_address() -> boolean),
78-
stun_servers: [String.t()]
84+
stun_servers: [String.t()],
85+
on_gathering_state_change: pid() | nil,
86+
on_connection_state_change: pid() | nil,
87+
on_data: pid() | nil,
88+
on_new_candidate: pid() | nil
7989
]
8090

8191
defguardp are_pairs_equal(p1, p2)
@@ -99,6 +109,38 @@ defmodule ExICE.ICEAgent do
99109
GenServer.start_link(__MODULE__, opts ++ [role: role, controlling_process: self()])
100110
end
101111

112+
@doc """
113+
Configures where to send gathering state change notifications.
114+
"""
115+
@spec on_gathering_state_change(pid(), pid() | nil) :: :ok
116+
def on_gathering_state_change(ice_agent, send_to) do
117+
GenServer.call(ice_agent, {:on_gathering_state_change, send_to})
118+
end
119+
120+
@doc """
121+
Configures where to send connection state change notifications.
122+
"""
123+
@spec on_connection_state_change(pid(), pid() | nil) :: :ok
124+
def on_connection_state_change(ice_agent, send_to) do
125+
GenServer.call(ice_agent, {:on_connection_state_change, send_to})
126+
end
127+
128+
@doc """
129+
Configures where to send data.
130+
"""
131+
@spec on_data(pid(), pid() | nil) :: :ok
132+
def on_data(ice_agent, send_to) do
133+
GenServer.call(ice_agent, {:on_data, send_to})
134+
end
135+
136+
@doc """
137+
Configures where to send new candidates.
138+
"""
139+
@spec on_new_candidate(pid(), pid() | nil) :: :ok
140+
def on_new_candidate(ice_agent, send_to) do
141+
GenServer.call(ice_agent, {:on_new_candidate, send_to})
142+
end
143+
102144
@doc """
103145
Gets local credentials.
104146
@@ -200,9 +242,15 @@ defmodule ExICE.ICEAgent do
200242

201243
{local_ufrag, local_pwd} = generate_credentials()
202244

245+
controlling_process = Keyword.fetch!(opts, :controlling_process)
246+
203247
state = %{
204248
state: :new,
205-
controlling_process: Keyword.fetch!(opts, :controlling_process),
249+
controlling_process: controlling_process,
250+
on_connection_state_change: opts[:on_connection_state_change] || controlling_process,
251+
on_gathering_state_change: opts[:on_gathering_state_change] || controlling_process,
252+
on_data: opts[:on_data] || controlling_process,
253+
on_new_candidate: opts[:on_new_candidate] || controlling_process,
206254
ta_timer: nil,
207255
gathering_transactions: %{},
208256
ip_filter: opts[:ip_filter],
@@ -230,6 +278,26 @@ defmodule ExICE.ICEAgent do
230278
{:ok, state}
231279
end
232280

281+
@impl true
282+
def handle_call({:on_gathering_state_change, send_to}, _from, state) do
283+
{:reply, :ok, %{state | on_gathering_state_change: send_to}}
284+
end
285+
286+
@impl true
287+
def handle_call({:on_connection_state_change, send_to}, _from, state) do
288+
{:reply, :ok, %{state | on_connection_state_change: send_to}}
289+
end
290+
291+
@impl true
292+
def handle_call({:on_data, send_to}, _from, state) do
293+
{:reply, :ok, %{state | on_data: send_to}}
294+
end
295+
296+
@impl true
297+
def handle_call({:on_new_candidate, send_to}, _from, state) do
298+
{:reply, :ok, %{state | on_new_candidate: send_to}}
299+
end
300+
233301
@impl true
234302
def handle_call(:get_local_credentials, _from, state) do
235303
{:reply, {:ok, state.local_ufrag, state.local_pwd}, state}
@@ -277,16 +345,13 @@ defmodule ExICE.ICEAgent do
277345
@impl true
278346
def handle_cast(:gather_candidates, %{gathering_state: :new} = state) do
279347
Logger.debug("Gathering state change: #{state.gathering_state} -> gathering")
280-
send(state.controlling_process, {:ex_ice, self(), {:gathering_state_change, :gathering}})
348+
notify(state.on_gathering_state_change, {:gathering_state_change, :gathering})
281349
state = %{state | gathering_state: :gathering}
282350

283351
{:ok, host_candidates} = Gatherer.gather_host_candidates(ip_filter: state.ip_filter)
284352

285353
for cand <- host_candidates do
286-
send(
287-
state.controlling_process,
288-
{:ex_ice, self(), {:new_candidate, Candidate.marshal(cand)}}
289-
)
354+
notify(state.on_new_candidate, {:new_candidate, Candidate.marshal(cand)})
290355
end
291356

292357
# TODO should we override?
@@ -512,7 +577,7 @@ defmodule ExICE.ICEAgent do
512577
{:noreply, state}
513578
end
514579
else
515-
send(state.controlling_process, {:ex_ice, self(), {:data, packet}})
580+
notify(state.on_data, {:data, packet})
516581
{:noreply, state}
517582
end
518583
end
@@ -949,7 +1014,7 @@ defmodule ExICE.ICEAgent do
9491014
)
9501015

9511016
Logger.debug("New srflx candidate: #{inspect(c)}")
952-
send(state.controlling_process, {:ex_ice, self(), {:new_candidate, Candidate.marshal(c)}})
1017+
notify(state.on_new_candidate, {:new_candidate, Candidate.marshal(c)})
9531018
add_srflx_cand(c, state)
9541019

9551020
cand ->
@@ -1292,12 +1357,12 @@ defmodule ExICE.ICEAgent do
12921357
cond do
12931358
state.gathering_state == :new and transaction_in_progress? ->
12941359
Logger.debug("Gathering state change: new -> gathering")
1295-
send(state.controlling_process, {:ex_ice, self(), {:gathering_state_change, :gathering}})
1360+
notify(state.on_gathering_state_change, {:gathering_state_change, :gathering})
12961361
%{state | gathering_state: :gathering}
12971362

12981363
state.gathering_state == :gathering and not transaction_in_progress? ->
12991364
Logger.debug("Gathering state change: gathering -> complete")
1300-
send(state.controlling_process, {:ex_ice, self(), {:gathering_state_change, :complete}})
1365+
notify(state.on_gathering_state_change, {:gathering_state_change, :complete})
13011366
%{state | gathering_state: :complete}
13021367

13031368
true ->
@@ -1346,7 +1411,7 @@ defmodule ExICE.ICEAgent do
13461411
end
13471412

13481413
Logger.debug("Gathering state change: #{state.gathering_state} -> new")
1349-
send(state.controlling_process, {:ex_ice, self(), {:gathering_state_change, :new}})
1414+
notify(state.on_gathering_state_change, {:gathering_state_change, :new})
13501415

13511416
%{
13521417
state
@@ -1404,7 +1469,7 @@ defmodule ExICE.ICEAgent do
14041469
@spec change_connection_state(atom(), map()) :: map()
14051470
def change_connection_state(new_conn_state, state) do
14061471
Logger.debug("Connection state change: #{state.state} -> #{new_conn_state}")
1407-
send(state.controlling_process, {:ex_ice, self(), {:connection_state_change, new_conn_state}})
1472+
notify(state.on_connection_state_change, {:connection_state_change, new_conn_state})
14081473
%{state | state: new_conn_state}
14091474
end
14101475

@@ -1620,4 +1685,7 @@ defmodule ExICE.ICEAgent do
16201685
end
16211686
end
16221687
end
1688+
1689+
defp notify(nil, _msg), do: :ok
1690+
defp notify(dst, msg), do: send(dst, {:ex_ice, self(), msg})
16231691
end

0 commit comments

Comments
 (0)