Passed
Push — master ( 69aa49...a72ce3 )
by Stefan
11:41
created

commonSbProfileChecks()   A

Complexity

Conditions 5
Paths 5

Size

Total Lines 23
Code Lines 18

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 18
dl 0
loc 23
rs 9.3554
c 0
b 0
f 0
cc 5
nc 5
nop 2
1
<?php
2
3
/*
4
 * *****************************************************************************
5
 * Contributions to this work were made on behalf of the GÉANT project, a 
6
 * project that has received funding from the European Union’s Framework 
7
 * Programme 7 under Grant Agreements No. 238875 (GN3) and No. 605243 (GN3plus),
8
 * Horizon 2020 research and innovation programme under Grant Agreements No. 
9
 * 691567 (GN4-1) and No. 731122 (GN4-2).
10
 * On behalf of the aforementioned projects, GEANT Association is the sole owner
11
 * of the copyright in all material which was developed by a member of the GÉANT
12
 * project. GÉANT Vereniging (Association) is registered with the Chamber of 
13
 * Commerce in Amsterdam with registration number 40535155 and operates in the 
14
 * UK as a branch of GÉANT Vereniging.
15
 * 
16
 * Registered office: Hoekenrode 3, 1102BR Amsterdam, The Netherlands. 
17
 * UK branch address: City House, 126-130 Hills Road, Cambridge CB2 1PQ, UK
18
 *
19
 * License: see the web/copyright.inc.php file in the file structure or
20
 *          <base_url>/copyright.php after deploying the software
21
 */
22
23
require_once dirname(dirname(dirname(__FILE__))) . "/config/_config.php";
24
25
// no SAML auth on this page. The API key authenticates the entity
26
27
$mode = "API";
28
29
$adminApi = new \web\lib\admin\API();
30
$validator = new \web\lib\common\InputValidation();
31
$optionParser = new \web\lib\admin\OptionParser();
32
33
if (!isset(\config\ConfAssistant::CONFIG['CONSORTIUM']['registration_API_keys']) || count(\config\ConfAssistant::CONFIG['CONSORTIUM']['registration_API_keys']) == 0) {
34
    $adminApi->returnError(web\lib\admin\API::ERROR_API_DISABLED, "API is disabled in this instance of CAT");
35
    exit(1);
36
}
37
38
$inputRaw = file_get_contents('php://input');
39
$inputDecoded = json_decode($inputRaw, TRUE);
40
if (!is_array($inputDecoded)) {
41
    $adminApi->returnError(web\lib\admin\API::ERROR_MALFORMED_REQUEST, "Unable to decode JSON POST data." . json_last_error_msg() . $inputRaw);
42
    exit(1);
43
}
44
45
if (!isset($inputDecoded['APIKEY'])) {
46
    $adminApi->returnError(web\lib\admin\API::ERROR_NO_APIKEY, "JSON request structure did not contain an APIKEY");
47
    exit(1);
48
}
49
50
$checkval = "FAIL";
51
foreach (\config\ConfAssistant::CONFIG['CONSORTIUM']['registration_API_keys'] as $key => $fed_name) {
52
    if ($inputDecoded['APIKEY'] == $key) {
53
        $mode = "API";
54
        $federation = $fed_name;
55
        $checkval = "OK-NEW";
56
    }
57
}
58
59
if ($checkval == "FAIL") {
60
    $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_APIKEY, "APIKEY is invalid");
61
    exit(1);
