Compare commits

...

22 Commits

Author SHA1 Message Date
Arnaud Fornerot 58a07356be resol merge 2020-06-17 08:52:17 +02:00
afornerot c0517eb238 envoyer un mail en cas d'erreur sur job cron (ref #159) 2020-06-16 11:10:51 +02:00
afornerot 3c08e2ef8f ajout d'un job de dump bdd (ref #158) 2020-06-16 10:06:13 +02:00
afornerot dfe6a90673 indicateurs (ref #156) 2020-06-16 09:09:59 +02:00
afornerot a379e52dea gestion de réponse à msg de chat (ref #8) 2020-06-12 14:02:19 +02:00
afornerot b49c25e07e System de mailing (ref #144) 2020-06-11 14:12:32 +02:00
afornerot a6e5cfbb81 possibilité de masquer les messages du chat (ref #155) 2020-06-09 17:31:03 +02:00
afornerot c49461aa58 possibilité de masquer les messages du chat (ref #155) 2020-06-09 17:28:47 +02:00
afornerot 2a1179ae9a datatable sur tableau des groupes rattachables à un user (ref #142) 2020-06-09 15:29:47 +02:00
afornerot 6baed4dea7 motivation obligatoire si mail non présent dans la liste blanche (ref #145) 2020-06-09 15:16:38 +02:00
afornerot f20eff9b05 gestion du niveau01 autre (ref #141) 2020-06-09 14:18:17 +02:00
afornerot e85f74cda5 compteur de visite group (ref #151) 2020-06-09 11:24:07 +02:00
afornerot e18790790b ajout compteur visite utilisateur (ref #150) 2020-06-09 09:53:25 +02:00
afornerot dc13f8a388 ajout de tooltip sur l'ensemble des boutons widgets (ref #148) 2020-06-08 16:07:39 +02:00
afornerot 28f84e2460 notification ajout suppression widget (ref #131) 2020-06-08 15:21:31 +02:00
afornerot 354d8df055 optimisation sur selection du projet associé à une tache (ref #138) 2020-06-08 12:13:43 +02:00
afornerot 6fb6fe6ab1 optimisation sur selection du projet associé à une tache (ref #138) 2020-06-08 11:43:17 +02:00
afornerot eac7f63094 navigation projet pour retour vers le groupe (ref #152) 2020-06-08 10:55:27 +02:00
afornerot a2c17379e4 date de fin sous forme calendrier (ref #153) 2020-06-08 09:52:16 +02:00
afornerot 7eae2ee972 formattage de la légende du login correcte (ref #132) 2020-06-08 09:16:26 +02:00
afornerot 920e6d66d3 permettre au propriétaire du groupe de changer le propriétaire (ref #146) 2020-06-08 09:07:16 +02:00
afornerot 228993dbd6 filtre de recherche sur le nom du propriétaire (ref #147) 2020-06-08 09:01:52 +02:00
77 changed files with 2697 additions and 331 deletions

View File

@ -4,7 +4,7 @@ cd /var/www/html/ninegate
ninegate_activer_localmail=$(CreoleGet ninegate_activer_localmail non)
if [[ "$ninegate_activer_localmail" = 'oui' ]]
then
php bin/console swiftmailer:spool:send --message-limit=100 --env=prod --transport swiftmailer.mailer.sendmail.transport
php bin/console swiftmailer:spool:send --message-limit=200 --env=prod --transport swiftmailer.mailer.sendmail.transport
else
php bin/console swiftmailer:spool:send --message-limit=100 --env=prod
php bin/console swiftmailer:spool:send --message-limit=200 --env=prod
fi

View File

@ -19,7 +19,7 @@ if [ "$1" == "restartifdown" ] && [ -n "${pid}" ] ; then
restart="no"
fi
if [[ "$restart" == "yes" ]]; then
if [ "$restart" == "yes" ] && [ "$1" != "stop" ] ; then
echo WEBSOCKET = START
cd /var/www/html/ninegate
bin/console gos:websocket:server --port $websocket_portinterne -a $websocket_url --no-debug -n -q --env=prod & disown

View File

@ -156,6 +156,12 @@ class SecurityController extends Controller
$dispatcher = new EventDispatcher();
$dispatcher->dispatch("security.interactive_login", $event);
// On enregistre sa visite
$user->setVisitedate(new \DateTime());
$user->setVisitecpt($user->getVisitecpt()+1);
$em->persist($user);
$em->flush();
if($redirect)
return $this->redirect($redirect);
else

View File

@ -48,7 +48,6 @@ class PurgeFileCommand extends Command
// Le script est-il executé via Cron:Exec
$this->byexec = $input->getArgument('byexec');
if($this->byexec=="") $this->byexec=false;
echo "pouet".$this->byexec;
$this->writelnred('');
$this->writelnred('== Core:PurgeFile');

View File

@ -0,0 +1,281 @@
<?php
namespace Cadoles\CoreBundle\Command;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Finder\Finder;
use Symfony\Component\Filesystem\Filesystem;
use Symfony\Component\HttpFoundation\File\File;
use Symfony\Component\HttpKernel\KernelInterface;
use Doctrine\DBAL\Connection as DBALConnection;
use Doctrine\ORM\EntityManager;
use Symfony\Component\Validator\Constraints\DateTime;
use Cadoles\CoreBundle\Entity\Statistic;
use function GuzzleHttp\json_encode;
class StatisticCommand extends Command
{
private $container;
private $em;
private $output;
private $filesystem;
private $rootlog;
private $byexec;
protected function configure()
{
$this
->setName('Core:Statistic')
->setDescription('Calculate Statistic')
->setHelp('This command Calculate Statistic')
->addArgument('cronid', InputArgument::OPTIONAL, 'ID Cron Job')
->addArgument('lastchance', InputArgument::OPTIONAL, 'Lastchance to run the cron')
->addArgument('byexec', InputArgument::OPTIONAL, 'By Cron:Exec')
;
}
protected function execute(InputInterface $input, OutputInterface $output)
{
$this->container = $this->getApplication()->getKernel()->getContainer();
$this->em = $this->container->get('doctrine')->getEntityManager();
$this->output = $output;
$this->filesystem = new Filesystem();
$this->rootlog = $this->container->get('kernel')->getRootDir()."/../var/logs/";
$alias = $this->container->getParameter('alias');
// Le script est-il executé via Cron:Exec
$this->byexec = $input->getArgument('byexec');
if($this->byexec=="") $this->byexec=false;
$this->writelnred('');
$this->writelnred('== Core:Statistic');
$this->writelnred('==========================================================================================================');
$now=new \DateTime('now');
$yesterday=clone $now;
$yesterday->sub(new \DateInterval('P1D'));
$groups=$this->em->getRepository("CadolesCoreBundle:Group")->findBy(["fgcanshare"=>true]);
// totcptvisite
$this->writelnred('');
$this->writelnred('== totcptvisite');
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptvisite"]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("totcptvisite");
$stat->setValue([]);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('SUM(user.visitecpt) as cpt')
->from('CadolesCoreBundle:User','user')
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
// totcptvisitegroup
$this->writelnred('');
$this->writelnred('== totcptvisitegroup');
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptvisitegroup"]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("totcptvisitegroup");
$stat->setValue([]);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('SUM(usergroup.visitecpt) as cpt')
->from('CadolesCoreBundle:UserGroup','usergroup')
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
// totcptmessage
$this->writelnred('');
$this->writelnred('== totcptmessage');
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptmessage"]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("totcptmessage");
$stat->setValue([]);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(message.id) as cpt')
->from('CadolesWebsocketBundle:Message','message')
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
// totcptblogarticle
$this->writelnred('');
$this->writelnred('== totcptblogarticle');
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptblogarticle"]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("totcptblogarticle");
$stat->setValue([]);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(blogarticle.id) as cpt')
->from('CadolesPortalBundle:Blogarticle','blogarticle')
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
// totcptprojecttask
$this->writelnred('');
$this->writelnred('== totcptprojecttask');
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptprojecttask"]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("totcptprojecttask");
$stat->setValue([]);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(projecttask.id) as cpt')
->from('CadolesPortalBundle:Projecttask','projecttask')
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
// groupcptvisite
$this->writelnred('');
$this->writelnred('== groupcptvisite');
foreach($groups as $group) {
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptvisite","group"=>$group]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("groupcptvisite");
$stat->setValue([]);
$stat->setGroup($group);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select(['SUM(usergroup.visitecpt) as cpt'])
->from('CadolesCoreBundle:UserGroup','usergroup')
->Where('usergroup.group=:group')
->setParameter('group', $group)
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
}
// groupcptmessage
$this->writelnred('');
$this->writelnred('== groupcptmessage');
foreach($groups as $group) {
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptmessage","group"=>$group]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("groupcptmessage");
$stat->setValue([]);
$stat->setGroup($group);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(message.id) as cpt')
->from('CadolesWebsocketBundle:Message','message')
->Where('message.group=:group')
->setParameter('group', $group)
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
}
// groupcptblogarticle
$this->writelnred('');
$this->writelnred('== groupcptblogarticle');
foreach($groups as $group) {
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptblogarticle","group"=>$group]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("groupcptblogarticle");
$stat->setValue([]);
$stat->setGroup($group);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(blogarticle.id) as cpt')
->from('CadolesPortalBundle:Blogarticle','blogarticle')
->from('CadolesPortalBundle:Blog','blog')
->Where('blogarticle.blog=blog')
->andwhere(":group MEMBER OF blog.groups")
->setParameter('group', $group)
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
}
// groupcptprojecttask
$this->writelnred('');
$this->writelnred('== groupcptprojecttask');
foreach($groups as $group) {
$stat=$this->em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptprojecttask","group"=>$group]);
if(!$stat) {
$stat=new Statistic();
$stat->setKeyvalue("groupcptprojecttask");
$stat->setValue([]);
$stat->setGroup($group);
}
$value=$stat->getValue();
$cpt= $this->em->createQueryBuilder()
->select('COUNT(projecttask.id) as cpt')
->from('CadolesPortalBundle:Projecttask','projecttask')
->from('CadolesPortalBundle:Project','project')
->Where('projecttask.project=project')
->andwhere(":group MEMBER OF project.groups")
->setParameter('group', $group)
->getQuery()->getOneOrNullResult();
$value[$now->format("Y-m-d")]=($cpt["cpt"]?$cpt["cpt"]:0);
$stat->setValue($value);
$this->em->persist($stat);
$this->em->flush();
}
$this->writeln('');
return 1;
}
private function writelnred($string) {
$this->output->writeln('<fg=red>'.$string.'</>');
$this->filesystem->appendToFile($this->rootlog.'cron.log', $string."\n");
if($this->byexec) $this->filesystem->appendToFile($this->rootlog.'exec.log', $string."\n");
}
private function writeln($string) {
$this->output->writeln($string);
$this->filesystem->appendToFile($this->rootlog.'cron.log', $string."\n");
if($this->byexec) $this->filesystem->appendToFile($this->rootlog.'exec.log', $string."\n");
}
}

View File

@ -203,66 +203,94 @@ class ConfigController extends Controller
$session=$this->get('session');
$config=$em->getRepository('CadolesCoreBundle:Config')->find("datauser");
$fields=$config->getValue();
$fields=json_decode($fields,true);
if(!is_array($fields)) $fields=[];
if($fields=="") {
// Valeur par défaut 0=caché / 1=falcultatif / 2=obligatoire
// Valeur par défaut 0=caché / 1=falcultatif / 2=obligatoire
if(!array_key_exists("firstname",$fields)) {
$fields["firstname"]["perm"]=1;
$fields["firstname"]["label"]="Prénom";
}
if(!array_key_exists("visible",$fields)) {
$fields["visible"]["perm"]=2;
$fields["visible"]["label"]="Visible";
}
if(!array_key_exists("authlevel",$fields)) {
$fields["authlevel"]["perm"]=2;
$fields["authlevel"]["label"]="Niveau d'authentification";
}
if(!array_key_exists("belongingpopulation",$fields)) {
$fields["belongingpopulation"]["perm"]=2;
$fields["belongingpopulation"]["label"]="Population d'appartenance";
}
if(!array_key_exists("job",$fields)) {
$fields["job"]["perm"]=1;
$fields["job"]["label"]="Métier";
}
if(!array_key_exists("position",$fields)) {
$fields["position"]["perm"]=1;
$fields["position"]["label"]="Fonction";
}
if(!array_key_exists("niveau02",$fields)) {
$fields["niveau02"]["perm"]=1;
$fields["niveau02"]["label"]="Niveau 02";
$fields["niveau02"]["label"]=$session->get('labelniveau02');
}
if(!array_key_exists("usualname",$fields)) {
$fields["usualname"]["perm"]=1;
$fields["usualname"]["label"]="Nom d'Usage";
}
if(!array_key_exists("gender",$fields)) {
$fields["gender"]["perm"]=1;
$fields["gender"]["label"]="Sexe";
}
if(!array_key_exists("givensname",$fields)) {
$fields["givensname"]["perm"]=1;
$fields["givensname"]["label"]="Autre Prénom";
}
if(!array_key_exists("telephonenumber",$fields)) {
$fields["telephonenumber"]["perm"]=1;
$fields["telephonenumber"]["label"]="Téléphone";
}
if(!array_key_exists("postaladress",$fields)) {
$fields["postaladress"]["perm"]=1;
$fields["postaladress"]["label"]="Adresse";
}
if(!array_key_exists("birthdate",$fields)) {
$fields["birthdate"]["perm"]=1;
$fields["birthdate"]["label"]="Date de Naissance";
}
if(!array_key_exists("birthcountry",$fields)) {
$fields["birthcountry"]["perm"]=1;
$fields["birthcountry"]["label"]="Pays de Naissance";
}
if(!array_key_exists("birthplace",$fields)) {
$fields["birthplace"]["perm"]=1;
$fields["birthplace"]["label"]="Ville de Naissance";
}
else {
$fields=json_decode($fields, true);
}
}
if(!array_key_exists("visite",$fields)) {
$fields["visite"]["perm"]=1;
$fields["visite"]["label"]="Visite";
}
if($session->get('viewniveau02')&&!array_key_exists("niveau02",$fields))
$fields["niveau02"]["perm"]=1;
elseif(!$session->get('viewniveau02'))
if(!$session->get('viewniveau02'))
unset($fields["niveau02"]);
if(array_key_exists("niveau02",$fields))
$fields["niveau02"]["label"]=$session->get('labelniveau02');
$form = $this->createForm(DatauserType::class,$config,array("mode"=>"datauser","fields" => $fields));
@ -311,59 +339,66 @@ class ConfigController extends Controller
$config=$em->getRepository('CadolesCoreBundle:Config')->find("datausers");
$fields=$config->getValue();
if($fields=="") {
// Valeur par défaut 0=caché / 3=visible
$fields=json_decode($fields, true);
if(!is_array($fields)) $fields=[];
// Valeur par défaut 0=caché / 3=visible
if(!array_key_exists("avatar",$fields)) {
$fields["avatar"]["perm"]=1;
$fields["avatar"]["label"]="Avatar";
}
if(!array_key_exists("login",$fields)) {
$fields["login"]["perm"]=1;
$fields["login"]["label"]="Login";
}
if(!array_key_exists("lastname",$fields)) {
$fields["lastname"]["perm"]=1;
$fields["lastname"]["label"]="Nom";
}
if(!array_key_exists("firstname",$fields)) {
$fields["firstname"]["perm"]=1;
$fields["firstname"]["label"]="Prenom";
}
if(!array_key_exists("email",$fields)) {
$fields["email"]["perm"]=1;
$fields["email"]["label"]="Email";
}
if(!array_key_exists("niveau01",$fields)) {
$fields["niveau01"]["perm"]=1;
$fields["niveau01"]["label"]="Niveau 01";
$fields["niveau01"]["label"]=$session->get('labelniveau01');
}
if(!array_key_exists("niveau02",$fields)) {
$fields["niveau02"]["perm"]=1;
$fields["niveau02"]["label"]="Niveau 02";
$fields["niveau02"]["label"]=$session->get('labelniveau02');
}
if(!array_key_exists("group",$fields)) {
$fields["group"]["perm"]=1;
$fields["group"]["label"]="Groupes";
}
if(!array_key_exists("job",$fields)) {
$fields["job"]["perm"]=1;
$fields["job"]["label"]="Métier";
}
if(!array_key_exists("position",$fields)) {
$fields["position"]["perm"]=1;
$fields["position"]["label"]="Fonction";
}
if(!array_key_exists("role",$fields)) {
$fields["role"]["perm"]=1;
$fields["role"]["label"]="Rôles";
}
if(!array_key_exists("telephonenumber",$fields)) {
$fields["telephonenumber"]["perm"]=1;
$fields["telephonenumber"]["label"]="Téléphone";
}
else {
$fields=json_decode($fields, true);
if(!array_key_exists("visitedate",$fields)) {
$fields["visitedate"]["perm"]=1;
$fields["visitedate"]["label"]="Visite";
}
$fields["niveau01"]["label"]=$session->get('labelniveau01');
if($session->get('viewniveau02')&&!array_key_exists("niveau02",$fields))
$fields["niveau02"]["perm"]=1;
elseif(!$session->get('viewniveau02'))
if(!$session->get('viewniveau02'))
unset($fields["niveau02"]);
if(array_key_exists("niveau02",$fields))
$fields["niveau02"]["label"]=$session->get('labelniveau02');
$form = $this->createForm(DatauserType::class,$config,array("mode"=>"datausers","fields" => $fields));
// Récupération des data du formulaire

View File

@ -103,8 +103,18 @@ class CoreController extends Controller
}
}
// Si niveau01 commence par autre = alors niveau01other obligatoire
$message="";
$niveau01=strtolower($user->getNiveau01()->getLabel());
if(stripos($niveau01,"autre")===0) {
if(!$user->getNiveau01other()) {
$toprofil=true;
$message="<br>Merci d'indiquer votre ".$this->getParameter("labelniveau01");
}
}
if($toprofil) {
return $this->redirect($this->generateUrl('cadoles_core_user',array("info"=>"Merci de compléter votre profil")));
return $this->redirect($this->generateUrl('cadoles_core_user',array("info"=>"Merci de compléter votre profil".$message)));
}
}

View File

@ -82,7 +82,9 @@ class GroupController extends Controller
$qb=$em->createQueryBuilder();
$qb->select('COUNT(table)')
->from($this->labelentity,'table')
->leftJoin('CadolesCoreBundle:User', 'u', 'WITH', 'table.owner = u.id')
->where('table.label LIKE :value')
->orWhere('u.username LIKE :value')
->setParameter("value", "%".$search["value"]."%");
if($access=="user") {
$qb->from("CadolesCoreBundle:UserGroup","ug")
@ -107,44 +109,46 @@ class GroupController extends Controller
// Parcours des Enregistrement
$qb = $em->createQueryBuilder();
$qb->select('table')->from($this->labelentity,'table');
$qb ->select('table')
->from($this->labelentity,'table')
->leftJoin('CadolesCoreBundle:User', 'u', 'WITH', 'table.owner = u.id');
if($access=="user") {
$qb->from("CadolesCoreBundle:UserGroup","ug")
->andWhere(("table.fgcanshare=:flag"))
->andWhere("table.id=ug.group")
->andWhere(":user=ug.user")
->leftJoin('CadolesCoreBundle:User', 'u', 'WITH', 'table.owner = u.id')
->setParameter("flag", true)
->setParameter("user", $this->getUser());
}
if($search["value"]!="") {
$qb ->andwhere('table.label LIKE :value')
->orWhere('u.username LIKE :value')
->setParameter("value", "%".$search["value"]."%");
}
switch($order[0]["column"]) {
case 1 :
case 2 :
$qb->orderBy('table.label',$order[0]["dir"]);
break;
case 2 :
case 3 :
$qb->orderBy('table.fgopen',$order[0]["dir"]);
break;
case 4 :
case 5 :
$qb->orderBy('table.fgcanshare',$order[0]["dir"]);
break;
case 5 :
case 6 :
$qb->orderBy('table.owner',$order[0]["dir"]);
break;
case 6 :
case 7 :
$qb->orderBy('table.fgcancreatepage',$order[0]["dir"]);
break;
case 7 :
case 8 :
$qb->orderBy('table.fgcancreatecalendar',$order[0]["dir"]);
break;
case 8 :
case 9 :
$qb->orderBy('table.fgcancreateblog',$order[0]["dir"]);
break;
case 9 :
case 10 :
$qb->orderBy('table.fgcancreateproject',$order[0]["dir"]);
break;
}
@ -169,7 +173,9 @@ class GroupController extends Controller
if($data->getId()>0&&!$data->getFgall()&&!$data->getFgTemplate()&&$this->isGranted('ROLE_ADMIN')) $action.="<a href='".$this->generateUrl('cadoles_core_config_group_delete', array('id'=>$data->getId()))."'><i class='fa fa-trash fa-fw fa-2x'></i></a>";
if(!$data->getFgall()) $action .="<a href='".$this->generateUrl('cadoles_core_config_group_users', array('id'=>$data->getId()))."'><i class='fa fa-users fa-2x fa-fw'></i></a>";
if($data->getFgcanshare())
$action.="<a href='".$this->generateUrl('cadoles_core_'.$access.'_group_statistic', array('id'=>$data->getId()))."'><i class='fa fa-bar-chart-o fa-fw fa-2x'></i></a>";
}
else {
$fgproprio=($user==$data->getOwner());
@ -186,9 +192,11 @@ class GroupController extends Controller
$action .="<a href='".$this->generateUrl('cadoles_core_'.$access.'_group_users', array('id'=>$data->getId()))."'><i class='fa fa-users fa-2x fa-fw'></i></a>";
}
else {
$action.="<a href='".$this->generateUrl('cadoles_core_'.$access.'_group_out', array('id'=>$data->getId()))."' data-method='out'><i class='fa fa-sign-out fa-fw fa-2x'></i></a>";
$action.="<a href='".$this->generateUrl('cadoles_core_'.$access.'_group_out', array('id'=>$data->getId()))."'><i class='fa fa-sign-out fa-fw fa-2x'></i></a>";
}
if($data->getFgcanshare())
$action.="<a href='".$this->generateUrl('cadoles_core_'.$access.'_group_statistic', array('id'=>$data->getId()))."'><i class='fa fa-bar-chart-o fa-fw fa-2x'></i></a>";
}
@ -196,14 +204,22 @@ class GroupController extends Controller
if($this->GetParameter("masteridentity")=="LDAP") $filtre=$data->getLdapfilter();
if($this->GetParameter("masteridentity")=="SSO") $filtre=$data->getAttributes();
if ($data->getIcon())
$groupinfo = "<img src='/".$this->container->getParameter('alias')."/".$data->getIcon()->getLabel()."' class='avatar' style='background-color:transparent'/>";
else
$groupinfo = "<img src='/".$this->container->getParameter('alias')."/uploads/icon/icon_pin.png' class='avatar' style='background-color:transparent'/>";
$userinfo="";
if($data->getOwner()) {
$userinfo.="<img style='cursor:pointer' onClick='seeUser(".$data->getOwner()->getId().")' src='/".$this->container->getParameter('alias')."/uploads/avatar/".$data->getOwner()->getAvatar()."' class='avatar' style='margin:0px 5px 0px 0px;display:inline-block;'>";
$userinfo.=$data->getOwner()->getUsername();
$userinfo.="<br>".$data->getOwner()->getUsername();
}
array_push($output["data"],array(
$action,
$groupinfo,
$data->getLabel(),
($data->getFgopen()?"oui":"non"),
$filtre,
@ -345,7 +361,7 @@ class GroupController extends Controller
// Avatar
$avatar="<img onClick='seeUser(".$data->getId().")' src='/".$this->container->getParameter('alias')."/uploads/avatar/".$data->getAvatar()."' style='width:30px;background-color:#337ab7;margin:auto;display:block;cursor:pointer;'>";
array_push($output["data"],array("DT_RowId"=>"user".$data->getId(),$action,$avatar,$data->getUsername(),$data->getEmail(),$fgmanager));
array_push($output["data"],array("DT_RowId"=>"user".$data->getId(),$action,$avatar,$data->getUsername(),$data->getEmail(),"",$fgmanager));
}
// Retour
@ -455,11 +471,11 @@ class GroupController extends Controller
$qb->setParameter("groupid",$id);
switch($order[0]["column"]) {
case 2 :
$qb->orderBy('user.username',$order[0]["dir"]);
$qb->orderBy('user.username',$order[0]["dir"]);
break;
case 3 :
$qb->orderBy('user.email',$order[0]["dir"]);
$qb->orderBy('user.email',$order[0]["dir"]);
break;
}
@ -487,9 +503,14 @@ class GroupController extends Controller
if($fgproprio) $fgmanager="Propriétaire du groupe";
}
// Visite
$visite="";
if($usergroup->getVisitedate()) {
$visite=$usergroup->getVisitedate()->format("d/m/Y H:i")."<br>nb = ".$usergroup->getVisitecpt();
}
array_push($output["data"],array("DT_RowId"=>"user".$data->getId(),$action,$avatar,$data->getUsername(),$data->getEmail(),$fgmanager));
array_push($output["data"],array("DT_RowId"=>"user".$data->getId(),$action,$avatar,$data->getUsername(),$data->getEmail(),$visite,$fgmanager));
}
// Retour
@ -970,8 +991,8 @@ class GroupController extends Controller
public function usergroupexportAction($id,Request $request, $access="config")
{
// Récupération de l'enregistrement courant
$data=$this->getData($id);
$this->canManager($data,$access);
$group=$this->getData($id);
$this->canManager($group,$access);
$em = $this->getDoctrine()->getManager();
$dir = $this->get('kernel')->getRootDir() . '/../uploads/export/';
@ -985,7 +1006,7 @@ class GroupController extends Controller
$e = '"'; // this is the default but i like to be explicit
// Entête de colonne
$data=["id","Login","Nom","Prénom","Email","Téléphone",$this->getParameter("labelniveau01"),$this->getParameter("labelniveau02"),"Métier","Fonction","Nom Usage","Autres Prénom","Sexe","Adresse","Date Naissance","Pays Naissance","Ville Naissance"];
$data=["id","Login","Nom","Prénom","Email","Téléphone",$this->getParameter("labelniveau01"),$this->getParameter("labelniveau02"),"Métier","Fonction","Nom Usage","Autres Prénom","Sexe","Adresse","Date Naissance","Pays Naissance","Ville Naissance","Date Visite","Nb Visites"];
fputcsv($csvh, $data, $d, $e);
// Liste des utilisateurs en fonction du role de l'utilisateur en cours
@ -1036,9 +1057,18 @@ class GroupController extends Controller
"birthdate"=>($user->getBirthdate()?$user->getBirthdate()->format("d/m/Y"):""),
"birthcountry"=>($user->getBirthcountry()?$user->getBirthcountry()->getLabel():""),
"birthplace"=>($user->getBirthplace()?$user->getBirthplace()->getLabel():""),
"visitedate"=>"",
"visitecpt"=>"",
];
$usergroup=$em->getRepository("CadolesCoreBundle:UserGroup")->findOneBy(["user"=>$user,"group"=>$group]);
if($usergroup) {
if($usergroup->getVisitedate()) {
$data["visitedate"]=$usergroup->getVisitedate()->format("d/m/Y H:i");
$data["visitecpt"]=$usergroup->getVisitecpt();
}
}
fputcsv($csvh, $data, $d, $e);
}
fclose($csvh);
@ -1049,6 +1079,36 @@ class GroupController extends Controller
return $response;
}
public function statisticAction($id,$access) {
$group=$this->getData($id);
$em = $this->getDoctrine()->getManager();
if(!$group) throw $this->createNotFoundException('Permission denied');
if($access!="config") {
$usergroup=$em->getRepository("CadolesCoreBundle:UserGroup")->findOneBy(["user"=>$this->getUser(),"group"=>$group]);
if(!$usergroup) throw $this->createNotFoundException('Permission denied');
}
$groupcptvisite=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptvisite","group"=>$group]);
$groupcptmessage=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptmessage","group"=>$group]);
$groupcptblogarticle=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptblogarticle","group"=>$group]);
$groupcptprojecttask=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"groupcptprojecttask","group"=>$group]);
return $this->render('CadolesCoreBundle:Group:statistic.html.twig',[
'useheader' => true,
'usemenu' => false,
'usesidebar' => ($access=="config"),
'access' => $access,
'group' => $group,
'groupcptvisite' => $groupcptvisite,
'groupcptmessage' => $groupcptmessage,
'groupcptblogarticle' => $groupcptblogarticle,
'groupcptprojecttask' => $groupcptprojecttask,
]);
}
protected function canManager($group,$access) {
if($access!="config") {
$em = $this->getDoctrine()->getManager();

View File

@ -159,7 +159,7 @@ class RegistrationController extends Controller
$action,
$data->getUsername(),
$data->getEmail(),
$data->getNiveau01()->getLabel(),
$data->getNiveau01()->getLabel()."<br>".$data->getNiveau01other(),
$data->getStatut()->getLabel(),
(is_null($data->getKeyexpire())?"":$data->getKeyexpire()->format('d/m/Y H:i:s'))
));
@ -195,8 +195,22 @@ class RegistrationController extends Controller
// Récupération des data du formulaire
$form->handleRequest($request);
// si mode de registration byuser
if($moderegistration=="byuser") {
$idstatut=2;
}
else {
// On recherche le domaine du mail dans la liste blanche
$email=explode("@",$data->getEmail());
$domaine=end($email);
$whitelist = $em->getRepository("CadolesCoreBundle:Whitelist")->findBy(["label"=>$domaine]);
$idstatut=(!$whitelist?1:2);
}
$statut = $em->getRepository("CadolesCoreBundle:Statut")->find($idstatut);
$data->setStatut($statut);
// Sur erreur
$this->getErrorForm(null,$form,$request,$data,"submit");
$this->getErrorForm(null,$form,$request,$data,"submit",$idstatut);
// Sur validation(z)
if ($form->get('submit')->isClicked() && $form->isValid()) {
@ -219,22 +233,7 @@ class RegistrationController extends Controller
$password = $encoder->encodePassword($data->getPassword(),$data->getSalt());
$data->setPassword($password);
*/
// si mode de registration byuser
if($moderegistration=="byuser") {
$idstatut=2;
}
else {
// On recherche le domaine du mail dans la liste blanche
$email=explode("@",$data->getEmail());
$domaine=end($email);
$whitelist = $em->getRepository("CadolesCoreBundle:Whitelist")->findBy(["label"=>$domaine]);
$idstatut=(!$whitelist?1:2);
}
$statut = $em->getRepository("CadolesCoreBundle:Statut")->find($idstatut);
$data->setStatut($statut);
// si non : validation par administrateur
if($idstatut==1) {
// Email à destination de l'inscript pour le prévenir qu'un administrateur doit valider
@ -287,10 +286,17 @@ class RegistrationController extends Controller
}
$url = $this->generateUrl('cadoles_core_config_registration', [], UrlGeneratorInterface::ABSOLUTE_URL);
$motivation = "Login = ".$data->getUsername()."\n";
$motivation.= "Nom = ".$data->getLastname()."\n";
$motivation.= "Prénom = ".$data->getFirstname()."\n";
$motivation.= "Mail = ".$data->getEmail()."\n";
$motivation.= $this->getParameter("labelniveau01")." = ".$data->getNiveau01()->getLabel()." ".$data->getNiveau01other()."\n\n";
$motivation.= $data->getMotivation();
$mail_params=array(
"subject" => $appname." : Inscription à valider",
"body_html"=>"Un utilisateur dont le mail nest pas en liste blanche souhaite sinscrire au ".$appname.".\nMerci dapprouver son inscription pour finaliser celle-ci.<br><br>Veuillez vérifier cette inscription à cette adresse:<br><a href='$url'>$url</a>",
"body_text"=>"Un utilisateur dont le mail nest pas en liste blanche souhaite sinscrire au ".$appname.".\nMerci dapprouver son inscription pour finaliser celle-ci.\n\nVeuillez vérifier cette inscription à cette adresse:\n$url"
"body_html"=>"Un utilisateur dont le mail nest pas en liste blanche souhaite sinscrire au ".$appname.".\nMerci dapprouver son inscription pour finaliser celle-ci.<br><br>Veuillez vérifier cette inscription à cette adresse:<br><a href='$url'>$url</a><br><br>".nl2br($motivation),
"body_text"=>"Un utilisateur dont le mail nest pas en liste blanche souhaite sinscrire au ".$appname.".\nMerci dapprouver son inscription pour finaliser celle-ci.\n\nVeuillez vérifier cette inscription à cette adresse:\n$url\n\n".$motivation
);
$message = $this->container->get('cadoles.core.service.mail');
@ -386,7 +392,7 @@ class RegistrationController extends Controller
$form->handleRequest($request);
// Sur erreur
$this->getErrorForm($id,$form,$request,$data,"send");
$this->getErrorForm($id,$form,$request,$data,"send",null);
// Sur validation
if ($form->get('save')->isClicked() && $form->isValid()) {
@ -581,7 +587,7 @@ class RegistrationController extends Controller
$form->handleRequest($request);
// Sur erreur
$this->getErrorForm($id,$form,$request,$data,"delete");
$this->getErrorForm($id,$form,$request,$data,"delete",null);
// Sur validation
if ($form->get('submit')->isClicked() && $form->isValid()) {
@ -838,7 +844,7 @@ class RegistrationController extends Controller
}
protected function getErrorForm($id,$form,$request,$data,$mode) {
protected function getErrorForm($id,$form,$request,$data,$mode,$idstatut) {
if ($form->get('submit')->isClicked()&&$mode=="delete") {
}
@ -859,6 +865,20 @@ class RegistrationController extends Controller
if($this->getUserBy("username",$data->getUsername())||$this->getUserBy("email",$data->getEmail())) {
$form->addError(new FormError('Un utilisateur utilise déjà ce login ou cet email'));
}
// Si niveau01 commence par autre = niveau01other obligatoire
$niveau01=strtolower($data->getNiveau01()->getLabel());
if(stripos($niveau01,"autre")===0) {
if(!$data->getNiveau01other()) {
$form->addError(new FormError("Merci d'indiquer votre ".$this->getParameter("labelniveau01")));
}
}
// Si validation par administrateur demander une motivation
if(is_null($data->getMotivation() )) {
$form->addError(new FormError("Attention, le suffixe de votre adresse mail nest pas dans la liste des administrations autorisées, merci de bien vouloir privilégier votre adresse professionnelle si vous en avez une.<br>Si ce nest pas le cas, il faut que vous renseigniez la case motivation de votre demande"));
}
}
if ($form->get('submit')->isClicked() && !$form->isValid()) {

View File

@ -0,0 +1,109 @@
<?php
namespace Cadoles\CoreBundle\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Session\Session;
use Symfony\Component\HttpFoundation\Response;
use Cadoles\PortalBundle\Entity\Page;
class StatisticController extends Controller
{
public function listAction(Request $request)
{
$em = $this->getDoctrine()->getManager();
$totcptvisite=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptvisite"]);
$totcptvisitegroup=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptvisitegroup"]);
$totcptmessage=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptmessage"]);
$totcptblogarticle=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptblogarticle"]);
$totcptprojecttask=$em->getRepository("CadolesCoreBundle:Statistic")->findOneBy(["keyvalue"=>"totcptprojecttask"]);
//groupcptvisite
$statistics=$em->getRepository("CadolesCoreBundle:Statistic")->findBy(["keyvalue"=>"groupcptvisite"]);
$groupcptvisite=[];
foreach($statistics as $statistic) {
$value=$statistic->getValue();
$tmp=[
"id" => $statistic->getGroup()->getId(),
"name" => $statistic->getGroup()->getLabel(),
"value" => end($value),
];
array_push($groupcptvisite,$tmp);
}
usort($groupcptvisite, function($a, $b) {
return $a['value'] <=> $b['value'];
});
$topgroupcptvisite = array_slice($groupcptvisite, -20);
//groupcptmessage
$statistics=$em->getRepository("CadolesCoreBundle:Statistic")->findBy(["keyvalue"=>"groupcptmessage"]);
$groupcptmessage=[];
foreach($statistics as $statistic) {
$value=$statistic->getValue();
$tmp=[
"id" => $statistic->getGroup()->getId(),
"name" => $statistic->getGroup()->getLabel(),
"value" => end($value),
];
array_push($groupcptmessage,$tmp);
}
usort($groupcptmessage, function($a, $b) {
return $a['value'] <=> $b['value'];
});
$topgroupcptmessage = array_slice($groupcptmessage, -20);
//groupcptblogarticle
$statistics=$em->getRepository("CadolesCoreBundle:Statistic")->findBy(["keyvalue"=>"groupcptblogarticle"]);
$groupcptblogarticle=[];
foreach($statistics as $statistic) {
$value=$statistic->getValue();
$tmp=[
"id" => $statistic->getGroup()->getId(),
"name" => $statistic->getGroup()->getLabel(),
"value" => end($value),
];
array_push($groupcptblogarticle,$tmp);
}
usort($groupcptblogarticle, function($a, $b) {
return $a['value'] <=> $b['value'];
});
$topgroupcptblogarticle = array_slice($groupcptblogarticle, -20);
//groupcptprojecttask
$statistics=$em->getRepository("CadolesCoreBundle:Statistic")->findBy(["keyvalue"=>"groupcptprojecttask"]);
$groupcptprojecttask=[];
foreach($statistics as $statistic) {
$value=$statistic->getValue();
$tmp=[
"id" => $statistic->getGroup()->getId(),
"name" => $statistic->getGroup()->getLabel(),
"value" => end($value),
];
array_push($groupcptprojecttask,$tmp);
}
usort($groupcptprojecttask, function($a, $b) {
return $a['value'] <=> $b['value'];
});
$topgroupcptprojecttask = array_slice($groupcptprojecttask, -20);
return $this->render('CadolesCoreBundle:Statistic:list.html.twig',[
'useheader' => true,
'usemenu' => false,
'usesidebar' => true,
'totcptvisite' => $totcptvisite,
'totcptvisitegroup' => $totcptvisitegroup,
'totcptmessage' => $totcptmessage,
'totcptblogarticle' => $totcptblogarticle,
'totcptprojecttask' => $totcptprojecttask,
'groupcptvisite' => $topgroupcptvisite,
'groupcptmessage' => $topgroupcptmessage,
'groupcptblogarticle' => $topgroupcptblogarticle,
'groupcptprojecttask' => $topgroupcptprojecttask,
]);
}
}

View File

@ -28,6 +28,7 @@ use Cadoles\CoreBundle\Entity\Niveau02;
use Cadoles\WebsocketBundle\Entity\Message;
use Cadoles\CoreBundle\Form\UserType;
use Cadoles\CoreBundle\Form\MailingType;
class UserController extends Controller
@ -225,6 +226,10 @@ class UserController extends Controller
break;
case 12 :
$qb->orderBy('user.visitedate',$order[0]["dir"]);
break;
case 13 :
$qb->orderBy('user.role',$order[0]["dir"]);
break;
}
@ -264,6 +269,10 @@ class UserController extends Controller
break;
case 10 :
$qb->orderBy('user.visitedate',$order[0]["dir"]);
break;
case 11 :
$qb->orderBy('user.role',$order[0]["dir"]);
break;
}
@ -295,11 +304,12 @@ class UserController extends Controller
array_push($tmp,$data->getFirstname());
array_push($tmp,"<a href='mailto:".$data->getEmail()."'>".$data->getEmail()."</a>");
array_push($tmp,$data->getTelephonenumber());
array_push($tmp,$data->getNiveau01()->getLabel());
array_push($tmp,$data->getNiveau01()->getLabel()."<br>".$data->getNiveau01other());
if($viewniveau02) array_push($tmp,($data->getNiveau02()!==null?$data->getNiveau02()->getLabel():""));
array_push($tmp,$groups);
array_push($tmp,$data->getJob());
array_push($tmp,$data->getPosition());
array_push($tmp,($data->getVisitedate()?$data->getVisitedate()->format("d/m/Y H:i")."<br>nb = ".$data->getVisitecpt():""));
array_push($tmp,$data->getRole());
array_push($output["data"],$tmp);
@ -769,6 +779,74 @@ class UserController extends Controller
}
public function mailingAction(Request $request) {
$form = $this->createForm(MailingType::class,$this->getUser(),array(
"perm"=>$this->isGranted('ROLE_ADMIN'),
"userid"=>$this->get('security.token_storage')->getToken()->getUser()->getId(),
));
// Récupération des data du formulaire
$form->handleRequest($request);
// Error si pas de message
if ($form->get('submit')->isClicked()) {
if(!$form->get('message')->getData()) {
$form->addError(new FormError("Merci de renseigner un message à votre mail"));
$errors = $form->getErrors();
foreach( $errors as $error ) {
$request->getSession()->getFlashBag()->add("error", $error->getMessage());
}
}
}
// Sur validation
if ($form->get('submit')->isClicked() && $form->isValid()) {
$users=[];
if($this->isGranted('ROLE_ADMIN')) {
$groups=$form->get('groups')->getData();
foreach($groups as $group) {
foreach($group->getUsers() as $usergroup) {
if(!in_array($usergroup->getUser()->getEmail(),$users)) {
array_push($users,$usergroup->getUser()->getEmail());
}
}
}
}
$niveau01s=$form->get('niveau01')->getData();
foreach($niveau01s as $niveau01) {
foreach($niveau01->getUsers() as $user) {
if(!in_array($user->getEmail(),$users)) {
array_push($users,$user->getEmail());
}
}
}
$text=$form->get("message")->getData();
$subject=$form->get("subject")->getData();
$template="template";
$mail_params=array(
"subject" => $subject,
"body_html"=>nl2br($text),
"body_text"=>$text
);
$from = $this->getParameter('noreply');
$fromName = $this->getUser()->getFirstname()." ".$this->getUser()->getLastname();
$message = $this->container->get('cadoles.core.service.mail');
foreach($users as $to) {
$message->sendEmail($template, $mail_params, $to, $from, $fromName);
}
return $this->redirectToRoute("cadoles_core_config");
}
return $this->render('CadolesCoreBundle:Mail:mailing.html.twig', [
'useheader' => true,
'usemenu' => false,
'usesidebar' => true,
'form' => $form->createView()
]);
}
public function exportuserAction(Request $request) {
$em = $this->getDoctrine()->getManager();
$dir = $this->get('kernel')->getRootDir() . '/../uploads/export/';
@ -1147,55 +1225,88 @@ class UserController extends Controller
$config=$em->getRepository('CadolesCoreBundle:Config')->find("datauser");
$fields=$config->getValue();
$fields=json_decode($fields,true);
if(!is_array($fields)) $fields=[];
if($fields=="") {
// Valeur par défaut 0=caché / 1=falcultatif / 2=obligatoire
// Valeur par défaut 0=caché / 1=falcultatif / 2=obligatoire
if(!array_key_exists("firstname",$fields)) {
$fields["firstname"]["perm"]=1;
$fields["firstname"]["label"]="Prénom";
}
if(!array_key_exists("visible",$fields)) {
$fields["visible"]["perm"]=2;
$fields["visible"]["label"]="Visible";
}
if(!array_key_exists("authlevel",$fields)) {
$fields["authlevel"]["perm"]=2;
$fields["authlevel"]["label"]="Niveau d'authentification";
}
if(!array_key_exists("belongingpopulation",$fields)) {
$fields["belongingpopulation"]["perm"]=2;
$fields["belongingpopulation"]["label"]="Population d'appartenance";
}
if(!array_key_exists("job",$fields)) {
$fields["job"]["perm"]=1;
$fields["job"]["label"]="Métier";
}
if(!array_key_exists("position",$fields)) {
$fields["position"]["perm"]=1;
$fields["position"]["label"]="Fonction";
}
if(!array_key_exists("niveau02",$fields)) {
$fields["niveau02"]["perm"]=1;
$fields["niveau02"]["label"]="Niveau 02";
}
if(!array_key_exists("usualname",$fields)) {
$fields["usualname"]["perm"]=1;
$fields["usualname"]["label"]="Nom d'Usage";
}
if(!array_key_exists("gender",$fields)) {
$fields["gender"]["perm"]=1;
$fields["gender"]["label"]="Sexe";
}
if(!array_key_exists("givensname",$fields)) {
$fields["givensname"]["perm"]=1;
$fields["givensname"]["label"]="Autre Prénom";
}
if(!array_key_exists("telephonenumber",$fields)) {
$fields["telephonenumber"]["perm"]=1;
$fields["telephonenumber"]["label"]="Téléphone";
}
if(!array_key_exists("postaladress",$fields)) {
$fields["postaladress"]["perm"]=1;
$fields["postaladress"]["label"]="Adresse";
}
if(!array_key_exists("birthdate",$fields)) {
$fields["birthdate"]["perm"]=1;
$fields["birthdate"]["label"]="Date de Naissance";
}
if(!array_key_exists("birthcountry",$fields)) {
$fields["birthcountry"]["perm"]=1;
$fields["birthcountry"]["label"]="Pays de Naissance";
}
if(!array_key_exists("birthplace",$fields)) {
$fields["birthplace"]["perm"]=1;
$fields["birthplace"]["label"]="Ville de Naissance";
}
if(!array_key_exists("visite",$fields)) {
$fields["visite"]["perm"]=1;
$fields["visite"]["label"]="Visite";
}
return $fields;
}
@ -1220,6 +1331,14 @@ class UserController extends Controller
if($this->getRegistrationBy("username",$data->getUsername())||$this->getRegistrationBy("email",$data->getEmail())) {
$form->addError(new FormError('Une inscription utilise déjà ce login ou cet email'));
}
// Si niveau01 commence par autre = niveau01other obligatoire
$niveau01=strtolower($data->getNiveau01()->getLabel());
if(stripos($niveau01,"autre")===0) {
if(!$data->getNiveau01other()) {
$form->addError(new FormError("Merci d'indiquer votre ".$this->getParameter("labelniveau01")));
}
}
}

View File

@ -176,6 +176,10 @@ class Group
*/
protected $messages;
/**
* @ORM\OneToMany(targetEntity="Statistic", mappedBy="group", cascade={"persist"}, orphanRemoval=true)
*/
private $statistics;
// Champs temporaire
protected $nosynconly;
@ -1018,4 +1022,38 @@ class Group
{
return $this->fgcancreateproject;
}
/**
* Add statistic
*
* @param \Cadoles\CoreBundle\Entity\Statistic $statistic
*
* @return Group
*/
public function addStatistic(\Cadoles\CoreBundle\Entity\Statistic $statistic)
{
$this->statistics[] = $statistic;
return $this;
}
/**
* Remove statistic
*
* @param \Cadoles\CoreBundle\Entity\Statistic $statistic
*/
public function removeStatistic(\Cadoles\CoreBundle\Entity\Statistic $statistic)
{
$this->statistics->removeElement($statistic);
}
/**
* Get statistics
*
* @return \Doctrine\Common\Collections\Collection
*/
public function getStatistics()
{
return $this->statistics;
}
}

View File

@ -123,6 +123,16 @@ class Registration implements UserInterface, \Serializable
*/
private $position;
/**
* @ORM\Column(type="string", length=150, nullable=true)
*/
private $niveau01other;
/**
* @ORM\Column(name="description", type="text", nullable=true)
*/
private $motivation;
/**
* @ORM\Column(type="integer", length=60, nullable=true)
*/
@ -738,4 +748,52 @@ class Registration implements UserInterface, \Serializable
{
return $this->groupid;
}
/**
* Set niveau01other
*
* @param string $niveau01other
*
* @return Registration
*/
public function setNiveau01other($niveau01other)
{
$this->niveau01other = $niveau01other;
return $this;
}
/**
* Get niveau01other
*
* @return string
*/
public function getNiveau01other()
{
return $this->niveau01other;
}
/**
* Set motivation
*
* @param string $motivation
*
* @return Registration
*/
public function setMotivation($motivation)
{
$this->motivation = $motivation;
return $this;
}
/**
* Get motivation
*
* @return string
*/
public function getMotivation()
{
return $this->motivation;
}
}

View File

@ -0,0 +1,118 @@
<?php
namespace Cadoles\CoreBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity
* @ORM\Table(name="statistic")
*/
class Statistic
{
/**
* @ORM\Column(type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
protected $id;
/**
* @ORM\Column(type="string")
*/
protected $keyvalue;
/**
* @var string
*
* @ORM\Column(type="array", nullable=true)
*/
private $value;
/**
* @ORM\ManyToOne(targetEntity="Group", inversedBy="statistics")
* @ORM\JoinColumn(name="group_id", referencedColumnName="id", nullable=true)
*/
private $group;
/**
* Get id
*
* @return integer
*/
public function getId()
{
return $this->id;
}
/**
* Set keyvalue
*
* @param string $keyvalue
*
* @return Statistic
*/
public function setKeyvalue($keyvalue)
{
$this->keyvalue = $keyvalue;
return $this;
}
/**
* Get keyvalue
*
* @return string
*/
public function getKeyvalue()
{
return $this->keyvalue;
}
/**
* Set value
*
* @param array $value
*
* @return Statistic
*/
public function setValue($value)
{
$this->value = $value;
return $this;
}
/**
* Get value
*
* @return array
*/
public function getValue()
{
return $this->value;
}
/**
* Set group
*
* @param \Cadoles\CoreBundle\Entity\Group $group
*
* @return Statistic
*/
public function setGroup(\Cadoles\CoreBundle\Entity\Group $group = null)
{
$this->group = $group;
return $this;
}
/**
* Get group
*
* @return \Cadoles\CoreBundle\Entity\Group
*/
public function getGroup()
{
return $this->group;
}
}

View File

@ -163,6 +163,21 @@ class User implements UserInterface, \Serializable
*/
private $viewcalendar;
/**
* @ORM\Column(type="datetime", nullable=true)
*/
private $visitedate;
/**
* @ORM\Column(type="integer", nullable=true)
*/
private $visitecpt;
/**
* @ORM\Column(type="string", length=150, nullable=true)
*/
private $niveau01other;
/**
* @ORM\ManyToOne(targetEntity="Country", inversedBy="users")
* @ORM\JoinColumn(nullable=true)
@ -1796,4 +1811,76 @@ class User implements UserInterface, \Serializable
{
return $this->projectcomments;
}
/**
* Set visitedate
*
* @param \DateTime $visitedate
*
* @return User
*/
public function setVisitedate($visitedate)
{
$this->visitedate = $visitedate;
return $this;
}
/**
* Get visitedate
*
* @return \DateTime
*/
public function getVisitedate()
{
return $this->visitedate;
}
/**
* Set visitecpt
*
* @param integer $visitecpt
*
* @return User
*/
public function setVisitecpt($visitecpt)
{
$this->visitecpt = $visitecpt;
return $this;
}
/**
* Get visitecpt
*
* @return integer
*/
public function getVisitecpt()
{
return $this->visitecpt;
}
/**
* Set niveau01other
*
* @param string $niveau01other
*
* @return User
*/
public function setNiveau01other($niveau01other)
{
$this->niveau01other = $niveau01other;
return $this;
}
/**
* Get niveau01other
*
* @return string
*/
public function getNiveau01other()
{
return $this->niveau01other;
}
}

View File

@ -44,7 +44,17 @@ class UserGroup
* @ORM\Column(type="string", length=60, nullable=true)
*/
private $keyvalue;
/**
* @ORM\Column(type="datetime", nullable=true)
*/
private $visitedate;
/**
* @ORM\Column(type="integer", nullable=true)
*/
private $visitecpt;
/**
* Get id
*
@ -150,4 +160,52 @@ class UserGroup
{
return $this->keyvalue;
}
/**
* Set visitedate
*
* @param \DateTime $visitedate
*
* @return UserGroup
*/
public function setVisitedate($visitedate)
{
$this->visitedate = $visitedate;
return $this;
}
/**
* Get visitedate
*
* @return \DateTime
*/
public function getVisitedate()
{
return $this->visitedate;
}
/**
* Set visitecpt
*
* @param integer $visitecpt
*
* @return UserGroup
*/
public function setVisitecpt($visitecpt)
{
$this->visitecpt = $visitecpt;
return $this;
}
/**
* Get visitecpt
*
* @return integer
*/
public function getVisitecpt()
{
return $this->visitecpt;
}
}

View File

@ -106,8 +106,9 @@
// Chargement de la sidebar
$iconniveau01 =$this->container->getParameter('iconniveau01');
$labelsniveau01 =$this->container->getParameter('labelsniveau01');
$labelniveau01 =$this->container->getParameter('labelsniveau01');
$labelniveau01 =$this->container->getParameter('labelniveau01');
$session->set('labelniveau01',$labelniveau01);
$session->set('labelsniveau01',$labelsniveau01);
$viewniveau02 =$this->container->getParameter('viewniveau02');
$iconniveau02 =$this->container->getParameter('iconniveau02');
@ -115,6 +116,7 @@
$labelniveau02 =$this->container->getParameter('labelniveau02');
$session->set('viewniveau02',$viewniveau02);
$session->set('labelniveau02',$labelniveau02);
$session->set('labelsniveau02',$labelsniveau02);
$moderegistration =$this->container->getParameter('moderegistration');
if($masteridentity!="SQL") $moderegistration="none";
@ -282,6 +284,19 @@
$session->set("sublogo", $niveau01->getLogo());
}
}
if($curentuser!="anon.") {
$visitedate=clone $curentuser->getVisitedate();
if($visitedate) $visitedate->add(new \DateInterval("PT1H"));
$now=new \DateTime();
if($visitedate<$now) {
$curentuser->setVisitedate($now);
$curentuser->setVisitecpt($curentuser->getVisitecpt()+1);
$this->em->persist($curentuser);
$this->em->flush();
}
}
}
}

View File

@ -58,28 +58,26 @@ class GroupType extends AbstractType
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px","readonly" => ($options["mode"]=="delete"?true:false))
]);
if($options["access"]=="config") {
$builder->add('owner',
Select2EntityType::class, array(
'label' => "Propriétaire",
'disabled' => ($options["mode"]=="delete"?true:false),
"required" => false,
'multiple' => false,
'remote_route' => 'cadoles_core_config_user_ajax_selectlist',
'class' => 'Cadoles\coreBundle\Entity\User',
'primary_key' => 'id',
'text_property' => 'username',
'minimum_input_length' => 2,
'page_limit' => 10,
'allow_clear' => true,
'delay' => 250,
'cache' => false,
'cache_timeout' => 60000, // if 'cache' is true
'language' => 'fr',
'placeholder' => 'Selectionner un propriétaire',
'attr' => array("class" => "form-control", "style" => "margin-bottom:15px")
));
}
$builder->add('owner',
Select2EntityType::class, array(
'label' => "Propriétaire",
'disabled' => ($options["mode"]=="delete"?true:false),
"required" => false,
'multiple' => false,
'remote_route' => 'cadoles_core_config_user_ajax_selectlist',
'class' => 'Cadoles\coreBundle\Entity\User',
'primary_key' => 'id',
'text_property' => 'username',
'minimum_input_length' => 2,
'page_limit' => 10,
'allow_clear' => true,
'delay' => 250,
'cache' => false,
'cache_timeout' => 60000, // if 'cache' is true
'language' => 'fr',
'placeholder' => 'Selectionner un propriétaire',
'attr' => array("class" => "form-control", "style" => "margin-bottom:15px")
));
}
if($options["access"]=="config") {

View File

@ -0,0 +1,116 @@
<?php
namespace Cadoles\CoreBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\HttpFoundation\Session\Session;
use Symfony\Component\Form\Extension\Core\Type\EmailType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\Extension\Core\Type\TextareaType;
use Symfony\Component\Form\Extension\Core\Type\RepeatedType;
use Symfony\Component\Form\Extension\Core\Type\PasswordType;
use Symfony\Component\Form\Extension\Core\Type\HiddenType;
use Symfony\Component\Form\Extension\Core\Type\ButtonType;
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Form\Extension\Core\Type\DateTimeType;
use Symfony\Component\Form\Extension\Core\Type\IntegerType;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Tetranz\Select2EntityBundle\Form\Type\Select2EntityType;
use Ivory\CKEditorBundle\Form\Type\CKEditorType;
use Doctrine\ORM\EntityRepository;
use Doctrine\ORM\Query\Expr\Join;
class MailingType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$session = new Session();
$builder->add('submit',
SubmitType::class, array(
"label" => "Envoyer",
"attr" => array("class" => "btn btn-success")
)
);
$perm=$options["perm"];
$userid=$options["userid"];
$builder
->add('niveau01',EntityType::class,[
"mapped" => false,
"required" => false,
"class" => "CadolesCoreBundle:Niveau01",
'multiple' => true,
"label" => $session->get('labelsniveau01'),
'placeholder' => '== Choisir '.$session->get('labelsniveau01').' ==',
"choice_label" => "label",
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px"),
"query_builder"=> function (EntityRepository $er) use($perm,$userid) {
if($perm)
return $er->createQueryBuilder('niveau01');
else {
$result=$er->createQueryBuilder("table")->innerJoin("CadolesCoreBundle:UserModo", "usermodo", Join::WITH, "table.id = usermodo.niveau01");
$result->andWhere("usermodo.user = :userid");
$result->setParameter('userid', $userid);
return $result;
}
}
]);
if($perm) {
$builder
->add('groups', Select2EntityType::class, [
'mapped' => false,
'label' => 'Groupes',
'class' => 'CadolesCoreBundle:Group',
'text_property' => 'label',
'multiple' => true,
'remote_route' => 'cadoles_core_ajax_group_list',
'primary_key' => 'id',
'text_property' => 'label',
'minimum_input_length' => 0,
'page_limit' => 100,
'allow_clear' => true,
'delay' => 250,
'cache' => false,
'cache_timeout' => 60000,
'language' => 'fr',
'placeholder' => 'Selectionner des groupes',
]);
}
$builder
->add('subject', TextType::class, [
"label" =>"Sujet",
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px"),
"mapped" => false
]);
$builder
->add("message",CKEditorType::class,[
'config_name' => 'small_config',
'label' => "Message",
'mapped'=> false,
'required' => true,
'attr' => array("class" => "form-control", "style" => "margin-bottom:15px"),
'config' => ["height" => "400px",'filebrowserUploadRoute' => 'cadoles_portal_user_pagewidget_upload']
]);
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Cadoles\CoreBundle\Entity\User',
'perm' => "boolean",
'userid' => "integer",
));
}
}

