giant massive dep upgrade and dialyxir-found error emporium (#371)
[akkoma] / test / pleroma / web / pleroma_api / controllers / two_factor_authentication_controller_test.exs
1 # Pleroma: A lightweight social networking server
2 # Copyright © 2017-2021 Pleroma Authors <https://pleroma.social/>
3 # SPDX-License-Identifier: AGPL-3.0-only
4
5 defmodule Pleroma.Web.PleromaAPI.TwoFactorAuthenticationControllerTest do
6 use Pleroma.Web.ConnCase, async: true
7
8 import Pleroma.Factory
9 alias Pleroma.MFA.Settings
10 alias Pleroma.MFA.TOTP
11
12 describe "GET /api/pleroma/accounts/mfa/settings" do
13 test "returns user mfa settings for new user", %{conn: conn} do
14 token = insert(:oauth_token, scopes: ["read", "follow"])
15 token2 = insert(:oauth_token, scopes: ["write"])
16
17 assert conn
18 |> put_req_header("authorization", "Bearer #{token.token}")
19 |> get("/api/pleroma/accounts/mfa")
20 |> json_response(:ok) == %{
21 "settings" => %{"enabled" => false, "totp" => false}
22 }
23
24 assert conn
25 |> put_req_header("authorization", "Bearer #{token2.token}")
26 |> get("/api/pleroma/accounts/mfa")
27 |> json_response(403) == %{
28 "error" => "Insufficient permissions: read:security."
29 }
30 end
31
32 test "returns user mfa settings with enabled totp", %{conn: conn} do
33 user =
34 insert(:user,
35 multi_factor_authentication_settings: %Settings{
36 enabled: true,
37 totp: %Settings.TOTP{secret: "XXX", delivery_type: "app", confirmed: true}
38 }
39 )
40
41 token = insert(:oauth_token, scopes: ["read", "follow"], user: user)
42
43 assert conn
44 |> put_req_header("authorization", "Bearer #{token.token}")
45 |> get("/api/pleroma/accounts/mfa")
46 |> json_response(:ok) == %{
47 "settings" => %{"enabled" => true, "totp" => true}
48 }
49 end
50 end
51
52 describe "GET /api/pleroma/accounts/mfa/backup_codes" do
53 test "returns backup codes", %{conn: conn} do
54 user =
55 insert(:user,
56 multi_factor_authentication_settings: %Settings{
57 backup_codes: ["1", "2", "3"],
58 totp: %Settings.TOTP{secret: "secret"}
59 }
60 )
61
62 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
63 token2 = insert(:oauth_token, scopes: ["read"])
64
65 response =
66 conn
67 |> put_req_header("authorization", "Bearer #{token.token}")
68 |> get("/api/pleroma/accounts/mfa/backup_codes")
69 |> json_response(:ok)
70
71 assert [<<_::bytes-size(6)>>, <<_::bytes-size(6)>>] = response["codes"]
72 user = refresh_record(user)
73 mfa_settings = user.multi_factor_authentication_settings
74 assert mfa_settings.totp.secret == "secret"
75 refute mfa_settings.backup_codes == ["1", "2", "3"]
76 refute mfa_settings.backup_codes == []
77
78 assert conn
79 |> put_req_header("authorization", "Bearer #{token2.token}")
80 |> get("/api/pleroma/accounts/mfa/backup_codes")
81 |> json_response(403) == %{
82 "error" => "Insufficient permissions: write:security."
83 }
84 end
85 end
86
87 describe "GET /api/pleroma/accounts/mfa/setup/totp" do
88 test "return errors when method is invalid", %{conn: conn} do
89 user = insert(:user)
90 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
91
92 response =
93 conn
94 |> put_req_header("authorization", "Bearer #{token.token}")
95 |> get("/api/pleroma/accounts/mfa/setup/torf")
96 |> json_response(400)
97
98 assert response == %{"error" => "undefined method"}
99 end
100
101 test "returns key and provisioning_uri", %{conn: conn} do
102 user =
103 insert(:user,
104 multi_factor_authentication_settings: %Settings{backup_codes: ["1", "2", "3"]}
105 )
106
107 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
108 token2 = insert(:oauth_token, scopes: ["read"])
109
110 response =
111 conn
112 |> put_req_header("authorization", "Bearer #{token.token}")
113 |> get("/api/pleroma/accounts/mfa/setup/totp")
114 |> json_response(:ok)
115
116 user = refresh_record(user)
117 mfa_settings = user.multi_factor_authentication_settings
118 secret = mfa_settings.totp.secret
119 refute mfa_settings.enabled
120 assert mfa_settings.backup_codes == ["1", "2", "3"]
121
122 assert response == %{
123 "key" => secret,
124 "provisioning_uri" => TOTP.provisioning_uri(secret, "#{user.email}")
125 }
126
127 assert conn
128 |> put_req_header("authorization", "Bearer #{token2.token}")
129 |> get("/api/pleroma/accounts/mfa/setup/totp")
130 |> json_response(403) == %{
131 "error" => "Insufficient permissions: write:security."
132 }
133 end
134 end
135
136 describe "GET /api/pleroma/accounts/mfa/confirm/totp" do
137 test "returns success result", %{conn: conn} do
138 secret = TOTP.generate_secret()
139 code = TOTP.generate_token(secret)
140
141 user =
142 insert(:user,
143 multi_factor_authentication_settings: %Settings{
144 backup_codes: ["1", "2", "3"],
145 totp: %Settings.TOTP{secret: secret}
146 }
147 )
148
149 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
150 token2 = insert(:oauth_token, scopes: ["read"])
151
152 assert conn
153 |> put_req_header("authorization", "Bearer #{token.token}")
154 |> post("/api/pleroma/accounts/mfa/confirm/totp", %{
155 password: "test",
156 code: code
157 })
158 |> json_response(:ok)
159
160 settings = refresh_record(user).multi_factor_authentication_settings
161 assert settings.enabled
162 assert settings.totp.secret == secret
163 assert settings.totp.confirmed
164 assert settings.backup_codes == ["1", "2", "3"]
165
166 assert conn
167 |> put_req_header("authorization", "Bearer #{token2.token}")
168 |> post("/api/pleroma/accounts/mfa/confirm/totp", %{
169 password: "test",
170 code: code
171 })
172 |> json_response(403) == %{
173 "error" => "Insufficient permissions: write:security."
174 }
175 end
176
177 test "returns error if password incorrect", %{conn: conn} do
178 secret = TOTP.generate_secret()
179 code = TOTP.generate_token(secret)
180
181 user =
182 insert(:user,
183 multi_factor_authentication_settings: %Settings{
184 backup_codes: ["1", "2", "3"],
185 totp: %Settings.TOTP{secret: secret}
186 }
187 )
188
189 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
190
191 response =
192 conn
193 |> put_req_header("authorization", "Bearer #{token.token}")
194 |> post("/api/pleroma/accounts/mfa/confirm/totp", %{
195 password: "xxx",
196 code: code
197 })
198 |> json_response(422)
199
200 settings = refresh_record(user).multi_factor_authentication_settings
201 refute settings.enabled
202 refute settings.totp.confirmed
203 assert settings.backup_codes == ["1", "2", "3"]
204 assert response == %{"error" => "Invalid password."}
205 end
206
207 test "returns error if code incorrect", %{conn: conn} do
208 secret = TOTP.generate_secret()
209
210 user =
211 insert(:user,
212 multi_factor_authentication_settings: %Settings{
213 backup_codes: ["1", "2", "3"],
214 totp: %Settings.TOTP{secret: secret}
215 }
216 )
217
218 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
219 token2 = insert(:oauth_token, scopes: ["read"])
220
221 response =
222 conn
223 |> put_req_header("authorization", "Bearer #{token.token}")
224 |> post("/api/pleroma/accounts/mfa/confirm/totp", %{
225 password: "test",
226 code: "code"
227 })
228 |> json_response(422)
229
230 settings = refresh_record(user).multi_factor_authentication_settings
231 refute settings.enabled
232 refute settings.totp.confirmed
233 assert settings.backup_codes == ["1", "2", "3"]
234 assert response == %{"error" => "invalid_token"}
235
236 assert conn
237 |> put_req_header("authorization", "Bearer #{token2.token}")
238 |> post("/api/pleroma/accounts/mfa/confirm/totp", %{
239 password: "test",
240 code: "code"
241 })
242 |> json_response(403) == %{
243 "error" => "Insufficient permissions: write:security."
244 }
245 end
246 end
247
248 describe "DELETE /api/pleroma/accounts/mfa/totp" do
249 test "returns success result", %{conn: conn} do
250 user =
251 insert(:user,
252 multi_factor_authentication_settings: %Settings{
253 backup_codes: ["1", "2", "3"],
254 totp: %Settings.TOTP{secret: "secret"}
255 }
256 )
257
258 token = insert(:oauth_token, scopes: ["write", "follow"], user: user)
259 token2 = insert(:oauth_token, scopes: ["read"])
260
261 assert conn
262 |> put_req_header("authorization", "Bearer #{token.token}")
263 |> delete("/api/pleroma/accounts/mfa/totp", %{password: "test"})
264 |> json_response(:ok)
265
266 settings = refresh_record(user).multi_factor_authentication_settings
267 refute settings.enabled
268 assert settings.totp.secret == nil
269 refute settings.totp.confirmed
270
271 assert conn
272 |> put_req_header("authorization", "Bearer #{token2.token}")
273 |> delete("/api/pleroma/accounts/mfa/totp", %{password: "test"})
274 |> json_response(403) == %{
275 "error" => "Insufficient permissions: write:security."
276 }
277 end
278 end
279 end