1<?php 2/** 3 * DokuWiki Plugin acknowledge (Helper Component) 4 * 5 * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html 6 * @author Andreas Gohr, Anna Dabrowska <dokuwiki@cosmocode.de> 7 */ 8 9 10class helper_plugin_acknowledge extends DokuWiki_Plugin 11{ 12 13 /** 14 * @return helper_plugin_sqlite|null 15 */ 16 public function getDB() 17 { 18 /** @var \helper_plugin_sqlite $sqlite */ 19 $sqlite = plugin_load('helper', 'sqlite'); 20 if ($sqlite === null) { 21 msg($this->getLang('error sqlite plugin missing'), -1); 22 return null; 23 } 24 if (!$sqlite->init('acknowledgement', __DIR__ . '/db')) { 25 return null; 26 } 27 28 return $sqlite; 29 } 30 31 /** 32 * Delete a page 33 * 34 * Cascades to delete all assigned data, etc. 35 * 36 * @param string $page Page ID 37 */ 38 public function removePage($page) 39 { 40 $sqlite = $this->getDB(); 41 if (!$sqlite) return; 42 43 $sql = "DELETE FROM pages WHERE page = ?"; 44 $sqlite->query($sql, $page); 45 } 46 47 /** 48 * Update last modified date of page 49 * 50 * @param string $page Page ID 51 * @param int $lastmod timestamp of last non-minor change 52 */ 53 public function storePageDate($page, $lastmod) 54 { 55 $sqlite = $this->getDB(); 56 if (!$sqlite) return; 57 58 $sql = "REPLACE INTO pages (page, lastmod) VALUES (?,?)"; 59 $sqlite->query($sql, $page, $lastmod); 60 } 61 62 /** 63 * @param string $page Page ID 64 * @param string $assignees comma separated list of users and groups 65 */ 66 public function setAssignees($page, $assignees) 67 { 68 $sqlite = $this->getDB(); 69 if (!$sqlite) return; 70 71 $sql = "REPLACE INTO assignments ('page', 'assignee') VALUES (?,?)"; 72 $sqlite->query($sql, $page, $assignees); 73 } 74 75 /** 76 * Clears assignments for a page 77 * 78 * @param string $page Page ID 79 */ 80 public function clearAssignments($page) 81 { 82 $sqlite = $this->getDB(); 83 if (!$sqlite) return; 84 85 $sql = "DELETE FROM assignments WHERE page = ?"; 86 $sqlite->query($sql, $page); 87 } 88 89 90 /** 91 * Is the given user one of the assignees for this page 92 * 93 * @param string $page Page ID 94 * @param string $user user name to check 95 * @param string[] $groups groups this user is in 96 * @return bool 97 */ 98 public function isUserAssigned($page, $user, $groups) 99 { 100 $sqlite = $this->getDB(); 101 if (!$sqlite) return false; 102 103 104 $sql = "SELECT assignee FROM assignments WHERE page = ?"; 105 $result = $sqlite->query($sql, $page); 106 $assignees = (string)$sqlite->res2single($result); 107 $sqlite->res_close($result); 108 109 return auth_isMember($assignees, $user, $groups); 110 } 111 112 /** 113 * Has the given user acknowledged the given page? 114 * 115 * @param string $page 116 * @param string $user 117 * @return bool|int timestamp of acknowledgement or false 118 */ 119 public function hasUserAcknowledged($page, $user) 120 { 121 $sqlite = $this->getDB(); 122 if (!$sqlite) return false; 123 124 $sql = "SELECT ack 125 FROM acks A, pages B 126 WHERE A.page = B.page 127 AND A.page = ? 128 AND A.user = ? 129 AND A.ack >= B.lastmod"; 130 131 $result = $sqlite->query($sql, $page, $user); 132 $acktime = $sqlite->res2single($result); 133 $sqlite->res_close($result); 134 135 return $acktime ? (int)$acktime : false; 136 } 137 138 /** 139 * Save user's acknowledgement for a given page 140 * 141 * @param string $page 142 * @param string $user 143 * @return bool 144 */ 145 public function saveAcknowledgement($page, $user) 146 { 147 $sqlite = $this->getDB(); 148 if (!$sqlite) return false; 149 150 $sql = "REPLACE INTO acks (page, user, ack) VALUES (?,?, strftime('%s','now'))"; 151 152 $result = $sqlite->query($sql, $page, $user); 153 $sqlite->res_close($result); 154 return true; 155 156 } 157 158 /** 159 * Fetch all assignments for a given user, with additional page information. 160 * 161 * @param string $user 162 * @return array|bool 163 */ 164 public function getUserAssignments($user) 165 { 166 $sqlite = $this->getDB(); 167 if (!$sqlite) return false; 168 169 global $USERINFO; 170 $groups = $USERINFO['grps']; 171 172 $sql = "SELECT * FROM assignments A 173 JOIN pages B 174 ON A.page = B.page 175 WHERE A.assignee LIKE ? OR A.assignee LIKE ?"; 176 177 $userWildcard = '%' . $user . '%'; 178 $groupWildcard = '%@' . $groups . '%'; 179 180 $result = $sqlite->query($sql, $userWildcard, $groupWildcard); 181 $assignments = $sqlite->res2arr($result); 182 $sqlite->res_close($result); 183 184 return $assignments; 185 } 186 187 /** 188 * Compare user's assignments with their past acknowledgements and return only pages 189 * without or with outdated acknowledgements 190 * 191 * @param string $user 192 * @param array $assignments 193 * @return array|bool 194 */ 195 public function filterAcknowledged($user, $assignments) 196 { 197 $sqlite = $this->getDB(); 198 if (!$sqlite) return false; 199 200 $sql = 'SELECT * FROM acks WHERE user = ?'; 201 $result = $sqlite->query($sql, $user); 202 $acknowledgements = $sqlite->res2arr($result); 203 $sqlite->res_close($result); 204 205 $listing = []; 206 $pageAcks = array_column($acknowledgements, 'ack', 'page'); 207 foreach ($assignments as $assignment) { 208 if ( 209 !in_array($assignment['page'], array_keys($pageAcks)) 210 || (int)$assignment['lastmod'] > (int)$pageAcks[$assignment['page']] 211 ) { 212 $listing[] = $assignment; 213 } 214 } 215 216 return $listing; 217 } 218 219 /** 220 * Returns all acknowledgements 221 * 222 * @return array|bool 223 */ 224 public function getAcknowledgements() 225 { 226 $sqlite = $this->getDB(); 227 if (!$sqlite) return false; 228 229 $sql = 'SELECT * FROM acks ORDER BY ack DESC'; 230 $result = $sqlite->query($sql); 231 $acknowledgements = $sqlite->res2arr($result); 232 $sqlite->res_close($result); 233 234 return $acknowledgements; 235 } 236} 237 238