src/Controller/VkApiController.php line 144

  1. <?php
  2. namespace App\Controller;
  3. use App\Entity\AgencyClients;
  4. use App\Entity\AgencyClientsHistoryDiposit;
  5. use App\Entity\User;
  6. use App\Entity\UserPlatform;
  7. use App\Entity\UserProject;
  8. use App\Entity\VkUser;
  9. use App\Form\TransactionFormType;
  10. use App\Service\BillingService;
  11. use Doctrine\ORM\EntityManagerInterface;
  12. use Doctrine\Persistence\ManagerRegistry;
  13. use Exception;
  14. use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
  15. use Symfony\Component\HttpFoundation\Request;
  16. use Symfony\Component\HttpFoundation\Response;
  17. use Symfony\Component\Routing\Annotation\Route;
  18. use Symfony\Contracts\HttpClient\Exception\ClientExceptionInterface;
  19. use Symfony\Contracts\HttpClient\Exception\DecodingExceptionInterface;
  20. use Symfony\Contracts\HttpClient\Exception\RedirectionExceptionInterface;
  21. use Symfony\Contracts\HttpClient\Exception\ServerExceptionInterface;
  22. use Symfony\Contracts\HttpClient\Exception\TransportExceptionInterface;
  23. use Symfony\Contracts\HttpClient\HttpClientInterface;
  24. class VkApiController extends AbstractController
  25. {
  26.     private $client;
  27.     
  28.     private $limit;
  29.     
  30.     private BillingService $billingService;
  31.     
  32.     public function __construct(HttpClientInterface $vkContentClient, private readonly ManagerRegistry $doctrineBillingService $billingService)
  33.     {
  34.         $this->client $vkContentClient;
  35.         $this->limit 50;
  36.         $this->billingService $billingService;
  37.     }
  38.     
  39.     #[Route(path'/api/vk/transaction/to/{clientId}/{amount}/{userProject}'name'vk_api_transaction')]
  40.     public function transactionToClient(string $clientIdstring $amountUserProject $userProject): Response
  41.     {
  42.         $entityManager $this->doctrine->getManager();
  43.         $user $this->getUser();
  44.         
  45.         if (!($user instanceof User)) {
  46.             return $this->json(['error' => 'Авторизуйтесь для выполнения данной операции.'], 500);
  47.         }
  48.         
  49.         if (!$user->isAdmin()) {
  50.             $needBalance intval($amount) * 100;
  51.             // Add amount
  52.             try {
  53.                 // TODO change $user->getMainUserProject() to required project
  54.                 
  55.                 if ($userProject == null) {
  56.                     $userProject $user->getMainUserProject();
  57.                 }
  58.                 $this->billingService->updateUserBalance($user'vk_transaction_to_client'$needBalance$userProjectnullnull, [
  59.                     'clientId' => $clientId
  60.                 ]);
  61.             } catch (Exception $exception) {
  62.                 //todo log
  63.                 //$exception->getMessage();
  64.                 return $this->json(['error' => $exception->getMessage()], 500);
  65.             }
  66.             $entityManager->persist($user);
  67.             $entityManager->flush();
  68.         }
  69.         
  70.         $response $this->client->request('POST'"https://ads.vk.com/api/v2/billing/transactions/to/$clientId.json", [
  71.             'json' => [
  72.                 'amount' => ($amount 1.2)
  73.             ]
  74.         ]);
  75.         
  76.         if ($response->getStatusCode() !== 200) {
  77.             return $this->json(['error' => 'Ошибка'], $response->getStatusCode());
  78.         }
  79.         
  80.         $response $response->toArray();
  81.         
  82.         $ACHistoryDiposit = new AgencyClientsHistoryDiposit();
  83.         $ACHistoryDiposit->setAmount($response['amount']);
  84.         $ACHistoryDiposit->setCreatedAt($response['created_at']);
  85.         $ACHistoryDiposit->setClientBalance($response['client_balance']);
  86.         $ACHistoryDiposit->setClientUsername($response['client_username']);
  87.         $ACHistoryDiposit->setUserEmail($user->getEmail());
  88.         
  89.         $entityManager->persist($ACHistoryDiposit);
  90.         $entityManager->flush();
  91.         
  92.         
  93.         return $this->json(['data' => $response]);
  94.         
  95.     }
  96.     
  97.     #[Route(path'/api/vk/getClients'name'vk_api_clients')]
  98.     public function getVkApiClients(Request $requestManagerRegistry $doctrine): Response
  99.     {
  100.         $entityManager $doctrine->getManager();
  101.         
  102.         $response $this->client->request('GET'"https://ads.vk.com/api/v2/agency/clients.json?limit=$this->limit");
  103.         $response $response->toArray();
  104.         
  105.         $responseCount $response['count'];
  106.         
  107.         if ($responseCount <= $this->limit) {
  108.             return $this->json($response);
  109.         }
  110.         
  111.         for ($offset 0$offset <= $responseCount$offset+=$this->limit) {
  112.             $responseOffset $this->client->request('GET'"https://ads.vk.com/api/v2/agency/clients.json?limit=$this->limit&offset=$offset");
  113.             foreach ($responseOffset->toArray()['items'] as $item) {
  114.                 
  115.                 $agencyClient null;
  116.                 $vkUser $this->doctrine->getRepository(VkUser::class)->findOneBy(['username' => $item['user']['username']]);
  117.                 
  118.                 if ($vkUser instanceof VkUser) {
  119.                     $agencyClient $this->doctrine->getRepository(AgencyClients::class)->findOneBy(['vkUser' => $vkUser]);
  120.                 } else {
  121.                     $agencyClient = new AgencyClients();
  122.                     $vkUser = new VkUser();
  123.                 }
  124.                 
  125.                 $this->updateVkClientInfo($item$vkUser$agencyClient);
  126.             }
  127.         }
  128.         
  129.         $clients $this->doctrine->getRepository(AgencyClients::class)->findAll();
  130.         
  131.         return $this->json([
  132.             "count" => count($clients),
  133.             "data" => $clients
  134.         ]);
  135.         
  136.     }
  137.     
  138.     #[Route(path'/api/vk/getVkUserClients'name'vk_api_user_clients')]
  139.     public function getVkUserClients(Request $requestManagerRegistry $doctrine): Response
  140.     {
  141.         $user $this->getUser();
  142.         
  143.         $userPlatform $this->doctrine->getRepository(UserPlatform::class)->findOneBy(['user' => $user'name' => 'ads.vk']);
  144.         
  145.         if (!($userPlatform instanceof UserPlatform)) {
  146.             return $this->json(['error' => 'Отсутствует токен для VK ADS'], 500);
  147.         }
  148.         
  149.         $token $userPlatform->getToken();
  150.         
  151.         $response $this->client->request('GET'"https://ads.vk.com/api/v3/manager/clients.json?limit=$this->limit", [
  152.             'auth_bearer' => $token
  153.         ]);
  154.         
  155.         if ($response->getStatusCode() !== 200) {
  156.             return $this->json(['error' => $response->toArray(false)['error']], $response->getStatusCode());
  157.         }
  158.         $response $response->toArray();
  159.         
  160.         $responseCount $response['count'];
  161.         for ($offset 0$offset <= $responseCount$offset+=$this->limit) {
  162.             $responseOffset $this->client->request('GET'"https://ads.vk.com/api/v3/manager/clients.json?limit=$this->limit&offset=$offset", [
  163.                 'auth_bearer' => $token
  164.             ]);
  165.             foreach ($responseOffset->toArray()['items'] as $item) {
  166.                 
  167.                 $agencyClient null;
  168.                 $vkUser $this->doctrine->getRepository(VkUser::class)->findOneBy(['username' => $item['user']['username']]);
  169.                 
  170.                 if ($vkUser instanceof VkUser) {
  171.                     $agencyClient $this->doctrine->getRepository(AgencyClients::class)->findOneBy(['vkUser' => $vkUser]);
  172.                 } else {
  173.                     $agencyClient = new AgencyClients();
  174.                     $vkUser = new VkUser();
  175.                 }
  176.                 $agencyClient->setUser($user);
  177.                 $clientId $item['user']['id'];
  178.                 $response $this->client->request('GET'"https://ads.vk.com/api/v2/agency/clients.json?_user__id=$clientId");
  179.                 
  180.                 if ($response->toArray()['count'] != 0) {
  181.                     $agencyClient->setIsLake(true);
  182.                 }
  183.                 
  184.                 $this->updateVkClientInfo($item$vkUser$agencyClient);
  185.             }
  186.         }
  187.         
  188.         $clients $this->doctrine->getRepository(AgencyClients::class)->findBy(['user' => $this->getUser(), 'isLake' => true]);
  189.         
  190.         return $this->json([
  191.             "count" => count($clients),
  192.             "data" => $clients
  193.         ]);
  194.         
  195.     }
  196.     
  197.     #[Route(path'/api/getUserClients/{user}'name'api_getUserAgencyClients')]
  198.     public function getUserAgencyClients(Request $requestManagerRegistry $doctrineUser $user): Response
  199.     {
  200.         $clients $this->doctrine->getRepository(AgencyClients::class)->findBy(['user' => $user]);
  201.         
  202.         return $this->json([
  203.             "count" => count($clients),
  204.             "data" => $clients
  205.         ]);
  206.     }
  207.     
  208.     #[Route(path'/agencyClients/getHistoryDiposits/{agencyClientUsername}'name'api_agencyClients_history_diposits')]
  209.     public function getHistoryDiposits(Request $requeststring $agencyClientUsername): Response
  210.     {
  211.         $ACHistoryDiposit $this->doctrine->getRepository(AgencyClientsHistoryDiposit::class)->findBy(['clientUsername' => $agencyClientUsername]);
  212.         
  213.         return $this->json([
  214.             "data" => $ACHistoryDiposit
  215.         ]);
  216.     }
  217.     
  218.     #[Route(path'/agencyClients/{agencyClientId}'name'app_edit_agency_client')]
  219.     public function editAgencyClient(Request $requeststring $agencyClientId): Response
  220.     {
  221.         $user $this->getUser();
  222.         $isAdmin false;
  223.         
  224.         if ($user instanceof User && $user->isAdmin()) {
  225.             $isAdmin true;
  226.         }
  227.         
  228.         $client $this->doctrine->getRepository(AgencyClients::class)->findOneBy(['id' => $agencyClientId]);
  229.         
  230.         if (!($client instanceof AgencyClients)) {
  231.             return $this->render('error404/index.html.twig');
  232.         }
  233.         
  234.         if ($client->getUser() != $user && !$isAdmin) {
  235.             return $this->render('error404/index.html.twig');
  236.         }
  237.         
  238.         $clientId $client->getVkUser()->getId();
  239.         $response $this->client->request('GET'"https://ads.vk.com/api/v2/agency/clients.json?_user__id=$clientId");
  240.         $item $response->toArray()['items'][0];
  241.         $vkUser $this->doctrine->getRepository(VkUser::class)->findOneBy(['username' => $item['user']['username']]);
  242.         $agencyClient $this->doctrine->getRepository(AgencyClients::class)->findOneBy(['vkUser' => $vkUser]);
  243.         
  244.         $this->updateVkClientInfo($item$vkUser$agencyClient);
  245.         
  246.         $client $this->doctrine->getRepository(AgencyClients::class)->findOneBy(['id' => $agencyClientId]);
  247.         
  248.         $form $this->createForm(TransactionFormType::class, null, ['projects' => $user->getUserProjects()]);
  249.         $form->handleRequest($request);
  250.         
  251.         $error = [];
  252.         
  253.         if ($form->isSubmitted()) {
  254.             if ($form->isValid()) {
  255.                 $response $this->transactionToClient($client->getVkUser()->getId(), $form->getData()['amount'], $form->get('project')->getData());
  256.                 $response json_decode($response->getContent(), true);
  257.                 if (array_key_exists('error'$response)) {
  258.                     $error[] = $response['error'];
  259.                 } else {
  260.                     return $this->redirectToRoute('app_edit_agency_client', ['agencyClientId' => $agencyClientId]);
  261.                 }
  262.             } else {
  263.                 $error[] = $form->getErrors();
  264.             }
  265.         }
  266.         
  267.         return $this->render('agency_clients/index.html.twig', [
  268.             'client' => $client,
  269.             'isAdmin' => $isAdmin,
  270.             'form' => $form,
  271.             'errors' => $error
  272.         ]);
  273.     }
  274.     
  275.     public function updateVkClientInfo($itemVkUser $vkUserAgencyClients $agencyClient) {
  276.         $agencyClient->setStatus($item['status']);
  277.         $agencyClient->setAccessType($item['access_type']);
  278.         
  279.         //account
  280.         $vkUser->setABalance($item['user']['account']['a_balance']);
  281.         $vkUser->setBalance($item['user']['account']['balance']);
  282.         $vkUser->setCurrency($item['user']['account']['currency']);
  283.         $vkUser->setCurrencyBalanceHold($item['user']['account']['currency_balance_hold']);
  284.         $vkUser->setFlags($item['user']['account']['flags']);
  285.         $vkUser->setAccountId($item['user']['account']['id']);
  286.         $vkUser->setIsNonresident($item['user']['account']['is_nonresident']);
  287.         $vkUser->setType($item['user']['account']['type']);
  288.         
  289.         //additional_emails
  290.         $vkUser->setAdditionalEmails($item['user']['additional_emails']);
  291.         
  292.         //additional_info
  293.         if ($item['user']['additional_info'] !== null) {
  294.             $vkUser->setAddress($item['user']['additional_info']['address']);
  295.             $vkUser->setClientInfo($item['user']['additional_info']['client_info']);
  296.             $vkUser->setClientName($item['user']['additional_info']['client_name']);
  297.             $vkUser->setEmail($item['user']['additional_info']['email']);
  298.             $vkUser->setName($item['user']['additional_info']['name']);
  299.             $vkUser->setPhone($item['user']['additional_info']['phone']);
  300.         }
  301.         
  302.         $vkUser->setClientUsername($item['user']['client_username']);
  303.         $vkUser->setId($item['user']['id']);
  304.         $vkUser->setStatus($item['user']['status']);
  305.         $vkUser->setTypes($item['user']['types']);
  306.         $vkUser->setUsername($item['user']['username']);
  307.         
  308.         $this->doctrine->getManager()->persist($vkUser);
  309.         $agencyClient->setVkUser($vkUser);
  310.         
  311.         $this->doctrine->getManager()->persist($agencyClient);
  312.         
  313.         $this->doctrine->getManager()->flush();
  314.     }
  315.     
  316.     #[Route(path'/panel'name'vk_api_getUserToken')]
  317.     public function getVkUserToken(Request $requestEntityManagerInterface $entityManager,): Response
  318.     {
  319.         $code $request->query->get('code');
  320.         $userId $request->query->get('user_id');
  321.         
  322.         $response $this->client->request('POST'"https://ads.vk.com/api/v2/oauth2/token.json", [
  323.             'headers' => [
  324.                 'Content-Type' => 'application/x-www-form-urlencoded',
  325.             ],
  326.             'body' => [
  327.                 'grant_type' => 'authorization_code',
  328.                 'code' => $code,
  329.                 'client_id' => '7XG62PqTbNY8smMK',
  330.                 'permanent' => true
  331.             ]
  332.         ]);
  333.         
  334.         if ($response->getStatusCode() !== 200) {
  335.             try {
  336.                 $response $response->toArray(false);
  337.                 
  338.                 if ($response['error'] == "token_limit_exceeded") {
  339.                     $this->client->request('POST'"https://ads.vk.com/api/v2/oauth2/token/delete.json", [
  340.                         'headers' => [
  341.                             'Content-Type' => 'application/x-www-form-urlencoded',
  342.                         ],
  343.                         'body' => [
  344.                             'client_id' => '7XG62PqTbNY8smMK',
  345.                             'client_secret' => '0ugLDBgjtj3mLgiOntKrwlcq9nEijUpWFjsiUF3PsWLlKkUUFmRlZvEF4oF68QdFViRZ03eNp4dfhV7UWJUKjmsgdeAbu89W1cHuvtPxXaFAWDbkn5BXMX2Z0S3IFa4msc2ShfocNtr7xUdCMe4lHbD4KI6sk7WiBxqgUyb93YBo5CcWS8GjoC537Tkr16XBp9caIx7Vx0YUF5Wa1FhCr5gHzHvpfFh5',
  346.                             'user_id' => $response['user_id']
  347.                         ]
  348.                     ]);
  349.                     
  350.                     $response $this->client->request('POST'"https://ads.vk.com/api/v2/oauth2/token.json", [
  351.                         'headers' => [
  352.                             'Content-Type' => 'application/x-www-form-urlencoded',
  353.                         ],
  354.                         'body' => [
  355.                             'grant_type' => 'authorization_code',
  356.                             'code' => $code,
  357.                             'client_id' => '7XG62PqTbNY8smMK',
  358.                             'permanent' => true
  359.                         ]
  360.                     ]);
  361.                 } else {
  362.                     return $this->json(['error' => $response['error']], 500);
  363.                 }
  364.             } catch (Exception $e) {
  365.                 return $this->json(['error' => $e->getMessage()], 500);
  366.             }
  367.         }
  368.         
  369.         $response $response->toArray(true);
  370.         
  371.         $user $this->getUser();
  372.         
  373.         $userPlatforms $this->doctrine->getRepository(UserPlatform::class)->findOneBy(['user' => $user'name' => 'ads.vk']);
  374.         
  375.         if (!($userPlatforms instanceof UserPlatform)) {
  376.             $userPlatforms = new UserPlatform();
  377.         }
  378.         
  379.         $userPlatforms->setUser($user);
  380.         $userPlatforms->setName('ads.vk');
  381.         $userPlatforms->setToken($response['access_token']);
  382.         
  383.         $entityManager->persist($userPlatforms);
  384.         
  385.         $entityManager->flush();
  386.         
  387.         return $this->redirectToRoute('app_user_platforms');
  388.         
  389.     }
  390. }