telephony.scm 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447
  1. ;;; GNU Guix --- Functional package management for GNU
  2. ;;; Copyright © 2021 Maxim Cournoyer <maxim.cournoyer@gmail.com>
  3. ;;;
  4. ;;; This file is part of GNU Guix.
  5. ;;;
  6. ;;; GNU Guix is free software; you can redistribute it and/or modify it
  7. ;;; under the terms of the GNU General Public License as published by
  8. ;;; the Free Software Foundation; either version 3 of the License, or (at
  9. ;;; your option) any later version.
  10. ;;;
  11. ;;; GNU Guix is distributed in the hope that it will be useful, but
  12. ;;; WITHOUT ANY WARRANTY; without even the implied warranty of
  13. ;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. ;;; GNU General Public License for more details.
  15. ;;;
  16. ;;; You should have received a copy of the GNU General Public License
  17. ;;; along with GNU Guix. If not, see <http://www.gnu.org/licenses/>.
  18. (define-module (tests services telephony)
  19. #:use-module (gnu build jami-service)
  20. #:use-module (gnu services telephony)
  21. #:use-module (srfi srfi-64))
  22. ;;; Tests for the (gnu services telephony) and related modules.
  23. (test-begin "jami-service")
  24. (define parse-dbus-reply
  25. (@@ (gnu build jami-service) parse-dbus-reply))
  26. (define parse-account-ids
  27. (@@ (gnu build jami-service) parse-account-ids))
  28. (define parse-account-details
  29. (@@ (gnu build jami-service) parse-account-details))
  30. (define parse-contacts
  31. (@@ (gnu build jami-service) parse-contacts))
  32. (define jami-account->alist
  33. (@@ (gnu services telephony) jami-account->alist))
  34. ;; $ dbus-send --print-reply --dest="cx.ring.Ring" \
  35. ;; "/cx/ring/Ring/ConfigurationManager" \
  36. ;; "cx.ring.Ring.ConfigurationManager.getAccountList"
  37. (define getAccountList-reply "\
  38. method return time=1622217253.386711 sender=:1.7 -> destination=:1.14 serial=140 reply_serial=2
  39. array [
  40. string \"addf37fbb558d6a0\"
  41. string \"d5cbeb7d08c98a65\"
  42. string \"398af0c6b74ce101\"
  43. ]
  44. ")
  45. (test-equal "parse-account-ids"
  46. '("addf37fbb558d6a0" "d5cbeb7d08c98a65" "398af0c6b74ce101")
  47. (parse-account-ids getAccountList-reply))
  48. ;; $ dbus-send --print-reply --dest="cx.ring.Ring" \
  49. ;; "/cx/ring/Ring/ConfigurationManager" \
  50. ;; "cx.ring.Ring.ConfigurationManager.getAccountDetails" \
  51. ;; 'string:398af0c6b74ce101'
  52. (define getAccountDetails-reply "\
  53. method return time=1622254991.789588 sender=:1.7 -> destination=:1.19 serial=145 reply_serial=2
  54. array [
  55. dict entry(
  56. string \"Account.accountDiscovery\"
  57. string \"false\"
  58. )
  59. dict entry(
  60. string \"Account.accountPublish\"
  61. string \"false\"
  62. )
  63. dict entry(
  64. string \"Account.activeCallLimit\"
  65. string \"-1\"
  66. )
  67. dict entry(
  68. string \"Account.alias\"
  69. string \"some-rendezvous-point-name\"
  70. )
  71. dict entry(
  72. string \"Account.allModeratorEnabled\"
  73. string \"true\"
  74. )
  75. dict entry(
  76. string \"Account.allowCertFromContact\"
  77. string \"true\"
  78. )
  79. dict entry(
  80. string \"Account.allowCertFromHistory\"
  81. string \"true\"
  82. )
  83. dict entry(
  84. string \"Account.allowCertFromTrusted\"
  85. string \"true\"
  86. )
  87. dict entry(
  88. string \"Account.archiveHasPassword\"
  89. string \"false\"
  90. )
  91. dict entry(
  92. string \"Account.audioPortMax\"
  93. string \"32766\"
  94. )
  95. dict entry(
  96. string \"Account.audioPortMin\"
  97. string \"16384\"
  98. )
  99. dict entry(
  100. string \"Account.autoAnswer\"
  101. string \"false\"
  102. )
  103. dict entry(
  104. string \"Account.defaultModerators\"
  105. string \"\"
  106. )
  107. dict entry(
  108. string \"Account.deviceID\"
  109. string \"94b4070fc7a8afa8482c777a9822c52e6af2e1bd\"
  110. )
  111. dict entry(
  112. string \"Account.deviceName\"
  113. string \"some-device\"
  114. )
  115. dict entry(
  116. string \"Account.dhtProxyListUrl\"
  117. string \"https://config.jami.net/proxyList\"
  118. )
  119. dict entry(
  120. string \"Account.displayName\"
  121. string \"some-rendezvous-point-name\"
  122. )
  123. dict entry(
  124. string \"Account.dtmfType\"
  125. string \"overrtp\"
  126. )
  127. dict entry(
  128. string \"Account.enable\"
  129. string \"true\"
  130. )
  131. dict entry(
  132. string \"Account.hasCustomUserAgent\"
  133. string \"false\"
  134. )
  135. dict entry(
  136. string \"Account.hostname\"
  137. string \"bootstrap.jami.net\"
  138. )
  139. dict entry(
  140. string \"Account.localInterface\"
  141. string \"default\"
  142. )
  143. dict entry(
  144. string \"Account.localModeratorsEnabled\"
  145. string \"true\"
  146. )
  147. dict entry(
  148. string \"Account.mailbox\"
  149. string \"\"
  150. )
  151. dict entry(
  152. string \"Account.managerUri\"
  153. string \"\"
  154. )
  155. dict entry(
  156. string \"Account.managerUsername\"
  157. string \"\"
  158. )
  159. dict entry(
  160. string \"Account.peerDiscovery\"
  161. string \"false\"
  162. )
  163. dict entry(
  164. string \"Account.presenceSubscribeSupported\"
  165. string \"true\"
  166. )
  167. dict entry(
  168. string \"Account.proxyEnabled\"
  169. string \"false\"
  170. )
  171. dict entry(
  172. string \"Account.proxyPushToken\"
  173. string \"\"
  174. )
  175. dict entry(
  176. string \"Account.proxyServer\"
  177. string \"dhtproxy.jami.net:[80-95]\"
  178. )
  179. dict entry(
  180. string \"Account.publishedAddress\"
  181. string \"\"
  182. )
  183. dict entry(
  184. string \"Account.publishedPort\"
  185. string \"5060\"
  186. )
  187. dict entry(
  188. string \"Account.publishedSameAsLocal\"
  189. string \"true\"
  190. )
  191. dict entry(
  192. string \"Account.rendezVous\"
  193. string \"true\"
  194. )
  195. dict entry(
  196. string \"Account.ringtoneEnabled\"
  197. string \"true\"
  198. )
  199. dict entry(
  200. string \"Account.ringtonePath\"
  201. string \"/usr/share/ring/ringtones/default.opus\"
  202. )
  203. dict entry(
  204. string \"Account.type\"
  205. string \"RING\"
  206. )
  207. dict entry(
  208. string \"Account.upnpEnabled\"
  209. string \"true\"
  210. )
  211. dict entry(
  212. string \"Account.useragent\"
  213. string \"\"
  214. )
  215. dict entry(
  216. string \"Account.username\"
  217. string \"ccb8bbe2382343f7feb140710ab48aaf1b55634e\"
  218. )
  219. dict entry(
  220. string \"Account.videoEnabled\"
  221. string \"true\"
  222. )
  223. dict entry(
  224. string \"Account.videoPortMax\"
  225. string \"65534\"
  226. )
  227. dict entry(
  228. string \"Account.videoPortMin\"
  229. string \"49152\"
  230. )
  231. dict entry(
  232. string \"DHT.PublicInCalls\"
  233. string \"true\"
  234. )
  235. dict entry(
  236. string \"DHT.port\"
  237. string \"7766\"
  238. )
  239. dict entry(
  240. string \"RingNS.account\"
  241. string \"3989b55313a911b6f0c004748b49b254f35c9ef6\"
  242. )
  243. dict entry(
  244. string \"RingNS.uri\"
  245. string \"\"
  246. )
  247. dict entry(
  248. string \"SRTP.enable\"
  249. string \"true\"
  250. )
  251. dict entry(
  252. string \"SRTP.keyExchange\"
  253. string \"sdes\"
  254. )
  255. dict entry(
  256. string \"SRTP.rtpFallback\"
  257. string \"false\"
  258. )
  259. dict entry(
  260. string \"STUN.enable\"
  261. string \"false\"
  262. )
  263. dict entry(
  264. string \"STUN.server\"
  265. string \"\"
  266. )
  267. dict entry(
  268. string \"TLS.certificateFile\"
  269. string \"/var/lib/jami/.local/share/jami/398af0c6b74ce101/ring_device.crt\"
  270. )
  271. dict entry(
  272. string \"TLS.certificateListFile\"
  273. string \"\"
  274. )
  275. dict entry(
  276. string \"TLS.ciphers\"
  277. string \"\"
  278. )
  279. dict entry(
  280. string \"TLS.method\"
  281. string \"Automatic\"
  282. )
  283. dict entry(
  284. string \"TLS.negotiationTimeoutSec\"
  285. string \"-1\"
  286. )
  287. dict entry(
  288. string \"TLS.password\"
  289. string \"\"
  290. )
  291. dict entry(
  292. string \"TLS.privateKeyFile\"
  293. string \"/var/lib/jami/.local/share/jami/398af0c6b74ce101/ring_device.key\"
  294. )
  295. dict entry(
  296. string \"TLS.requireClientCertificate\"
  297. string \"true\"
  298. )
  299. dict entry(
  300. string \"TLS.serverName\"
  301. string \"\"
  302. )
  303. dict entry(
  304. string \"TLS.verifyClient\"
  305. string \"true\"
  306. )
  307. dict entry(
  308. string \"TLS.verifyServer\"
  309. string \"true\"
  310. )
  311. dict entry(
  312. string \"TURN.enable\"
  313. string \"true\"
  314. )
  315. dict entry(
  316. string \"TURN.password\"
  317. string \"ring\"
  318. )
  319. dict entry(
  320. string \"TURN.realm\"
  321. string \"ring\"
  322. )
  323. dict entry(
  324. string \"TURN.server\"
  325. string \"turn.jami.net\"
  326. )
  327. dict entry(
  328. string \"TURN.username\"
  329. string \"ring\"
  330. )
  331. ]
  332. ")
  333. (test-equal "parse-account-details; username, alias and display name"
  334. '("ccb8bbe2382343f7feb140710ab48aaf1b55634e" ;username
  335. "some-rendezvous-point-name" ;alias
  336. "some-rendezvous-point-name") ;displayName
  337. (let ((account-details (parse-account-details getAccountDetails-reply)))
  338. (list (assoc-ref account-details "Account.username")
  339. (assoc-ref account-details "Account.alias")
  340. (assoc-ref account-details "Account.displayName"))))
  341. (define getContacts-reply "\
  342. method return time=1627014042.752673 sender=:1.113 -> destination=:1.186 serial=220 reply_serial=2
  343. array [
  344. array [
  345. dict entry(
  346. string \"added\"
  347. string \"1578883327\"
  348. )
  349. dict entry(
  350. string \"confirmed\"
  351. string \"true\"
  352. )
  353. dict entry(
  354. string \"id\"
  355. string \"1c7d5a09464223442549fef172a3cf6f4de9b01c\"
  356. )
  357. ]
  358. array [
  359. dict entry(
  360. string \"added\"
  361. string \"1623107941\"
  362. )
  363. dict entry(
  364. string \"confirmed\"
  365. string \"true\"
  366. )
  367. dict entry(
  368. string \"id\"
  369. string \"5903c6c9ac5cb863c64e559add3d5d1c8c563449\"
  370. )
  371. ]
  372. array [
  373. dict entry(
  374. string \"added\"
  375. string \"1595996256\"
  376. )
  377. dict entry(
  378. string \"confirmed\"
  379. string \"true\"
  380. )
  381. dict entry(
  382. string \"id\"
  383. string \"ff2d72a548693214fb3a0f0f7a943b5e2bb9be03\"
  384. )
  385. ]
  386. ]")
  387. (test-equal "parse-account-contacts"
  388. '((("added" . "1578883327")
  389. ("confirmed" . "true")
  390. ("id" . "1c7d5a09464223442549fef172a3cf6f4de9b01c"))
  391. (("added" . "1623107941")
  392. ("confirmed" . "true")
  393. ("id" . "5903c6c9ac5cb863c64e559add3d5d1c8c563449"))
  394. (("added" . "1595996256")
  395. ("confirmed" . "true")
  396. ("id" . "ff2d72a548693214fb3a0f0f7a943b5e2bb9be03")))
  397. (parse-contacts getContacts-reply))
  398. (define getContacts-empty-reply "\
  399. method return time=1627400787.873988 sender=:1.1197 -> destination=:1.1463 serial=2127 reply_serial=2
  400. array [
  401. ]")
  402. (test-equal "parse-account-contacts, empty array"
  403. '()
  404. (parse-contacts getContacts-empty-reply))
  405. (define %dummy-jami-account (jami-account
  406. (archive "/tmp/dummy.gz")))
  407. (define %dummy-jami-account-2 (jami-account
  408. (archive "/tmp/dummy.gz")
  409. (rendezvous-point? #t)
  410. (peer-discovery? #f)
  411. (bootstrap-hostnames '("bootstrap.me"
  412. "fallback.another.host"))
  413. (name-server-uri "https://my.name.server")))
  414. (test-equal "jami-account->alist, no account detail value set"
  415. '()
  416. (jami-account->alist %dummy-jami-account))
  417. (test-equal "jami-account->alist, with account detail values"
  418. '(("Account.hostname" . "bootstrap.me;fallback.another.host")
  419. ("Account.peerDiscovery" . "false")
  420. ("Account.rendezVous" . "true")
  421. ("RingNS.uri" . "https://my.name.server"))
  422. (sort (jami-account->alist %dummy-jami-account-2)
  423. (lambda (x y)
  424. (string<=? (car x) (car y)))))
  425. (test-end)