62
}
63
64
65
// let's instantiate the fed, we will need it later
66
$fed = new \core\Federation($federation);
67
// it's a valid admin; what does he want to do?
68
if (!array_key_exists($inputDecoded['ACTION'], web\lib\admin\API::ACTIONS)) {
69
    $adminApi->returnError(web\lib\admin\API::ERROR_NO_ACTION, "JSON request structure did not contain a valid ACTION");
70
    exit(1);
71
}
72
// it's a valid ACTION, so let's sanitise the input parameters
73
$scrubbedParameters = $adminApi->scrub($inputDecoded, $fed);
74
$paramNames = [];
75
foreach ($scrubbedParameters as $oneParam) {
76
    $paramNames[] = $oneParam['NAME'];
77
}
78
// are all the required parameters (still) in the request?
79
foreach (web\lib\admin\API::ACTIONS[$inputDecoded['ACTION']]['REQ'] as $oneRequiredAttribute) {
80
    if (!in_array($oneRequiredAttribute, $paramNames)) {
81
        $adminApi->returnError(web\lib\admin\API::ERROR_MISSING_PARAMETER, "At least one required parameter for this ACTION is missing: $oneRequiredAttribute");
82
        exit(1);
83
    }
84
}
85
86
switch ($inputDecoded['ACTION']) {
87
    case web\lib\admin\API::ACTION_NEWINST:
88
        // create the inst, no admin, no attributes
89
        $typeRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_INSTTYPE);
90
        if ($typeRaw === FALSE) {
91
            throw new Exception("We did not receive a valid participant type!");
92
        }
93
        $type = $validator->partType($typeRaw);
94
        $idp = new \core\IdP($fed->newIdP($type, "PENDING", "API"));
95
        // now add all submitted attributes
96
        $inputs = $adminApi->uglify($scrubbedParameters);
97
        $optionParser->processSubmittedFields($idp, $inputs["POST"], $inputs["FILES"]);
98
        $adminApi->returnSuccess([web\lib\admin\API::AUXATTRIB_CAT_INST_ID => $idp->identifier]);
99
        break;
100
    case web\lib\admin\API::ACTION_DELINST:
101
        try {
102
            $idp = $validator->existingIdP($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_INST_ID));
103
        } catch (Exception $e) {
104
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "IdP identifier does not exist!");
105
            exit(1);
106
        }
107
        $idp->destroy();
108
        $adminApi->returnSuccess([]);
109
        break;
110
    case web\lib\admin\API::ACTION_ADMIN_LIST:
111
        try {
112
            $idp = $validator->existingIdP($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_INST_ID));
113
        } catch (Exception $e) {
114
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "IdP identifier does not exist!");
115
            exit(1);
116
        }
117
        $adminApi->returnSuccess($idp->listOwners());
118
        break;
119
    case web\lib\admin\API::ACTION_ADMIN_ADD:
120
        // IdP in question
121
        try {
122
            $idp = $validator->existingIdP($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_INST_ID));
123
        } catch (Exception $e) {
124
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "IdP identifier does not exist!");
125
            exit(1);
126
        }
127
        // here is the token
128
        $mgmt = new core\UserManagement();
129
        // we know we have an admin ID but scrutinizer wants this checked more explicitly
130
        $admin = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_ADMINID);
131
        if ($admin === FALSE) {
132
            throw new Exception("A required parameter is missing, and this wasn't caught earlier?!");
133
        }
134
        $newtokens = $mgmt->createTokens(true, [$admin], $idp);
135
        $URL = "https://" . $_SERVER['SERVER_NAME'] . dirname($_SERVER['SCRIPT_NAME']) . "/action_enrollment.php?token=" . array_keys($newtokens)[0];
136
        $success = ["TOKEN URL" => $URL, "TOKEN" => array_keys($newtokens)[0]];
137
        // done with the essentials - display in response. But if we also have an email address, send it there
138
        $email = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_TARGETMAIL);
139
        if ($email !== FALSE) {
140
            $sent = \core\common\OutsideComm::adminInvitationMail($email, "EXISTING-FED", array_keys($newtokens)[0], $idp->name, $fed, $idp->type);
141
            $success["EMAIL SENT"] = $sent["SENT"];
142
            if ($sent["SENT"] === TRUE) {
143
                $success["EMAIL TRANSPORT SECURE"] = $sent["TRANSPORT"];
144
            }
145
        }
146
        $adminApi->returnSuccess($success);
