aboutsummaryrefslogtreecommitdiff
path: root/app
diff options
context:
space:
mode:
authorvincent-peugnet <v.peugnet@free.fr>2019-01-15 04:04:01 +0100
committervincent-peugnet <v.peugnet@free.fr>2019-01-15 04:04:01 +0100
commit2ff846f7fb65998cd6cf151554434f56f116d4f2 (patch)
tree8106cf1744dc7545e1482fd98bae16ea3628c153 /app
parent8e79f279938f0fff64ddd381d073c2c277dd2d5c (diff)
parentde195c2fca2f4b77a54be68fb58cd0ccee10a5b7 (diff)
downloadwcms-2ff846f7fb65998cd6cf151554434f56f116d4f2.tar.gz
wcms-2ff846f7fb65998cd6cf151554434f56f116d4f2.zip
Merge branch 'implement-timeline' into develop
Diffstat (limited to 'app')
-rw-r--r--app/class/art2.php3
-rw-r--r--app/class/controllerart.php76
-rw-r--r--app/class/controllerconnect.php36
-rw-r--r--app/class/controllerhome.php5
-rw-r--r--app/class/controllertimeline.php56
-rw-r--r--app/class/dbitem.php32
-rw-r--r--app/class/event.php156
-rw-r--r--app/class/modeltimeline.php139
-rw-r--r--app/class/routes.php7
-rw-r--r--app/view/templates/backtopbar.php2
-rw-r--r--app/view/templates/connect.php4
-rw-r--r--app/view/templates/navart.php2
-rw-r--r--app/view/templates/timeline.php90
13 files changed, 554 insertions, 54 deletions
diff --git a/app/class/art2.php b/app/class/art2.php
index 2341ff9..a7e94f3 100644
--- a/app/class/art2.php
+++ b/app/class/art2.php
@@ -44,9 +44,6 @@ class Art2
const LEN = 255;
const LENTEXT = 2**20;
const SECUREMAX = 2;
- const LENCOULEUR = 7;
- const DEBUT = '(?id=';
- const FIN = ')';
const TABS = ['main', 'css', 'header', 'body', 'nav', 'aside', 'footer', 'javascript'];
const VAR_DATE = ['date', 'datecreation', 'datemodif', 'daterender'];
diff --git a/app/class/controllerart.php b/app/class/controllerart.php
index 00b7558..20ef634 100644
--- a/app/class/controllerart.php
+++ b/app/class/controllerart.php
@@ -33,13 +33,19 @@ class Controllerart extends Controller
public function importart()
{
- $art = $this->artmanager->get($this->art);
+ if (isset($_SESSION['artupdate']) && $_SESSION['artupdate']['id'] == $this->art->id()) {
+ $art = new Art2($_SESSION['artupdate']);
+ unset($_SESSION['artupdate']);
+ } else {
+ $art = $this->artmanager->get($this->art);
+ }
if ($art !== false) {
$this->art = $art;
return true;
} else {
return false;
}
+
}
@@ -104,9 +110,9 @@ class Controllerart extends Controller
} else {
$page = ['head' => $this->art->renderhead(), 'body' => $this->art->renderbody()];
}
- if($canread) {
+ if ($canread) {
$this->art->addaffcount();
- if($this->user->level() < 2) {
+ if ($this->user->level() < 2) {
$this->art->addvisitcount();
}
}
@@ -208,40 +214,56 @@ class Controllerart extends Controller
public function update($id)
{
$this->setart($id, 'artupdate');
- $_SESSION['workspace']['showrightpanel'] = isset($_POST['workspace']['showrightpanel']);
- $_SESSION['workspace']['showleftpanel'] = isset($_POST['workspace']['showleftpanel']);
-
- if (!empty($_POST['fontsize']) && $_POST['fontsize'] !== Config::fontsize()) {
- Config::setfontsize($_POST['fontsize']);
- Config::savejson();
- }
-
+ $this->movepanels();
+ $this->fontsize();
$date = new DateTimeImmutable($_POST['pdate'] . $_POST['ptime'], new DateTimeZone('Europe/Paris'));
$date = ['date' => $date];
- if ($this->importart() && $this->canedit()) {
+ if ($this->importart()) {
+ if ($this->canedit()) {
+
+ // Check if someone esle edited the page during the editing.
+ $oldart = clone $this->art;
+ $this->art->hydrate($_POST);
- $oldart = clone $this->art;
- $this->art->hydrate($_POST);
+ if (self::COMBINE && $_POST['thisdatemodif'] === $oldart->datemodif('string')) {
- if (self::COMBINE) {
- if ($_POST['thisdatemodif'] === $oldart->datemodif('string')) {
- $compare = $this->artmanager->combine($this->art, $oldart);
- if (!empty($compare['diff'])) {
- $this->art->hydrate($compare['mergeart']);
- }
}
- }
- $this->art->hydrate($date);
- $this->art->updateedited();
- $this->art->addauthor($this->user->id());
- $this->artmanager->update($this->art);
- $this->routedirect('artedit', ['art' => $this->art->id()]);
-
+ $this->art->hydrate($date);
+ $this->art->updateedited();
+ $this->art->addauthor($this->user->id());
+
+
+ $this->artmanager->update($this->art);
+
+ $this->routedirect('artedit', ['art' => $this->art->id()]);
+
//$this->showtemplate('updatemerge', $compare);
+ } else {
+ // If the editor session finished during the editing, let's try to reconnect to save the editing
+ $_SESSION['artupdate'] = $_POST;
+ $_SESSION['artupdate']['id'] = $this->art->id();
+ $this->routedirect('connect');
+ }
+
+ }
+ $this->routedirect('art');
+ }
+
+ public function movepanels()
+ {
+ $_SESSION['workspace']['showrightpanel'] = isset($_POST['workspace']['showrightpanel']);
+ $_SESSION['workspace']['showleftpanel'] = isset($_POST['workspace']['showleftpanel']);
+ }
+
+ public function fontsize()
+ {
+ if (!empty($_POST['fontsize']) && $_POST['fontsize'] !== Config::fontsize()) {
+ Config::setfontsize($_POST['fontsize']);
+ Config::savejson();
}
}
diff --git a/app/class/controllerconnect.php b/app/class/controllerconnect.php
index 5328447..d6aa7a2 100644
--- a/app/class/controllerconnect.php
+++ b/app/class/controllerconnect.php
@@ -6,31 +6,33 @@ class Controllerconnect extends Controller
public function log()
{
if (isset($_POST['log'])) {
- if (isset($_POST['id'])) {
- $id = $_POST['id'];
- } else {
- $id = null;
- }
+ $id = $_POST['id'] ?? null;
+ $route = $_POST['route'] ?? 'home';
if ($_POST['log'] === 'login') {
- $this->login($id);
+ $this->login($route, $id);
} elseif ($_POST['log'] === 'logout') {
- $this->logout($id);
+ $this->logout($route, $id);
}
}
-
}
public function connect()
{
- $this->showtemplate('connect', []);
+ if(isset($_SESSION['artupdate'])) {
+ $artupdate['route'] = 'artedit';
+ $artupdate['id'] = $_SESSION['artupdate']['id'];
+ } else {
+ $artupdate = [$route = 'home'];
+ }
+ $this->showtemplate('connect', $artupdate);
}
- public function login($id)
+ public function login($route, $id = null)
{
if (isset($_POST['pass'])) {
$this->user = $this->usermanager->passwordcheck($_POST['pass']);
@@ -41,21 +43,21 @@ class Controllerconnect extends Controller
}
}
- if (!empty($id)) {
- $this->routedirect('artread/', ['art' => $id]);
+ if ($id !== null) {
+ $this->routedirect($route, ['art' => $id]);
} else {
- $this->routedirect('home');
+ $this->routedirect($route);
}
}
- public function logout($id)
+ public function logout($route, $id = null)
{
$this->user = $this->usermanager->logout();
$this->usermanager->writesession($this->user);
- if (!empty($id)) {
- $this->routedirect('artread/', ['art' => $id]);
+ if ($id !== null && $route !== 'home') {
+ $this->routedirect($route, ['art' => $id]);
} else {
- $this->routedirect('home');
+ $this->routedirect($route);
}
}
diff --git a/app/class/controllerhome.php b/app/class/controllerhome.php
index caeb652..f5b3068 100644
--- a/app/class/controllerhome.php
+++ b/app/class/controllerhome.php
@@ -17,11 +17,6 @@ class Controllerhome extends Controller
public function desktop()
{
- $this->table2();
- }
-
- public function table2()
- {
$table = $this->modelhome->getlister();
$this->opt = $this->modelhome->optinit($table);
diff --git a/app/class/controllertimeline.php b/app/class/controllertimeline.php
new file mode 100644
index 0000000..7e617e1
--- /dev/null
+++ b/app/class/controllertimeline.php
@@ -0,0 +1,56 @@
+<?php
+
+class Controllertimeline extends Controller
+{
+ /**
+ * @var Modeltimeline
+ */
+ protected $eventmanager;
+
+ public function __construct($render) {
+ parent::__construct($render);
+ $this->eventmanager = new Modeltimeline;
+ }
+
+ public function desktop()
+ {
+ $eventlist = $this->eventmanager->showlast(['message'], 100, 0);
+
+ $groupedeventlist = $this->eventmanager->group($eventlist);
+
+ $this->showtemplate('timeline', ['eventlist' => $eventlist, 'groupedeventlist' => $groupedeventlist]);
+
+ }
+
+ public function add()
+ {
+ if($this->user->level() >= Modeluser::EDITOR && !empty($_POST['message'])) {
+
+ $event = new Event($_POST);
+ $event->stamp();
+ $event->setid($this->eventmanager->getlastfreeid());
+ $this->eventmanager->add($event);
+ }
+ $this->routedirect('timeline');
+ }
+
+ public function clap()
+ {
+ if(isset($_POST['id']) && isset($_POST['clap'])) {
+ $event = $this->eventmanager->get(intval($_POST['id']));
+ $event->addclap();
+ $this->eventmanager->add($event);
+ }
+ $this->routedirect('timeline');
+
+ }
+}
+
+
+
+
+
+
+
+
+?> \ No newline at end of file
diff --git a/app/class/dbitem.php b/app/class/dbitem.php
new file mode 100644
index 0000000..2035316
--- /dev/null
+++ b/app/class/dbitem.php
@@ -0,0 +1,32 @@
+<?php
+
+class Dbitem
+{
+ public function hydrate($datas)
+ {
+ foreach ($datas as $key => $value) {
+ $method = 'set' . $key;
+
+ if (method_exists($this, $method)) {
+ $this->$method($value);
+ }
+ }
+
+ }
+
+ public function dry()
+ {
+ $array = [];
+ foreach (get_object_vars($this) as $var => $value) {
+ if (in_array($var, $this::VAR_DATE)) {
+ $array[$var] = $this->$var('string');
+ } else {
+ $array[$var] = $this->$var();
+ }
+ }
+ return $array;
+ }
+}
+
+
+?> \ No newline at end of file
diff --git a/app/class/event.php b/app/class/event.php
new file mode 100644
index 0000000..9fc75d2
--- /dev/null
+++ b/app/class/event.php
@@ -0,0 +1,156 @@
+<?php
+
+class Event extends Dbitem
+{
+ protected $id;
+ protected $date;
+ protected $type;
+ protected $user;
+ protected $target;
+ protected $message;
+ protected $clap = 0;
+
+ const EVENT_TYPES = ['message', 'art_add', 'art_edit', 'art_delete', 'media_add', 'media_delete', 'font_add'];
+ const EVENT_BASE = ['message'];
+ const EVENT_ART = ['art_add', 'art_edit', 'art_delete'];
+ const EVENT_MEDIA = ['media_add', 'media_delete'];
+ const EVENT_FONT = ['font_add', 'font_delete'];
+ const MESSAGE_MAX_LENGTH = 2 ** 10;
+
+ const VAR_DATE = ['date'];
+
+ public function __construct($datas)
+ {
+ $this->hydrate($datas);
+ }
+
+ public function stamp()
+ {
+ $this->date = new DateTimeImmutable(null, timezone_open("Europe/Paris"));
+ $this->user = idclean($this->user);
+ if (in_array($this->type, self::EVENT_ART)) {
+ $this->target = idclean($this->target);
+ } elseif ($this->type === 'message') {
+ $this->message = htmlspecialchars($this->message);
+ }
+ }
+
+ public function addclap()
+ {
+ $this->clap ++;
+ }
+
+ // _____________________ G E T __________________________
+
+ public function id()
+ {
+ return $this->id;
+ }
+
+ public function date($type = 'datetime')
+ {
+ switch ($type) {
+ case 'datetime':
+ return $this->date;
+ break;
+
+ case 'string':
+ return $this->date->format(DateTime::ISO8601);
+ break;
+
+ case 'hrdi':
+ $now = new DateTimeImmutable(null, timezone_open("Europe/Paris"));
+ return hrdi($this->date->diff($now));
+ break;
+
+ }
+ }
+
+ public function type()
+ {
+ return $this->type;
+ }
+
+ public function user()
+ {
+ return $this->user;
+ }
+
+ public function target()
+ {
+ return $this->target;
+ }
+
+ public function message()
+ {
+ return $this->message;
+ }
+
+ public function clap()
+ {
+ return $this->clap;
+ }
+
+
+
+ // ________________________ S E T ____________________
+
+ public function setid($id)
+ {
+ if (is_int($id)) {
+ $this->id = $id;
+ }
+ }
+
+ public function setdate($date)
+ {
+ if ($date instanceof DateTimeImmutable) {
+ $this->date = $date;
+ } elseif (is_string($date)) {
+ $this->date = DateTimeImmutable::createFromFormat(DateTime::ISO8601, $date, new DateTimeZone('Europe/Paris'));
+ }
+ }
+
+ public function settype($type)
+ {
+ if (in_array($type, self::EVENT_TYPES)) {
+ $this->type = $type;
+ }
+ }
+
+ public function setuser($user)
+ {
+ if (is_string($user) && strlen($user) < Model::MAX_ID_LENGTH) {
+ $this->user = $user;
+ }
+ }
+
+ public function settarget($target)
+ {
+ if (is_string($target) && strlen($target) < Model::MAX_ID_LENGTH) {
+ $this->target = $target;
+ }
+ }
+
+ public function setmessage($message)
+ {
+ if (is_string($message) && strlen($message) < self::MESSAGE_MAX_LENGTH) {
+ $this->message = $message;
+ }
+ }
+
+ public function setclap($clap)
+ {
+ if(is_int($clap)) {
+ $this->clap = $clap;
+ }
+ }
+
+
+
+
+
+}
+
+
+?> \ No newline at end of file
diff --git a/app/class/modeltimeline.php b/app/class/modeltimeline.php
new file mode 100644
index 0000000..b575dda
--- /dev/null
+++ b/app/class/modeltimeline.php
@@ -0,0 +1,139 @@
+<?php
+
+class Modeltimeline extends Modeldb
+{
+ const EVENT_BASE = ['message'];
+ const EVENT_ART = ['art_add', 'art_edit', 'art_delete'];
+ const EVENT_MEDIA = ['media_add', 'media_delete'];
+ const EVENT_FONT = ['font_add', 'font_delete'];
+
+ public function __construct()
+ {
+ parent::__construct();
+ $this->storeinit('timeline');
+ }
+
+ public function get(int $id)
+ {
+ $eventdata = $this->repo->findById($id);
+ if ($eventdata !== false) {
+ return new Event($eventdata);
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Retrun a list of Event objects
+ *
+ * @return array array of Event where the key is the Event id.
+ */
+ public function getlister() : array
+ {
+ $eventlist = [];
+ $datalist = $this->repo->findAll();
+ foreach ($datalist as $eventdata) {
+ $event = new Event($eventdata);
+ $id = intval($event->id());
+ $eventlist[$id] = $event;
+ }
+ return $eventlist;
+ }
+
+
+ public function getlisterid(array $idlist = []) : array
+ {
+ $eventdatalist = $this->repo->query()
+ ->where('__id', 'IN', $idlist)
+ ->execute();
+
+ $eventlist = [];
+ foreach ($eventdatalist as $id => $eventdata) {
+ $eventlist[$id] = new Event($eventdata);
+ }
+ return $eventlist;
+ }
+
+
+ /**
+ * Store event
+ *
+ * @param Event The event to be stored in the repositery
+ *
+ * @return bool retrun true if it works, false if it fails
+ */
+ public function add(Event $event) : bool
+ {
+ $eventdata = new \JamesMoss\Flywheel\Document($event->dry());
+ $eventdata->setId($event->id());
+ $result = $this->repo->store($eventdata);
+ return $result;
+ }
+
+ /**
+ * Return last free id
+ *
+ * @return int id
+ */
+ public function getlastfreeid() : int
+ {
+ $idlist = $this->list();
+
+ if (!empty($idlist)) {
+ $id = max($idlist);
+ $id++;
+ } else {
+ $id = 1;
+ }
+ return $id;
+ }
+
+ public function group(array $events)
+ {
+ $id = 0;
+ $subid = 0;
+ $lastuser = null;
+ foreach ($events as $event) {
+ if($event->user() !== $lastuser) {
+ $subid = 0;
+ $id ++;
+ $groupedevents[$id]['user'] = $event->user();
+ } else {
+ $subid ++;
+ }
+ $groupedevents[$id][$subid] = $event;
+ $lastuser = $event->user();
+ }
+ return $groupedevents;
+ }
+
+ public function showlast(array $types, int $qty = 25, int $offset = 0)
+ {
+ $types = array_intersect($types, $this->types());
+
+ $eventdatalist = $this->repo->query()
+ ->where('type', 'IN', $types)
+ ->orderBy('date DESC')
+ ->limit($qty, $offset)
+ ->execute();
+
+ $eventlist = [];
+ foreach ($eventdatalist as $id => $eventdata) {
+ $eventlist[] = new Event($eventdata);
+ }
+
+ $eventlist = array_reverse($eventlist);
+ return $eventlist;
+ }
+
+
+ public function types()
+ {
+ return array_merge(self::EVENT_ART, self::EVENT_BASE, self::EVENT_MEDIA, self::EVENT_MEDIA);
+ }
+
+
+}
+
+
+?> \ No newline at end of file
diff --git a/app/class/routes.php b/app/class/routes.php
index a72d2e9..2ccc269 100644
--- a/app/class/routes.php
+++ b/app/class/routes.php
@@ -22,14 +22,17 @@ class Routes
['POST', '/!media/upload', 'Controllermedia#upload', 'mediaupload'],
['POST', '/!media/folder', 'Controllermedia#folder', 'mediafolder'],
['GET', '/!font', 'Controllerfont#desktop', 'font'],
+ ['GET', '/!font/render', 'Controllerfont#render', 'fontrender'],
+ ['POST', '/!font/add', 'Controllerfont#add', 'fontadd'],
['POST', '/!admin', 'Controlleradmin#update', 'adminupdate'],
['GET', '/!admin', 'Controlleradmin#desktop', 'admin'],
['GET', '/!user', 'Controlleruser#desktop', 'user'],
['POST', '/!user/add', 'Controlleruser#add', 'useradd'],
['POST', '/!user/update', 'Controlleruser#update', 'userupdate'],
['GET', '/!info', 'Controllerinfo#desktop', 'info'],
- ['GET', '/!font/render', 'Controllerfont#render', 'fontrender'],
- ['POST', '/!font/add', 'Controllerfont#add', 'fontadd'],
+ ['GET', '/!timeline', 'Controllertimeline#desktop', 'timeline'],
+ ['POST', '/!timeline/add', 'Controllertimeline#add', 'timelineadd'],
+ ['POST', '/!timeline/clap', 'Controllertimeline#clap', 'timelineclap'],
['GET', '/[cid:art]/', 'Controllerart#read', 'artread/'],
['GET', '/[cid:art]', 'Controllerart#read', 'artread'],
['GET', '/[cid:art]/add', 'Controllerart#add', 'artadd'],
diff --git a/app/view/templates/backtopbar.php b/app/view/templates/backtopbar.php
index 78e9181..d6b522e 100644
--- a/app/view/templates/backtopbar.php
+++ b/app/view/templates/backtopbar.php
@@ -15,6 +15,7 @@
<form action="<?= $this->url('log') ?>" method="post" id="connect">
<input type="password" name="pass" id="loginpass" placeholder="password">
+<input type="hidden" name="route" value="home">
<input type="submit" name="log" value="login">
</form>
@@ -22,6 +23,7 @@
<?php } else { ?>
<span>
+<a href="<?= $this->url('timeline') ?>" <?= $tab == 'timeline' ? 'class="actualpage"' : '' ?>>timeline</a>
<a href="<?= $this->url('user') ?>" <?= $tab == 'user' ? 'class="actualpage"' : '' ?>><?= $user->id() ?></a> <i><?= $user->level() ?></i>
</span>
diff --git a/app/view/templates/connect.php b/app/view/templates/connect.php
index 06fe9c8..5d7ee5c 100644
--- a/app/view/templates/connect.php
+++ b/app/view/templates/connect.php
@@ -11,7 +11,11 @@
<?php if($user->isvisitor()) { ?>
+<?= $route === 'artedit' ? '<p>Your edits have been temporary saved. You need to connect and update to store it completly</p>' : '' ?>
+
<form action="<?= $this->url('log') ?>" method="post">
+<input type="hidden" name="route" value="<?= $route ?>">
+<input type="hidden" name="id" value="<?= $id ?>">
<input type="password" name="pass" id="loginpass" placeholder="password">
<input name="log" type="submit" value="login">
</form>
diff --git a/app/view/templates/navart.php b/app/view/templates/navart.php
index be3b248..1e6b551 100644
--- a/app/view/templates/navart.php
+++ b/app/view/templates/navart.php
@@ -72,6 +72,7 @@
<li class="drop">
<form action="<?= $this->url('log') ?>" method="post">
<input type="password" name="pass" id="loginpass" placeholder="password">
+ <input type="hidden" name="route" value="artread/">
<input type="hidden" name="id" value="<?= $art->id() ?>">
<input type="submit" name="log" value="login" id="button">
</form>
@@ -82,6 +83,7 @@
<li class="drop">
<form action="<?= $this->url('log') ?>" method="post">
<input type="hidden" name="id" value="<?= $art->id() ?>">
+ <input type="hidden" name="route" value="artread/">
<input type="submit" name="log" value="logout" id="button">
</form>
</li>
diff --git a/app/view/templates/timeline.php b/app/view/templates/timeline.php
new file mode 100644
index 0000000..fcf8afd
--- /dev/null
+++ b/app/view/templates/timeline.php
@@ -0,0 +1,90 @@
+<?php $this->layout('layout', ['title' => 'timeline', 'css' => $css . 'home.css', 'favicon' => '']) ?>
+
+
+
+
+<?php $this->start('page') ?>
+
+
+<body>
+
+ <?php $this->insert('backtopbar', ['user' => $user, 'tab' => 'timeline']) ?>
+
+<?php if($user->iseditor()) { ?>
+
+<main class="timeline">
+
+<h1>Timeline</h1>
+
+<ul>
+
+<?php
+foreach ($groupedeventlist as $eventuser) {
+
+ if($user->id() === $eventuser['user']) {
+ $class = 'class="self user"';
+ } else {
+ $class = 'class="user"';
+ }
+ echo '<li '. $class .'>';
+ echo '<h3>'. $eventuser['user'] .'</h3>';
+ echo' <ul>';
+ foreach ($eventuser as $key => $event) {
+ if($key !== 'user') {
+ echo '<li class="event">';
+ switch ($event->type()) {
+ case 'message':
+ echo '<p class="eline">'. $event->message() .'</p>';
+ break;
+ }
+
+ ?>
+
+
+ <?= !empty($event->clap()) ? '<b class="eline">'. $event->clap() .'</b>' : '' ?>
+
+ <span class="details">
+
+ <?php if($user->id() !== $eventuser['user']) {?>
+ <form class="eline" method="post" action="<?= $this->url('timelineclap') ?>">
+ <input type="hidden" name="id" value="<?= $event->id() ?>">
+ <input type="submit" name="clap" value="👌">
+ </form>
+ <?php } ?>
+
+
+ <i class="eline"><?= $event->date('hrdi') ?> ago</i>
+
+ </span>
+
+ </li>
+
+ <?php
+ }
+ }
+ echo '</ul></li>';
+}
+?>
+
+</ul>
+
+<form action="<?= $this->url('timelineadd') ?>" method="post">
+
+<input type="hidden" name="type" value="message">
+
+<input type="hidden" name="user" value="<?= $user->id() ?>">
+
+<label for="message">message</label>
+<textarea name="message" id="message" cols="30" rows="10" autofocus></textarea>
+<input type="submit" value="send">
+</form>
+
+</main>
+
+<?php } ?>
+
+</body>
+
+
+
+<?php $this->stop() ?> \ No newline at end of file