@@ -3,7 +3,7 @@ import gleam/bool
33import gleam/dict . { type Dict }
44import gleam/erlang/process . { type Subject }
55import gleam/list
6- import gleam/option . { type Option , None , Some }
6+ import gleam/option . { None , Some }
77import gleam/otp/actor
88import gleam/result
99import gleam/set . { type Set }
@@ -13,6 +13,10 @@ const mds_port = 5353
1313
1414const all_services_type = "_services._dns-sd._udp.local"
1515
16+ // TODO: should I keep this re-export, or do something else?
17+ pub type IpAddress =
18+ toss . IpAddress
19+
1620/// Describes a service fully discovered via DNS-SD.
1721pub type ServiceDescription {
1822 ServiceDescription (
@@ -35,10 +39,8 @@ pub type ServiceDescription {
3539 port : Int ,
3640 /// Any TXT records that the service advertises (can be empty).
3741 txt_values : List ( String ) ,
38- /// The IPv4 address, if advertised.
39- ipv4 : Option ( # ( Int , Int , Int , Int ) ) ,
40- /// The IPv6 address, if advertised.
41- ipv6 : Option ( # ( Int , Int , Int , Int , Int , Int , Int , Int ) ) ,
42+ /// The resolved IP address
43+ ip : IpAddress ,
4244 )
4345}
4446
@@ -288,24 +290,26 @@ fn description_from_records(
288290 service_type : String ,
289291 instance_name : String ,
290292) -> Result ( ServiceDescription , Nil ) {
291- use # ( priority , weight , port , target_name ) <- result . try (
292- list . find_map ( records , fn ( record ) {
293- case record {
294- dns . SrvRecord ( priority : , weight : , port : , target_name : , .. ) ->
295- Ok ( # ( priority , weight , port , target_name ) )
296- _ -> Error ( Nil )
297- }
298- } ) ,
299- )
293+ let try_find = fn ( with : fn ( ResourceRecord ) -> Result ( a, Nil ) , apply ) {
294+ result . try ( list . find_map ( records , with ) , apply )
295+ }
300296
301- let # ( ipv4 , ipv6 ) =
302- list . fold ( records , # ( None , None ) , fn ( ips , record ) {
303- case record {
304- dns . ARecord ( ip : , .. ) -> # ( Some ( ip ) , ips . 1 )
305- dns . AaaaRecord ( ip : , .. ) -> # ( ips . 0 , Some ( ip ) )
306- _ -> ips
307- }
308- } )
297+ use # ( priority , weight , port , target_name ) <- try_find ( fn ( record ) {
298+ case record {
299+ dns . SrvRecord ( priority : , weight : , port : , target_name : , .. ) ->
300+ Ok ( # ( priority , weight , port , target_name ) )
301+ _ -> Error ( Nil )
302+ }
303+ } )
304+
305+ use ip <- try_find ( fn ( record ) {
306+ case record {
307+ dns . ARecord ( ip : , .. ) -> Ok ( toss . Ipv4Address ( ip . 0 , ip . 1 , ip . 2 , ip . 3 ) )
308+ dns . AaaaRecord ( ip : , .. ) ->
309+ Ok ( toss . Ipv6Address ( ip . 0 , ip . 1 , ip . 2 , ip . 3 , ip . 4 , ip . 5 , ip . 6 , ip . 7 ) )
310+ _ -> Error ( Nil )
311+ }
312+ } )
309313
310314 let txt_values =
311315 list . flat_map ( records , fn ( record ) {
@@ -315,19 +319,14 @@ fn description_from_records(
315319 }
316320 } )
317321
318- case option . is_some ( ipv4 ) || option . is_some ( ipv6 ) {
319- True ->
320- Ok ( ServiceDescription (
321- service_type : ,
322- instance_name : ,
323- target_name : ,
324- priority : ,
325- weight : ,
326- port : ,
327- txt_values : ,
328- ipv4 : ,
329- ipv6 : ,
330- ) )
331- False -> Error ( Nil )
332- }
322+ Ok ( ServiceDescription (
323+ service_type : ,
324+ instance_name : ,
325+ target_name : ,
326+ priority : ,
327+ weight : ,
328+ port : ,
329+ txt_values : ,
330+ ip : ,
331+ ) )
333332}
0 commit comments