147
        break;
148
    case web\lib\admin\API::ACTION_ADMIN_DEL:
149
        // IdP in question
150
        try {
151
            $idp = $validator->existingIdP($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_INST_ID));
152
        } catch (Exception $e) {
153
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "IdP identifier does not exist!");
154
            exit(1);
155
        }
156
        $currentAdmins = $idp->listOwners();
157
        $toBeDeleted = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_ADMINID);
158
        if ($toBeDeleted === FALSE) {
159
            throw new Exception("A required parameter is missing, and this wasn't caught earlier?!");
160
        }
161
        $found = FALSE;
162
        foreach ($currentAdmins as $oneAdmin) {
163
            if ($oneAdmin['MAIL'] == $toBeDeleted) {
164
                $found = TRUE;
165
                $mgmt = new core\UserManagement();
166
                $mgmt->removeAdminFromIdP($idp, $oneAdmin['ID']);
167
            }
168
        }
169
        if ($found) {
170
            $adminApi->returnSuccess([]);
171
        }
172
        $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "The admin with ID $toBeDeleted is not associated to IdP " . $idp->identifier);
173
        break;
174
    case web\lib\admin\API::ACTION_STATISTICS_FED:
175
        $adminApi->returnSuccess($fed->downloadStats("array"));
176
        break;
177
    case \web\lib\admin\API::ACTION_NEWPROF_RADIUS:
178
    // fall-through intended: both get mostly identical treatment
179
    case web\lib\admin\API::ACTION_NEWPROF_SB:
180
        try {
181
            $idp = $validator->existingIdP($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_INST_ID));
182
        } catch (Exception $e) {
183
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "IdP identifier does not exist!");
184
            exit(1);
185
        }
186
        if ($inputDecoded['ACTION'] == web\lib\admin\API::ACTION_NEWPROF_RADIUS) {
187
            $type = "RADIUS";
188
        } else {
189
            $type = "SILVERBULLET";
190
        }
191
        $profile = $idp->newProfile($type);
192
        if ($profile === NULL) {
193
            $adminApi->returnError(\web\lib\admin\API::ERROR_INTERNAL_ERROR, "Unable to create a new Profile, for no apparent reason. Please contact support.");
194
            exit(1);
195
        }
196
        $inputs = $adminApi->uglify($scrubbedParameters);
197
        $optionParser->processSubmittedFields($profile, $inputs["POST"], $inputs["FILES"]);
198
        if ($inputDecoded['ACTION'] == web\lib\admin\API::ACTION_NEWPROF_SB) {
199
            // auto-accept ToU?
200
            if ($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_TOU) !== FALSE) {
201
                $profile->addAttribute("hiddenprofile:tou_accepted", NULL, 1);
202
            }
203
            // we're done at this point
204
            $adminApi->returnSuccess([\web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID => $profile->identifier]);
205
            break;
206
        }
207
        if (!$profile instanceof core\ProfileRADIUS) {
208
            throw new Exception("Can't be. This is only here to convince Scrutinizer that we're really talking RADIUS.");
209
        }
210
        /* const AUXATTRIB_PROFILE_REALM = 'ATTRIB-PROFILE-REALM';
211
          const AUXATTRIB_PROFILE_OUTERVALUE = 'ATTRIB-PROFILE-OUTERVALUE'; */
212
        $realm = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_PROFILE_REALM);
213
        $outer = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_PROFILE_OUTERVALUE);
214
        if ($realm !== FALSE) {
215
            if ($outer === FALSE) {
216
                $outer = "";
217
                $profile->setAnonymousIDSupport(FALSE);
218
            } else {
219
                $outer = $outer . "@";
220
                $profile->setAnonymousIDSupport(TRUE);
221
            }
222
            $profile->setRealm($outer . $realm);
223
        }
224
        /* const AUXATTRIB_PROFILE_TESTUSER = 'ATTRIB-PROFILE-TESTUSER'; */