View File

@ -76,10 +76,21 @@ class RegistrationType extends AbstractType
EntityType::class,
array("class" => "CadolesCoreBundle:Niveau01",
"label" => $session->get('labelniveau01'),
'placeholder' => '== Choisir '.$session->get('labelniveau01').' ==',
"choice_label" => "label",
"disabled" => ($options["mode"]=="delete"?true:false),
"disabled" => ($options["mode"]=="delete"?true:false),
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px","readonly" => ($options["mode"]=="delete"?true:false))));
$builder->add('niveau01other',
TextType::class, array(
"label" =>"Autre ".$session->get('labelniveau01'),
"disabled" => ($options["mode"]=="delete"?true:false),
"required" => false,
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px")
)
);
# Password
if($options["mode"]!="delete"&&$options["mode"]!="send") {
$builder->add('password',
@ -296,6 +307,14 @@ class RegistrationType extends AbstractType
}
}
$builder->add('motivation',
TextareaType::class, array(
"label" => "Motivation",
"required" => false,
"disabled" => ($options["mode"]=="delete"?true:false),
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px; height: 90px")
)
);
}
public function configureOptions(OptionsResolver $resolver)

View File

@ -16,6 +16,8 @@ use Symfony\Component\Form\Extension\Core\Type\ButtonType;
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Form\Extension\Core\Type\DateTimeType;
use Symfony\Component\Form\Extension\Core\Type\IntegerType;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Tetranz\Select2EntityBundle\Form\Type\Select2EntityType;
@ -82,6 +84,7 @@ class UserType extends AbstractType
EntityType::class,
array("class" => "CadolesCoreBundle:Niveau01",
"label" => $session->get('labelniveau01'),
'placeholder' => '== Choisir '.$session->get('labelniveau01').' ==',
"choice_label" => "label",
"query_builder"=> function (EntityRepository $er) use($access,$perm,$userid) {
if($access=="config") {
@ -100,7 +103,17 @@ class UserType extends AbstractType
},
"disabled" => ($options["mode"]=="delete"||$options["masteridentity"]!="SQL"?true:false),
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px","readonly" => ($options["mode"]=="delete"?true:false))));
$builder->add('niveau01other',
TextType::class, array(
"label" =>"Autre ".$session->get('labelniveau01'),
"disabled" => ($options["mode"]=="delete"?true:false),
"required" => false,
"attr" => array("class" => "form-control", "style" => "margin-bottom:15px")
)
);
if($options["mode"]!="delete"&&$options["masteridentity"]=="SQL") {
$builder->add('password',
RepeatedType::class, array(
@ -360,6 +373,22 @@ class UserType extends AbstractType
}
}
if(!array_key_exists("visite",$fields)) $fields["visite"]["perm"]==2;
if($fields["visite"]["perm"]!=0) {
$builder->add('visitedate', DateTimeType::class, [
"label" => 'Date de dernière visite',
"disabled" => true,
"required" => ($fields["visite"]["perm"]==2),
"widget" => 'single_text',
]);
$builder->add('visitecpt', IntegerType::class, [
"label" => 'Nombre de visites',
"required" => ($fields["visite"]["perm"]==2),
"disabled" => true,
]);
}
# Avatar
$builder->add('avatar',HiddenType::class, array("empty_data" => "noavatar.png"));

View File

@ -257,6 +257,10 @@ cadoles_core_config_user_ajax_selectlist:
path: /config/user/ajax/selectlist
defaults: { _controller: CadolesCoreBundle:User:selectlist, access: config }
cadoles_core_config_mailing:
path: /config/mailing
defaults: { _controller: CadolesCoreBundle:User:mailing }
cadoles_core_config_importuser:
path: /config/importuser
defaults: { _controller: CadolesCoreBundle:User:importuser }
@ -368,6 +372,10 @@ cadoles_core_config_group_users:
path: /config/group/users/{id}
defaults: { _controller: CadolesCoreBundle:Group:users, access: config }
cadoles_core_config_group_statistic:
path: /config/group/statistic/{id}
defaults: { _controller: CadolesCoreBundle:Group:statistic, access: config }
cadoles_core_config_group_ajax_usersnotin:
path: /config/group/ajax/usersnotin/{id}
defaults: { _controller: CadolesCoreBundle:Group:ajaxusersnotin, access: config }
@ -417,6 +425,10 @@ cadoles_core_user_group_users:
path: /user/group/users/{id}
defaults: { _controller: CadolesCoreBundle:Group:users, access: user }
cadoles_core_user_group_statistic:
path: /user/group/statistic/{id}
defaults: { _controller: CadolesCoreBundle:Group:statistic, access: user }
cadoles_core_user_group_out:
path: /user/group/out/{id}
defaults: { _controller: CadolesCoreBundle:Group:out, access: user }
@ -467,8 +479,10 @@ cadoles_core_config_whitelist_ajax_list:
path: /config/whitelist/ajax/list
defaults: { _controller: CadolesCoreBundle:Whitelist:ajaxlist }
#== Statistic =============================================================================================================
cadoles_core_config_statistic:
path: /config/statistic
defaults: { _controller: CadolesCoreBundle:Statistic:list }
#== REST ==================================================================================================================
cadoles_core_rest_user:

View File

@ -31,13 +31,14 @@
<table class="table table-striped table-bordered table-hover" id="dataTables" style="width:100%">
<thead>
<tr>
<th width="130px" class="no-sort">Action</th>
<th width="160px" class="no-sort">Action</th>
<th class="no-sort text-center">Icone</th>
<th>Label</th>
<th>Ouvert</th>
<th class="no-sort {% if masteridentity=="SQL" %} no-visible {% endif %}">Filtre</th>
{% if portal_activate %}
<th>Groupe de Travail</th>
<th>Propriétaire</th>
<th class="text-center">Propriétaire</th>
{% if access=="config" %}
<th>Création Pages</th>
<th>Création Calendriers</th>
@ -57,10 +58,10 @@
{% block localjavascript %}
$(document).ready(function() {
$('#dataTables').DataTable({
columnDefs: [ { "targets": 'no-sort', "orderable": false },{ "targets": 'no-visible', "visible": false } ],
columnDefs: [ { "targets": 'no-sort', "orderable": false },{ "targets": 'no-visible', "visible": false },{"targets": "text-center", "className": "text-center"} ],
responsive: true,
iDisplayLength: 100,
order: [[ 1, "asc" ]],
order: [[ 2, "asc" ]],
processing: true,
serverSide: true,
ajax: "{{ path('cadoles_core_'~access~'_group_ajax_list') }}",

View File

@ -0,0 +1,131 @@
{% extends '@CadolesCore/base.html.twig' %}
{% block pagewrapper %}
<h1 class="page-header">Statistiques {{ group.label }}</h1>
<a class="btn btn-default" href={{ path('cadoles_core_'~access~'_group') }}>Fermer</a>
<br><br>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Compteur de visites journalière
</div>
<div class="panel-body">
<div id="groupcptvisite"></div>
</div>
</div>
<div class="row">
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre de message dans les tchat
</div>
<div class="panel-body">
<div id="groupcptmessage"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre d'articles de blog
</div>
<div class="panel-body">
<div id="groupcptblogarticle"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre de tâches
</div>
<div class="panel-body">
<div id="groupcptprojecttask"></div>
</div>
</div>
</div>
</div>
{% endblock %}
{% block localjavascript %}
$(document).ready(function() {
groupcptvisite();
groupcptmessage();
groupcptblogarticle();
groupcptprojecttask();
$(window).resize(function() {
window.groupcptvisite.redraw();
window.groupcptmessage.redraw();
window.groupcptblogarticle.redraw();
window.groupcptprojecttask.redraw();
});
});
function groupcptvisite() {
window.groupcptvisite = Morris.Area({
element: 'groupcptvisite',
data: [
{% set before = 0 %}
{% for date, cpt in groupcptvisite.value %}
{% set now = cpt - before %}
{% set before = cpt %}
{ x: '{{ date }}', a: {{ now }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ['Nombre de visites']
});
}
function groupcptmessage() {
window.groupcptmessage = Morris.Area({
element: 'groupcptmessage',
data: [
{% for date, cpt in groupcptmessage.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ['Nombre total de messages tchat']
});
}
function groupcptblogarticle() {
window.groupcptblogarticle = Morris.Area({
element: 'groupcptblogarticle',
data: [
{% for date, cpt in groupcptblogarticle.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ["Nombre total d'articles de blog"]
});
}
function groupcptprojecttask() {
window.groupcptprojecttask = Morris.Area({
element: 'groupcptprojecttask',
data: [
{% for date, cpt in groupcptprojecttask.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ["Nombre total de tâches"]
});
}
{% endblock %}

View File

@ -29,7 +29,8 @@
<th width="70px" class="no-sort">Action</th>
<th width="70px" class="no-sort">Avatar</th>
<th width="200px">Login</th>
<th>Email</th>
<th>Email</th>
<th class="no-sort">Visite</th>
{% if group.fgcanshare %}
<th class="no-sort">Manager</th>
{% endif %}
@ -56,6 +57,7 @@
<th width="70px" class="no-sort">Avatar</th>
<th width="200px">Login</th>
<th>Email</th>
<th class="no-sort">Visite</th>
{% if group.fgcanshare %}
<th class="no-sort">Manager</th>
{% endif %}

View File

@ -0,0 +1,54 @@
{% extends '@CadolesCore/base.html.twig' %}
{% block pagewrapper %}
{{ form_start(form) }}
<h1 class="page-header">
Mailing
</h1>
{{ form_widget(form.submit) }}
<br><br>
{% if app.session.flashbag.has('error') %}
<div class='alert alert-danger' style='margin: 5px 0px'>
<strong>Erreur</strong><br>
{% for flashMessage in app.session.flashbag.get('error') %}
{{ flashMessage }}<br>
{% endfor %}
</div>
{% endif %}
{% if app.session.flashbag.has('notice') %}
<div class='alert alert-info' style='margin: 5px 0px'>
<strong>Information</strong><br>
{% for flashMessage in app.session.flashbag.get('notice') %}
{{ flashMessage }}<br>
{% endfor %}
</div>
{% endif %}
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-pencil fa-fw"></i> Destinataires
</div>
<div class="panel-body">
{{ form_row(form.niveau01) }}
{% if form.groups is defined %}
{{ form_row(form.groups) }}
{% endif %}
</div>
</div>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-envelop fa-fw"></i> Mail
</div>
<div class="panel-body">
{{ form_row(form.subject) }}
{{ form_row(form.message) }}
</div>
</div>
{{ form_end(form) }}
{% endblock %}

View File

@ -32,7 +32,7 @@
<div class='alert alert-danger' style='margin: 5px 0px'>
<strong>Erreur</strong><br>
{% for flashMessage in app.session.flashbag.get('error') %}
{{ flashMessage }}<br>
{{ flashMessage | raw }}<br>
{% endfor %}
</div>
{% endif %}
@ -41,7 +41,7 @@
<div class='alert alert-info' style='margin: 5px 0px'>
<strong>Information</strong><br>
{% for flashMessage in app.session.flashbag.get('notice') %}
{{ flashMessage }}<br>
{{ flashMessage | raw }}<br>
{% endfor %}
</div>
{% endif %}
@ -68,8 +68,8 @@
<div class='alert alert-info' style='font-size: 80%;padding: 5px;margin-top: -10px;'>
Caractères interdits = accent, espace, caractères spéciaux sauf @ . - _<br>
Taille minimum = {{keyterm}} caractères
Doit être constitué de chiffres, de lettres et caractères spéciaux
Taille minimum = 5 caractères<br>
Formatez votre login sous la forme prenom.nom dans la mesure du possible
</div>
{% if form.password is defined %}
@ -94,6 +94,16 @@
{% if form.visible is defined %} {{ form_row(form.visible) }} {% endif %}
</div>
</div>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-pencil fa-fw"></i> Motivations
</div>
<div class="panel-body">
{{ form_row(form.motivation) }}
</div>
</div>
</div>
<div class="col-sm-6">
@ -105,6 +115,7 @@
{% if form.job is defined %} {{ form_row(form.job) }} {% endif %}
{% if form.position is defined %} {{ form_row(form.position) }} {% endif %}
{{ form_row(form.niveau01) }}
<div id="niveau01other">{{ form_row(form.niveau01other) }}</div>
{% if form.niveau02 is defined %} {{ form_row(form.niveau02) }} {% endif %}
</div>
</div>
@ -164,6 +175,10 @@
hideshow();
});
$(document.body).on("change","#registration_niveau01",function(){
hideshow();
});
$(document.body).on("change","#registration_niveau02",function(){
$.ajax({
method: "POST",
@ -188,6 +203,15 @@
$("#blockcity").hide();
$("#registration_birthplace").val([]).trigger('change');
}
niveau01=$("#registration_niveau01 option:selected").text().toLowerCase();
if(niveau01.startsWith("autre")) {
$("#niveau01other").show();
}
else {
$("#registration_niveau01other").val("");
$("#niveau01other").hide();
}
}
$(document).ready(function() {

View File

@ -0,0 +1,263 @@
{% extends '@CadolesCore/base.html.twig' %}
{% block pagewrapper %}
<h1 class="page-header">Statistiques</h1>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Compteur de visites journalière
</div>
<div class="panel-body">
<div id="totcptvisite"></div>
</div>
</div>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Compteur de visites journalière des groupes de travail
</div>
<div class="panel-body">
<div id="totcptvisitegroup"></div>
</div>
</div>
<div class="row">
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre de message dans les tchat
</div>
<div class="panel-body">
<div id="totcptmessage"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre d'articles de blog
</div>
<div class="panel-body">
<div id="totcptblogarticle"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> Evolution du nombre de tâches
</div>
<div class="panel-body">
<div id="totcptprojecttask"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> TOP 20 des groupes les plus visités
</div>
<div class="panel-body">
<div id="groupcptvisite"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> TOP 20 des groupes avec le plus de messages chat
</div>
<div class="panel-body">
<div id="groupcptmessage"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> TOP 20 des groupes avec le plus d'articles de blog
</div>
<div class="panel-body">
<div id="groupcptblogarticle"></div>
</div>
</div>
</div>
<div class="col col-md-6">
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-table fa-fw"></i> TOP 20 des groupes avec le plus de tâches
</div>
<div class="panel-body">
<div id="groupcptprojecttask"></div>
</div>
</div>
</div>
</div>
{% endblock %}
{% block localjavascript %}
$(document).ready(function() {
totcptvisite();
totcptvisitegroup();
totcptmessage();
totcptblogarticle();
totcptprojecttask();
groupcptvisite();
groupcptmessage();
groupcptblogarticle();
groupcptprojecttask();
$(window).resize(function() {
window.totcptvisite.redraw();
window.totcptvisitegroup.redraw();
window.totcptmessage.redraw();
window.totcptblogarticle.redraw();
window.totcptprojecttask.redraw();
});
});
function totcptvisite() {
window.totcptvisite = Morris.Area({
element: 'totcptvisite',
data: [
{% set before = 0 %}
{% for date, cpt in totcptvisite.value %}
{% set now = cpt - before %}
{% set before = cpt %}
{ x: '{{ date }}', a: {{ now }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ['Nombre de visites']
});
}
function totcptvisitegroup() {
window.totcptvisitegroup = Morris.Area({
element: 'totcptvisitegroup',
data: [
{% set before = 0 %}
{% for date, cpt in totcptvisitegroup.value %}
{% set now = cpt - before %}
{% set before = cpt %}
{ x: '{{ date }}', a: {{ now }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ['Nombre de visites des groupes']
});
}
function totcptmessage() {
window.totcptmessage = Morris.Area({
element: 'totcptmessage',
data: [
{% for date, cpt in totcptmessage.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ['Nombre total de messages tchat']
});
}
function totcptblogarticle() {
window.totcptblogarticle = Morris.Area({
element: 'totcptblogarticle',
data: [
{% for date, cpt in totcptblogarticle.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ["Nombre total d'articles de blog"]
});
}
function totcptprojecttask() {
window.totcptprojecttask = Morris.Area({
element: 'totcptprojecttask',
data: [
{% for date, cpt in totcptprojecttask.value %}
{ x: '{{ date }}', a: {{ cpt }} }{% if not loop.last %},{%endif%}
{% endfor %}
],
xkey: 'x',
ykeys: ['a'],
labels: ["Nombre total de tâches"]
});
}
function groupcptvisite() {
window.groupcptvisite = Morris.Donut({
element: 'groupcptvisite',
data: [
{% for cpt in groupcptvisite %}
{label: "{{ cpt.name|raw }}", value: {{ cpt.value }}}{% if not loop.last %},{%endif%}
{% endfor %}
],
resize: true,
redraw: true
});
}
function groupcptmessage() {
window.groupcptmessage = Morris.Donut({
element: 'groupcptmessage',
data: [
{% for cpt in groupcptmessage %}
{label: "{{ cpt.name|raw }}", value: {{ cpt.value }}}{% if not loop.last %},{%endif%}
{% endfor %}
],
resize: true,
redraw: true
});
}
function groupcptblogarticle() {
window.groupcptblogarticle = Morris.Donut({
element: 'groupcptblogarticle',
data: [
{% for cpt in groupcptblogarticle %}
{label: "{{ cpt.name|raw }}", value: {{ cpt.value }}}{% if not loop.last %},{%endif%}
{% endfor %}
],
resize: true,
redraw: true
});
}
function groupcptprojecttask() {
window.groupcptprojecttask = Morris.Donut({
element: 'groupcptprojecttask',
data: [
{% for cpt in groupcptprojecttask %}
{label: "{{ cpt.name|raw }}", value: {{ cpt.value }}}{% if not loop.last %},{%endif%}
{% endfor %}
],
resize: true,
redraw: true
});
}
{% endblock %}

View File

@ -27,7 +27,7 @@
<div class='alert alert-danger' style='margin: 5px 0px'>
<strong>Erreur</strong><br>
{% for flashMessage in app.session.flashbag.get('error') %}
{{ flashMessage }}<br>
{{ flashMessage | raw }}<br>
{% endfor %}
</div>
<br>
@ -37,7 +37,7 @@
<div class='alert alert-info' style='margin: 5px 0px'>
<strong>Information</strong><br>
{% for flashMessage in app.session.flashbag.get('notice') %}
{{ flashMessage }}<br>
{{ flashMessage | raw }}<br>
{% endfor %}
</div>
<br>
@ -46,7 +46,7 @@
{% if info is defined and info %}
<div class='alert alert-info' style='margin: 5px 0px'>
<strong>Information</strong><br>
{{ info }}<br>
{{ info | raw }}<br>
</div>
<br>
{% endif %}
@ -75,8 +75,8 @@
<div class='alert alert-info' style='font-size: 80%;padding: 5px;margin-top: -10px;'>
Caractères interdits = accent, espace, caractères spéciaux sauf @ . - _<br>
Taille minimum = {{keyterm}} caractères
Doit être constitué de chiffres, de lettres et caractères spéciaux
Taille minimum = 5 caractères<br>
Formatez votre login sous la forme prenom.nom dans la mesure du possible
</div>
{% if form.password is defined %}
@ -114,6 +114,7 @@
{% if form.job is defined %}{{ form_row(form.job) }}{% endif %}
{% if form.position is defined %}{{ form_row(form.position) }}{% endif %}
{{ form_row(form.niveau01) }}
<div id="niveau01other">{{ form_row(form.niveau01other) }}</div>
{% if form.niveau02 is defined %}{{ form_row(form.niveau02) }}{% endif %}
</div>
</div>
@ -261,6 +262,20 @@
</div>
</div>
</div>
{% if form.visitedate is defined %}
<div id="panelvisite" class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-user fa-fw"></i> Visite
</div>
<div class="panel-body">
{{ form_row(form.visitedate) }}
{{ form_row(form.visitecpt) }}
</div>
</div>
{% endif %}
</div>
</div>
@ -280,7 +295,7 @@
<table id="tbllistgroup" class="table table-striped table-bordered table-hover" style="width:100%">
<thead>
<tr>
<th width="70px">Action</th>
<th width="70px" class="no-sort">Action</th>
<th>Groupe</th>
</tr>
</thead>
@ -299,7 +314,7 @@
{% endif %}
<tr id="listgroup{{ group.id }}" style="{{ style }}">
<td><a style="cursor:pointer"><i class="fa fa-plus fa-fw" onclick="addLinkGroup({{ group.id }})"></i></a></td>
<td width="70px"><a style="cursor:pointer"><i class="fa fa-plus fa-fw" onclick="addLinkGroup({{ group.id }})"></i></a></td>
<td id="listgrouplabel{{ group.id }}">
{{ group.label }}
</td>
@ -366,13 +381,15 @@
{% block localjavascript %}
$(document).ready(function() {
{% if access=="profil" %}
{% if access=="user" %}
{% set color = app.session.get('color') %}
$(".sidebar").remove();
$("body").removeClass("body");
$("body").addClass("simple");
$("body").attr('style', 'background-color: #{{ color['colorbody'] }} !important');
$("#page-wrapper").css("margin","auto");
$("#page-wrapper").css("max-width","1000px");
$("#page-wrapper").css("border-left","none");
{% endif %}
// Vider le password
@ -402,6 +419,10 @@
hideshow();
});
$(document.body).on("change","#user_niveau01",function(){
hideshow();
});
$(document.body).on("change","#user_niveau02",function(){
$.ajax({
method: "POST",
@ -433,6 +454,15 @@
else {
$("#panelmodos").hide();
}
niveau01=$("#user_niveau01 option:selected").text().toLowerCase();
if(niveau01.startsWith("autre")) {
$("#niveau01other").show();
}
else {
$("#user_niveau01other").val("");
$("#niveau01other").hide();
}
}
@ -450,6 +480,14 @@
linkmodos+={{ modo.niveau01.id }}+",";
{% endfor %}
$("#user_linkmodos").val(linkmodos);
$('#tbllistgroup').DataTable({
columnDefs: [ { "targets": 'no-sort', "orderable": false },{ "targets": 'no-visible', "visible": false } ],
responsive: true,
iDisplayLength: 100,
processing: true,
order: [[ 1, "asc" ]],
});
});
function removeLinkGroup(id) {

View File

@ -45,6 +45,7 @@ td { font-size: 10px; }
<th class="no-sort {% if fields["group"] is defined and fields["group"].perm==0 %}no-visible{% endif %}">Groupes</th>
<th class="{% if fields["job"] is defined and fields["job"].perm==0 %}no-visible{% endif %}">Métier</th>
<th class="{% if fields["position"] is defined and fields["position"].perm==0 %}no-visible{% endif %}">Fonction</th>
<th class="{% if fields["visitedate"] is defined and fields["visitedate"].perm==0 %}no-visible{% endif %}">Visite</th>
<th class="{% if fields["role"] is defined and fields["role"].perm==0 %}no-visible{% endif %}">Rôle</th>
</tr>
</thead>

View File

@ -18,8 +18,10 @@
{%if viewniveau02 and user.niveau02%}<b>{{ labelniveau02 }}</b> = {{ user.niveau02.label }}<br>{% endif %}
{%if user.job %}<b>Métier</b> = {{ user.job }}<br>{%endif%}
{%if user.position %}<b>Fonction</b> = {{ user.position }}<br>{%endif%}
{%if user.postaladress %}<b>Adresse</b> = {{ user.postaladress }}<br><br>{%endif%}
{%if user.postaladress %}<b>Adresse</b> = {{ user.postaladress }}<br>{%endif%}
{%if user.visitedate %}<b>Date de dernière visite</b> = {{ user.visitedate|date('d/m/Y H:i') }}<br>{%endif%}
{%if user.visitecpt %}<b>Nombre de visites</b> = {{ user.visitecpt }}<br>{%endif%}
<br>
{% set fgtitle=false %}
{% for usergroup in user.groups %}
{% if usergroup.group.fgcanshare %}

View File

@ -15,9 +15,13 @@ use Cadoles\CronBundle\Entity\Cron;
class CronCommand extends ContainerAwareCommand
{
private $container;
private $em;
private $output;
private $filesystem;
private $rootlog;
use LockableTrait;
protected function configure()
@ -30,8 +34,8 @@ class CronCommand extends ContainerAwareCommand
protected function execute(InputInterface $input, OutputInterface $output)
{
$entityManager = $this->getContainer()->get('doctrine')->getManager();
$this->container = $this->getApplication()->getKernel()->getContainer();
$this->em = $this->container->get('doctrine')->getEntityManager();
$this->output = $output;
$this->filesystem = new Filesystem();
$this->rootlog = $this->getContainer()->get('kernel')->getRootDir()."/../var/logs/";
@ -48,9 +52,9 @@ class CronCommand extends ContainerAwareCommand
return 0;
}
$crons = $entityManager->getRepository('CadolesCronBundle:Cron')->toexec();
$crons = $this->em->getRepository('CadolesCronBundle:Cron')->toexec();
$i=0;
if($crons) {
$now=new \DateTime();
$this->writelnred('');
@ -67,7 +71,7 @@ class CronCommand extends ContainerAwareCommand
// Dans la synchro il y a un clear du manager ce qui perturbe totalement le manager de Core:Exec
// Il pert le lien avec la boucle sur crons
// Alors si dans le cron il y a la synchro alors on n'execute que lui le reste sera executé lors du prochain passage
$cronsynchro=$entityManager->getRepository('CadolesCronBundle:Cron')->find(100);
$cronsynchro=$this->em->getRepository('CadolesCronBundle:Cron')->find(100);
if($cronsynchro&&in_array($cronsynchro,$crons)) {
$crons=[$cronsynchro];
@ -83,8 +87,8 @@ class CronCommand extends ContainerAwareCommand
$now=new \DateTime();
$cron->setStartexecdate($now);
//$cron->setStatut(1);
$entityManager->persist($cron);
$entityManager->flush();
$this->em->persist($cron);
$this->em->flush();
// Récupération de la commande
$command = $this->getApplication()->find($cron->getCommand());
@ -111,7 +115,7 @@ class CronCommand extends ContainerAwareCommand
// Revenir sur le cron encours à cause du clear du manager présent dans la synchro
// Sinon le manager se pomme et génère des nouveaux enregistrement plutot que mettre à jour celui en cours
$cron=$entityManager->getRepository('CadolesCronBundle:Cron')->find($idcron);
$cron=$this->em->getRepository('CadolesCronBundle:Cron')->find($idcron);
}
catch(\Exception $e) {
$this->writelnred("JOB EN ERREUR");
@ -139,11 +143,14 @@ class CronCommand extends ContainerAwareCommand
if($returnCode!=1) {
$cron->setStatut(3);
if($cron->getRepeatcall()>0) $cron->setRepeatexec($cron->getRepeatexec()+1);
// Envoyer un mail à l'ensemble des administrateurs
$this->sendMailerror();
}
}
$entityManager->persist($cron);
$entityManager->flush();
$this->em->persist($cron);
$this->em->flush();
}
if($crons) {
@ -154,6 +161,37 @@ class CronCommand extends ContainerAwareCommand
}
}
private function sendMailerror() {
$appname="";
$config = $this->em->getRepository("CadolesCoreBundle:Config")->findOneBy(["id"=>"appname"]);
if($config) $appname = $config->getValue();
$noreply = $this->container->getParameter('noreply');
// Email à l'ensemble administrateurs pour les prévenir qu'il y a une personne à valider
$emailadmins= $this->em->createQueryBuilder()
->select('table.email')
->from("CadolesCoreBundle:User",'table')
->where('table.role = :value')
->setParameter("value", "ROLE_ADMIN")
->getQuery()
->getResult(\Doctrine\ORM\Query::HYDRATE_SCALAR);
$to=array();
$from = $noreply;
$fromName = $appname;
foreach($emailadmins as $emailadmin) {
array_push($to,$emailadmin["email"]);
}
$mail_params=array(
"subject" => $appname." : ERREUR SUR EXECUTION JOB",
"body_html"=> "ATTENTION UN JOB EST EN ERREUR. MERCI DE VERIFIER LES LOGS.",
"body_text"=> "ATTENTION UN JOB EST EN ERREUR. MERCI DE VERIFIER LES LOGS."
);
$message = $this->container->get('cadoles.core.service.mail');
$message->sendEmail("template", $mail_params, $to, $from, $fromName);
}
private function writelnred($string) {
$this->output->writeln('<fg=red>'.$string.'</>');
$this->filesystem->appendToFile($this->rootlog.'cron.log', $string."\n");

View File

@ -26,7 +26,7 @@ class CronexecCommand extends ContainerAwareCommand
protected function configure()
{
$this
->setName('Cron:Exec')
->setName('Cron:Run')
->setDescription("Executer les commandes présente dans le bus des commandes à exécuter à la volet")
;
}
@ -48,7 +48,7 @@ class CronexecCommand extends ContainerAwareCommand
$cronexecs=$this->em->getRepository("CadolesCronBundle:Cronexec")->findAll();
if($cronexecs) {
$this->writelnred('');
$this->writelnred('== Cron:Exec');
$this->writelnred('== Cron:Run');
$this->writelnred('==========================================================================================================');
foreach($cronexecs as $cron) {

View File

@ -0,0 +1,95 @@
<?php
namespace Cadoles\CronBundle\Command;
use Symfony\Bundle\FrameworkBundle\Command\ContainerAwareCommand;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\ArrayInput;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Filesystem\Filesystem;
use Symfony\Component\HttpFoundation\Response;
use Cadoles\CronBundle\Entity\Cron;
class DumpCommand extends ContainerAwareCommand
{
private $container;
private $em;
private $output;
private $filesystem;
private $rootlog;
private $datahost;
private $database;
private $username;
private $password;
private $path;
protected function configure()
{
$this
->setName('Cron:Dump')
->setDescription('Dump database for backup')
->addArgument('env', InputArgument::OPTIONAL, 'env Mail')
->addArgument('cronid', InputArgument::OPTIONAL, 'ID Cron Job')
->addArgument('lastchance', InputArgument::OPTIONAL, 'Lastchance to run the cron')
;
}
protected function execute(InputInterface $input, OutputInterface $output)
{
$this->container = $this->getApplication()->getKernel()->getContainer();
$this->em = $this->container->get('doctrine')->getEntityManager();
$this->output = $output;
$this->filesystem = new Filesystem();
$this->rootlog = $this->container->get('kernel')->getRootDir()."/../var/logs/";
$mailer_host = $this->getContainer()->getParameter('mailer_host');
$this->writelnred('');
$this->writelnred('== Cron:Dump');
$this->writelnred('==========================================================================================================');
$this->datahost = $this->getContainer()->getParameter('database_host');
$this->database = $this->getContainer()->getParameter('database_name') ;
$this->username = $this->getContainer()->getParameter('database_user') ;
$this->password = $this->getContainer()->getParameter('database_password') ;
$cmd = sprintf('mysqldump -h %s -B %s -u %s --password=%s'
, $this->datahost
, $this->database
, $this->username
, $this->password
);
$result = $this->runCommand($cmd);
if($result['exit_status'] == 0) {
$this->filesystem->dumpFile($this->rootlog."ninegate.sql", $result['output']);
}
$this->writeln('');
return 1;
}
protected function runCommand($command)
{
$command .=" >&1";
exec($command, $output, $exit_status);
return array(
"output" => $output
, "exit_status" => $exit_status
);
}
private function writelnred($string) {
$this->output->writeln('<fg=red>'.$string.'</>');
$this->filesystem->appendToFile($this->rootlog.'cron.log', $string."\n");
}
private function writeln($string) {
$this->output->writeln($string);
$this->filesystem->appendToFile($this->rootlog.'cron.log', $string."\n");
}
}

View File

@ -60,9 +60,9 @@ class InitDataCommand extends ContainerAwareCommand
$entity->setRepeatexec(0);
$entity->setRepeatinterval(60);
$entity->setNextexecdate($entity->getSubmitdate());
$entity->setJsonargument('{"message-limit":"100","env":"prod"}');
$this->entityManager->persist($entity);
}
$entity->setJsonargument('{"message-limit":"200","env":"prod"}');
$this->entityManager->persist($entity);
// Job synchronisation des comptes utilisateur
@ -139,6 +139,43 @@ class InitDataCommand extends ContainerAwareCommand
$entity->setNextexecdate($nextdate);
$this->entityManager->persist($entity);
}
// Job Statistic
// Toute les 24h à 23h30
$entity = $this->entityManager->getRepository('CadolesCronBundle:Cron')->find(210);
if(!$entity) {
$entity = new Cron;
$nextdate=$entity->getSubmitdate();
$nextdate->setTime(23,30);
$entity->setCommand("Core:Statistic");
$entity->setDescription("Cacul des indicateurs d'usages");
$entity->setId(210);
$entity->setStatut(2);
$entity->setRepeatcall(0);
$entity->setRepeatexec(0);
$entity->setRepeatinterval(86400);
$entity->setNextexecdate($nextdate);
$this->entityManager->persist($entity);
}
// Job Dump
// Toute les 24h à 2h00
$entity = $this->entityManager->getRepository('CadolesCronBundle:Cron')->find(220);
if(!$entity) {
$entity = new Cron;
$nextdate=$entity->getSubmitdate();
$nextdate->setTime(2,0);
$entity->setCommand("Cron:Dump");
$entity->setDescription("Sauvegarde de la BDD");
$entity->setId(220);
$entity->setStatut(2);
$entity->setRepeatcall(0);
$entity->setRepeatexec(0);
$entity->setRepeatinterval(86400);
$entity->setNextexecdate($nextdate);
$this->entityManager->persist($entity);
}
// CRON PORTAIL
// Job purge des registrations obsolètes
// Toute les 5mn

View File

@ -10,6 +10,9 @@ use Symfony\Bundle\FrameworkBundle\Console\Application;
use Symfony\Component\Console\Input\ArrayInput;
use Symfony\Component\Console\Output\BufferedOutput;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\HttpFoundation\BinaryFileResponse;
use Symfony\Component\HttpFoundation\ResponseHeaderBag;
use Cadoles\CronBundle\Entity\Cron;
use Cadoles\CronBundle\Form\CronType;
@ -70,7 +73,7 @@ class CronController extends Controller
// Order
switch($order[0]["column"]) {
case 1 :
$qb->orderBy('table.id',$order[0]["dir"]);
$qb->orderBy('table.nextexecdate',$order[0]["dir"]);
break;
case 2 :
$qb->orderBy('table.command',$order[0]["dir"]);
@ -81,9 +84,6 @@ class CronController extends Controller
case 4 :
$qb->orderBy('table.statut',$order[0]["dir"]);
break;
case 5 :
$qb->orderBy('table.nextexecdate',$order[0]["dir"]);
break;
}
// Execution de la requete d'affichage
@ -104,7 +104,7 @@ class CronController extends Controller
if($data->getRepeatCall()>0 AND $data->getRepeatCall()<=$data->getRepeatExec())
$nextexec="Déjà rejoué ".$data->getRepeatExec()." fois";
array_push($output["data"],array($action,$data->getId(),$data->getCommand(),$data->getDescription(),$data->getStatutLabel(),$nextexec));
array_push($output["data"],array($action,$nextexec,$data->getCommand(),$data->getDescription(),$data->getStatutLabel()));
}
// Retour
@ -189,18 +189,25 @@ class CronController extends Controller
return new Response(json_encode($content), 200);
}
public function logAction(Request $request, $id)
public function logAction()
{
$kernel = $this->get('kernel');
$path = $this->get('kernel')->getRootDir() . '/../var/logs/'.$id.'.log';
$content = file_get_contents($path);
return $this->render('CadolesCronBundle:Cron:logs.html.twig', [
'useheader' => true,
'usemenu' => false,
'usesidebar' => true,
"title" => "LOG = ".$id,
"content" => $content
'usesidebar' => true
]);
}
public function getlogAction(Request $request, $id)
{
$kernel = $this->get('kernel');
if($id=="dump")
$file = $this->get('kernel')->getRootDir() . '/../var/logs/ninegate.sql';
else
$file = $this->get('kernel')->getRootDir() . '/../var/logs/'.$id.'.log';
$response = new BinaryFileResponse($file);
$response->setContentDisposition(ResponseHeaderBag::DISPOSITION_ATTACHMENT);
return $response;
}
}

View File

@ -23,6 +23,9 @@ cadoles_cron_config_cronexecread:
defaults: { _controller: CadolesCronBundle:Cron:cronexecread }
cadoles_cron_config_log:
path: /config/cron/log/{id}
path: /config/cron/log
controller: CadolesCronBundle:Cron:log
defaults: { id: "cron" }
cadoles_cron_config_getlog:
path: /config/cron/getlog/{id}
controller: CadolesCronBundle:Cron:getlog

View File

@ -17,11 +17,10 @@
<thead>
<tr>
<th width="70px" class="no-sort">Action</th>
<th>Order</th>
<th>Prochaine exécution</th>
<th>Command</th>
<th>Description</th>
<th>Statut</th>
<th>Prochaine exécution</th>
</tr>
</thead>
</table>

View File

@ -1,19 +1,10 @@
{% extends '@CadolesCore/base.html.twig' %}
{% block pagewrapper %}
<h1 class="page-header">{{ title }}</h1>
<h1 class="page-header">Télécharger les logs</h1>
<a class="btn btn-default" href={{ path("cadoles_cron_config_log",{"id":"cron"}) }}>Log CRON</a>
<a class="btn btn-default" href={{ path("cadoles_cron_config_log",{"id":"prod"}) }}>Log PROD</a>
<a class="btn btn-default" href={{ path("cadoles_cron_config_log",{"id":"dev"}) }}>Log DEV</a>
<br><br>
<div class="panel panel-primary">
<div class="panel-heading">
<i class="fa fa-pencil fa-fw"></i> Logs
</div>
<div class="panel-body">
{{ content | nl2br }}
</div>
</div>
<a class="btn btn-default" href={{ path("cadoles_cron_config_getlog",{"id":"cron"}) }}>Log CRON</a>
<a class="btn btn-default" href={{ path("cadoles_cron_config_getlog",{"id":"prod"}) }}>Log PROD</a>
<a class="btn btn-default" href={{ path("cadoles_cron_config_getlog",{"id":"dev"}) }}>Log DEV</a>
<a class="btn btn-default" href={{ path("cadoles_cron_config_getlog",{"id":"dump"}) }}>Dump de la Base</a>
{% endblock %}

View File

@ -515,6 +515,24 @@ class PageController extends Controller
}
*/
// Compteur de visite
if($this->getUser()) {
$group=$em->getRepository("CadolesCoreBundle:Group")->find($groupid);
if($group && $group->getFgcanshare()) {
$usergroup=$em->getRepository("CadolesCoreBundle:UserGroup")->findoneby(["group"=>$group,"user"=>$this->getUser()]);
if($usergroup) {
$visitedate=$usergroup->getVisitedate();
if($visitedate) $visitedate->add(new \DateInterval("PT1H"));
$now=new \DateTime();
if($visitedate<$now) {
$usergroup->setVisitedate($now);
$usergroup->setVisitecpt($usergroup->getVisitecpt()+1);
$em->persist($usergroup);
$em->flush();
}
}
}
}
// Type Calendrier
if($entity->getPageCategory()->getId()==-100) {

View File

@ -130,11 +130,25 @@ class PagewidgetController extends Controller
}
$entity->setParameter($param);
$em = $this->getDoctrine()->getManager();
$em->persist($entity);
$em->flush();
// Notification création widget
$groups=$page->getGroups();
if($groups[0]) {
if($groups[0]->getFgcanshare()) {
$message="Création Widget ".$entity->getName();
$usergroup=$em->getRepository("CadolesCoreBundle:Usergroup")->findOneBy(["group"=>$groups[0],"user"=>$this->getUser()]);
if($usergroup) {
$key=$usergroup->getKeyvalue();
$websocket = $this->container->get('cadoles.websocket.pushmessage')->send($key,$this->getUser()->getId(),$groups[0]->getId(),$message);
}
}
}
if($access=="config") {
if($by=="view")
return $this->redirect($this->generateUrl('cadoles_portal_config_page_view',["id"=>$idpage]));
@ -267,6 +281,19 @@ class PagewidgetController extends Controller
if(!$canupdate) throw $this->createNotFoundException('Permission denied');
}
// Notification création widget
$groups=$entity->getPage()->getGroups();
if($groups[0]) {
if($groups[0]->getFgcanshare()) {
$message="Suppression Widget ".$entity->getName();
$usergroup=$em->getRepository("CadolesCoreBundle:Usergroup")->findOneBy(["group"=>$groups[0],"user"=>$this->getUser()]);
if($usergroup) {
$key=$usergroup->getKeyvalue();
$websocket = $this->container->get('cadoles.websocket.pushmessage')->send($key,$this->getUser()->getId(),$groups[0]->getId(),$message);
}
}
}
// Supression du pagewidget
$em->remove($entity);
$em->flush();

View File

@ -352,6 +352,22 @@ class ProjectController extends Controller
if (!$entity) throw $this->createNotFoundException('Unable to find entity.');
}
// On recherche la premiere page associé au groupe du projet
$idpage=null;
if($id!=0) {
$groups=$entity->getGroups();
if($groups) {
if($groups[0]->getFgcanshare()) {
$pages=$groups[0]->getPages();
if($pages) {
$idpage=$pages[0]->getId();
$groups=$pages[0]->getGroups();
$idgroup=$groups[0]->getId();
}
}
}
}
// Permissions
$user=$this->getUser();
if($access=="config") {
@ -415,7 +431,9 @@ class ProjectController extends Controller
'projects' => $projects,
'countarticles' => $count,
'pagination' => $pagination,
'page' => $page
'page' => $page,
'idpage' => $idpage,
'idgroup' => $idgroup
]);
}

View File

@ -28,14 +28,16 @@ class ProjecttaskController extends Controller
return $this->createForm(ProjecttaskType::class, $entity, [
"mode" => "update",
"access" => $access,
"user" => $this->getUser()
"user" => $this->getUser(),
"projecttask" => $entity
]);
}
else {
return $this->createForm(ProjecttaskType::class, $entity, [
"mode" => "submit",
"access" => $access,
"user" => $this->getUser()
"user" => $this->getUser(),
"projecttask" => $entity
]);
}
}
@ -48,7 +50,13 @@ class ProjecttaskController extends Controller
if($project) $entity->setProject($project);
$entity->setPriority(0);
$entity->setPercentage(0);
$pageid=$request->get("page");
if($pageid) {
$page=$em->getRepository("CadolesPortalBundle:Page")->find($pageid);
$groups=$page->getGroups();
$idgroup=$groups[0]->getId();
}
$form = $this->entityForm($entity,$access);
$form->handleRequest($request);
@ -76,7 +84,10 @@ class ProjecttaskController extends Controller
}
}
return $this->redirect($this->generateUrl('cadoles_portal_'.$access.'_projecttask_view',["id"=>$entity->getId()]));
if(is_null($pageid))
return $this->redirect($this->generateUrl('cadoles_portal_'.$access.'_projecttask_view',["id"=>$entity->getId()]));
else
return $this->redirect($this->generateUrl('cadoles_portal_'.$access.'_page_view',["id"=>$pageid,"usage"=>"group","group"=>$idgroup]));
}
return $this->render($this->labelentity.':edit.html.twig', [
@ -87,7 +98,8 @@ class ProjecttaskController extends Controller
'entity' => $entity,
'mode' => "submit",
'access' => $access,
'form' => $form->createView()
'form' => $form->createView(),
'pageid' => $pageid
]);
}
@ -186,6 +198,21 @@ class ProjecttaskController extends Controller
$entity = $em->getRepository($this->labelentity)->find($id);
if (!$entity) throw $this->createNotFoundException('Unable to find entity.');
// On recherche la premiere page associé au groupe du projet
$groups=$entity->getProject()->getGroups();
$idpage=null;
$idgroup=null;
if($groups) {
if($groups[0]->getFgcanshare()) {
$pages=$groups[0]->getPages();
if($pages) {
$idpage=$pages[0]->getId();
$groups=$pages[0]->getGroups();
$idgroup=$groups[0]->getId();
}
}
}
// Permissions
$user=$this->getUser();
if($access=="config") {
@ -278,7 +305,9 @@ class ProjecttaskController extends Controller
'canadd' => $canadd,
'projects' => $projects,
'projecttasks' => $projecttasks,
'files' => $files
'files' => $files,
'idpage' => $idpage,
'idgroup' => $idgroup,
]);
}

View File

@ -23,6 +23,7 @@ class ProjecttaskType extends AbstractType
public function buildForm(FormBuilderInterface $builder, array $options)
{
$user=$options['user'];
$projecttask=$options['projecttask'];
$builder
->add('submit', SubmitType::class, [
@ -49,6 +50,7 @@ class ProjecttaskType extends AbstractType
->add('end', DateType::class, [
"label" => 'A Réaliser avant le',
"required" => false,
"widget" => 'single_text',
])
->add('percentage', IntegerType::class, [
@ -79,28 +81,46 @@ class ProjecttaskType extends AbstractType
]);
}
else {
$builder
->add('project', EntityType::class, [
'label' => 'Projet associé',
'class' => 'CadolesPortalBundle:Project',
'choice_label' => 'name',
"disabled" => ($options["mode"]=="update"?true:false),
'placeholder' => '-- Sélectionnez un Projet --',
'query_builder' => function(EntityRepository $er) use ($user) {
$qb=$er->createQueryBuilder('project');
return $qb->select('project')
->where('project.user=:user')
->orwhere(':user MEMBER OF project.writers')
if(!$projecttask->getProject()) {
$builder
->add('project', EntityType::class, [
'label' => 'Projet associé',
'class' => 'CadolesPortalBundle:Project',
'choice_label' => 'name',
"disabled" => ($options["mode"]=="update"?true:false),
'placeholder' => '-- Sélectionnez un Projet --',
'query_builder' => function(EntityRepository $er) use ($user) {
$qb=$er->createQueryBuilder('project');
return $qb->select('project')
->where('project.user=:user')
->orwhere(':user MEMBER OF project.writers')
->from('CadolesCoreBundle:UserGroup','usergroup')
->orwhere('usergroup.group MEMBER OF project.groups AND usergroup.user=:user')
->from('CadolesCoreBundle:UserGroup','usergroup')
->orwhere('usergroup.group MEMBER OF project.groups AND usergroup.user=:user')
->from('CadolesCoreBundle:User','user')
->andwhere("user=:user")
->from('CadolesCoreBundle:User','user')
->andwhere("user=:user")
->setparameter('user',$user);
},
]);
->setparameter('user',$user);
},
]);
}
else {
$builder
->add('project', EntityType::class, [
'label' => 'Projet associé',
'class' => 'CadolesPortalBundle:Project',
'choice_label' => 'name',
"disabled" => ($options["mode"]=="update"?true:false),
'placeholder' => '-- Sélectionnez un Projet --',
'query_builder' => function(EntityRepository $er) use ($projecttask) {
$qb=$er->createQueryBuilder('project');
return $qb->select('project')
->where('project.id=:project')
->setparameter('project',$projecttask->getProject()->getId());
},
]);
}
}
$builder->add('user',
@ -132,7 +152,8 @@ class ProjecttaskType extends AbstractType
'data_class' => 'Cadoles\PortalBundle\Entity\Projecttask',
'mode' => 'string',
'access' => 'string',
'user' => 'Cadoles\CoreBundle\Entity\User'
'user' => 'Cadoles\CoreBundle\Entity\User',
'projecttask' => 'Cadoles\PortalBundle\Entity\Projecttask'
]);
}
}

View File

@ -386,7 +386,7 @@
else {
var myclass="";
if(forcereload) myclass="pageframereload";
$("#pagecontainer").append("<iframe id='frameitem-"+id+"' class='pageframe "+myclass+"' src='"+url+"' style='border:none; width:100%'></iframe>");
$("#pagecontainer").append("<iframe onload='this.contentWindow.focus()' id='frameitem-"+id+"' class='pageframe "+myclass+"' src='"+url+"' style='border:none; width:100%'></iframe>");
}
resizeFrame();
@ -428,7 +428,7 @@
else {
var myclass="";
if(forcereload) myclass="pageframereload";
$("#pagecontainer").append("<iframe id='page-"+id+"' data-category='"+catid+"' class='pageframe "+myclass+"' src='"+url+"' style='border:none; width:100%'></iframe>");
$("#pagecontainer").append("<iframe onload='this.contentWindow.focus()' id='page-"+id+"' data-category='"+catid+"' class='pageframe "+myclass+"' src='"+url+"' style='border:none; width:100%'></iframe>");
}
// Détruire le badge associé car normalement de fait on a lu les notif
@ -436,7 +436,6 @@
$("#badge-"+groupid).remove()
}
// Cacher les actions possibles sur la page
$("#menuupdate").hide();
$("#menushare").hide();
@ -456,14 +455,17 @@
if(usage=="group") $("#menuwidgetgroup").show();
}
// On resize les frame
resizeFrame();
// Mettre le focus dans la frame
//$("#page-"+id).contentWindow.focus();
}
// Affichages des pages
function showGoto(url) {
$("#pagecontainer").append("<iframe id='goto' class='pageframe pageframereload' src='"+url+"' style='border:none; width:100%'></iframe>");
$("#pagecontainer").append("<iframe onload='this.contentWindow.focus()' id='goto' class='pageframe pageframereload' src='"+url+"' style='border:none; width:100%'></iframe>");
// On resize les frame
resizeFrame();

View File

@ -22,7 +22,7 @@
{% endif %}
<div id="pageiframe" style="{% if entity.maxwidth>0%} max-width:{{ entity.maxwidth }}px; margin:auto; {% endif %}">
<iframe src="{{entity.url|replace({'#login#': username})}}" id="frameContent" style="border:none;" width="100%" height="100%"></iframe>
<iframe onload='this.contentWindow.focus()' src="{{entity.url|replace({'#login#': username})}}" id="frameContent" style="border:none;" width="100%" height="100%"></iframe>
</div>
{% endblock %}

View File

@ -328,7 +328,7 @@
// Suppression d'un widget
function delWidget(idwidget) {
var txt;
var r = confirm("Confirmez-vous la suppression de ce widget ?");
var r = confirm("ATTENTION\nConfirmez-vous la suppression de ce widget ?\n\nL'ensemble du contenu sera définitivement perdu !!");
if (r == true) {
$.ajax({
method: "POST",

View File

@ -15,8 +15,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-alert" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -30,8 +30,8 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}

View File

@ -21,19 +21,19 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-blog" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if access=="config" %}
<a href='{{ path('cadoles_portal_config_blog') }}' style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
<a title="Gérer mes Blogs" href='{{ path('cadoles_portal_config_blog') }}' style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
{% else %}
{% set idblog = "" %}
{% set url= path('cadoles_portal_user_blog_view') %}
{% if usage=="group" and firstblog is defined %}
{% set url= path('cadoles_portal_user_blog_view',{id:firstblog}) %}
{% endif %}
<a onClick="showFrameitem('blog','{{ url }}',true)" style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
<a title="Gérer mes Blogs" onClick="showFrameitem('blog','{{ url }}',true)" style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
{% endif %}
</div>

View File

@ -37,12 +37,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}
<i class="fa fa-plus fa-fw" onClick="addBookmark({{ entity.id }},false)" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-plus fa-fw" title="Ajouter un Favori" onClick="addBookmark({{ entity.id }},false)" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}
@ -99,7 +99,7 @@
{% if canadd %}
<div class="grid-item {{ stylegrid }}">
<div onClick="addBookmark({{ entity.id }},false)" class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div title="Ajouter un Favori" onClick="addBookmark({{ entity.id }},false)" class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div class="item-link clearfix">
<div class="grid-item-logo">
<img class="grid-item-img imageshadow" height="110" src="/{{ alias }}/uploads/icon/icon_add.png">

View File

@ -20,17 +20,17 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-calendar" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if access=="config" %}
<a href='{{ path('cadoles_portal_config_calendar') }}' style="{{ stylewidgetmenu }}"><i class="fa fa-paper-plane fa-fw"></i></a>
<a title="Gérer mes Calendriers" href='{{ path('cadoles_portal_config_calendar') }}' style="{{ stylewidgetmenu }}"><i class="fa fa-paper-plane fa-fw"></i></a>
{% else %}
{% set url= path('cadoles_portal_'~access~'_calendar_view') %}
{% if usage=="group" and firstcalendar is defined %}
{% set url= path('cadoles_portal_'~access~'_calendar_view',{id:firstcalendar}) %}
{% endif %}
<a onClick="showFrameitem('calendar','{{ url }}',true)" style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
<a title="Gérer mes Calendriers" onClick="showFrameitem('calendar','{{ url }}',true)" style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
{% endif %}
</div>

View File

@ -29,8 +29,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-chat" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -14,8 +14,8 @@
{% if canupdate %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}

View File

@ -28,12 +28,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'all'}) }}');" title='Ajouter des fichiers'><i class="fa fa-plus fa-fw"></i></a>
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'all'}) }}');" title='Ajouter des Fichiers'><i class="fa fa-plus fa-fw"></i></a>
{% endif %}
</div>
{% endif %}
@ -96,13 +96,13 @@
{% if canadd %}
<div class="grid-item grid-small">
<div data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'all'}) }}');" title='Ajouter des fichiers' class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'all'}) }}');" title='Ajouter des Fichiers' class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div class="item-link clearfix">
<div class="grid-item-logo">
<img class="grid-item-img imageshadow" height="110" src="/{{ alias }}/uploads/icon/icon_add.png">
</div>
<div class="grid-item-title">
<h2>Ajouter un fichier</h2>
<h2>Ajouter des Fichiers</h2>
</div>
</div>
</div>

View File

@ -39,8 +39,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-flux" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -25,8 +25,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-frame" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -28,12 +28,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'image'}) }}');" title='Ajouter des fichiers'><i class="fa fa-plus fa-fw"></i></a>
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'image'}) }}');" title='Ajouter des Images'><i class="fa fa-plus fa-fw"></i></a>
{% endif %}
</div>
{% endif %}
@ -83,14 +83,14 @@
{% if canadd %}
<div class="grid-item grid-list" style="{{ stylewidgetbodyreverse }};">
<div class="grid-item-content">
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'image'}) }}');" title='Ajouter des fichiers'>
<a style="{{ stylewidgetmenu }}" data-toggle="modal" data-target="#mymodal" onClick="ModalLoad('mymodal','Fichiers','{{ path('cadoles_core_'~access~'_file_upload',{'id': 'widget-'~entity.id,'type':'image'}) }}');" title='Ajouter des Images'>
<div class="item-link clearfix">
<div class="grid-item-logo">
<img class="grid-item-img imageshadow" height="110" src="/{{ alias }}/uploads/icon/icon_add.png" />
</div>
<div class="grid-item-title">
<h2 style="{{ stylewidgetbodyreverse }}">Ajouter une image</h2>
<h2 style="{{ stylewidgetbodyreverse }}">Ajouter des Images</h2>
</div>
</div>
</a>

