CoreController.php 21KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724
  1. <?php
  2. namespace Muzich\CoreBundle\Controller;
  3. use Muzich\CoreBundle\lib\Controller;
  4. //use Sensio\Bundle\FrameworkExtraBundle\Configuration\Template;
  5. use Muzich\CoreBundle\Entity\FollowUser;
  6. use Muzich\CoreBundle\Entity\FollowGroup;
  7. //use Doctrine\ORM\Query;
  8. use Muzich\CoreBundle\Form\Element\ElementAddForm;
  9. use Muzich\CoreBundle\Managers\ElementManager;
  10. use Muzich\CoreBundle\Entity\Element;
  11. use Symfony\Component\HttpFoundation\RedirectResponse;
  12. use Muzich\CoreBundle\Form\Search\ElementSearchForm;
  13. use Symfony\Component\Routing\Exception\ResourceNotFoundException;
  14. use Muzich\CoreBundle\Entity\Tag;
  15. use Muzich\CoreBundle\Managers\TagManager;
  16. use Muzich\CoreBundle\Entity\UsersTagsFavorites;
  17. use Muzich\CoreBundle\Managers\ElementReportManager;
  18. use Muzich\CoreBundle\Propagator\EventUser;
  19. use Muzich\CoreBundle\Entity\User;
  20. use Symfony\Component\HttpFoundation\Request;
  21. use Muzich\CoreBundle\Security\Context as SecurityContext;
  22. class CoreController extends Controller
  23. {
  24. /**
  25. * Action permettant de changer le language
  26. *
  27. * @param string $language
  28. * @return RedirectResponse
  29. */
  30. public function changeLanguageAction($language)
  31. {
  32. if($language != null)
  33. {
  34. $old = $this->container->get('request')->getLocale();
  35. $this->getRequest()->setLocale($language);
  36. }
  37. $url_referer = $this->container->get('request')->headers->get('referer');
  38. $url_referer = str_replace(
  39. $siteurl = $this->container->getParameter('siteurl'),
  40. '',
  41. $url_referer
  42. );
  43. try {
  44. $params = $this->get('router')->match($url_referer);
  45. } catch (ResourceNotFoundException $exc) {
  46. return $this->redirect($this->generateUrl('home', array('_locale' => $language)));
  47. }
  48. $params['_locale'] = $language;
  49. $route = $params['_route'];
  50. unset($params['_route'], $params['_controller']);
  51. $new_url = $this->generateUrl($route, $params);
  52. return new RedirectResponse($new_url);
  53. }
  54. /**
  55. * Determiner la locale automatiquement
  56. * @return string
  57. */
  58. protected function determineLocale()
  59. {
  60. $lang = $this->container->get('request')
  61. ->getPreferredLanguage($this->container->getParameter('supported_langs'));
  62. // Si on a une lang en sortie,
  63. if (is_null($lang))
  64. {
  65. // TODO: Récupérer ce paramètre dans la config
  66. $lang = 'fr';
  67. }
  68. return $lang;
  69. }
  70. /**
  71. *
  72. * Cette action est écrite pour les utilisateur redirigé du a l'absence de
  73. * lague dans leur route.
  74. * Cette redirection n'est pas interne au code, elle est actuellement effectué
  75. * par le .htaccess lorsque il n'y as pas d'url (en plus de muzi.ch/
  76. */
  77. public function automaticLanguageAction()
  78. {
  79. $lang = $this->determineLocale();
  80. if ($this->getUser() != 'anon.')
  81. {
  82. return $this->redirect($this->generateUrl('home', array('_locale' => $lang)));
  83. }
  84. else
  85. {
  86. return $this->redirect($this->generateUrl('index', array('_locale' => $lang)));
  87. }
  88. }
  89. /**
  90. * Cette action permet a un utilisateur de suivre ou de ne plus suivre
  91. * un utilisateur ou un groupe.
  92. *
  93. * @param string $type
  94. * @param int $id
  95. * @param string $salt
  96. */
  97. public function followAction($type, $id, $token)
  98. {
  99. if (($response = $this->mustBeConnected()))
  100. {
  101. return $response;
  102. }
  103. $user = $this->getUser();
  104. /**
  105. * Bug lors des tests: L'user n'est pas 'lié' a celui en base par doctrine.
  106. * Docrine le voit si on faire une requete directe.
  107. */
  108. if ($this->container->getParameter('env') == 'test')
  109. {
  110. $user = $this->getDoctrine()->getRepository('MuzichCoreBundle:User')->findOneById(
  111. $this->container->get('security.context')->getToken()->getUser()->getId(),
  112. array()
  113. )->getSingleResult();
  114. }
  115. // Vérifications préléminaires
  116. if ($user->getPersonalHash($id) != $token
  117. || !in_array($type, array('user', 'group'))
  118. || !is_numeric($id)
  119. || ($user->getId() == $id && $type == 'user')
  120. )
  121. {
  122. throw $this->createNotFoundException();
  123. }
  124. // On tente de récupérer l'enregistrement FollowUser / FollowGroup
  125. $em = $this->getDoctrine()->getEntityManager();
  126. $Follow = $em
  127. ->getRepository('MuzichCoreBundle:Follow' . ucfirst($type))
  128. ->findOneBy(
  129. array(
  130. 'follower' => $user->getId(),
  131. ($type == 'user') ? 'followed' : 'group' => $id
  132. )
  133. )
  134. ;
  135. // Si il existe déjà c'est qu'il ne veut plus suivre
  136. if ($Follow)
  137. {
  138. if ($type == 'user')
  139. {
  140. // L'utilisateur suis déjà, on doit détruire l'entité
  141. $event = new EventUser($this->container);
  142. $event->removeFromFollow($Follow->getFollowed(), $this->getUser());
  143. $em->persist($Follow->getFollowed());
  144. }
  145. $em->remove($Follow);
  146. $em->flush();
  147. $following = false;
  148. }
  149. // Sinon, c'est qu'il veut le suivre
  150. else
  151. {
  152. // On récupére l'entité a suivre
  153. $followed = $em->getRepository('MuzichCoreBundle:'.ucfirst($type))->find($id);
  154. if (!$followed) {
  155. throw $this->createNotFoundException('No '.$type.' found for id '.$id);
  156. }
  157. // On instancie te renseigne l'objet Follow****
  158. if ($type == 'user') { $Follow = new FollowUser(); }
  159. else { $Follow = new FollowGroup(); }
  160. $Follow->setFollower($user);
  161. if ($type == 'user')
  162. {
  163. $Follow->setFollowed($followed);
  164. $event = new EventUser($this->container);
  165. $event->addToFollow($followed, $this->getUser());
  166. $em->persist($followed);
  167. }
  168. else { $Follow->setGroup($followed); }
  169. $em->persist($Follow);
  170. $em->flush();
  171. $following = true;
  172. }
  173. if ($this->getRequest()->isXmlHttpRequest())
  174. {
  175. return $this->jsonResponse(array(
  176. 'status' => 'success',
  177. 'following' => $following
  178. ));
  179. }
  180. else
  181. {
  182. return $this->redirect($this->container->get('request')->headers->get('referer'));
  183. }
  184. }
  185. /**
  186. * Procédure d'ajout d'un element
  187. */
  188. public function elementAddAction($group_slug)
  189. {
  190. if (($non_condition = $this->userHaveNonConditionToMakeAction(SecurityContext::ACTION_ELEMENT_ADD)) !== false)
  191. {
  192. return $this->jsonResponseError($non_condition);
  193. }
  194. if ($this->getRequest()->getMethod() != 'POST')
  195. {
  196. throw $this->createNotFoundException();
  197. }
  198. $user = $this->getUser(true, array('join' => array('groups_owned_groups_tags')));
  199. $em = $this->getDoctrine()->getEntityManager();
  200. /*
  201. * Contrôle préléminaire si groupe précisé
  202. */
  203. $group = null;
  204. if ($group_slug)
  205. {
  206. $group = $this->findGroupWithSlug($group_slug);
  207. if (!$group->userCanAddElement($this->getUserId()))
  208. {
  209. $group = null;
  210. throw $this->createNotFoundException('Vous ne pouvez pas ajouter d\'éléments a ce groupe');
  211. }
  212. }
  213. $element = new Element();
  214. $element->setType('none');
  215. $form = $this->getAddForm($element);
  216. $form->bind($this->getRequest());
  217. if ($form->isValid())
  218. {
  219. /**
  220. * Bug lors des tests: L'user n'est pas 'lié' a celui en base par doctrine.
  221. * Docrine le voit si on faire une requete directe.
  222. */
  223. if ($this->container->getParameter('env') == 'test')
  224. {
  225. $user = $this->getDoctrine()->getRepository('MuzichCoreBundle:User')->findOneById(
  226. $this->container->get('security.context')->getToken()->getUser()->getId(),
  227. array()
  228. )->getSingleResult();
  229. }
  230. // On utilise le gestionnaire d'élément
  231. $factory = new ElementManager($element, $em, $this->container);
  232. $factory->proceedFill($user);
  233. // Si on a précisé un groupe dans lequel mettre l'element
  234. if ($group)
  235. {
  236. $element->setGroup($group);
  237. $redirect_url = $this->generateUrl('show_group', array('slug' => $group_slug));
  238. }
  239. else
  240. {
  241. $redirect_url = $this->generateUrl('home');
  242. }
  243. // Un bug fait que le champ 'need_tags' n'est pas automatiquement renseigné pour l'élement,
  244. // Alors on le fait en manuel ici ... zarb
  245. $form_values = $this->getRequest()->get($form->getName());
  246. if (array_key_exists('need_tags', $form_values))
  247. {
  248. if ($form_values['need_tags'])
  249. {
  250. $element->setNeedTags(true);
  251. }
  252. }
  253. // On signale que cet user a modifié ses diffusions
  254. $user->setData(User::DATA_DIFF_UPDATED, true);
  255. $em->persist($user);
  256. $em->persist($element);
  257. $em->flush();
  258. if ($this->getRequest()->isXmlHttpRequest())
  259. {
  260. // Récupération du li
  261. if (!$group)
  262. {
  263. $html = $this->render('MuzichCoreBundle:SearchElement:li.element.html.twig', array(
  264. 'element' => $element,
  265. 'class_color' => 'odd' // TODO: n'est plus utilisé
  266. ))->getContent();
  267. }
  268. else
  269. {
  270. $html = $this->render('MuzichCoreBundle:SearchElement:li.element.html.twig', array(
  271. 'element' => $element,
  272. 'class_color' => 'odd', // TODO: n'est plus utilisé
  273. 'no_group_name' => true
  274. ))->getContent();
  275. }
  276. return $this->jsonResponse(array(
  277. 'status' => 'success',
  278. 'html' => $html,
  279. 'groups' => (!$group)?$this->isAddedElementCanBeInGroup($element):array()
  280. ));
  281. }
  282. else
  283. {
  284. return $this->redirect($redirect_url);
  285. }
  286. }
  287. else
  288. {
  289. if ($this->getRequest()->isXmlHttpRequest())
  290. {
  291. // Récupération des erreurs
  292. $validator = $this->container->get('validator');
  293. $errorList = $validator->validate($form);
  294. $errors = array();
  295. foreach ($errorList as $error)
  296. {
  297. $errors[] = $this->trans($error->getMessage(), array(), 'validators');
  298. }
  299. foreach ($form->getErrors() as $error)
  300. {
  301. if (!in_array($err = $this->trans($error->getMessageTemplate(), array(), 'validators'), $errors))
  302. {
  303. $errors[] = $err;
  304. }
  305. }
  306. return $this->jsonResponse(array(
  307. 'status' => 'error',
  308. 'errors' => $errors
  309. ));
  310. }
  311. else
  312. {
  313. if (!$group_slug)
  314. {
  315. $search_object = $this->getElementSearcher();
  316. $search_form = $this->getSearchForm($search_object);
  317. $add_form = $form;
  318. return $this->render('MuzichHomeBundle:Home:index.html.twig', array(
  319. 'search_tags_id' => $search_object->getTags(),
  320. 'user' => $this->getUser(),
  321. 'add_form' => $add_form->createView(),
  322. 'add_form_name' => 'add',
  323. 'search_form' => $search_form->createView(),
  324. 'search_form_name' => 'search',
  325. 'network_public' => $search_object->isNetworkPublic(),
  326. 'elements' => $search_object->getElements($this->getDoctrine(), $this->getUserId()),
  327. 'more_count' => $this->container->getParameter('search_default_count')*2,
  328. 'ids_display' => $search_object->getIdsDisplay()
  329. ));
  330. }
  331. else
  332. {
  333. $group = $this->findGroupWithSlug($group_slug);
  334. $search_object = $this->createSearchObject(array(
  335. 'group_id' => $group->getId()
  336. ));
  337. ($group->getOwner()->getId() == $this->getUserId()) ? $his = true : $his = false;
  338. if ($his || $group->getOpen())
  339. {
  340. $add_form = $form;
  341. }
  342. return $this->render('MuzichHomeBundle:Show:showGroup.html.twig', array(
  343. 'group' => $group,
  344. 'his_group' => ($group->getOwner()->getId() == $this->getUserId()) ? true : false,
  345. 'elements' => $search_object->getElements($this->getDoctrine(), $this->getUserId()),
  346. 'following' => $this->getUser()->isFollowingGroupByQuery($this->getDoctrine(), $group->getId()),
  347. 'user' => $this->getUser(),
  348. 'add_form' => (isset($add_form)) ? $add_form->createView() : null,
  349. 'add_form_name' => (isset($add_form)) ? 'add' : null,
  350. 'more_count' => null,
  351. 'more_route' => 'show_group_more',
  352. 'ids_display' => $search_object->getIdsDisplay()
  353. ));
  354. }
  355. }
  356. }
  357. }
  358. /**
  359. * Action non ajax nettoyant la liste de tags du chercheur d'éléments
  360. *
  361. * @return RedirectResponse
  362. */
  363. public function filterClearAction()
  364. {
  365. $es = $this->getElementSearcher();
  366. $es->update(array('tags' => array()));
  367. $this->setElementSearcherParams($es->getParams());
  368. return $this->redirect($this->container->get('request')->headers->get('referer'));
  369. }
  370. /**
  371. * Action non ajax de selection de ses tags favoris pour le chercheur d'élément
  372. *
  373. * @return RedirectResponse
  374. */
  375. public function filterMytagsAction()
  376. {
  377. $this->getElementSearcher(null, true);
  378. return $this->redirect($this->container->get('request')->headers->get('referer'));
  379. }
  380. /**
  381. * Action de récupération ajax de l'id des tags favoris de son profil
  382. *
  383. * @return Response
  384. */
  385. public function getFavoriteTagsAction()
  386. {
  387. // On construit l'element searcher avec les tags favoris
  388. $es = $this->getElementSearcher(null, true);
  389. // Et on retourne les tags
  390. return $this->jsonResponse(array(
  391. 'response' => 'success',
  392. 'tags' => $es->getTags()
  393. ));
  394. }
  395. /**
  396. * Ajout d'un tag en base.
  397. */
  398. public function addTagAction()
  399. {
  400. if (($non_condition = $this->userHaveNonConditionToMakeAction(SecurityContext::ACTION_TAG_ADD)) !== false)
  401. {
  402. return $this->jsonResponseError($non_condition);
  403. }
  404. if (strlen((($tag_name = $this->getRequest()->request->get('tag_name'))))
  405. < $this->container->getParameter('tag_add_min_length'))
  406. {
  407. return $this->jsonResponse(array(
  408. 'status' => 'error',
  409. 'errors' => array($this->trans(
  410. 'tags.add.errors.min',
  411. array(
  412. '%limit%' => $this->container->getParameter('tag_add_min_length')
  413. ),
  414. 'userui'
  415. )
  416. )));
  417. }
  418. if (strlen($tag_name) > $this->container->getParameter('tag_add_max_length'))
  419. {
  420. return $this->jsonResponse(array(
  421. 'status' => 'error',
  422. 'errors' => array($this->trans(
  423. 'tags.add.errors.max',
  424. array(
  425. '%limit%' => $this->container->getParameter('tag_add_max_length')
  426. ),
  427. 'userui'
  428. )
  429. )));
  430. }
  431. $tagManager = new TagManager();
  432. $tag = $tagManager->addTag(
  433. $this->getDoctrine(),
  434. $tag_name,
  435. $this->getUser(),
  436. $this->getRequest()->request->get('argument')
  437. );
  438. return $this->jsonResponse(array(
  439. 'status' => 'success',
  440. 'tag_id' => $tag->getId(),
  441. 'tag_name' => $tag->getName()
  442. ));
  443. }
  444. /**
  445. * Action ajax qui ajoute le tags précisé en paramétre aux tags favoris de
  446. * l'utilisateur.
  447. *
  448. * @param int $tag_id
  449. * @param string $token
  450. * @return Response
  451. */
  452. public function addTagToFavoritesAction($tag_id, $token)
  453. {
  454. if (($response = $this->mustBeConnected(true)))
  455. {
  456. return $response;
  457. }
  458. if (!($tag = $this->getDoctrine()->getRepository('MuzichCoreBundle:Tag')
  459. ->findOneById($tag_id)) || $this->getUser()->getPersonalHash($tag_id) != $token)
  460. {
  461. return $this->jsonResponse(array(
  462. 'status' => 'error',
  463. 'errors' => array('NotFound')
  464. ));
  465. }
  466. $user = $this->getUser();
  467. /**
  468. * Bug lors des tests: L'user n'est pas 'lié' a celui en base par doctrine.
  469. * Docrine le voit si on faire une requete directe.
  470. */
  471. if ($this->container->getParameter('env') == 'test')
  472. {
  473. $user = $this->getDoctrine()->getRepository('MuzichCoreBundle:User')->findOneById(
  474. $this->container->get('security.context')->getToken()->getUser()->getId(),
  475. array()
  476. )->getSingleResult();
  477. }
  478. // On contrôle au préalable que le tag ne fait pas déjà partie des favoris de
  479. // l'utilisateur
  480. if (!$this->getDoctrine()->getRepository('MuzichCoreBundle:UsersTagsFavorites')
  481. ->findOneBy(array(
  482. 'user' => $this->getUserId(),
  483. 'tag' => $tag->getId()
  484. )))
  485. {
  486. // Si il ne l'est pas, on créer ce nouvel objet de relation
  487. $fav = new UsersTagsFavorites();
  488. $fav->setTag($tag);
  489. $fav->setUser($user);
  490. $fav->setPosition(0);
  491. $this->getDoctrine()->getEntityManager()->persist($fav);
  492. $this->getDoctrine()->getEntityManager()->flush();
  493. }
  494. return $this->jsonResponse(array(
  495. 'status' => 'success'
  496. ));
  497. }
  498. /**
  499. * Cette action (ajax) configure l'appartenance d'un élément a un groupe.
  500. * Le groupe et l'élément doivent appartenir a l'utilisateur en cours.
  501. *
  502. * @param int $element_id
  503. * @param int $group_id
  504. * @param string $token
  505. * @return Response
  506. */
  507. public function setElementGroupAction($element_id, $group_id, $token)
  508. {
  509. if (($response = $this->mustBeConnected(true)))
  510. {
  511. return $response;
  512. }
  513. if (!($element = $this->getDoctrine()->getRepository('MuzichCoreBundle:Element')
  514. ->findOneById($element_id))
  515. || !($group = $this->getDoctrine()->getRepository('MuzichCoreBundle:Group')
  516. ->findOneById($group_id))
  517. || $this->getUser()->getPersonalHash($element_id) != $token)
  518. {
  519. return $this->jsonResponse(array(
  520. 'status' => 'error',
  521. 'errors' => array('NotFound')
  522. ));
  523. }
  524. if ($element->getOwner()->getId() != $this->getUserId()
  525. || $group->getOwner()->getId() != $this->getUserId()
  526. )
  527. {
  528. return $this->jsonResponse(array(
  529. 'status' => 'error',
  530. 'errors' => array('NotAllowed')
  531. ));
  532. }
  533. // a partir d'ici on a tout ce qu'il faut
  534. $element->setGroup($group);
  535. $this->getDoctrine()->getEntityManager()->persist($element);
  536. $this->getDoctrine()->getEntityManager()->flush();
  537. // On récupère le nouveau dom de l'élément
  538. $html = $this->render('MuzichCoreBundle:SearchElement:element.html.twig', array(
  539. 'element' => $element
  540. ))->getContent();
  541. return $this->jsonResponse(array(
  542. 'status' => 'success',
  543. 'html' => $html,
  544. 'dom_id' => 'element_'.$element->getId()
  545. ));
  546. }
  547. /**
  548. * Action (ajax) permettant de signaler un élément comme contenu non approprié.
  549. *
  550. * @param int $element_id
  551. * @param string $token
  552. * @return Response
  553. */
  554. public function reportElementAction($element_id, $token)
  555. {
  556. if (($non_condition = $this->userHaveNonConditionToMakeAction(SecurityContext::ACTION_ELEMENT_ALERT)) !== false)
  557. {
  558. return $this->jsonResponseError($non_condition);
  559. }
  560. if (!($element = $this->getDoctrine()->getRepository('MuzichCoreBundle:Element')
  561. ->findOneById($element_id))
  562. || $this->getUser()->getPersonalHash($element_id) != $token)
  563. {
  564. return $this->jsonResponse(array(
  565. 'status' => 'error',
  566. 'errors' => array('NotFound')
  567. ));
  568. }
  569. // On utilise le manager de rapport
  570. $erm = new ElementReportManager($element);
  571. $erm->add($this->getUser());
  572. $this->getDoctrine()->getEntityManager()->persist($element);
  573. $this->getDoctrine()->getEntityManager()->flush();
  574. return $this->jsonResponse(array(
  575. 'status' => 'success'
  576. ));
  577. }
  578. /**
  579. * Il arrive que l'on configure le chercheur d'élément de façon a ce qu'il
  580. * affiche une liste d'élément précis (collection d'id). Cette action
  581. * supprime cette configuration de façon a ce que le chercheur fonctionne
  582. * normalement.
  583. *
  584. * @return \Symfony\Component\HttpFoundation\Response
  585. */
  586. public function filterRemoveIdsAction()
  587. {
  588. if (($response = $this->mustBeConnected(true)))
  589. {
  590. return $response;
  591. }
  592. $es = $this->getElementSearcher();
  593. $es->setIds(null);
  594. $es->setIdsDisplay(null);
  595. $this->setElementSearcherParams($es->getParams());
  596. $html = $this->render('MuzichCoreBundle:SearchElement:default.html.twig', array(
  597. 'user' => $this->getUser(),
  598. 'elements' => $es->getElements($this->getDoctrine(), $this->getUserId())
  599. ))->getContent();
  600. return $this->jsonResponse(array(
  601. 'status' => 'success',
  602. 'html' => $html
  603. ));
  604. }
  605. /**
  606. * Url de récupération des plugins/application qui vienne partager une url
  607. * @param Request $request
  608. */
  609. public function shareFromAction(Request $request)
  610. {
  611. return $this->redirect($this->generateUrl('home', array(
  612. 'from_url' => $request->get('from_url'),
  613. // On ne se préoccupe pas de la locale coté plugins/applications
  614. '_locale' => $this->determineLocale()
  615. )));
  616. }
  617. public function renderSideMenuAction()
  618. {
  619. $user = $this->getUser(true, array('join' => array(
  620. 'followeds_users', 'followers_users', 'followeds_groups'
  621. )), true);
  622. return $this->render(
  623. 'MuzichCoreBundle:Menu:side_menu.html.twig',
  624. array(
  625. 'followeds_users' => $user->getFollowedsUsers(),
  626. 'followeds_groups' => $user->getFollowedGroups(),
  627. 'followers_users' => $user->getFollowersUsers()
  628. )
  629. );
  630. }
  631. public function testErrorAction()
  632. {
  633. throw new \Exception('test error');
  634. }
  635. }