Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.
Common duplication problems, and corresponding solutions are:
1 | <?php |
||
50 | class StepUpAuthenticationService |
||
51 | { |
||
52 | /** |
||
53 | * @var \Surfnet\StepupBundle\Service\LoaResolutionService |
||
54 | */ |
||
55 | private $loaResolutionService; |
||
56 | |||
57 | /** |
||
58 | * @var \Surfnet\StepupGateway\GatewayBundle\Entity\SecondFactorRepository |
||
59 | */ |
||
60 | private $secondFactorRepository; |
||
61 | |||
62 | /** |
||
63 | * @var \Surfnet\StepupGateway\ApiBundle\Service\YubikeyService |
||
64 | */ |
||
65 | private $yubikeyService; |
||
66 | |||
67 | /** |
||
68 | * @var \Surfnet\StepupBundle\Service\SmsSecondFactorService |
||
69 | */ |
||
70 | private $smsService; |
||
71 | |||
72 | /** |
||
73 | * @var \Symfony\Component\Translation\TranslatorInterface |
||
74 | */ |
||
75 | private $translator; |
||
76 | |||
77 | /** |
||
78 | * @var \Psr\Log\LoggerInterface |
||
79 | */ |
||
80 | private $logger; |
||
81 | |||
82 | /** |
||
83 | * @var SecondFactorTypeService |
||
84 | */ |
||
85 | private $secondFactorTypeService; |
||
86 | |||
87 | /** |
||
88 | * @param LoaResolutionService $loaResolutionService |
||
89 | * @param SecondFactorRepository $secondFactorRepository |
||
90 | * @param YubikeyService $yubikeyService |
||
91 | * @param SmsSecondFactorService $smsService |
||
92 | * @param TranslatorInterface $translator |
||
93 | * @param LoggerInterface $logger |
||
94 | * @param SecondFactorTypeService $secondFactorTypeService |
||
95 | */ |
||
96 | public function __construct( |
||
113 | |||
114 | /** |
||
115 | * @param string $identityNameId |
||
116 | * @param Loa $requiredLoa |
||
117 | * @return \Doctrine\Common\Collections\Collection |
||
118 | */ |
||
119 | public function determineViableSecondFactors( |
||
139 | |||
140 | /** |
||
141 | * Retrieves the required LoA for the authenticating user |
||
142 | * |
||
143 | * @see StepUpAuthenticationServiceTest::test_resolve_highest_required_loa_conbinations |
||
144 | * The possible flows through the method are tested in this test case. Any additional possible outcomes should |
||
145 | * be covered in this test. |
||
146 | * |
||
147 | * @see https://github.com/OpenConext/Stepup-Deploy/wiki/Institution-Specific-LoA |
||
148 | * The flow of the LoA determination is described in detail in this document. The parameters of this method |
||
149 | * match the inputs described in the flow diagram. |
||
150 | * |
||
151 | * @param string $requestedLoa <SP-LoA> Optional. The value of the AuthnConextClassRef attribute in the |
||
152 | * AuthnRequest from the SP. |
||
153 | * |
||
154 | * Example: 'https://example.com/authentication/loa1' |
||
155 | * |
||
156 | * @param array $spConfiguredLoas <LoAs> Optional. An associative array mapping schacHomeOrganization to LoA. |
||
157 | * This array is configured on the gateway for each SP. All keys in the |
||
158 | * spConfiguredLoas array should be normalized (lower cased). |
||
159 | * |
||
160 | * Example: |
||
161 | * [ |
||
162 | * '__default__' => 'https://example.com/authentication/loa1', |
||
163 | * 'institution_a' => 'https://example.com/authentication/loa2', |
||
164 | * 'institution_b' => 'https://example.com/authentication/loa3', |
||
165 | * ] |
||
166 | * |
||
167 | * @param string $normalizedIdpSho <IdP-SHO> Optional. Value of the schacHomeOrganization attribute from the |
||
|
|||
168 | * Assertion from the IdP. The SHO should be normalized (lower cased) as |
||
169 | * it will be used to be compared against the $spConfiguredLoas who have |
||
170 | * also been normalized. |
||
171 | * |
||
172 | * Example: 'institution_a', '' |
||
173 | * |
||
174 | * @param string $normalizedUserSho <User-SHO> Optional. The schacHomeOrganization that the user belongs to, this is |
||
175 | * the schacHomeOrganization that was provided during registration of the |
||
176 | * token. The SHO should be normalized (lower cased) as it will be used |
||
177 | * to be compared against the $spConfiguredLoas who have also been |
||
178 | * normalized. |
||
179 | * |
||
180 | * Example: 'institution_b', '' |
||
181 | * |
||
182 | * @return Loa |
||
183 | * |
||
184 | * @throws UnknownInstitutionException Raised when neither <User-SHO> or <IdP-SHO> is provided but <LoAs> |
||
185 | * are configured for institutions other than __default__. |
||
186 | * |
||
187 | * @throws InstitutionMismatchException <User-SHO> or <IdP-SHO> are configured and <LoAs> are provided for an |
||
188 | * institution other than __default__ but the <User-SHO> and <IdP-SHO> do |
||
189 | * not match. |
||
190 | * |
||
191 | * @throws LoaCannotBeGivenException Raised when no LoA candidates are found or when none of the candidate |
||
192 | * LoAs are valid (known to the application). |
||
193 | * |
||
194 | * @SuppressWarnings(PHPMD.CyclomaticComplexity) |
||
195 | * @SuppressWarnings(PHPMD.NPathComplexity) |
||
196 | */ |
||
197 | public function resolveHighestRequiredLoa( |
||
283 | |||
284 | /** |
||
285 | * Test if the spConfiguredLoas has institution specific LoA configurations other than the |
||
286 | * default LoA configuration. |
||
287 | * |
||
288 | * @param array $spConfiguredLoas |
||
289 | * |
||
290 | * @return bool |
||
291 | */ |
||
292 | private function hasNonDefaultSpConfiguredLoas(array $spConfiguredLoas) |
||
297 | |||
298 | /** |
||
299 | * Returns whether the given Loa identifier identifies the minimum Loa, intrinsic to being authenticated via an IdP. |
||
300 | * |
||
301 | * @param Loa $loa |
||
302 | * @return bool |
||
303 | */ |
||
304 | public function isIntrinsicLoa(Loa $loa) |
||
308 | |||
309 | /** |
||
310 | * @param VerifyYubikeyOtpCommand $command |
||
311 | * @return YubikeyOtpVerificationResult |
||
312 | */ |
||
313 | public function verifyYubikeyOtp(VerifyYubikeyOtpCommand $command) |
||
343 | |||
344 | /** |
||
345 | * @param string $secondFactorId |
||
346 | * @return string |
||
347 | */ |
||
348 | public function getSecondFactorIdentifier($secondFactorId) |
||
355 | |||
356 | /** |
||
357 | * @return int |
||
358 | */ |
||
359 | public function getSmsOtpRequestsRemainingCount() |
||
363 | |||
364 | /** |
||
365 | * @return int |
||
366 | */ |
||
367 | public function getSmsMaximumOtpRequestsCount() |
||
371 | |||
372 | /** |
||
373 | * @param SendSmsChallengeCommand $command |
||
374 | * @return bool |
||
375 | */ |
||
376 | public function sendSmsChallenge(SendSmsChallengeCommand $command) |
||
391 | |||
392 | /** |
||
393 | * @param VerifyPossessionOfPhoneCommand $command |
||
394 | * @return OtpVerification |
||
395 | */ |
||
396 | public function verifySmsChallenge(VerifyPossessionOfPhoneCommand $command) |
||
400 | |||
401 | public function clearSmsVerificationState() |
||
405 | |||
406 | /** |
||
407 | * Return the lower-cased schacHomeOrganization of the user based on his vetted tokens. |
||
408 | * |
||
409 | * Comparisons on SHO values should always be case insensitive. Stepup |
||
410 | * configuration always contains SHO values lower-cased, so this getter |
||
411 | * can be used to compare the SHO with configured values. |
||
412 | * |
||
413 | * @see StepUpAuthenticationService::resolveHighestRequiredLoa() |
||
414 | * |
||
415 | * @param string $identityNameId Used to load vetted tokens |
||
416 | * @return string either the SHO or an empty string |
||
417 | */ |
||
418 | public function getNormalizedUserShoByIdentityNameId($identityNameId) |
||
424 | } |
||
425 |
Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.