View File

@ -22,12 +22,12 @@
{% if canupdate %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}
<a href="{{ path('cadoles_core_user_group_submit') }}" target="_top">
<a title="Ajouter un Groupe" href="{{ path('cadoles_core_user_group_submit') }}" target="_top">
<i class="fa fa-plus fa-fw" style="{{ stylewidgetmenu }}"></i>
</a>
{% endif %}
@ -76,7 +76,7 @@
{% if canadd %}
<div class="grid-item grid-small">
<div class="grid-item-content" style="{{ stylewidgetbodyreverse }};">
<a href="{{path('cadoles_core_user_group_submit')}}" target="_top" style="{{ stylewidgetbodyreverse }};">
<a title="Ajouter un Groupe" href="{{path('cadoles_core_user_group_submit')}}" target="_top" style="{{ stylewidgetbodyreverse }};">
<div class="item-link clearfix">
<div class="grid-item-logo">
@ -85,7 +85,7 @@
<div class="grid-item-title">
<h2>Ajouter un groupe</h2>
<h2>Ajouter un Groupe</h2>
</div>
</div>
</a>

View File

@ -41,8 +41,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-groupmessage" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -23,8 +23,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-info" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -37,12 +37,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd and access!="config"%}
<i class="fa fa-plus fa-fw" onClick="addBookmark({{ entity.id }},true)" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-plus fa-fw" title="Ajouter un Favori" onClick="addBookmark({{ entity.id }},true)" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}
@ -176,14 +176,14 @@
{% if (canadd and access!="config") %}
<div class="grid-item {{ stylegrid }}">
<div onClick="addBookmark({{ entity.id }},true)" class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div title="Ajouter un Favori" onClick="addBookmark({{ entity.id }},true)" class="grid-item-content" style="background-color: #{{color['main']}};cursor:pointer;">
<div class="item-link clearfix">
<div class="grid-item-logo">
<img class="grid-item-img imageshadow" height="110" src="/{{ alias }}/uploads/icon/icon_add.png">
</div>
<div class="grid-item-title">
<h2>Ajouter</h2>
<span>Ajouter un Favoris</<span>
<span>Ajouter un Favori</<span>
</div>
</div>
</div>
@ -243,7 +243,7 @@
<a style="cursor:pointer" class="item-preview"><i style="color: #FFF" class="fa fa-info" title="Informations sur ce service"></i></a>
{% endif %}
{% if canadd %}
<a style="cursor:pointer" onClick="heartBookmark({{ item.id }})" class="item-heart"><i style="color: #FFF" class="fa fa-heart" title="Ajouter aux favoris"></i></a>
<a style="cursor:pointer" onClick="heartBookmark({{ item.id }})" class="item-heart"><i style="color: #FFF" class="fa fa-heart" title="Ajouter aux Favoris"></i></a>
{% endif %}
{% if item.protected and not app.user %}