225
        $testuser = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_PROFILE_TESTUSER);
226
        if ($testuser !== FALSE) {
227
            $profile->setRealmCheckUser(TRUE, $testuser);
228
        }
229
        /* const AUXATTRIB_PROFILE_INPUT_HINT = 'ATTRIB-PROFILE-HINTREALM';
230
          const AUXATTRIB_PROFILE_INPUT_VERIFY = 'ATTRIB-PROFILE-VERIFYREALM'; */
231
        $hint = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_PROFILE_INPUT_HINT);
232
        $enforce = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_PROFILE_INPUT_VERIFY);
233
        if ($enforce !== FALSE) {
234
            $profile->setInputVerificationPreference($enforce, $hint);
235
        }
236
        /* const AUXATTRIB_PROFILE_EAPTYPE */
237
        $iterator = 1;
238
        foreach ($scrubbedParameters as $oneParam) {
239
            if ($oneParam['NAME'] == web\lib\admin\API::AUXATTRIB_PROFILE_EAPTYPE && is_int($oneParam["VALUE"])) {
240
                $type = new \core\common\EAP($oneParam["VALUE"]);
241
                $profile->addSupportedEapMethod($type, $iterator);
242
                $iterator = $iterator + 1;
243
            }
244
        }
245
        // reinstantiate $profile freshly from DB - it was updated in the process
246
        $profileFresh = new core\ProfileRADIUS($profile->identifier);
247
        $profileFresh->prepShowtime();
248
        $adminApi->returnSuccess([\web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID => $profileFresh->identifier]);
249
        break;
250
    case web\lib\admin\API::ACTION_ENDUSER_NEW:
251
        $prof_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
252
        if ($prof_id === FALSE) {
253
            exit(1);
254
        }
255
        $evaluation = $adminApi->commonSbProfileChecks($fed, $prof_id);
256
        if ($evaluation === FALSE) {
257
            exit(1);
258
        }
259
        list($idp, $profile) = $evaluation;
260
        $user = $validator->string($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERNAME));
261
        $expiryRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_EXPIRY);
262
        if ($expiryRaw === FALSE) {
263
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "The expiry date wasn't found in the request.");
264
            exit(1);
265
        }
266
        $expiry = new DateTime($expiryRaw);
267
        try {
268
            $retval = $profile->addUser($user, $expiry);
0 ignored issues
show
Bug introduced by
The method addUser() does not exist on core\ProfileRADIUS. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

268
            /** @scrutinizer ignore-call */ 
269
            $retval = $profile->addUser($user, $expiry);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
269
        } catch (Exception $e) {
270
            $adminApi->returnError(web\lib\admin\API::ERROR_INTERNAL_ERROR, "The operation failed. Maybe a duplicate username, or malformed expiry date?");
271
            exit(1);
272
        }
273
        if ($retval == 0) {// that didn't work, it seems
274
            $adminApi->returnError(web\lib\admin\API::ERROR_INTERNAL_ERROR, "The operation failed subtly. Contact the administrators.");
275
            exit(1);
276
        }
277
        $adminApi->returnSuccess([web\lib\admin\API::AUXATTRIB_SB_USERNAME => $user, \web\lib\admin\API::AUXATTRIB_SB_USERID => $retval]);
278
        break;
279
    case \web\lib\admin\API::ACTION_ENDUSER_DEACTIVATE:
280
    // fall-through intended: both actions are very similar
281
    case \web\lib\admin\API::ACTION_TOKEN_NEW:
282
        $profile_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
283
        if ($profile_id === FALSE) {
284
            exit(1);
285
        }
286
        $evaluation = $adminApi->commonSbProfileChecks($fed, $profile_id);
287
        if ($evaluation === FALSE) {
288
            exit(1);
289
        }
290
        list($idp, $profile) = $evaluation;
291
        $userId = $validator->integer($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERID));
