1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
|
<?php
namespace App\Controllers;
use App\Database;
use App\Errors\AppException;
use App\Errors\ErrorCode;
use App\Errors\UnknownError;
use App\Models\Device;
use App\Models\User;
use App\Types\LoginFlow;
use App\Types\LoginType;
use App\Types\UserRegistrationKind;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\JsonResponse;
class LoginController
{
/**
* GET /_matrix/client/r0/login
*/
public function supportedLoginTypes(): Response
{
return new JsonResponse([
"flows" => [
(new LoginFlow(LoginType::PASSWORD))->toArray(),
],
]);
}
/**
* POST /_matrix/client/v3/login
*/
public function login(): Response
{
$request = Request::createFromGlobals();
$body = json_decode($request->getContent(), true);
// validate login type
$loginType = null;
try {
$loginType = LoginType::from($body["type"]);
} catch (\ValueError $error) {
throw new UnknownError("Bad login type.", Response::HTTP_BAD_REQUEST);
}
// get user id
$userId = $body["identifier"]["user"];
#if ($loginType == LoginType::PASSWORD) {}
$user = User::fetchWithPassword($userId, $body["password"]);
if (! $user) {
throw new AppException(ErrorCode::FORBIDDEN, "Invalid credentials.", Response::HTTP_FORBIDDEN);
}
$deviceId = $body["device_id"] ?? "";
$device = $user->fetchDevice($deviceId);
if (! $device) {
$device = Device::new(
$user->getId(),
initialDisplayName: $body["initial_device_display_name"] ?? "",
);
}
return new JsonResponse([
"access_token" => $device->getAccessToken(),
"device_id" => $device->getId(),
"expires_in_ms" => 60000,
"refresh_token" => $device->getRefreshToken(),
"user_id" => $user->getId(),
#"well_known" => [],
]);
}
/**
* POST /_matrix/client/v3/register
*/
public function register(): Response
{
$request = Request::createFromGlobals();
$body = json_decode($request->getContent(), true);
$kind = UserRegistrationKind::from($request->query->get("kind") ?? "user");
$username = $body["username"];
$userId = "@$username:$_ENV[DOMAIN]";
Database::getInstance()->query("insert into users (id, password) values (:id, :password)", [
"id" => $userId,
"password" => $body["password"],
]);
$device_id = $body["device_id"] ?? "";
$initialDeviceDisplayName = $body["initialDeviceDisplayName"] ?? "";
$device = Device::new($userId, $device_id, $initialDeviceDisplayName);
$device->insert();
return new JsonResponse([
"access_token" => $device->getAccessToken(),
"device_id" => $device->getId(),
"expires_in_ms" => 60000,
"refresh_token" => $device->getRefreshToken(),
"user_id" => $userId,
]);
}
}
|