View File

@ -37,12 +37,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd and access!="config"%}
<a href="{{ path('cadoles_portal_user_page_application') }}">
<a title="Ajouter une Application" href="{{ path('cadoles_portal_user_page_application') }}">
<i class="fa fa-plus fa-fw" style="{{ stylewidgetmenu }}"></i>
</a>
{% endif %}
@ -195,14 +195,14 @@
{% if canadd %}
<div class="grid-item {{ stylegrid }}">
<div class="grid-item-content" style="background-color: #{{colormain}};cursor:pointer;">
<a href="{{ path('cadoles_portal_user_page_application') }}">
<a title="Ajouter une Application" href="{{ path('cadoles_portal_user_page_application') }}">
<div class="item-link clearfix">
<div class="grid-item-logo">
<img class="grid-item-img imageshadow" height="110" src="/{{ alias }}/uploads/icon/icon_add.png">
</div>
<div class="grid-item-title">
<h2>Ajouter</h2>
<span>Ajouter un Favoris</<span>
<span>Ajouter une Application</<span>
</div>
</div>
</a>

View File

@ -28,8 +28,8 @@
{% if canupdate %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}

View File

@ -28,8 +28,8 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}

View File

@ -21,19 +21,19 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-project" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if access=="config" %}
<a href='{{ path('cadoles_portal_config_project') }}' style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
{% else %}
{% set idproject = "" %}
{% set url= path('cadoles_portal_user_project_view') %}
{% set url= path('cadoles_portal_user_projecttask_submit') %}
{% if usage=="group" and firstproject is defined %}
{% set url= path('cadoles_portal_user_project_view',{id:firstproject}) %}
{% set url= path('cadoles_portal_user_projecttask_submit',{idproject:firstproject,page:entity.page.id}) %}
{% endif %}
<a onClick="showFrameitem('project','{{ url }}',true)" style="{{ stylewidgetmenu }}"><i class="fa fa-plus fa-fw"></i></a>
<a onClick="showFrameitem('project','{{ url }}',true)" style="{{ stylewidgetmenu }}" title="Ajouter une Tâche"><i class="fa fa-plus fa-fw"></i></a>
{% endif %}
</div>
@ -61,36 +61,30 @@
{% set colortask = projecttask.projecttasktag.color %}
{% endif %}
<div class="grid-item-content" style="background-color:#{{ colortask }}">
<a href="{{ path('cadoles_portal_'~access~'_projecttask_view',{'id':projecttask.id}) }}">
<a title="Voir la Tâche" href="{{ path('cadoles_portal_'~access~'_projecttask_view',{'id':projecttask.id,page:entity.page.id}) }}">
<div class="item-link clearfix">
<div class="grid-item-logo" style="height:55px;width:10%; text-align: center;">
{% if projecttask.user is empty %}
<img class='grid-item-img avatar' src="/{{ alias }}/uploads/avatar/{{ projecttask.owner.avatar }}" style="width:55px; height:auto">
{% else %}
<img class='grid-item-img avatar' src="/{{ alias }}/uploads/avatar/{{ projecttask.user.avatar }}" style="width:55px; height:auto">
{% endif %}
</div>
<div class="grid-item-title" style="width:90%">
<div class="grid-item-logo" style="width:10%; margin:0px; text-align: center;">
{% if projecttask.user is empty %}
<img class='grid-item-img avatar' src="/{{ alias }}/uploads/avatar/{{ projecttask.owner.avatar }}" style="width:55px; height:auto">
{% else %}
<img class='grid-item-img avatar' src="/{{ alias }}/uploads/avatar/{{ projecttask.user.avatar }}" style="width:55px; height:auto">
{% endif %}
</div>
<div class="grid-item-title" style="width:90%; position:initial; display: inline-block; padding:0px">
<h2 style="line-height:18px;height:auto;padding-left:5px;">{{projecttask.name}}</h2>
<h2 style="max-height: 40px; overflow-y: hidden;line-height:18px;">{{projecttask.name}}</h2>
<div class="pull-left" style="font-size:9px;">Affectée à
<div style="font-size:9px; display:inline-block; width:40%;padding-left:5px;">Affectée à
{% if projecttask.user is empty %}
{{ projecttask.owner.username }}
{% else %}
{{ projecttask.user.username }}
{% endif %}
<br>Crée le {{ projecttask.submit|date("d/m/Y à H:i") }}
<br>Dans le project {{projecttask.project.name }}
<br>Dans le projet {{projecttask.project.name }}
</div>
<div class="pull-right" style="margin-top:-5px; width:80px; text-align: center;">
<div style="font-size:35px; line-height:30px">
{{ projecttask.percentage }}<i style="font-size:12px">%</i>
</div>
</div>
<div class="pull-right" style="text-align: right; font-size:9px;">
<div style="text-align: right; font-size:9px; display:inline-block; width:35%;">
Priorité = {{ projecttask.priority }}</br>
Avant le = {{ projecttask.end|date("d/m/Y") }}</br>
{% if projecttask.projecttasktag %}
@ -100,6 +94,11 @@
Statut = {{ projecttask.projecttaskstatus.name }}<br>
{% endif %}
</div>
<div style="margin-top:-5px; text-align: right; display:inline-block; width:20%;">
<div style="font-size:35px; line-height:30px">
{{ projecttask.percentage }}<i style="font-size:12px">%</i>
</div>
</div>
</div>