292
        if ($userId === FALSE) {
293
            $adminApi->returnError(\web\lib\admin\API::ERROR_INVALID_PARAMETER, "User ID is not an integer.");
294
            exit(1);
295
        }
296
        $additionalInfo = [];
297
        switch ($inputDecoded['ACTION']) { // this is where the two differ
298
            case \web\lib\admin\API::ACTION_ENDUSER_DEACTIVATE:
299
                $result = $profile->deactivateUser($userId);
0 ignored issues
show
Bug introduced by
The method deactivateUser() does not exist on core\ProfileRADIUS. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

299
                /** @scrutinizer ignore-call */ 
300
                $result = $profile->deactivateUser($userId);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
300
                break;
301
            case \web\lib\admin\API::ACTION_TOKEN_NEW:
302
                $counter = $validator->integer($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_TOKEN_ACTIVATIONS));
303
                if (!is_integer($counter)) {
304
                    $counter = 1;
305
                }
306
                $invitation = core\SilverbulletInvitation::createInvitation($profile->identifier, $userId, $counter);
307
                $result = TRUE;
308
                $additionalInfo[\web\lib\admin\API::AUXATTRIB_TOKENURL] = $invitation->link();
309
                $additionalInfo[\web\lib\admin\API::AUXATTRIB_TOKEN] = $invitation->invitationTokenString;
310
                $emailRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_TARGETMAIL);
311
                if ($emailRaw) { // an email parameter was specified
312
                    $email = $validator->email($emailRaw);
313
                    if (is_string($email)) { // it's a valid address
314
                        $retval = $invitation->sendByMail($email);
315
                        $additionalInfo["EMAIL SENT"] = $retval["SENT"];
316
                        if ($retval["SENT"]) {
317
                            $additionalInfo["EMAIL TRANSPORT SECURE"] = $retval["TRANSPORT"];
318
                        }
319
                    }
320
                }
321
                $smsRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_TARGETSMS);
322
                if ($smsRaw !== FALSE) {
323
                    $sms = $validator->sms($smsRaw);
324
                    if (is_string($sms)) {
325
                        $wasSent = $invitation->sendBySms($sms);
326
                        $additionalInfo["SMS SENT"] = $wasSent == core\common\OutsideComm::SMS_SENT ? TRUE : FALSE;
327
                    }
328
                }
329
                break;
330
        }
331
332
        if ($result !== TRUE) {
333
            $adminApi->returnError(\web\lib\admin\API::ERROR_INVALID_PARAMETER, "These parameters did not lead to an existing, active user.");
334
            exit(1);
335
        }
336
        $adminApi->returnSuccess($additionalInfo);
337
        break;
338
    case \web\lib\admin\API::ACTION_ENDUSER_IDENTIFY:
339
        $profile_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
340
        if ($profile_id === FALSE) {
341
            exit(1);
342
        }
343
        $evaluation = $adminApi->commonSbProfileChecks($fed, $profile_id);
344
        if ($evaluation === FALSE) {
345
            exit(1);
346
        }
347
        list($idp, $profile) = $evaluation;
348
        $userId = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERID);
349
        $userName = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERNAME);
350
        $certSerial = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_CERTSERIAL);
351
        if ($userId === FALSE && $userName === FALSE && $certSerial === FALSE) {
352
            // we need at least one of those
353
            $adminApi->returnError(\web\lib\admin\API::ERROR_MISSING_PARAMETER, "At least one of User ID, Username, or certificate serial is required.");
354
        }
355
        $userlist = $profile->listAllUsers();
0 ignored issues
show
Bug introduced by
The method listAllUsers() does not exist on core\ProfileRADIUS. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

355
        /** @scrutinizer ignore-call */ 
356
        $userlist = $profile->listAllUsers();

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
356
        if ($userName === FALSE && $certSerial === FALSE) { // we got a user ID
357
            if (!isset($userlist[$userId])) {
358
                return $adminApi->returnError(\web\lib\admin\API::ERROR_INVALID_PARAMETER, "This user ID does not exist in this profile.");
359
            }
360
            $adminApi->returnSuccess([$userId => $userlist[$userId]]);
361
        }
