aboutsummaryrefslogtreecommitdiffstats
path: root/test
diff options
context:
space:
mode:
Diffstat (limited to 'test')
-rw-r--r--test/lisp/url/url-auth-tests.el249
1 files changed, 249 insertions, 0 deletions
diff --git a/test/lisp/url/url-auth-tests.el b/test/lisp/url/url-auth-tests.el
new file mode 100644
index 00000000000..36c177f9dad
--- /dev/null
+++ b/test/lisp/url/url-auth-tests.el
@@ -0,0 +1,249 @@
1;;; url-auth-tests.el --- Test suite for url-auth.
2
3;; Copyright (C) 2015 Free Software Foundation, Inc.
4
5;; Author: Jarno Malmari <jarno@malmari.fi>
6
7;; This program is free software; you can redistribute it and/or modify
8;; it under the terms of the GNU General Public License as published by
9;; the Free Software Foundation, either version 3 of the License, or
10;; (at your option) any later version.
11
12;; This program is distributed in the hope that it will be useful,
13;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15;; GNU General Public License for more details.
16
17;; You should have received a copy of the GNU General Public License
18;; along with this program. If not, see <http://www.gnu.org/licenses/>.
19
20;;; Commentary:
21
22;; Test HTTP authentication methods.
23
24;;; Code:
25
26(require 'ert)
27(require 'url-auth)
28
29(defvar url-auth-test-challenges nil
30 "List of challenges for testing.
31Each challenge is a plist. Values are as presented by the
32server's WWW-Authenticate header field.")
33
34;; Set explicitly for easier modification for re-runs.
35(setq url-auth-test-challenges
36 (list
37 (list :qop "auth"
38 :nonce "uBr3+qkQBybTr/dKWkmpUqVO7SaEwWYzyTKO7g==$"
39 :uri "/random/path"
40 :method "GET"
41 :realm "Some test realm"
42 :cnonce "YWU4NDcxYWMxMDAxMjlkMjAwMDE4MjI5MDAwMGY4NGQ="
43 :nc "00000001"
44 :username "jytky"
45 :password "xi5Ac2HEfKt1lKKO05DCSqsK0u7hqqtsT"
46 :expected-ha1 "af521db3a83abd91262fead04fa31892"
47 :expected-ha2 "e490a6a147c79404b365d1f6059ddda5"
48 :expected-response "ecb6396e93b9e09e31f19264cfd8f854")
49 (list :nonce "a1be8a3065e00c5bf190ad499299aea5"
50 :opaque "d7c2a27230fc8c74bb6e06be8c9cd189"
51 :realm "The Test Realm"
52 :username "user"
53 :password "passwd"
54 :uri "/digest-auth/auth/user/passwd"
55 :method "GET"
56 :expected-ha1 "19c41161a8720edaeb7922ef8531137d"
57 :expected-ha2 "b44272ea65ee4af7fb26c5dba58f6863"
58 :expected-response "46c47a6d8e1fa95a3efcf49724af3fe7")
59 (list :nonce "servernonce"
60 :username "user"
61 :password "passwd"
62 :realm "The Test Realm 1"
63 :uri "/digest-auth/auth/user/passwd"
64 :method "GET"
65 :expected-ha1 "00f848f943c9a05dd06c932a7334f120"
66 :expected-ha2 "b44272ea65ee4af7fb26c5dba58f6863"
67 :expected-response "b8a48cdc9aa9e514509a5a5c53d4e8cf")
68 (list :nonce "servernonce"
69 :username "user"
70 :password "passwd"
71 :realm "The Test Realm 2"
72 :uri "/digest-auth/auth/user/passwd"
73 :method "GET"
74 :expected-ha1 "74d6abd3651d6b8260733d8a4c37ec1a"
75 :expected-ha2 "b44272ea65ee4af7fb26c5dba58f6863"
76 :expected-response "0d84884d967e04440efc77e9e2b5b561")))
77
78(ert-deftest url-auth-test-digest-create-key ()
79 "Check user credentials in their hashed form."
80 (dolist (challenge url-auth-test-challenges)
81 (let ((key (url-digest-auth-create-key (plist-get challenge :username)
82 (plist-get challenge :password)
83 (plist-get challenge :realm)
84 (plist-get challenge :method)
85 (plist-get challenge :uri))))
86 (should (= (length key) 2))
87 (should (string= (nth 0 key) (plist-get challenge :expected-ha1)))
88 (should (string= (nth 1 key) (plist-get challenge :expected-ha2)))
89 )))
90
91(ert-deftest url-auth-test-digest-auth-retrieve-cache ()
92 "Check how the entry point retrieves cached authentication.
93Essential is how realms and paths are matched."
94
95 (let* ((url-digest-auth-storage
96 '(("example.org:80"
97 ("/path/auth1" "auth1user" "key")
98 ("/path" "pathuser" "key")
99 ("/" "rootuser" "key")
100 ("realm1" "realm1user" "key")
101 ("realm2" "realm2user" "key")
102 ("/path/auth2" "auth2user" "key"))
103 ("example.org:443"
104 ("realm" "secure_user" "key"))
105 ("rootless.org:80" ; no "/" entry for this on purpose
106 ("/path" "pathuser" "key")
107 ("realm" "realmuser" "key"))))
108 (attrs (list (cons "nonce" "servernonce")))
109 auth)
110
111 (dolist (row (list
112 ;; If :expected-user is `nil' it indicates
113 ;; authentication information shouldn't be found.
114
115 ;; non-existent server
116 (list :url "http://other.com/path" :realm nil :expected-user nil)
117
118 ;; unmatched port
119 (list :url "http://example.org:444/path" :realm nil :expected-user
120il)
121
122 ;; root, no realm
123 (list :url "http://example.org/"
124 :realm nil :expected-user "rootuser")
125
126 ;; root, no realm, explicit port
127 (list :url "http://example.org:80/"
128 :realm nil :expected-user "rootuser")
129
130 (list :url "http://example.org/unknown"
131 :realm nil :expected-user "rootuser")
132
133 ;; realm specified, overrides any path
134 (list :url "http://example.org/"
135 :realm "realm1" :expected-user "realm1user")
136
137 ;; realm specified, overrides any path
138 (list :url "http://example.org/"
139 :realm "realm2" :expected-user "realm2user")
140
141 ;; authentication determined by path
142 (list :url "http://example.org/path/auth1/query"
143 :realm nil :expected-user "auth1user")
144
145 ;; /path shadows /path/auth2, hence pathuser is expected
146 (list :url "http://example.org/path/auth2/query"
147 :realm nil :expected-user "pathuser")
148
149 (list :url "https://example.org/path"
150 :realm nil :expected-user "secure_user")
151
152 ;; not really secure user but using the same port
153 (list :url "http://example.org:443/path"
154 :realm nil :expected-user "secure_user")
155
156 ;; preferring realm user over path, even though no
157 ;; realm specified (not sure why)
158 (list :url "http://rootless.org/"
159 :realm nil :expected-user "realmuser")
160 ;; second variant for the same case
161 (list :url "http://rootless.org/unknown/path"
162 :realm nil :expected-user "realmuser")
163
164 ;; path match
165 (list :url "http://rootless.org/path/query?q=a"
166 :realm nil :expected-user "pathuser")
167
168 ;; path match, realm match, prefer realm
169 (list :url "http://rootless.org/path/query?q=a"
170 :realm "realm" :expected-user "realmuser")
171 ))
172 (setq auth (url-digest-auth (plist-get row :url)
173 nil nil
174 (plist-get row :realm) attrs))
175 (if (plist-get row :expected-user)
176 (progn (should auth)
177 (should (string-match ".*username=\"\\(.*?\\)\".*" auth))
178 (should (string= (match-string 1 auth)
179 (plist-get row :expected-user))))
180 (should-not auth)))))
181
182(ert-deftest url-auth-test-digest-auth ()
183 "Check common authorization string contents.
184Challenges with qop are not checked for response since a unique
185cnonce is used for generating them which is not mocked by the
186test and cannot be passed by arguments to `url-digest-auth'."
187 (dolist (challenge url-auth-test-challenges)
188 (let* ((attrs (append
189 (list (cons "nonce" (plist-get challenge :nonce)))
190 (if (plist-get challenge :qop)
191 (list (cons "qop" (plist-get challenge :qop))))))
192 (url (concat "http://example.org" (plist-get challenge :uri)))
193 url-digest-auth-storage
194 auth)
195 ;; Add authentication info to cache so `url-digest-auth' can
196 ;; complete without prompting minibuffer input.
197 (setq url-digest-auth-storage
198 (list
199 (list "example.org:80"
200 (cons (or (plist-get challenge :realm) "/")
201 (cons (plist-get challenge :username)
202 (url-digest-auth-create-key (plist-get challenge :username)
203 (plist-get challenge :password)
204 (plist-get challenge :realm)
205 (plist-get challenge :method)
206 (plist-get challenge :uri)))))))
207 (setq auth (url-digest-auth (url-generic-parse-url url) nil nil
208 (plist-get challenge :realm) attrs))
209 (should auth)
210 (should (string-prefix-p "Digest " auth))
211 (should (string-match ".*username=\"\\(.*?\\)\".*" auth))
212 (should (string= (match-string 1 auth)
213 (plist-get challenge :username)))
214 (should (string-match ".*realm=\"\\(.*?\\)\".*" auth))
215 (should (string= (match-string 1 auth)
216 (plist-get challenge :realm)))
217
218 (if (plist-member challenge :qop)
219 (progn
220 ;; We don't know these, just check that they exists.
221 (should (string-match-p ".*response=\".*?\".*" auth))
222 (should (string-match-p ".*nc=\".*?\".*" auth))
223 (should (string-match-p ".*cnonce=\".*?\".*" auth)))
224 (should (string-match ".*response=\"\\(.*?\\)\".*" auth))
225 (should (string= (match-string 1 auth)
226 (plist-get challenge :expected-response))))
227 )))
228
229(ert-deftest url-auth-test-digest-auth-opaque ()
230 "Check that `opaque' value is added to result when presented by
231the server."
232 (let* ((url-digest-auth-storage
233 '(("example.org:80" ("/" "user" "key"))))
234 (attrs (list (cons "nonce" "anynonce")))
235 auth)
236 ;; Get authentication info from cache without `opaque'.
237 (setq auth (url-digest-auth "http://example.org/path" nil nil nil attrs))
238 (should auth)
239 (should-not (string-match-p "opaque=" auth))
240
241 ;; Add `opaque' to attributes.
242 (push (cons "opaque" "opaque-value") attrs)
243 (setq auth (url-digest-auth "http://example.org/path" nil nil nil attrs))
244 (should auth)
245 (should (string-match ".*opaque=\"\\(.*?\\)\".*" auth))
246 (should (string= (match-string 1 auth) "opaque-value"))))
247
248(provide 'url-auth-tests)
249;;; url-auth-tests.el ends here