View File

@ -20,8 +20,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-separator" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -27,12 +27,12 @@
{% if canupdate or canadd %}
<div class="widgetmenu">
{% if canupdate %}
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
{% if canadd %}
<i class="fa fa-th fa-fw" onClick="listSlide({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i title="Gérer le Carrousel" class="fa fa-th fa-fw" onClick="listSlide({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
{% endif %}
</div>
{% endif %}

View File

@ -20,8 +20,8 @@
<div class="widget {%if entity.border %} widget-bordered {%else%} widget-notbordered {%endif%} widget-url" data-id="{{ entity.id }}" loc="{{ entity.loc }}" style="{{ stylewidget }}" height="{{ entity.height }}px">
{% if canupdate %}
<div class="widgetmenu">
<i class="fa fa-trash fa-fw" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-trash fa-fw" title="Supprimer le Widget" onClick="delWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
<i class="fa fa-file fa-fw" title="Modifier le Widget" onClick="modWidget({{ entity.id }})" style="{{ stylewidgetmenu }}"></i>
</div>
{% endif %}

View File

@ -12,8 +12,14 @@
<a href='{{ path('cadoles_portal_config_project_delete', { id: entity.id }) }}' data-method='delete' data-confirm='Êtes-vous sûr de vouloir supprimer ?' title='Supprimer'><i class='fa fa-trash fa-fw'></i></a>
</div>
{% endif %}
<div style="margin:10px 0px 10px 0px; text-align:left; display:inline-block;width:49%">
{% if not idpage is empty %}
<a href="{{path('cadoles_portal_user_page_view',{id:idpage,usage:'group',group:idgroup})}}" class="btn btn-default">Revenir sur le Groupe</a>
{% endif %}
</div>
<div style="margin:10px 0px 10px 0px; text-align:right;">
<div style="margin:10px 0px 10px 0px; text-align:right; display:inline-block;width:50%">
<label for="alltask" class="control-label">Afficher les tâches fermées</label>
<input id="alltask" name="alltask" type="checkbox" class="switch" style="margin-right:20px">

View File

@ -19,7 +19,11 @@
{% set projectid=entity.project.id %}
{%endif%}
<a class="btn btn-default" href='{{ path('cadoles_portal_'~access~'_project_view',{'id':projectid})}}'>Annuler</a>
{% if pageid is empty %}
<a class="btn btn-default" href='{{ path('cadoles_portal_'~access~'_project_view',{'id':projectid})}}'>Annuler</a>
{% else %}
<a class="btn btn-default" href="{{path('cadoles_core_home',{id:pageid})}}" target="_top">Annuler</a>
{% endif %}
{% endif %}
{% if mode=="update" %}

View File

@ -35,7 +35,12 @@
<a href="{{ path('cadoles_portal_config_project_view', {id:entity.project.id})}}">{{ entity.project.name }}</a>
</div>
{% else %}
<br>
<div style="margin:10px 0px 10px 0px; text-align:left; display:inline-block;width:49%">
{% if not idpage is empty %}
<a href="{{path('cadoles_portal_user_page_view',{id:idpage,usage:'group',group:idgroup})}}" class="btn btn-default">Revenir sur le Groupe</a>
{% endif %}
</div>
<ul class="nav navbar-default nav-pills">
<li id="menuproject-0" class="{% if entity.id is not defined %}active{%endif%}" style="cursor:pointer">
<a href="{{ path("cadoles_portal_user_project_view") }}">

View File

@ -55,17 +55,34 @@ class ChatController extends Controller
}
// Récupération des message du groupe
$messages=$em->getRepository("CadolesWebsocketBundle:Message")->findBy(["group"=>$group],["submitdate"=>"DESC"],30);
// Récupération des message parent du groupe
$messages=$em->getRepository("CadolesWebsocketBundle:Message")->findBy(["group"=>$group,"parent"=>null],["submitdate"=>"DESC"],30);
foreach($messages as $message) {
$haveread = ($message->getReaders()->contains($user));
$message->setHaveread($haveread);
$havesee = ($message->getSees()->contains($user));
$message->setHaveread($haveread);
$message->setHavesee($havesee);
if(!$haveread) {
$message->addReader($this->getUser());
$em->persist($message);
$em->flush();
}
foreach($message->getChilds() as $child) {
$haveread = ($child->getReaders()->contains($user));
$havesee = ($child->getSees()->contains($user));
$child->setHaveread($haveread);
$child->setHavesee($havesee);
if(!$haveread) {
$child->addReader($this->getUser());
$em->persist($child);
$em->flush();
}
}
}
// Création du formulaire
@ -138,8 +155,8 @@ class ChatController extends Controller
$usergroup=$em->getRepository("CadolesCoreBundle:UserGroup")->findOneBy(["group"=>$group,"user"=>$user]);
if(!$usergroup) die();
// On récupere les messages
$messages=$em->getRepository("CadolesWebsocketBundle:Message")->findBy(["group"=>$group],["submitdate"=>"DESC"],10);
// On récupere les messages parent
$messages=$em->getRepository("CadolesWebsocketBundle:Message")->findBy(["group"=>$group,"parent"=>null],["submitdate"=>"DESC"],10);
foreach($messages as $message) {
$tmp=[];
@ -147,9 +164,21 @@ class ChatController extends Controller
$tmp["message"]=$message->getTopic();
$tmp["submitdate"]=$message->getSubmitdate();
$tmp["userid"]=$message->getUser()->getId();
$tmp["userlastname"]=$message->getUser()->getLastname();
$tmp["userfirstname"]=$message->getUser()->getFirstname();
$tmp["userlastname"]=$message->getUser()->getLastname()." ".$message->getUser()->getFirstname();
$tmp["useravatar"]=$message->getUser()->getAvatar();
$tmp["childs"]=[];
foreach($message->getChilds() as $child) {
$tmpchild=[];
$tmpchild["id"]=$child->getId();
$tmpchild["message"]=$child->getTopic();
$tmpchild["submitdate"]=$child->getSubmitdate();
$tmpchild["userid"]=$child->getUser()->getId();
$tmpchild["userlastname"]=$child->getUser()->getLastname()." ".$child->getUser()->getFirstname();
$tmpchild["useravatar"]=$child->getUser()->getAvatar();
array_push($tmp["childs"],$tmpchild);
}
array_push($output,$tmp);
}

View File

@ -40,6 +40,16 @@ class Message
*/
private $group;
/**
* @ORM\ManyToOne(targetEntity="Cadoles\WebsocketBundle\Entity\message", inversedBy="childs")
*/
private $parent;
/**
* @ORM\OneToMany(targetEntity="Cadoles\WebsocketBundle\Entity\Message", mappedBy="parent", cascade={"persist"}, orphanRemoval=true)
*/
protected $childs;
/**
* @ORM\ManyToMany(targetEntity="Cadoles\CoreBundle\Entity\User", inversedBy="messagereaders", cascade={"persist"})
* @ORM\JoinTable(name="messageuserread",
@ -70,7 +80,18 @@ class Message
return $this;
}
private $havesee;
public function getHavesee()
{
return $this->havesee;
}
public function setHavesee($havesee) {
$this->havesee = $havesee;
return $this;
}
/**
* Constructor
*/
@ -254,4 +275,62 @@ class Message
{
return $this->sees;
}
/**
* Set parent
*
* @param \Cadoles\WebsocketBundle\Entity\message $parent
*
* @return Message
*/
public function setParent(\Cadoles\WebsocketBundle\Entity\message $parent = null)
{
$this->parent = $parent;
return $this;
}
/**
* Get parent
*
* @return \Cadoles\WebsocketBundle\Entity\message
*/
public function getParent()
{
return $this->parent;
}
/**
* Add child
*
* @param \Cadoles\WebsocketBundle\Entity\Message $child
*
* @return Message
*/
public function addChild(\Cadoles\WebsocketBundle\Entity\Message $child)
{
$this->childs[] = $child;
return $this;
}
/**
* Remove child
*
* @param \Cadoles\WebsocketBundle\Entity\Message $child
*/
public function removeChild(\Cadoles\WebsocketBundle\Entity\Message $child)
{
$this->childs->removeElement($child);
}
/**
* Get childs
*
* @return \Doctrine\Common\Collections\Collection
*/
public function getChilds()
{
return $this->childs;
}
}

