custom/plugins/SystemIntegration/src/Services/VirginUser/VirginUser.php line 1163

Open in your IDE?
  1. <?php
  2. namespace Virgin\SystemIntegration\Services\VirginUser;
  3. use phpDocumentor\Reflection\Types\This;
  4. use Shopware\Core\Checkout\Customer\CustomerEntity;
  5. use Shopware\Core\Checkout\Customer\SalesChannel\AbstractLoginRoute;
  6. use Shopware\Core\Checkout\Customer\SalesChannel\AccountService;
  7. use Shopware\Core\Framework\Context;
  8. use Shopware\Core\Framework\DataAbstractionLayer\EntityRepository;
  9. use Shopware\Core\Framework\DataAbstractionLayer\Search\Criteria;
  10. use Shopware\Core\Framework\DataAbstractionLayer\Search\Filter\EqualsFilter;
  11. use Shopware\Core\Framework\Validation\DataBag\RequestDataBag;
  12. use Shopware\Core\System\SalesChannel\ContextTokenResponse;
  13. use Shopware\Core\System\SalesChannel\SalesChannelContext;
  14. use Symfony\Component\HttpFoundation\Cookie;
  15. use Symfony\Component\HttpFoundation\Request;
  16. use Symfony\Component\HttpFoundation\Session\Session;
  17. use Symfony\Contracts\Translation\TranslatorInterface;
  18. use Virgin\GDPRPlugin\Service\PrivacyService;
  19. use Virgin\LeadManager\Utils\Services\LeadGenerationService;
  20. use Virgin\ProductModelExtension\Custom\Club\ClubEntity;
  21. use Virgin\SystemIntegration\Exception\VirginApiException;
  22. use Virgin\SystemIntegration\Services\RestApiClient;
  23. use Shopware\Core\Framework\Validation\DataValidator;
  24. use Shopware\Core\Framework\Validation\DataValidationDefinition;
  25. use Symfony\Component\Validator\Constraints\Email;
  26. use Shopware\Core\System\SystemConfig\SystemConfigService;
  27. use Virgin\SystemIntegration\Services\Selling\Subscription;
  28. use Symfony\Component\Security\Core\Exception\BadCredentialsException;
  29. use Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException;
  30. use Shopware\Core\Checkout\Customer\Exception\InactiveCustomerException;
  31. use Virgin\VirginCustomElement\Service\LandingPageService;
  32. class VirginUser
  33. {
  34. const CONTACT_LEADPURO = 100;
  35. // COSTANTI PER LA GESTIONE DEL TIPO DI UTILIZZATORE //
  36. const PERSONTYPE_LEAD = 0;
  37. const PERSONTYPE_SOCIO = 1;
  38. const PERSONTYPE_EXSOCIO = 2;
  39. const PERSONTYPE_INSOLUTO = 3;
  40. const PERSONTYPE_BLACKLIST = 4;
  41. const PERSONTYPE_DROPECCEZ = 5;
  42. const PERSONTYPE_NN = 6;
  43. const PERSONTYPE_LEADLAYER = 7;
  44. const PERSONDESC_LEAD = 'Lead';
  45. const PERSONDESC_SOCIO = 'Socio';
  46. const PERSONDESC_EXSOCIO = 'ExSocio';
  47. const PERSONDESC_INSOLUTO = 'Insoluto';
  48. const PERSONDESC_BLACKLIST = 'BlackList';
  49. const PERSONDESC_DROPECCEZ = 'Drop Eccezione'; //drop eccezione è una cancellazione anticipata rispetto alla naturale data di scadenza del'abbonamento es. motivi di salute
  50. const PERSONDESC_LEADLAYER = 'Lead Layer';
  51. const PERSONDESC_NN = 'Non Disponibile';
  52. // COSTANTI PER GESTIONE TIPO DI APPUNTAMENTO //
  53. const APP_INFO = 1;
  54. const APP_TRY = 2;
  55. // -------------------------------------//
  56. const ERROR_PSW_VAIGLOBAL_WRONG = 'VAPI API Error Forbidden';
  57. const ERROR_EXERP_DUPLICATE = 'Esiste già un cliente registrato su Exerp con questa email.';
  58. const HOME_TRAINING_CLUB_CODE = 233;
  59. private $personDesc;
  60. private $personType;
  61. /** @var GlobalUser */
  62. private $globalUser;
  63. /** @var ExerpUser */
  64. private $exerp_User;
  65. /** @var PartnerUser */
  66. private $partner_User;
  67. /** @var LeadLayerUser $leadLayer_User */
  68. private $leadLayer_User;
  69. private $errorCode;
  70. private $errorDesc;
  71. /** @var EntityRepository */
  72. private $customerRepository;
  73. private $partnerGroup;
  74. /** @var LeadGenerationService */
  75. private $leadService;
  76. /** @var RestApiClient */
  77. private $restApiClient;
  78. private $clubRepository;
  79. /** @var SystemConfigService
  80. */
  81. private SystemConfigService $systemConfigService;
  82. /** @var DataValidator
  83. */
  84. private $dataValidator;
  85. /** @var PrivacyService */
  86. private $privacyService;
  87. private $isInLeadLayer;
  88. private $customerGroupRepository;
  89. /** @var AccountService */
  90. private $accountService;
  91. /** @var TranslatorInterface */
  92. private $translator;
  93. /**
  94. * @var AbstractLoginRoute
  95. */
  96. private $loginRoute;
  97. /**
  98. * @var ClubEntity
  99. */
  100. private $clubEntity;
  101. /**
  102. * @var CustomerEntity|null
  103. */
  104. private $customerEntity;
  105. /**
  106. * @var Session
  107. */
  108. private $session;
  109. public function __construct(
  110. $customerRepository,
  111. $leadService,
  112. $restApiClient,
  113. $clubRepository,
  114. $systemConfigService,
  115. $dataValidator,
  116. $privacyService,
  117. $customerGroupRepository,
  118. $accountService,
  119. $translator,
  120. AbstractLoginRoute $loginRoute,
  121. Session $session
  122. )
  123. {
  124. $this->customerRepository = $customerRepository;
  125. $this->leadService = $leadService;
  126. $this->restApiClient = $restApiClient;
  127. $this->clubRepository = $clubRepository;
  128. $this->systemConfigService = $systemConfigService;
  129. $this->dataValidator = $dataValidator;
  130. $this->privacyService = $privacyService;
  131. $this->customerGroupRepository = $customerGroupRepository;
  132. $this->accountService = $accountService;
  133. $this->translator = $translator;
  134. $this->loginRoute = $loginRoute;
  135. $this->session = $session;
  136. }
  137. public function checkPersonFull($email, $password, $codFisc)
  138. {
  139. $response = $this->restApiClient->checkPerson($email, $password, $codFisc);
  140. if ($response!=""){
  141. $this->mapResponseToObject($response);
  142. $this->DetectPersonType();
  143. $this->GetSubscription();
  144. }
  145. return json_decode($response, true);
  146. }
  147. public function checkPerson($email, $codFisc = null)
  148. {
  149. $response = $this->restApiClient->checkPerson($email, null, $codFisc);
  150. // var_dump($response);
  151. if ($response!=""){
  152. $this->mapResponseToObject($response);
  153. $this->DetectPersonType();
  154. $this->GetSubscription();
  155. }
  156. return $response;
  157. }
  158. public function checkPersonByExerpInfo($exerpId, $campaignCode)
  159. {
  160. $response = $this->restApiClient->checkPersonByExerpInfo($exerpId, $campaignCode);
  161. if ($response!=""){
  162. $this->mapResponseToObject($response);
  163. $this->DetectPersonType();
  164. $this->GetSubscription();
  165. }
  166. return $response;
  167. }
  168. public function mapResponseToObject($response): VirginUser
  169. {
  170. $this->personType = self::PERSONTYPE_NN;
  171. $response = json_decode($response);
  172. $this->personDesc = $response->personDesc;
  173. $this->errorCode = $response->errorCode;
  174. $this->errorDesc = $response->errorDesc;
  175. $this->exerp_User = null;
  176. $this->globalUser = null;
  177. $this->leadLayer_User = null;
  178. $this->isInLeadLayer = false;
  179. $this->partner_User = null;
  180. if (isset($response->exerp_User)) {
  181. $this->exerp_User = new ExerpUser();
  182. $this->exerp_User->setErrorCode($response->exerp_User->errorCode);
  183. $this->exerp_User->setErrorDesc($response->exerp_User->errorDesc);
  184. $this->exerp_User->setId($response->exerp_User->id);
  185. $this->exerp_User->setCenterId($response->exerp_User->centerId);
  186. $this->exerp_User->setExternalId($response->exerp_User->externalId);
  187. $this->exerp_User->setEmail($response->email);
  188. $this->exerp_User->setCustomerGroup($response->customerGroup);
  189. }
  190. if (isset($response->exerp_Person)) {
  191. if(is_array($response->exerp_Person)){
  192. $key = array_search('ACTIVE',array_column($response->exerp_Person,'status'));
  193. if($key === false) {
  194. $this->personType = self::PERSONTYPE_EXSOCIO;
  195. } else {
  196. $this->personType = self::PERSONTYPE_SOCIO;
  197. }
  198. if($key>0){
  199. $response->exerp_Person=$response->exerp_Person[$key];
  200. }else{
  201. $response->exerp_Person= reset($response->exerp_Person);
  202. }
  203. }
  204. $user = $response->exerp_Person;
  205. $this->exerp_User = new ExerpUser();
  206. $this->exerp_User->setCenterId($user->personId->center);
  207. $this->exerp_User->setId($user->personId->id);
  208. $this->exerp_User->setExternalId($user->personId->externalId);
  209. $this->exerp_User->setPersonStatus($user->status);
  210. $this->exerp_User->setGender($user->gender);
  211. $this->exerp_User->setLastName($user->lastName);
  212. $this->exerp_User->setFirstName($user->firstName);
  213. $this->exerp_User->setCodFisc($user->codFisc);
  214. $this->exerp_User->setPersonType($user->personType);
  215. $this->exerp_User->setEmail($response->email);
  216. $this->exerp_User->setCustomerGroup($response->customerGroup);
  217. //var_dump($this->exerp_User );
  218. }
  219. if (isset($response->global_User)) {
  220. $this->globalUser = new GlobalUser(
  221. $response->global_User->userId,
  222. $response->global_User->firstName,
  223. $response->global_User->lastName,
  224. $response->global_User->email,
  225. $response->global_User->gender,
  226. $response->global_User->dateOfBirth,
  227. $response->global_User->externalId,
  228. $response->global_User->claims,
  229. $response->global_User->error,
  230. $response->global_User->token,
  231. $response->global_User->refreshToken
  232. );
  233. if ($this->getGlobalUser()->getToken() !=null && $this->session->get('tokenGlobal') != $this->getGlobalUser()->getToken()){
  234. $this->session->set('refreshTokenGlobal', $this->getGlobalUser()->getRefreshToken());
  235. $this->session->set('tokenGlobal', $this->getGlobalUser()->getToken());
  236. $this->session->set('tokenGlobalTimestamp', new \DateTime());
  237. }
  238. }
  239. if (isset($response->leadLayer_User)) {
  240. $this->isInLeadLayer = true;
  241. $this->leadLayer_User = new LeadLayerUser();
  242. $this->leadLayer_User->setNome($response->leadLayer_User->nome);
  243. $this->leadLayer_User->setCognome($response->leadLayer_User->cognome);
  244. $this->leadLayer_User->setCanale($response->leadLayer_User->canale);
  245. $this->leadLayer_User->setGuidLead($response->leadLayer_User->guid_lead);
  246. $this->leadLayer_User->setGiornoPredefinito($response->leadLayer_User->giorno_predefinito);
  247. $this->leadLayer_User->setOrarioPredefinito($response->leadLayer_User->orario_predefinito);
  248. $this->leadLayer_User->setClubDescrizione($response->leadLayer_User->club_Descrizione);
  249. $this->leadLayer_User->setGuidClub($response->leadLayer_User->guid_Club);
  250. $this->leadLayer_User->setTelefono($response->leadLayer_User->telefono);
  251. $this->leadLayer_User->setEmail($response->leadLayer_User->email);
  252. $this->leadLayer_User->setCanale($response->leadLayer_User->canale);
  253. $this->leadLayer_User->setPrivacy($response->leadLayer_User->privacy);
  254. }
  255. if (isset($response->partnerUser)) {
  256. $this->partner_User = new PartnerUser();
  257. $this->partner_User->setEmail($response->partnerUser->email ?? null);
  258. $this->partner_User->setUserName($response->partnerUser->userName ?? null);
  259. $this->partner_User->setSurnameName($response->partnerUser->surnameName ?? null);
  260. $this->partner_User->setBirthdate($response->partnerUser->birthdate ?? null);
  261. $this->partner_User->setBirthPlace($response->partnerUser->birthPlace ?? null);
  262. $this->partner_User->setFiscalCode($response->partnerUser->fiscalCode ?? null);
  263. $this->partner_User->setCustomerGroup($response->partnerUser->customerGroup ?? null);
  264. $this->partner_User->setItalian($response->partnerUser->italian ?? null);
  265. $this->partner_User->setNation($response->partnerUser->nation ?? null);
  266. $this->partner_User->setPhoneNumber($response->partnerUser->phoneNumber ?? null);
  267. $this->partner_User->setResidentAddress($response->partnerUser->residentAddress ?? null);
  268. $this->partner_User->setResidentCity($response->partnerUser->residentCity ?? null);
  269. $this->partner_User->setClubId($response->partnerUser->clubId ?? null);
  270. $this->setPartnerGroup($response->partnerUser->customerGroup ?? null);
  271. }
  272. return $this;
  273. }
  274. private function DetectPersonType()
  275. {
  276. $personType = $this->personType;
  277. $inExerp = isset($this->exerp_User) ? true : false;
  278. $inLeadLayer = isset($this->leadLayer_User) ? true : false;
  279. if ($inExerp) {
  280. // Socio da verificarne il tipo
  281. $externalId = $this->exerp_User->getExternalId();
  282. $personDetails = $this->restApiClient->getPersonDetail($externalId);
  283. if (isset($personDetails)) {
  284. $personDetailsArray = json_decode($personDetails,true);
  285. $personDetails = json_decode($personDetails);
  286. $this->exerp_User->setPersonType($personDetails->person->personType);
  287. $this->exerp_User->setPersonStatus($personDetails->person->status);
  288. $this->exerp_User->setCodFisc($personDetails->person->codFisc);
  289. $this->exerp_User->setSuspended($personDetails->personTypeAndStatus->suspended);
  290. $this->exerp_User->setBlackListed($personDetails->personTypeAndStatus->blacklisted);
  291. $this->exerp_User->setSubscriptions($personDetails->subscriptions);
  292. $this->exerp_User->setFirstName($personDetails->person->firstName);
  293. $this->exerp_User->setLastName($personDetails->person->lastName);
  294. $this->exerp_User->setCenterId($personDetails->person->personId->center);
  295. if($personDetailsArray['person']['status'] == 'TEMPORARYINACTIVE'
  296. || $personDetailsArray['person']['status'] == 'INACTIVE') {
  297. $key = array_search('ACTIVE',array_column($personDetailsArray['subscriptions'],'state'));
  298. if($key===false){
  299. // Sub Appena acquistata ma non attiva quindi sono TEMPORARYINACTIVE ma sub non ancora attiva
  300. $key = array_search('CREATED',array_column($personDetailsArray['subscriptions'],'state'));
  301. }
  302. if($key===false){
  303. // Sub in stato freeze
  304. $key = array_search('FROZEN',array_column($personDetailsArray['subscriptions'],'state'));
  305. }
  306. if($key===false){
  307. // se non è attivo cerco per sub appena creato
  308. $personType = self::PERSONTYPE_EXSOCIO;
  309. }else{
  310. $personType = self::PERSONTYPE_SOCIO;
  311. }
  312. } else {
  313. if($personDetailsArray['person']['status'] =='ACTIVE'){
  314. $key = array_search('ACTIVE',array_column($personDetailsArray['subscriptions'],'state'));
  315. if($key===false){
  316. $key = array_search('CREATED',array_column($personDetailsArray['subscriptions'],'state'));
  317. }
  318. if($key===false){
  319. $key = array_search('FROZEN',array_column($personDetailsArray['subscriptions'],'state'));
  320. }
  321. if($key===false){
  322. $key = array_search('CREATED',array_column($personDetailsArray['subscriptions'],'state'));
  323. }
  324. //var_dump($key);
  325. if($key === false) {
  326. $personType = self::PERSONTYPE_EXSOCIO;
  327. } else {
  328. $personType = self::PERSONTYPE_SOCIO;
  329. }
  330. }else{
  331. $personType = self::PERSONTYPE_EXSOCIO;
  332. }
  333. }
  334. };
  335. $balance = $this->restApiClient->getBalance($externalId);
  336. if (isset($balance)) {
  337. $this->exerp_User->setBalance($balance["totalPayableDebt"]);
  338. }
  339. if ($this->exerp_User->getBalance() > 0) {
  340. $personType = self::PERSONTYPE_INSOLUTO;
  341. }
  342. if ($this->exerp_User->getBlackListed()) {
  343. $personType = self::PERSONTYPE_BLACKLIST;
  344. }
  345. //var_dump($this->exerp_User->getPersonStatus());
  346. if($this->exerp_User->getPersonStatus() =='LEAD'){
  347. $personType = self::PERSONTYPE_LEAD;
  348. }
  349. }else{
  350. $personType = self::PERSONTYPE_LEAD;
  351. if ($inLeadLayer) {
  352. $personType = self::PERSONTYPE_LEADLAYER;
  353. }
  354. }
  355. $this->personType = $personType;
  356. $this->PersonTypeDesc();
  357. // var_dump($this->personType );
  358. }
  359. private function PersonTypeDesc()
  360. {
  361. switch ($this->personType) {
  362. case self::PERSONTYPE_LEAD:
  363. $this->personDesc = self::PERSONDESC_LEAD;
  364. break;
  365. case self::PERSONTYPE_EXSOCIO:
  366. $this->personDesc = self::PERSONDESC_EXSOCIO;
  367. break;
  368. case self::PERSONTYPE_INSOLUTO:
  369. $this->personDesc = self::PERSONDESC_INSOLUTO;
  370. break;
  371. case self::PERSONTYPE_BLACKLIST:
  372. $this->personDesc = self::PERSONDESC_BLACKLIST;
  373. break;
  374. case self::PERSONTYPE_SOCIO:
  375. $this->personDesc = self::PERSONDESC_SOCIO;
  376. break;
  377. case self::PERSONTYPE_DROPECCEZ:
  378. $this->personDesc = self::PERSONDESC_DROPECCEZ;
  379. break;
  380. case self::PERSONTYPE_LEADLAYER:
  381. $this->personDesc = self::PERSONDESC_LEADLAYER;
  382. break;
  383. case self::PERSONDESC_NN:
  384. $this->personDesc = self::PERSONDESC_NN;
  385. }
  386. }
  387. public function GetSubscription()
  388. {
  389. if (isset($this->exerp_User)) {
  390. $exerpId=null;
  391. $exrpCenterId=null;
  392. if($this->exerp_User->getId() != '' || $this->exerp_User->getId() != null){
  393. $exerpId = $this ->exerp_User->getId();
  394. $exrpCenterId=$this ->exerp_User->getCenterId();
  395. }
  396. if ($exerpId!=null) {
  397. $response = $this->restApiClient->getPersonSubscriptions($exerpId ,$exrpCenterId);
  398. if (isset($response)) {
  399. $subJson = json_decode($response,true);
  400. if($subJson['item'] != null) {
  401. $item = array_search('ACTIVE',array_column($subJson['item'],'state'));
  402. if($item !== false){
  403. $sub = new Subscription();
  404. $sub->setName($subJson['item'][$item]['product']['name']);
  405. $sub->setPeriodLength($subJson['item'][$item]['product']['periodLength']);
  406. $sub->setPeriodUnit($subJson['item'][$item]['product']['periodUnit']);
  407. $sub->setType($subJson['item'][$item]['product']['type']);
  408. $sub->setStartDate($subJson['item'][$item]['startDate']);
  409. $sub->setEndDate($subJson['item'][$item]['endDate']);
  410. $sub->setSubscriptionId($subJson['item'][$item]['subscriptionId']['center']. 'ss' .$subJson['item'][$item]['subscriptionId']['id']);
  411. $sub->setState($subJson['item'][$item]['state']);
  412. $sub->setSubState($subJson['item'][$item]['subState']);
  413. $this->exerp_User->setSubscriptions($sub);
  414. }
  415. }
  416. }
  417. }
  418. }
  419. }
  420. /**
  421. * @param RequestDataBag $data
  422. * @return string|null
  423. */
  424. public function CheckFormParamsToStorefront(RequestDataBag $data): ?string
  425. {
  426. $firstname = $data->get('name');
  427. $lastname = $data->get('lastname');
  428. $phone = $data->get('phone');
  429. $phonePrefix = $data->get('intlPrefix');
  430. $email = $data->get('email');
  431. $privacy = $data->get('privacy');
  432. $club = $data->get('club');
  433. $zipcode = $data->get('zipcode');
  434. $validation = new DataValidationDefinition('customer.email');
  435. $validation->add('email', new Email());
  436. if (empty($firstname) || empty($lastname) || empty($phone) || empty($email) || empty($club)) {
  437. return 'lead-manager.form.message.errorMessage';
  438. }
  439. $response = $this->leadService->getCaptchaResponse($_POST['g-recaptcha-response'], $this->systemConfigService->get('LeadManager.config.secretKey'));
  440. if (!$response->success) {
  441. return 'lead-manager.form.message.invalidCaptcha';
  442. }
  443. if (!preg_match($this->systemConfigService->get('LeadManager.config.textRegex'), $firstname) || !preg_match($this->systemConfigService->get('LeadManager.config.textRegex'), $lastname) || !preg_match($this->systemConfigService->get('LeadManager.config.numberRegex'), $phone)) {
  444. return 'lead-manager.form.message.errorRegexFields';
  445. }
  446. try {
  447. $this->dataValidator->validate(['email' => $email], $validation);
  448. } catch (\Exception $e) {
  449. return $e->getMessage();
  450. }
  451. return null;
  452. }
  453. /**
  454. * @param array $formParams
  455. * @param SalesChannelContext $context
  456. * @return string|null
  457. */
  458. public function handlePerson(array $formParams, SalesChannelContext $context): ?string
  459. {
  460. $privacy = $formParams['privacy'] ?? false;
  461. if (!empty($_SESSION['utm_params'])) {
  462. $this->restApiClient->insertUtmParams($_SESSION['utm_params'], $formParams['email'], $formParams['firstName'], $formParams['lastName']);
  463. unset($_SESSION['utm_params']);
  464. }
  465. if ($this->getPersonType()!=self::PERSONTYPE_LEAD && $this->getPersonType()!=self::PERSONTYPE_LEADLAYER){
  466. return 'lead-manager.form.message.userRegistered';
  467. }
  468. if ($this->getErrorDesc()){
  469. return 'lead-manager.account.genericErrorLogin';
  470. }
  471. try {
  472. $this->saveCurrentLead(
  473. null,
  474. $formParams['email'],
  475. $formParams['firstName'],
  476. $formParams['lastName'],
  477. $formParams['phone'],
  478. $formParams['club'],
  479. $privacy,
  480. null,
  481. $context
  482. );
  483. } catch (VirginApiException $e) {
  484. } catch (\Exception $e) {
  485. return 'lead-manager.form.message.errorRegistration';
  486. }
  487. return null;
  488. }
  489. /**
  490. * @param array $formParams
  491. * @param string|null $guid
  492. * @return void
  493. * @throws VirginApiException
  494. * @throws \Exception
  495. */
  496. private function upsertLeadToLayer(array $formParams, string $guid=null): void
  497. {
  498. if ($guid){
  499. $lead = $this->restApiClient->getLead(['guid' => $guid]);
  500. } else {
  501. $lead = $this->restApiClient->getLead(['email' => $formParams['email']]);
  502. }
  503. if ($lead != []) {
  504. $this->restApiClient->updateLeadAndAppointment($formParams);
  505. } else {
  506. $this->restApiClient->insertLeadAndAppointment($formParams);
  507. }
  508. }
  509. /**
  510. * @param array $customerData
  511. * @param SalesChannelContext $context
  512. * @return false|void
  513. */
  514. public function updateLead(array $customerData, SalesChannelContext $context)
  515. {
  516. if (empty($customerData)) {
  517. return false;
  518. }
  519. try {
  520. $currentLead = $this->getCurrentLead();
  521. if (
  522. $currentLead['firstName'] != $customerData['name'] ||
  523. $currentLead['lastName'] != $customerData['surname'] ||
  524. $currentLead['phoneNumber'] != $customerData['phone'] ||
  525. $currentLead['email'] != $customerData['email'] ||
  526. $currentLead['clubId'] != $customerData['clubId']
  527. ) {
  528. $this->saveCurrentLead(
  529. $currentLead['guid_lead'],
  530. $customerData['email'],
  531. $customerData['name'],
  532. $customerData['surname'],
  533. $customerData['phone'],
  534. $currentLead['clubId'],
  535. $currentLead['privacy'],
  536. $currentLead['timestamp'],
  537. $context
  538. );
  539. }
  540. } catch (\Exception $e) {
  541. return false;
  542. }
  543. }
  544. public function getCustomerGroupIdByVirginUserTypeCode($userTypeCode)
  545. {
  546. $customerGroupEntity = $this->customerGroupRepository->search(
  547. (new Criteria())->addFilter(new EqualsFilter('customFields.virgin_user_type_code', $userTypeCode))
  548. , Context::createDefaultContext())->first();
  549. return $customerGroupEntity->getId();
  550. }
  551. public function getCustomerGroupIdByName($customerGroupName)
  552. {
  553. $customerGroupEntity = $this->customerGroupRepository->search(
  554. (new Criteria())->addFilter(new EqualsFilter('name', $customerGroupName))
  555. , Context::createDefaultContext())->first();
  556. return $customerGroupEntity->getId();
  557. }
  558. public function writeCookies($formParams)
  559. {
  560. $params = [
  561. 'name' => $formParams['firstName'],
  562. 'lastname' => $formParams['lastName'],
  563. 'phone' => $formParams['phone'],
  564. 'email' => $formParams['email'],
  565. 'userType' => '', // handle CRM user type
  566. ];
  567. $this->leadService->createCookie($params);
  568. }
  569. /**
  570. * @param $data
  571. * @param SalesChannelContext $context
  572. * @return array
  573. */
  574. public function LoginManager($data, SalesChannelContext $context): array
  575. {
  576. $email = $data->get('username');
  577. $password = $data->get('password');
  578. $checkPersonResponse = $this->checkPersonFull($email , $password,null);
  579. if (!$checkPersonResponse || $this->errorCode == 500) {
  580. return [
  581. 'login' => false,
  582. 'errorMessage' => $this->translator->trans('lead-manager.form.message.checkpersonFail')
  583. ];
  584. }
  585. $this->setCustomerEntity($this->getCustomerByEmail($email, $context));
  586. $this->setClub($context);
  587. if ($checkPersonResponse['personDesc'] == "LEAD" || $checkPersonResponse['personDesc'] == "LEADLAYER") {
  588. return [
  589. 'login' => false,
  590. 'errorMessage' => $this->translator->trans('lead-manager.form.message.accountLoginOldLead'),
  591. 'personType' => $this->getPersonType()
  592. ];
  593. }
  594. if ($this->errorDesc == self::ERROR_PSW_VAIGLOBAL_WRONG) {
  595. return [
  596. 'login' => false,
  597. 'errorMessage' => $this->translator->trans('lead-manager.form.message.accountLogin'),
  598. 'personType' => $this->getPersonType()
  599. ];
  600. }
  601. if (!empty($this->errorDesc)) {
  602. return [
  603. 'login' => false,
  604. 'errorMessage' => $this->translator->trans('lead-manager.account.genericErrorLogin'),
  605. 'personType' => $this->getPersonType()
  606. ];
  607. }
  608. if ($this->getGlobalUser() == null || $this->getExerpUser() == null){
  609. return [
  610. 'login' => false,
  611. 'errorMessage' => $this->translator->trans('lead-manager.form.message.checkpersonFail')
  612. ];
  613. }
  614. //user is not on shopware, implicit registration
  615. if (!$this->getCustomerEntity()) {
  616. $this->setCustomerEntity($this->registerFromGlobal($context, $email, $password));
  617. if (!$this->getCustomerEntity()){
  618. return [
  619. 'login' => false,
  620. 'errorMessage' => $this->translator->trans('lead-manager.form.message.checkpersonFail'),
  621. ];
  622. }
  623. }
  624. $customerUpdateArray = $this->getUpdateShopwareFields($password);
  625. $customFields = [
  626. 'lead_implicit_registration' => false,
  627. 'privacy_consent' => null,
  628. 'home_training' => $this->getIsHomeTraining(),
  629. ];
  630. if ($this->getPartnerUser()) {
  631. $customFields = array_merge($customFields, $this->getPartnerUser()->getObjectVars());
  632. }
  633. $customerUpdateArray['id'] = $this->getCustomerEntity()->getId();
  634. $customerUpdateArray['customFields'] = $customFields;
  635. if (!empty($_SESSION['utm_params'])) {
  636. $this->restApiClient->insertUtmParams($_SESSION['utm_params'], $email, $this->getCustomerEntity()->getFirstName(), $this->getCustomerEntity()->getLastName(), 'LOGIN');
  637. unset($_SESSION['utm_params']);
  638. }
  639. if ($this->leadLayer_User){
  640. $customerUpdateArray['customFields']['virgin_guid'] = $this->leadLayer_User->getGuidLead();
  641. } else {
  642. error_log("LoginManager - no leadLayer_user for ".$email);
  643. }
  644. try {
  645. if ($this->getPersonType() != VirginUser::PERSONTYPE_BLACKLIST) {
  646. $this->customerRepository->update([$customerUpdateArray], $context->getContext());
  647. $this->loginRoute->login($data, $context);
  648. if ($this->getCustomerEntity()->getCustomFields() &&
  649. isset($this->getCustomerEntity()->getCustomFields()['unsolved_under_evaluation']) &&
  650. $this->getCustomerEntity()->getCustomFields()['unsolved_under_evaluation']
  651. ) {
  652. $this->customerRepository->update([
  653. [
  654. 'id' => $this->getCustomerEntity()->getId(),
  655. 'customFields' => [
  656. 'unsolved_under_evaluation' => false,
  657. ],
  658. ],
  659. ], $context->getContext());
  660. }
  661. }
  662. $this->session->set('personType', $this->getPersonType());
  663. $response = [
  664. 'login' => true,
  665. 'personType' => $this->getPersonType(),
  666. 'customerEntity' => $this->getCustomerEntity()
  667. ];
  668. } catch (BadCredentialsException|UnauthorizedHttpException|InactiveCustomerException $e) {
  669. //login ko
  670. switch ($e) {
  671. case $e instanceof UnauthorizedHttpException:
  672. case $e instanceof BadCredentialsException:
  673. default:
  674. $errorMessage = $this->translator->trans('lead-manager.form.message.accountLogin');
  675. }
  676. $response = [
  677. 'login' => false,
  678. 'errorMessage' => $errorMessage,
  679. 'personType' => $this->getPersonType(),
  680. 'customerEntity' => $this->getCustomerEntity()
  681. ];
  682. }
  683. return $response;
  684. }
  685. /**
  686. * @param string $email
  687. * @param SalesChannelContext $salesChannelContext
  688. * @return CustomerEntity | null
  689. */
  690. private function getCustomerByEmail(string $email, SalesChannelContext $salesChannelContext): ?CustomerEntity
  691. {
  692. $criteria = new Criteria();
  693. $criteria->addFilter(new EqualsFilter('customer.email', $email));
  694. /** @var CustomerEntity $customerEntity */
  695. return $this->customerRepository->search($criteria, $salesChannelContext->getContext())->first();
  696. }
  697. /**
  698. * @param string $urlLogin
  699. * @param string $urlCourses
  700. * @return string
  701. * @throws VirginApiException
  702. */
  703. public function getURL_TO_PersonalAreaCMS(string $urlLogin, string $urlCourses ): string
  704. {
  705. $token = $this->getGlobalToken();
  706. if (!$token){
  707. return "#";
  708. }
  709. return $urlLogin.'?token='.$token.'&landingurl='.$urlCourses;
  710. }
  711. /**
  712. * @return mixed|null
  713. * @throws VirginApiException
  714. */
  715. public function getGlobalToken()
  716. {
  717. if ($this->session->get('tokenGlobalTimestamp') &&
  718. (new \DateTime())->diff($this->session->get('tokenGlobalTimestamp'))->m < 120
  719. ){
  720. return $this->session->get('tokenGlobal');
  721. }
  722. $tokenData = $this->restApiClient->GlobalRefreshToken($this->session->get('refreshTokenGlobal'));
  723. if (!$tokenData){
  724. return null;
  725. }
  726. $this->session->set('refreshTokenGlobal', $tokenData['token']);
  727. $this->session->set('tokenGlobal', $tokenData['oneTimeToken']);
  728. $this->session->set('tokenGlobalTimestamp', new \DateTime());
  729. return $tokenData['oneTimeToken'];
  730. }
  731. /**
  732. * @return mixed
  733. */
  734. public function getPersonDesc()
  735. {
  736. return $this->personDesc;
  737. }
  738. /**
  739. * @param mixed $personDesc
  740. */
  741. public function setPersonDesc($personDesc): void
  742. {
  743. $this->personDesc = $personDesc;
  744. }
  745. /**
  746. * @return mixed
  747. */
  748. public function getPersonType()
  749. {
  750. return $this->personType;
  751. }
  752. /**
  753. * @param GlobalUser $globalUser
  754. */
  755. public function setGlobalUser(GlobalUser $globalUser): void
  756. {
  757. $this->globalUser = $globalUser;
  758. }
  759. /**
  760. * @return GlobalUser | null
  761. */
  762. public function getGlobalUser(): ?GlobalUser
  763. {
  764. return $this->globalUser ?? null;
  765. }
  766. /**
  767. * @return ExerpUser | null
  768. */
  769. public function getExerpUser(): ?ExerpUser
  770. {
  771. return $this->exerp_User ?? null;
  772. }
  773. /**
  774. * @param ExerpUser $exerp_User
  775. */
  776. public function setExerpUser(ExerpUser $exerp_User): void
  777. {
  778. $this->exerp_User = $exerp_User;
  779. }
  780. /**
  781. * @return mixed
  782. */
  783. public function getErrorCode()
  784. {
  785. return $this->errorCode;
  786. }
  787. /**
  788. * @param mixed $errorCode
  789. */
  790. public function setErrorCode($errorCode): void
  791. {
  792. $this->errorCode = $errorCode;
  793. }
  794. /**
  795. * @return mixed
  796. */
  797. public function getErrorDesc()
  798. {
  799. return $this->errorDesc;
  800. }
  801. /**
  802. * @param mixed $errorDesc
  803. */
  804. public function setErrorDesc($errorDesc): void
  805. {
  806. $this->errorDesc = $errorDesc;
  807. }
  808. /**
  809. * @return LeadLayerUser
  810. */
  811. public function getLeadLayerUser(): ?LeadLayerUser
  812. {
  813. return $this->leadLayer_User;
  814. }
  815. /**
  816. * @param LeadLayerUser $leadLayer_User
  817. */
  818. public function setLeadLayerUser(LeadLayerUser $leadLayer_User): void
  819. {
  820. $this->leadLayer_User = $leadLayer_User;
  821. }
  822. /**
  823. * @return mixed
  824. */
  825. public function getIsInLeadLayer()
  826. {
  827. return $this->isInLeadLayer;
  828. }
  829. /**
  830. * @param mixed $isInLeadLayer
  831. */
  832. public function setIsInLeadLayer($isInLeadLayer): void
  833. {
  834. $this->isInLeadLayer = $isInLeadLayer;
  835. }
  836. /**
  837. * @return mixed
  838. */
  839. public function getPartnerGroup()
  840. {
  841. return $this->partnerGroup;
  842. }
  843. /**
  844. * @param mixed $partnerGroup
  845. */
  846. public function setPartnerGroup($partnerGroup): void
  847. {
  848. $customerGroups = explode(",", $partnerGroup);
  849. if(count($customerGroups) > 1) {
  850. $this->partnerGroup = $customerGroups[1];
  851. } else {
  852. $this->partnerGroup = $customerGroups[0];
  853. }
  854. }
  855. /**
  856. * @return PartnerUser
  857. */
  858. public function getPartnerUser():? PartnerUser
  859. {
  860. return $this->partner_User;
  861. }
  862. /**
  863. * @param PartnerUser $partner_User
  864. */
  865. public function setPartnerUser(PartnerUser $partner_User)
  866. {
  867. $this->partner_User = $partner_User;
  868. }
  869. /**
  870. * @return mixed
  871. */
  872. public function getCustomerGroupId()
  873. {
  874. if($this->getExerpUser() != null && !empty($this->getExerpUser()->getCustomerGroup())) {
  875. $customerGroupId = $this->getCustomerGroupIdByName($this->getExerpUser()->getCustomerGroup());
  876. } else {
  877. if(!empty($this->getPartnerGroup())) {
  878. $customerGroupId = $this->getCustomerGroupIdByName($this->getPartnerGroup());
  879. if(empty($customerGroupId)) {
  880. $customerGroupId = $this->getCustomerGroupIdByVirginUserTypeCode($this->getPersonType());
  881. }
  882. } else {
  883. $customerGroupId = $this->getCustomerGroupIdByVirginUserTypeCode($this->getPersonType());
  884. }
  885. }
  886. return $customerGroupId;
  887. }
  888. private function registerFromGlobal(SalesChannelContext $context, $email, $password): CustomerEntity
  889. {
  890. $shopwareUserBasicData = [
  891. 'firstName' => $this->getGlobalUser()->getFirstName(),
  892. 'lastName' => $this->getGlobalUser()->getLastName(),
  893. 'salutationId' => $this->leadService->getDefaultSalutation($context),
  894. 'email' => $email,
  895. 'password' => $password,
  896. ];
  897. //registrazione implicita
  898. return $this->leadService->prepareRegistrationData($context, $shopwareUserBasicData, false);
  899. }
  900. /**
  901. * @param string|null $password
  902. * @return array|null
  903. */
  904. private function getUpdateShopwareFields(string $password=null): ?array
  905. {
  906. if (!$this->getCustomerEntity()){
  907. return null;
  908. }
  909. //clubentity
  910. $updateArray = [
  911. 'active' => true,
  912. 'group' => [
  913. 'id' => $this->getCustomerGroupId()
  914. ],
  915. 'extensions' => ['preferredClubId' => $this->getClubEntity() ? $this->getClubEntity()->getId() : null],
  916. ];
  917. if ($this->getCustomerEntity()->getFirstName() != $this->getGlobalUser()->getFirstName()) {
  918. $updateArray['firstName'] = $this->getGlobalUser()->getFirstName();
  919. }
  920. if ($this->getCustomerEntity()->getLastName() != $this->getGlobalUser()->getLastName()) {
  921. $updateArray['lastName'] = $this->getGlobalUser()->getLastName();
  922. }
  923. if ($password && !password_verify($password, $this->customerEntity->getPassword())){
  924. $updateArray['password'] = $password;
  925. }
  926. return $updateArray;
  927. }
  928. /**
  929. * @param SalesChannelContext $context
  930. * @return void
  931. */
  932. private function setClub(SalesChannelContext $context)
  933. {
  934. if ($this->getExerpUser()) {
  935. $criteria = new Criteria();
  936. $criteria->addFilter(new EqualsFilter('club.centerId', $this->getExerpUser()->getCenterId()));
  937. /** @var ClubEntity $clubEntity */
  938. $this->clubEntity = $this->clubRepository->search($criteria, $context->getContext())->first();
  939. }
  940. }
  941. /**
  942. * @return ClubEntity|null
  943. */
  944. public function getClubEntity(): ? ClubEntity
  945. {
  946. return $this->clubEntity;
  947. }
  948. /**
  949. * @return bool
  950. */
  951. private function getIsHomeTraining(): bool
  952. {
  953. return $this->getExerpUser()->getCenterId() == $this::HOME_TRAINING_CLUB_CODE;
  954. }
  955. private function isImplicit()
  956. {
  957. return $this->customerEntity->getCustomFields()['lead_implicit_registration'] ?? false;
  958. }
  959. /**
  960. * @return CustomerEntity|null
  961. */
  962. public function getCustomerEntity(): ?CustomerEntity
  963. {
  964. return $this->customerEntity;
  965. }
  966. /**
  967. * @param CustomerEntity|null $customerEntity
  968. * @return void
  969. */
  970. private function setCustomerEntity(?CustomerEntity $customerEntity)
  971. {
  972. $this->customerEntity = $customerEntity;
  973. }
  974. /**
  975. * @throws \Exception
  976. */
  977. public function getCurrentLead(){
  978. if (
  979. $this->session->get('leadUser') &&
  980. (new \DateTime())->diff(
  981. (new \DateTime())->setTimestamp($this->session->get('leadUser')['timestamp'])
  982. )->days > 30
  983. ) {
  984. $this->session->set('leadUser', null);
  985. throw new \Exception('Expired Lead');
  986. }
  987. if (isset($_COOKIE['leadUser'])){
  988. $this->session->set('leadUser', json_decode($_COOKIE['leadUser'], true));
  989. }
  990. return $this->session->get('leadUser');
  991. }
  992. /**
  993. * @param string|null $guid
  994. * @param string $email
  995. * @param string $firstName
  996. * @param string $lastName
  997. * @param string $phoneNumber
  998. * @param string $clubId
  999. * @param bool $privacy
  1000. * @param string|null $timestamp
  1001. * @param SalesChannelContext $context
  1002. * @throws VirginApiException
  1003. */
  1004. public function saveCurrentLead(
  1005. ?string $guid,
  1006. string $email,
  1007. string $firstName,
  1008. string $lastName,
  1009. string $phoneNumber,
  1010. string $clubId,
  1011. bool $privacy,
  1012. ?string $timestamp,
  1013. SalesChannelContext $context,
  1014. bool $skipUpsertLeadToLayer= false
  1015. ): void
  1016. {
  1017. $update = true;
  1018. if (!$guid){
  1019. $dateTime = new \DateTime();
  1020. $guid = $dateTime->getTimestamp() . $email;
  1021. $timestamp = $dateTime->getTimestamp();
  1022. $update = false;
  1023. }
  1024. $user = [
  1025. 'guid_lead' => $guid,
  1026. 'firstName' => $firstName,
  1027. 'lastName' => $lastName,
  1028. 'email' => $email,
  1029. 'phoneNumber' => $phoneNumber,
  1030. 'clubId' => $clubId,
  1031. 'privacy' => $privacy,
  1032. 'timestamp' => $timestamp,
  1033. ];
  1034. $this->session->set('leadUser', $user);
  1035. //todo
  1036. $privacyText = "";
  1037. if ($privacyText) {
  1038. $user['privacyJson'] = $privacyText;
  1039. }
  1040. if ($clubId == 'digital'){
  1041. return;
  1042. } else {
  1043. $criteria = new Criteria();
  1044. $criteria->addFilter(new EqualsFilter('club.id', $clubId));
  1045. /** @var ClubEntity $clubEntity */
  1046. $clubEntity = $this->clubRepository->search($criteria, $context->getContext())->first();
  1047. $user['guid_club'] = $clubEntity->getGuidVirgin();
  1048. $user['clubName'] = $clubEntity->getName();
  1049. }
  1050. if (!$skipUpsertLeadToLayer) {
  1051. $this->upsertLeadToLayer($user, $update ? $guid : null);
  1052. }
  1053. }
  1054. /**
  1055. * @param string|null $email
  1056. * @return bool
  1057. */
  1058. public function canBuy(string $email = null): bool
  1059. {
  1060. if ($email){
  1061. $this->checkPerson($email);
  1062. }
  1063. return match ($this->getPersonType()) {
  1064. $this::PERSONTYPE_LEAD,
  1065. $this::PERSONTYPE_LEADLAYER,
  1066. $this::PERSONTYPE_DROPECCEZ,
  1067. $this::PERSONTYPE_EXSOCIO => true,
  1068. default => false,
  1069. };
  1070. }
  1071. }