362
        if ($userId === FALSE && $certSerial === FALSE) { // we got a username
363
            $key = array_search($userName, $userlist);
364
            if ($key === FALSE) {
365
                return $adminApi->returnError(\web\lib\admin\API::ERROR_INVALID_PARAMETER, "This username does not exist in this profile.");
366
            }
367
            $adminApi->returnSuccess([$key => $userlist[$key]]);
368
        }
369
        if ($userId === FALSE && $userName === FALSE) { // we got a cert serial
370
            $serial = explode(":", $certSerial);
371
            $cert = new \core\SilverbulletCertificate($serial[1], $serial[0]);
372
            if ($cert->status == \core\SilverbulletCertificate::CERTSTATUS_INVALID) {
373
                $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial not found.");
374
            }
375
            if ($cert->profileId != $profile->identifier) {
376
                $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial does not belong to this profile.");
377
            }
378
            $adminApi->returnSuccess([$cert->userId => $userlist[$cert->userId]]);
379
        }
380
        $adminApi->returnError(\web\lib\admin\API::ERROR_INVALID_PARAMETER, "Only exactly one of User ID, username or cert serial can be specified.");
381
        break;
382
    case \web\lib\admin\API::ACTION_ENDUSER_LIST:
383
    // fall-through: those two are similar
384
    case \web\lib\admin\API::ACTION_TOKEN_LIST:
385
        $profile_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
386
        if ($profile_id === FALSE) {
387
            exit(1);
388
        }
389
        $evaluation = $adminApi->commonSbProfileChecks($fed, $profile_id);
390
        if ($evaluation === FALSE) {
391
            exit(1);
392
        }
393
        list($idp, $profile) = $evaluation;
394
        $allUsers = $profile->listAllUsers();
395
        // this is where they differ
396
        switch ($inputDecoded['ACTION']) {
397
            case \web\lib\admin\API::ACTION_ENDUSER_LIST:
398
                $adminApi->returnSuccess($allUsers);
399
                break;
400
            case \web\lib\admin\API::ACTION_TOKEN_LIST:
401
                $user = $validator->integer($adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERID));
402
                if ($user !== FALSE) {
403
                    $allUsers = [$user];
404
                }
405
                $tokens = [];
406
                foreach ($allUsers as $oneUser) {
407
                    $tokens = array_merge($tokens, $profile->userStatus($oneUser));
0 ignored issues
show
Bug introduced by
The method userStatus() does not exist on core\ProfileRADIUS. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

407
                    $tokens = array_merge($tokens, $profile->/** @scrutinizer ignore-call */ userStatus($oneUser));

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
408
                }
409
                // reduce to important subset of information
410
                $infoSet = [];
411
                foreach ($tokens as $oneTokenObject) {
412
                    $infoSet[$oneTokenObject->userId] = [\web\lib\admin\API::AUXATTRIB_TOKEN => $oneTokenObject->invitationTokenString, "STATUS" => $oneTokenObject->invitationTokenStatus];
413
                }
414
                $adminApi->returnSuccess($infoSet);
415
        }
416
        break;
417
    case \web\lib\admin\API::ACTION_TOKEN_REVOKE:
418
        $tokenRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_TOKEN);
419
        if ($tokenRaw === FALSE) {
420
            exit(1);
421
        }
422
        $token = new core\SilverbulletInvitation($tokenRaw);
423
        if ($token->invitationTokenStatus !== core\SilverbulletInvitation::SB_TOKENSTATUS_VALID && $token->invitationTokenStatus !== core\SilverbulletInvitation::SB_TOKENSTATUS_PARTIALLY_REDEEMED) {
424
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "This is not a currently valid token.");
425
            exit(1);
426
        }
427
        $token->revokeInvitation();
428
        $adminApi->returnSuccess([]);
429
        break;
