Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
93.10% covered (success)
93.10%
54 / 58
n/a
0 / 0
CRAP
n/a
0 / 0
1<?php
2
3/**
4 * @file
5 * Login action: authenticate with username and password.
6 */
7
8    declare(strict_types=1);
9
10    require_once __DIR__.'/PosDevice.php';
11
12    /**
13     * Action callable: login with username and password (POST body + GET device).
14     *
15     * Validates credentials (USER or STAFF), grants session, returns JSON with errorcode and session.
16     *
17     * @param string $body JSON body with username, password.
18     * @param array<string, mixed> $query Query params: device.
19     * @param \ConxHelper $conx Connection helper (from LoginService; uses ->global for central DB).
20     * @param \Psr\Log\LoggerInterface $logger Logger (from LoggerFactory).
21     * @param \UppServices\SessionService $sessionService Session service for grant.
22     * @return array{output: string, contentType: string} JSON output and content type.
23     */
24    return function (string $body, array $query, \ConxHelper $conx, \Psr\Log\LoggerInterface $logger, \UppServices\SessionService $sessionService): array {
25        $retval = ApplicationError::Success;
26        $userinfo = null;
27
28        if ($body === '') {
29            $output = json_encode(['errorcode' => ApplicationError::Parameters]);
30            return ['output' => $output, 'contentType' => 'application/json; charset=utf-8'];
31        }
32
33        $logger->info("User login from remote IP: ".getRemoteIp());
34        $data = json_decode($body, true);
35        $logger->debug("DUMP OF POST DATA:".PHP_EOL.print_r($data, true).PHP_EOL);
36        
37        if ($data === null) {
38            $logger->error("Invalid JSON format in post request data");
39            $output = json_encode(['errorcode' => ApplicationError::Generic]);
40            return ['output' => $output, 'contentType' => 'application/json; charset=utf-8'];
41        }
42
43        $deviceid = $query['device'] ?? null;
44        if (!$deviceid) {
45            $logger->error("Missing 'device' parameter in url request");
46            $retval = ApplicationError::Parameters;
47        }
48
49        if (success($retval)) {
50            $username = $data['username'] ?? null;
51            if (!$username) {
52                $logger->error("Mandatory argument 'username' not provided in post data.");
53                $retval = ApplicationError::Parameters;
54            }
55        }
56        
57        if (success($retval)) {
58            $password = $data['password'] ?? null;
59            if (!$password) {
60                $logger->error("Mandatory argument 'password' not provided in post data.");
61                $retval = ApplicationError::Parameters;
62            }
63        }
64
65        if (success($retval)) {
66            $username = trim(strtolower((string) ($data['username'] ?? '')));
67            $password = (string) ($data['password'] ?? '');
68            
69            $results = [];
70            
71            $sql = "select * from USER where lower(email) = '".$username."' and password = '".$password."' and status in ('PA', 'AC')";
72            $res = $conx->global->runsql(['USER'], $sql, $results);
73            if ($res && count($results) > 0) {
74                $userinfo = $results[0];
75                $logger->info("Login succesfull for user '".$username."' -- objid [".$userinfo['objid']."]");
76            } 
77            else {
78                $res = $conx->global->query("STAFF", ['email' => $username, 'status' => 'AC'], $results);
79                if ($res && count($results) > 0) {
80                    $res = $conx->global->query("USER", ["objid" => $results[0]['user'], "password" => $password, "status" => ['PA', 'AC']], $results);
81                    if ($res && count($results) > 0) {
82                        $userinfo = $results[0];
83                        $logger->info("Login succesfull for user '".$username."' -- objid [".$userinfo['objid']."]");
84                    }
85                }
86            }
87            
88            if (!$userinfo) {
89                $logger->error("No valid users/waiters found for email '".$username."' with password.");
90                $retval = ApplicationError::Unauthorized;
91            }
92        }
93
94        if (success($retval)) {
95            $retval = grant_posdevice($conx, (string) $deviceid);
96        }
97
98        if (success($retval)) {
99            $userinfo['session'] = null;
100            $retval = $sessionService->grantSession($conx, $deviceid, $userinfo['objid'], $userinfo['session']);
101        }
102
103        if (success($retval)) {
104            $userinfo['photo'] = toUrl($userinfo['photo']);
105            $result = ["errorcode" => $retval, "session" => $userinfo['session']];
106        } 
107        else {
108            $result = ["errorcode" => $retval];
109        }
110
111        $output = json_encode($result);
112        return ['output' => $output, 'contentType' => 'application/json; charset=utf-8'];
113    };