View File

@ -30,6 +30,9 @@
.message-toread {
font-weight:bold;
}
.message-see {
display:none;
}
.msgavatar {
float:left;
@ -43,6 +46,33 @@
line-height: 12px;
margin-bottom: 10px;
}
.msgreplys {
margin-bottom:10px;
}
.messagereply {
padding:0px;
border-top: 1px solid #{{ colorbodyfont }};
font-size:12px;
}
.btnreplymessage {
padding: 5px;
background-color: #{{ colorbodyfont }};
color : #{{ colorbodyback }};
border-radius:5px;
cursor:pointer;
}
.btnreplymessage:hover {
color : #{{ colorbodyback }};
}
.replymessage { display:none}
.replymessage textarea {
width:100%;
margin:20px 0px 5px 0px;
height:150px;
}
.sendreply { width:100%}
.bootstrap-switch{
margin-top:5px;
}
@ -63,10 +93,12 @@
{{ form_start(form) }}
<div id="topchat" class='row'>
{{ form_widget(form.message) }}
<input id="sendbymail" type="checkbox" id="item_essential" name="item[essential]" style="float:right" class='switch' ></input>
<label class="custom-control-label" for="sendbymail">Envoyer par Mail ?</label>
<input id="sendbymail" type="checkbox" style="float:right" class='switch' ></input>
<label class="custom-control-label" for="sendbymail" style="color:#{{ colorbodyback }}">Envoyer par Mail ?</label>
<a id="sendbtn" class="btn btn-success" style="margin-top:5px; width:100%; margin-bottom:15px">Envoyer</a>
<div id="useronline" style="margin-bottom:10px"></div>
<input id="unsee" type="checkbox" style="float:right" class='switch' onChange="switchsee()"></input>
<label class="custom-control-label" for="unsee" style="color:#{{ colorbodyback }}">Afficher les messages masqués ?</label>
</div>
@ -77,11 +109,20 @@
{% if not message.haveread %}
{% set classread="message-toread" %}
{% endif %}
<div id='message-{{message.id}}' class='message row {{classread}}'>
{% set classsee="" %}
{% if message.havesee %}
{% set classsee="message-see" %}
{% endif %}
<div id='message-{{message.id}}' class='message row {{classread}} {{classsee}}'>
<div class='msgavatar'>
<img style='cursor:pointer' onclick='seeUser({{message.user.id}})' id='user_avatar_img' src='/{{ alias }}/uploads/avatar/{{message.user.avatar}}' class='avatar'><br>
{% if fgmanager or message.user == app.user %}
<i class='delmessage fa fa-trash fa-fw' data-id='{{message.id}}' style='cursor: pointer;'></i>
<i class='delmessage fa fa-trash fa-fw' data-id='{{message.id}}' title='Supprimer' style='cursor: pointer;'></i>
{% endif %}
{% if not message.havesee %}
<i id="hidemessage-{{message.id}}" class='hidemessage fa fa-eye-slash fa-fw' title='Ne plus afficher' data-id='{{message.id}}' style='cursor: pointer;'></i>
{% endif %}
</div>
<div class='msgdiv'>
@ -90,6 +131,39 @@
<small>{{message.submitdate|date('d/m/Y H:i')}}</small>
</div>
<div class='msgtopic'>{{message.topic | raw}}</div>
<div id="msgreplys-{{message.id}}" class='msgreplys'>
{% for child in message.childs | reverse %}
{% set classread="" %}
{% if not child.haveread %}
{% set classread="message-toread" %}
{% endif %}
{% set classsee="" %}
{% if child.havesee %}
{% set classsee="message-see" %}
{% endif %}
<div id='message-{{child.id}}' class='message messagereply {{classread}} {{classsee}}'>
{{child.topic | raw | nl2br }}
<div style='cursor:pointer' onclick='seeUser({{child.user.id}})'><small>{{ child.user.lastname }} {{ child.user.firstname }}</small></div>
<small>{{child.submitdate|date('d/m/Y H:i')}}</small>
{% if fgmanager or child.user == app.user %}
<i class='delmessage fa fa-trash fa-fw' data-id='{{child.id}}' title='Supprimer' style='cursor: pointer;'></i>
{% endif %}
{% if not child.havesee %}
<i id="hidemessage-{{child.id}}" class='hidemessage fa fa-eye-slash fa-fw' title='Ne plus afficher' data-id='{{child.id}}' style='cursor: pointer;'></i>
{% endif %}
</div>
{% endfor %}
</div>
<a class="btnreplymessage" data-id='{{message.id}}'>Répondre</a>
<div id="replymessage-{{message.id}}" class="replymessage">
<textarea></textarea>
<a id="sendreply" class="btn btn-success sendreply" data-id='{{message.id}}'>Envoyer</a>
</div>
</div>
</div>
{% endfor %}
@ -294,12 +368,20 @@
html+="<div class='msgavatar'>";
html+="<img style='pointer:cursor' onclick='seeUser("+payload.msg.userid+")' id='user_avatar_img' src='/{{ alias }}/uploads/avatar/"+payload.msg.avatar+"' class='avatar'><br>";
if(payload.msg.userid=={{app.user.id}} || '{{ fgmanager }}'=='1') {
html+="<i class='delmessage fa fa-trash fa-fw' data-id='"+payload.msg.id+"' style='cursor: pointer;'></i>";
html+="<i class='delmessage fa fa-trash fa-fw' data-id='"+payload.msg.id+"' title='Supprimer' style='cursor: pointer;'></i>";
}
html+="<i id='hidemessage-"+payload.msg.id+"' class='hidemessage fa fa-eye-slash fa-fw' data-id='"+payload.msg.id+"' title='Ne plus afficher' style='cursor: pointer;'></i>";
html+="</div>";
html+="<div class='msgdiv'>"
html+="<div class='msgtitle'>"+payload.msg.lastname+"<br><small>"+new Date(payload.msg.submitdate.date).toLocaleDateString("fr-FR", dateoptions)+"</small></div>";
html+="<div class='msgtopic'>"+payload.msg.message+"</div>";
html+="<div id='msgreplys-"+payload.msg.id+"' class='msgreplys'></div>";
html+="<a class='btnreplymessage' data-id='"+payload.msg.id+"'>Répondre</a>";
html+="<div id='replymessage-"+payload.msg.id+"' class='replymessage'>";
html+="<textarea></textarea>";
html+="<a id='sendreply' class='btn btn-success sendreply' data-id='"+payload.msg.id+"'>Envoyer</a>";
html+="</div>";
html+="</div>";
html+="</div>";
$(".mychat").prepend(html);
@ -307,6 +389,24 @@
//console.log("Received message by "+payload.msg.userid+" = ",payload.msg);
}
if(payload.msgreply) {
// Si on reçoit une réponse forcement le parent est de nouveau visible
$("#message-"+payload.msgreply.parent).removeClass ("message-see");
// On ajout la réponse
html ="<div id='message-"+payload.msgreply.id+"' class='message messagereply message-toread'>";
html+=nl2br(payload.msgreply.message);
html+="<div style='cursor:pointer' onclick='seeUser("+payload.msgreply.userid+")'><small>"+payload.msgreply.lastname+"</small></div>";
html+="<small>"+new Date(payload.msgreply.submitdate.date).toLocaleDateString("fr-FR", dateoptions)+"</small>";
if(payload.msgreply.userid=={{app.user.id}} || '{{ fgmanager }}'=='1') {
html+="<i class='delmessage fa fa-trash fa-fw' data-id='"+payload.msgreply.id+"' title='Supprimer' style='cursor: pointer;'></i>";
}
html+="<i id='hidemessage-"+payload.msgreply.id+"' class='hidemessage fa fa-eye-slash fa-fw' data-id='"+payload.msgreply.id+"' title='Ne plus afficher' style='cursor: pointer;'></i>";
html+="</div>";
$("#msgreplys-"+payload.msgreply.parent).prepend(html);
}
if(payload.log) {
console.log("Received message", payload.log);
}
@ -351,6 +451,21 @@
});
}
function nl2br (str, is_xhtml) {
if (typeof str === 'undefined' || str === null) {
return '';
}
var breakTag = (is_xhtml || typeof is_xhtml === 'undefined') ? '<br />' : '<br>';
return (str + '').replace(/([^>\r\n]?)(\r\n|\n\r|\r|\n)/g, '$1' + breakTag + '$2');
}
function switchsee() {
$(".message-see").hide();
if($("#unsee").bootstrapSwitch('state')) {
$(".message-see").show();
}
}
$( "#sendbtn" ).click(function() {
sendbtn();
});
@ -469,6 +584,75 @@
}
}
$(document).on('click', '.hidemessage', function(){
hidemessage($(this).data("id"));
});
function hidemessage(id) {
$.ajax({
method: "POST",
url: "{{ path('cadoles_websocket_message_see') }}",
data: {
id:id
},
success: function() {
$("#message-"+id).addClass ("message-see");
$("#hidemessage-"+id).remove();
if(!$("#unsee").bootstrapSwitch('state')) {
$("#message-"+id).hide();
}
else {
$("#message-"+id).show();
}
}
});
}
$(document).on('click', '.btnreplymessage', function(){
btnreplymessage($(this).data("id"));
});
function btnreplymessage(id) {
$("#replymessage-"+id).toggle();
$("#replymessage-"+id+" textarea").focus();
}
$(document).on('click', '.sendreply', function(){
sendreply($(this).data("id"));
});
function sendreply(id) {
try {
// Flager que l'envoit c'est fait
tosend=false;
$("#replymessage-"+id+" a").html("Envoyer");
$("#replymessage-"+id+" a").removeClass("btn-danger");
$("#replymessage-"+id+" a").css('cursor','auto');
// Push envent sur le websocket
var data = "<p>"+$("#replymessage-"+id+" textarea").val()+"</p>";
event={mykey: "{{userkey}}", type: "reply", message: data, parent: id};
session.publish("websocket/channel/{{groupid}}", event);
$("#replymessage-"+id+" textarea").val("");
$("#replymessage-"+id).hide();
}
catch(error) {
// L'envoi ne s'est pas fait
console.log("Retry to send");
// On flag le fait de retenter l'envoit à la reconnexion
tosend=true;
// On signal que l'envoi est en cours sur le bouton
$("#replymessage-"+id+" a").html("Envoi en cours");
$("#replymessage-"+id+" a").addClass("btn-danger");
$("#replymessage-"+id+" a").css('cursor','progress');
}
}
$(document).on('click', '#listtoavatar img', function(){
var mail = ";"+$(this).data("mail");
$("#mailto").val($("#mailto").val().replace(mail, ""));
@ -476,6 +660,8 @@
});
function recuplastmsg() {
console.log("recuplastmsg");
$.ajax({
method: "POST",
url: "{{ path('cadoles_websocket_message_list') }}",
@ -486,20 +672,47 @@
$.each(datas, function(i,data) {
// Le message a-t-il été déposé durant la déconnexion ?
if(!$("#message-"+data.id).length) {
html ="<div id='message-"+data.id+"' class='message row'>";
html ="<div id='message-"+data.id+"' class='message row message-toread'>";
html+="<div class='msgavatar'>";
html+="<img style='cursor:pointer' onclick='seeUser("+data.userid+")' id='user_avatar_img' src='/{{ alias }}/uploads/avatar/"+data.useravatar+"' class='avatar'><br>";
if(data.userid=={{app.user.id}} || '{{ fgmanager }}'=='1') {
html+="<i class='delmessage fa fa-trash fa-fw' data-id='"+data.id+"' style='cursor: pointer;'></i>";
}
if (!data.havesee) {
html+="<i id='hidemessage-"+data.id+"' class='hidemessage fa fa-eye-slash fa-fw' data-id='"+data.id+"' title='Ne plus afficher' style='cursor: pointer;'></i>";
}
html+="</div>";
html+="<div class='msgdiv'>"
html+="<div class='msgtitle'>"+data.userlastname+"<br><small>"+new Date(data.submitdate.date).toLocaleDateString("fr-FR", dateoptions)+"</small></div>";
html+="<div class='msgtopic'>"+data.message+"</div>";
html+="<div id='msgreplys-"+data.id+"' class='msgreplys'>";
html+="</div>";
html+="<a class='btnreplymessage' data-id='"+data.id+"'>Répondre</a>";
html+="<div id='replymessage-"+data.id+"' class='replymessage'>";
html+="<textarea></textarea>";
html+="<a id='sendreply' class='btn btn-success sendreply' data-id='"+data.id+"'>Envoyer</a>";
html+="</div>";
html+="</div>";
html+="</div>";
$(".mychat").prepend(html);
}
$.each(data.childs, function(i,child) {
if(!$("#message-"+child.id).length) {
html ="<div id='message-"+child.id+"' class='message messagereply message-toread'>";
html+=nl2br(child.message);
html+="<div style='cursor:pointer' onclick='seeUser("+child.userid+")'><small>"+child.userlastname+"</small></div>";
html+="<small>"+new Date(child.submitdate.date).toLocaleDateString("fr-FR", dateoptions)+"</small>";
if(child.userid=={{app.user.id}} || '{{ fgmanager }}'=='1') {
html+="<i class='delmessage fa fa-trash fa-fw' data-id='"+child.id+"' title='Supprimer' style='cursor: pointer;'></i>";
}
html+="<i id='hidemessage-"+child.id+"' class='hidemessage fa fa-eye-slash fa-fw' data-id='"+child.id+"' title='Ne plus afficher' style='cursor: pointer;'></i>";
html+="</div>";
$("#msgreplys-"+data.id).prepend(html);
}
});
});
}
});
@ -521,8 +734,9 @@
function addOnline(userid, useravatar, userlastname, userfirstname) {
if(!$("#online"+userid).length) {
html = "<span id='online"+userid+"'>";
html+= "<img style='cursor:pointer; width:30px; height:30px; margin-right:5px;' onclick='seeUser("+userid+")' title='"+userlastname+" "+userfirstname+"' id='user_avatar_img' src='/{{ alias }}/uploads/avatar/"+useravatar+"' class='avatar'>";
html = "<span id='online"+userid+"' style='width:70px; height:105px; display:inline-block; text-align: center; font-size: 10px; color:#{{ colorbodyback }}; text-transform: uppercase; line-height:11px;overflow-wrap: break-word;vertical-align:top;'>";
html+= "<img style='cursor:pointer; width:40px; height:40px; margin-bottom:5px;' onclick='seeUser("+userid+")' title='"+userlastname+" "+userfirstname+"' id='user_avatar_img' src='/{{ alias }}/uploads/avatar/"+useravatar+"' class='avatar'>";
html+= userlastname+" "+userfirstname;
html+= "</span>";
$("#useronline").append(html);
}

View File

@ -151,6 +151,40 @@ class WebsocketTopic implements TopicInterface
$topic->broadcast(['msg' => $return]);
}
if($event["type"]=="reply") {
$parent=$this->em->getRepository("CadolesWebsocketBundle:Message")->find($event["parent"]);
if($parent) {
$message=new Message();
$message->setTopic($event["message"]);
$message->setUser($user);
$message->setGroup($group);
$message->setParent($parent);
$this->em->persist($message);
$this->em->flush();
// Si commentaire sur une message : il faut replacer le message en unsee pour tt le monde
foreach($parent->getSees() as $see) {
$parent->removeSee($see);
}
$this->em->persist($parent);
$this->em->flush();
$return["id"]=$message->getId();
$return["lastname"]=$user->getLastname()." ".$user->getFirstname();
$return["avatar"]=$user->getAvatar();
$return["submitdate"]=$message->getSubmitdate();
$return["message"]=$event["message"];
$return["userid"]=$user->getId();
$return["parent"]=$event["parent"];
//this will broadcast the message to ALL subscribers of this topic.
$topic->broadcast(['msgreply' => $return]);
}
else
$topic->broadcast(['log' => "Message parent introuvable"]);
}
if($event["type"]=="del") {
$message=$this->em->getRepository("CadolesWebsocketBundle:Message")->find($event["id"]);
if($message&&($usergroup->getFgmanager()||$message->getUser()==$user||$user->getRole()=="ROLE_ADMIN"||$user->getRole()=="ROLE_MODO" )) {

View File

@ -40,7 +40,6 @@ INSERT IGNORE INTO `sidebar` (`id`, `parent_id`, `roworder`, `label`, `path`, `f
(1240, 1200, 1240, 'Groupes', 'cadoles_core_config_group', 'fa-users', 'ROLE_ADMIN,ROLE_MODO', ''),
(1250, 1200, 1250, 'Inscriptions', 'cadoles_core_config_registration', 'fa-pencil-square-o', 'ROLE_ADMIN,ROLE_MODO', ''),
(1260, 1200, 1260, 'Utilisateurs', 'cadoles_core_config_user', 'fa-child', 'ROLE_ADMIN,ROLE_MODO', ''),
(1270, 1200, 1270, 'Import Utilisateurs', 'cadoles_core_config_importuser', 'fa-download', 'ROLE_ADMIN,ROLE_MODO', 'importuser_activate'),
(1500, NULL, 1500, 'PORTAIL', NULL, 'fa-cubes', 'ROLE_ADMIN,ROLE_MODO', 'portal_activate'),
(1510, 1500, 1510, 'Modèles de Page', 'cadoles_portal_config_pagetemplate', 'fa-copy', 'ROLE_ADMIN,ROLE_MODO', 'portal_activate'),
@ -77,9 +76,14 @@ INSERT IGNORE INTO `sidebar` (`id`, `parent_id`, `roworder`, `label`, `path`, `f
(3160, 3000, 3160, 'Piwik', 'cadoles_portal_config_syncpiwik', 'fa-signal', 'ROLE_ADMIN,ROLE_MODO', 'widpiwik_activate_syncenvole'),
(3230, 3000, 3230, 'Wordpress', 'cadoles_portal_config_syncwordpress', 'fa-wordpress', 'ROLE_ADMIN,ROLE_MODO', 'activate_widwordpress'),
(6000, NULL, 6000, 'OUTILS', NULL, 'fa-wrench', 'ROLE_ADMIN,ROLE_MODO', ''),
(6010, 6000, 6010, 'Statistiques', 'cadoles_core_config_statistic', 'fa-bar-chart-o', 'ROLE_ADMIN,ROLE_MODO', ''),
(6020, 6000, 6020, 'Mailing', 'cadoles_core_config_mailing', 'fa-envelope', 'ROLE_ADMIN,ROLE_MODO', ''),
(6030, 6000, 6030, 'Import Utilisateurs', 'cadoles_core_config_importuser', 'fa-download', 'ROLE_ADMIN,ROLE_MODO', 'importuser_activate'),
(7000, NULL, 7000, 'CRON', NULL, 'fa-bolt', 'ROLE_ADMIN,ROLE_MODO', 'cron_activate'),
(7010, 7000, 7010, 'Jobs', 'cadoles_cron_config', 'fa-bullseye', 'ROLE_ADMIN,ROLE_MODO', 'cron_activate'),
(7020, 7000, 7020, 'Logs', 'cadoles_cron_config_log', 'fa-list-alt', 'ROLE_ADMIN,ROLE_MODO', 'cron_activate');
(7020, 7000, 7020, 'Logs / Dump', 'cadoles_cron_config_log', 'fa-list-alt', 'ROLE_ADMIN,ROLE_MODO', 'cron_activate');
@ -130,7 +134,6 @@ INSERT IGNORE permmodo (`route`, `visible`) VALUES
('cadoles_core_config_group',1),
('cadoles_core_config_registration',1),
('cadoles_core_config_user',1),
('cadoles_core_config_importuser',0),
('cadoles_portal_config_pagetemplate',1),
('cadoles_portal_config_page',1),
('cadoles_portal_config_item',1),
@ -143,5 +146,8 @@ INSERT IGNORE permmodo (`route`, `visible`) VALUES
('cadoles_portal_config_synclimesurvey',0),
('cadoles_portal_config_syncmoodle',0),
('cadoles_portal_config_syncwordpress',0),
('cadoles_core_config_statistic',1),
('cadoles_core_config_mailing',1),
('cadoles_core_config_importuser',0),
('cadoles_cron_config',0),
('cadoles_cron_config_log',0);