430
    case \web\lib\admin\API::ACTION_CERT_LIST:
431
        $prof_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
432
        $user_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_USERID);
433
        if ($prof_id === FALSE || !is_int($user_id)) {
434
            exit(1);
435
        }
436
        $evaluation = $adminApi->commonSbProfileChecks($fed, $prof_id);
437
        if ($evaluation === FALSE) {
438
            exit(1);
439
        }
440
        list($idp, $profile) = $evaluation;
441
        $invitations = $profile->userStatus($user_id);
442
        // now pull out cert information from the object
443
        $certs = [];
444
        foreach ($invitations as $oneInvitation) {
445
            $certs = array_merge($certs, $oneInvitation->associatedCertificates);
446
        }
447
        // extract relevant subset of information from cert objects
448
        $certDetails = [];
449
        foreach ($certs as $cert) {
450
            $certDetails[$cert->ca_type . ":" . $cert->serial] = ["ISSUED" => $cert->issued, "EXPIRY" => $cert->expiry, "STATUS" => $cert->status, "DEVICE" => $cert->device, "CN" => $cert->username, "ANNOTATION" => $cert->annotation];
451
        }
452
        $adminApi->returnSuccess($certDetails);
453
        break;
454
    case \web\lib\admin\API::ACTION_CERT_REVOKE:
455
        $prof_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
456
        if ($prof_id === FALSE) {
457
            exit(1);
458
        }
459
        $evaluation = $adminApi->commonSbProfileChecks($fed, $prof_id);
460
        if ($evaluation === FALSE) {
461
            exit(1);
462
        }
463
        list($idp, $profile) = $evaluation;
464
        // tear apart the serial
465
        $serialRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_CERTSERIAL);
466
        if ($serialRaw === FALSE) {
467
            exit(1);
468
        }
469
        $serial = explode(":", $serialRaw);
470
        $cert = new \core\SilverbulletCertificate($serial[1], $serial[0]);
471
        if ($cert->status == \core\SilverbulletCertificate::CERTSTATUS_INVALID) {
472
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial not found.");
473
        }
474
        if ($cert->profileId != $profile->identifier) {
475
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial does not belong to this profile.");
476
        }
477
        $cert->revokeCertificate();
478
        $adminApi->returnSuccess([]);
479
        break;
480
    case \web\lib\admin\API::ACTION_CERT_ANNOTATE:
481
        $prof_id = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_CAT_PROFILE_ID);
482
        if ($prof_id === FALSE) {
483
            exit(1);
484
        }
485
        $evaluation = $adminApi->commonSbProfileChecks($fed, $prof_id);
486
        if ($evaluation === FALSE) {
487
            exit(1);
488
        }
489
        list($idp, $profile) = $evaluation;
490
        // tear apart the serial
491
        $serialRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_CERTSERIAL);
492
        if ($serialRaw === FALSE) {
493
            exit(1);
494
        }
495
        $serial = explode(":", $serialRaw);
496
        $cert = new \core\SilverbulletCertificate($serial[1], $serial[0]);
497
        if ($cert->status == \core\SilverbulletCertificate::CERTSTATUS_INVALID) {
498
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial not found.");
499
        }
500
        if ($cert->profileId != $profile->identifier) {
501
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Serial does not belong to this profile.");
502
        }
503
        $annotationRaw = $adminApi->firstParameterInstance($scrubbedParameters, web\lib\admin\API::AUXATTRIB_SB_CERTANNOTATION);
504
        if ($annotationRaw === FALSE) {
505
            $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_PARAMETER, "Unable to extract annotation.");
506
            break;
507
        }
508
        $annotation = json_decode($annotationRaw, TRUE);
509
        $cert->annotate($annotation);
510
        $adminApi->returnSuccess([]);
511
        
512
        break;
513
        
514
    default:
515
        $adminApi->returnError(web\lib\admin\API::ERROR_INVALID_ACTION, "Not implemented yet.");
516
}