X-Git-Url: https://git.piment-noir.org/?a=blobdiff_plain;f=src%2FController%2FPersonController.php;h=6b4120545ec9196498d354910457e2de92407f97;hb=80ec112fadb2fb94341049775f12fd5496662129;hp=0fb898527414e14ff7c940e3744cd8ea7f2c1edb;hpb=b607789316c3ff7c7e01b9ad4ade2bc72ff61780;p=Project_proches_de_moi-server.git diff --git a/src/Controller/PersonController.php b/src/Controller/PersonController.php index 0fb8985..6b41205 100644 --- a/src/Controller/PersonController.php +++ b/src/Controller/PersonController.php @@ -2,8 +2,10 @@ namespace App\Controller; use App\Entity\Person; +use App\Entity\Localisation; +use \Datetime; use Symfony\Bundle\FrameworkBundle\Controller\Controller; -#use FOS\RestBundle\Controller\FOSRestController; +use FOS\RestBundle\Controller\FOSRestController; use FOS\RestBundle\Controller\Annotations as Rest; use FOS\RestBundle\View\ViewHandler; use FOS\RestBundle\View\View; @@ -12,24 +14,30 @@ use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Response; use Symfony\Component\Routing\Generator\UrlGeneratorInterface; -class PersonController extends Controller +class PersonController extends FOSRestController { /** * @Rest\Post( - * path = "/api/person/inscription", + * path = "/api/person/register", * name = "create_person" * ) * @Rest\View(StatusCode = Response::HTTP_CREATED) - * @ParamConverter("person", converter="fos_rest.request_body") */ - public function createPersonAction(Person $person) + public function createPersonAction(Request $request) { + $person = new Person(); + $person->setFirstname($request->get('firstname')); + $person->setLastName($request->get('lastname')); + //TODO: email creation should normally have a verification step + $person->setEmail($request->get('email')); + $person->setPassword($request->get('password')); + $person->setOnline(false); + $em = $this->getDoctrine()->getManager(); $em->persist($person); $em->flush(); - //TODO: use ViewHandler return $this->view($person, Response::HTTP_CREATED, ['Location' => $this->generateUrl('show_person', ['id' => $person->getId(), UrlGeneratorInterface::ABSOLUTE_URL])]); } @@ -39,72 +47,215 @@ class PersonController extends Controller */ public function removePersonAction(Request $request) { + //TODO: check that the authenticated user have the same id $em = $this->getDoctrine()->getManager(); $person = $em->getRepository('App:Person')->find($request->get('id')); + $friends = $em->getRepository('App:Friendship')->findBy(['person' => $request->get('id')]); + $friends_with_me = $em->getRepository('App:Friendship')->findBy(['friend' => $request->get('id')]); + $localisations = $em->getRepository('App:Localisation')->findBy(['person' => $request->get('id')]); - if (!empty($person)) { - $em->remove($person); + if (!empty($localisations)) { + foreach ($localisations as $localisation) { + $em->remove($localisation); + } $em->flush(); } - //TODO: remove localisation and friendship + + if (!empty($friends)) { + foreach ($friends as $friend) { + $em->remove($friend); + } + $em->flush(); + } + + if (!empty($friends_with_me)) { + foreach ($friends_with_me as $friend) { + $em->remove($friend); + } + $em->flush(); + } + + if (!empty($person)) { + $em->remove($person); + $em->flush(); + } } /** * @Rest\Put( - * path = "/api/person/{id}/update", + * path = "/api/person/{id}", * name = "update_person" * ) * @Rest\View(StatusCode = Response::HTTP_CREATED) */ public function updatePersonAction(Request $request) { + //TODO: check that the authenticated user have the same id $em = $this->getDoctrine()->getManager(); $person = $em->getRepository('App:Person')->find($request->get('id')); - $viewHandler = $this->get('fos_rest.view_handler'); - if (empty($person)) { - return $this->PersonNotFound($viewHandler); + return $this->PersonNotFound(); } $person->setFirstName($request->get('firstname')); $person->setLastName($request->get('lastname')); + //TODO: email update should normally have a verification step $person->setEmail($request->get('email')); $em->merge($person); $em->flush(); - //TODO: use ViewHandler return $this->view($person, Response::HTTP_CREATED, ['Location' => $this->generateUrl('show_person', ['id' => $person->getId(), UrlGeneratorInterface::ABSOLUTE_URL])]); } /** - * @Rest\Get("/api/person/{id}/friends/localisation") + * @Rest\Post( + * path = "/api/person/authenticate", + * name = "authenticate_person" + * ) + * @Rest\View(StatusCode = Response::HTTP_ACCEPTED) */ - public function getFriendsLocalisationAction(Request $request) + public function authenticatePersonAction(Request $request) { + $em = $this->getDoctrine()->getManager(); + $person = $em->getRepository('App:Person')->findOneBy(['email' => $request->get('email')]); + if (empty($person)) { + return $this->PersonNotFound(); + } + + if ($request->get('password') != $person->getPassword()) { + return $this->PersonWrongPassword(); + } else { + return $this->view($person, Response::HTTP_ACCEPTED, ['Location' => $this->generateUrl('show_person', ['id' => $person->getId(), UrlGeneratorInterface::ABSOLUTE_URL])]); + } } /** * @Rest\Get("/api/person/{id}/localisations") + * @Rest\View() */ public function getLocalisationsAction(Request $request) { + //TODO: Check that the authenticated user is allowed to see the localisation $em = $this->getDoctrine()->getManager(); $localisations = $em->getRepository('App:Localisation')->findBy(['person' => $request->get('id')]); - $viewHandler = $this->get('fos_rest.view_handler'); + if (empty($localisations)) { + return $this->PersonLocalisationsNotFound(); + } + + return $localisations; + } + + /** + * @Rest\Get( + * path = "/api/person/{id}/localisations/fuzzy/{distance}", + * name = "person_localisations_fuzzy", + * requirements = {"id"="\d+", "distance"="\d+"} + * ) + * @Rest\View() + */ + public function getLocalisationsFuzzyAction(Request $request) + { + //TODO: Check that the authenticated user is allowed to see the localisation + $em = $this->getDoctrine()->getManager(); + $localisations = $em->getRepository('App:Localisation')->findBy(['person' => $request->get('id')]); if (empty($localisations)) { - return $this->PersonLocalisationsNotFound($viewHandler); + return $this->PersonLocalisationsNotFound(); + } + + if (!$this->chk_distance($request->get('distance'), 200, 500)) { + return $this->PersonLocalisationFuzzyWrongDistance(); + } + + $fuzzy_localisations = array_map(function($item) use ($request) { return $this->randomizeLocation($item, $request->get('distance'), 200, 500); }, $localisations); + + return $fuzzy_localisations; + } + + private function getLastLocalisation($em, $id) { + $query = $em->createQuery("SELECT l1 FROM App\Entity\Localisation l1 WHERE l1.person = :person and l1.timestamp = (SELECT MAX(l2.timestamp) FROM App\Entity\Localisation l2 WHERE l2.person = l1.person)"); + $query->setParameter('person', $id); + $result = $query->getResult(); + if (!empty($result)) { + return $result[0]; + } + } + + /** + * @Rest\Get("/api/person/{id}/localisation") + * @Rest\View() + */ + public function getLocalisationAction(Request $request) + { + //TODO: Check that the authenticated user is allowed to see the localisation + $em = $this->getDoctrine()->getManager(); + + $localisation = $this->getLastLocalisation($em, $request->get('id')); + + if (empty($localisation)) { + return $this->PersonLocalisationNotFound(); + } + + return $localisation; + } + + private function chk_distance($distance, $min, $max) { + if ($distance >= $min && $distance <= $max) { + return true; + } else { + return false; + } + } + + private function randomizeLocation($localisation, $distance, $min, $max) { + // Generate random float in [0, 1[, [0, 1) + $u = rand(0, getrandmax() - 1) / getrandmax(); + $v = rand(0, getrandmax() - 1) / getrandmax(); + + if ($this->chk_distance($distance, $min, $max)) { + $r = $distance / 111300; + } else { + return $this->PersonLocalisationFuzzyWrongDistance(); } - $view = View::create($localisations); - $view->setFormat('json'); + $w = $r * sqrt($u); + $t = 2 * pi() * $v; - return $viewHandler->handle($view); + $x = $w * cos($t); + $lng_off = $x / cos(deg2rad($localisation->getLatitude())); + $lat_off = $w * sin($t); + $fuzzy_localisation = new Localisation(); + $fuzzy_localisation->setTimestamp($localisation->getTimestamp()); + $fuzzy_localisation->setLatitude($localisation->getLatitude() + $lat_off); + $fuzzy_localisation->setLongitude($localisation->getLongitude() + $lng_off); + return $fuzzy_localisation; + } + + /** + * @Rest\Get( + * path = "/api/person/{id}/localisation/fuzzy/{distance}", + * name = "person_localisation_fuzzy", + * requirements = {"id"="\d+", "distance"="\d+"} + * ) + * @Rest\View() + */ + public function getLocalisationFuzzyAction(Request $request) + { + //TODO: Check that the authenticated user is allowed to see the localisation + $em = $this->getDoctrine()->getManager(); + + $localisation = $this->getLastLocalisation($em, $request->get('id')); + + if (empty($localisation)) { + return $this->PersonLocalisationNotFound(); + } + + return $this->randomizeLocation($localisation, $request->get('distance'), 200, 500); } /** @@ -113,124 +264,199 @@ class PersonController extends Controller */ public function updateLocalisationAction(Request $request) { + //TODO: Check that the authenticated user is allowed to update the localisation + $em = $this->getDoctrine()->getManager(); + + $person = $em->getRepository('App:Person')->find($request->get('id')); + + if (empty($person)) { + return $this->PersonNotFound(); + } + + $datetime = new DateTime($request->get('timestamp')); + $localisation = new Localisation(); - $localisation->setPerson($request->get('id')); - $localisation->setTimestamp($request->get('timestamp')); + $localisation->setPerson($person); + $localisation->setTimestamp($datetime); $localisation->setLatitude($request->get('latitude')); $localisation->setLongitude($request->get('longitude')); - $em = $this->getDoctrine()->getManager(); - $em->persist($localisation); $em->flush(); } /** - * @Rest\Get( - * path = "/api/person/{id}", - * name = "show_person", - * requirements = {"id"="\d+"} - * ) - * @Rest\View() - */ - public function showPerson(Request $request) - { + * @Rest\Get( + * path = "/api/person/{id}", + * name = "show_person", + * requirements = {"id"="\d+"} + * ) + * @Rest\View() + */ + public function showPerson(Request $request) + { $em = $this->getDoctrine()->getManager(); $person = $em->getRepository('App:Person')->find($request->get('id')); - $viewHandler = $this->get('fos_rest.view_handler'); + if (empty($person)) { + return $this->PersonNotFound(); + } + + return $person; + } + + /** + * @Rest\Get( + * path = "/api/person/{id}/friends", + * name = "show_person_friends", + * requirements = {"id"="\d+"} + * ) + * @Rest\View() + */ + public function showPersonFriends(Request $request) + { + $em = $this->getDoctrine()->getManager(); + $person = $em->getRepository('App:Person')->find($request->get('id')); + + if (empty($person)) { + return $this->PersonNotFound(); + } + + return $person->getFriends(); + } + + /** + * @Rest\Get( + * path = "/api/person/{id}/friendswithme", + * name = "show_person_friends_with_me", + * requirements = {"id"="\d+"} + * ) + * @Rest\View() + */ + public function showPersonFriendsWithMe(Request $request) + { + $em = $this->getDoctrine()->getManager(); + $person = $em->getRepository('App:Person')->find($request->get('id')); if (empty($person)) { - return $this->PersonNotFound($viewHandler); + return $this->PersonNotFound(); } - $view = View::create($person); - $view->setFormat('json'); + $friends_with_me = $person->getFriendsWithMe(); - return $viewHandler->handle($view); - } + return $friends_with_me; + } - /** - * @Rest\Get( - * path = "/api/person/{email}", - * name = "show_person_by_email", - * requirements = {"email"="\s+"} - * ) - * @Rest\View() - */ - public function showPersonByEmail(Request $request) - { + /** + * @Rest\Get( + * path = "/api/persons", + * name = "show_persons" + * ) + * @Rest\View() + */ + public function showPersons(Request $request) + { $em = $this->getDoctrine()->getManager(); - $person = $em->getRepository('App:Person')->findOneBy(['email' => $request->get('email')]); + $persons = $em->getRepository('App:Person')->findAll(); + + if (empty($persons)) { + return $this->PersonsNotFound(); + } + + return $persons; + } - $viewHandler = $this->get('fos_rest.view_handler'); + /** + * @Rest\Put( + * path = "/api/person/{id}/online", + * name = "set_person_online" + * ) + * @Rest\View(StatusCode = Response::HTTP_CREATED) + */ + public function onlinePersonAction(Request $request) + { + //TODO: check that the authenticated user have the same id + $em = $this->getDoctrine()->getManager(); + $person = $em->getRepository('App:Person')->find($request->get('id')); if (empty($person)) { - return $this->PersonNotFound($viewHandler); + return $this->PersonNotFound(); } - $view = View::create($person); - $view->setFormat('json'); + $person->setOnline(true); - return $viewHandler->handle($view); - } + $em->merge($person); + $em->flush(); + } - /** - * @Rest\Get( - * path = "/api/person/{id}/friends", - * name = "show_person_friends", - * requirements = {"id"="\d+"} - * ) - * @Rest\View() - */ - public function showPersonFriends(Request $request) - { + /** + * @Rest\Put( + * path = "/api/person/{id}/offline", + * name = "set_person_offline" + * ) + * @Rest\View(StatusCode = Response::HTTP_CREATED) + */ + public function offlinePersonAction(Request $request) + { + //TODO: check that the authenticated user have the same id $em = $this->getDoctrine()->getManager(); $person = $em->getRepository('App:Person')->find($request->get('id')); - $viewHandler = $this->get('fos_rest.view_handler'); - if (empty($person)) { - return $this->PersonNotFound($viewHandler); + return $this->PersonNotFound(); } - $view = View::create($person->getFriends()); - $view->setFormat('json'); + $person->setOnline(false); - return $viewHandler->handle($view); - } + $em->merge($person); + $em->flush(); + } - /** - * @Rest\Get( - * path = "/api/person/{email}/friends", - * name = "show_person_friends_by_email", - * requirements = {"email"="\s+"} - * ) - * @Rest\View() - */ - public function showPersonFriendsByEmail(Request $request) - { + /** + * @Rest\Post( + * path = "/api/person/search", + * name = "search_person" + * ) + * @Rest\View() + */ + public function searchPerson(Request $request) + { $em = $this->getDoctrine()->getManager(); - $person = $em->getRepository('App:Person')->findOneBy(['email' => $request->get('email')]); + $query = $em->createQuery("SELECT DISTINCT p FROM App\Entity\Person p WHERE + p.firstname LIKE :keyword or + p.lastname LIKE :keyword or + p.email LIKE :keyword"); + $query->setParameter('keyword', '%'.$request->get('keyword').'%'); + $persons = $query->getResult(); + + if (empty($persons)) { + return $this->PersonNotFound(); + } - $viewHandler = $this->get('fos_rest.view_handler'); + return $persons; + } - if (empty($person)) { - return $this->PersonNotFound($viewHandler); - } + private function PersonNotFound() { + return View::create(['message' => 'Person not found'], Response::HTTP_NOT_FOUND); + } - $view = View::create($person->getFriends()); - $view->setFormat('json'); + private function PersonsNotFound() { + return View::create(['message' => 'Persons not found'], Response::HTTP_NOT_FOUND); + } - return $viewHandler->handle($view); - } + private function PersonLocalisationNotFound() { + return View::create(['message' => 'Person localisation not found'], Response::HTTP_NOT_FOUND); + } - private function PersonNotFound($viewHandler) { - return $viewHandler->handle(View::create(['message' => 'Person not found'], Response::HTTP_NOT_FOUND)); - } + private function PersonLocalisationsNotFound() { + return View::create(['message' => 'Person localisations not found'], Response::HTTP_NOT_FOUND); + } - private function PersonLocalisationsNotFound($viewHandler) { - return $viewHandler->handle(View::create(['message' => 'Person localisations not found'], Response::HTTP_NOT_FOUND)); - } + private function PersonWrongPassword() { + return View::create(['message' => 'Supplied password do not match'], Response::HTTP_UNAUTHORIZED); + } + private function PersonLocalisationFuzzyWrongDistance() { + return View::create(['message' => 'Distance range do not match'], Response::HTTP_NOT_ACCEPTABLE); + } }