Commit 8726b3a73cf5515c594be8516703aae448e60b6b

Authored by kevin_fourie
1 parent e11e8cdc

Merged in from STABLE trunk...

KTS-1397
"Extending subscription to subfolders"
Fixed. Added a DB column to indicate that subfolders should be included. Refactored the way subscribing worked to use ajax.

Committed by: Megan Watson
Reviewed by: Conrad Vermeulen


git-svn-id: https://kt-dms.svn.sourceforge.net/svnroot/kt-dms/STABLE/branches/3.5.3a-Release-Branch@9292 c91229c3-7414-0410-bfa2-8a42b809f60b
lib/subscriptions/Subscription.inc
@@ -4,31 +4,31 @@ @@ -4,31 +4,31 @@
4 * Document Management Made Simple 4 * Document Management Made Simple
5 * Copyright (C) 2008 KnowledgeTree Inc. 5 * Copyright (C) 2008 KnowledgeTree Inc.
6 * Portions copyright The Jam Warehouse Software (Pty) Limited 6 * Portions copyright The Jam Warehouse Software (Pty) Limited
7 - * 7 + *
8 * This program is free software; you can redistribute it and/or modify it under 8 * This program is free software; you can redistribute it and/or modify it under
9 * the terms of the GNU General Public License version 3 as published by the 9 * the terms of the GNU General Public License version 3 as published by the
10 * Free Software Foundation. 10 * Free Software Foundation.
11 - * 11 + *
12 * This program is distributed in the hope that it will be useful, but WITHOUT 12 * This program is distributed in the hope that it will be useful, but WITHOUT
13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 14 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
15 * details. 15 * details.
16 - * 16 + *
17 * You should have received a copy of the GNU General Public License 17 * You should have received a copy of the GNU General Public License
18 * along with this program. If not, see <http://www.gnu.org/licenses/>. 18 * along with this program. If not, see <http://www.gnu.org/licenses/>.
19 - *  
20 - * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco, 19 + *
  20 + * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco,
21 * California 94120-7775, or email info@knowledgetree.com. 21 * California 94120-7775, or email info@knowledgetree.com.
22 - * 22 + *
23 * The interactive user interfaces in modified source and object code versions 23 * The interactive user interfaces in modified source and object code versions
24 * of this program must display Appropriate Legal Notices, as required under 24 * of this program must display Appropriate Legal Notices, as required under
25 * Section 5 of the GNU General Public License version 3. 25 * Section 5 of the GNU General Public License version 3.
26 - * 26 + *
27 * In accordance with Section 7(b) of the GNU General Public License version 3, 27 * In accordance with Section 7(b) of the GNU General Public License version 3,
28 * these Appropriate Legal Notices must retain the display of the "Powered by 28 * these Appropriate Legal Notices must retain the display of the "Powered by
29 - * KnowledgeTree" logo and retain the original copyright notice. If the display of the 29 + * KnowledgeTree" logo and retain the original copyright notice. If the display of the
30 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices 30 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices
31 - * must display the words "Powered by KnowledgeTree" and retain the original 31 + * must display the words "Powered by KnowledgeTree" and retain the original
32 * copyright notice. 32 * copyright notice.
33 * Contributor( s): ______________________________________ 33 * Contributor( s): ______________________________________
34 * 34 *
@@ -62,6 +62,10 @@ class Subscription extends KTEntity { @@ -62,6 +62,10 @@ class Subscription extends KTEntity {
62 */ 62 */
63 var $bIsAlerted; 63 var $bIsAlerted;
64 /** 64 /**
  65 + * Whether subfolders should be included
  66 + */
  67 + var $bWithSubFolders;
  68 + /**
65 * The subscription database table to use 69 * The subscription database table to use
66 */ 70 */
67 var $sTableName; 71 var $sTableName;
@@ -155,6 +159,24 @@ class Subscription extends KTEntity { @@ -155,6 +159,24 @@ class Subscription extends KTEntity {
155 } 159 }
156 160
157 /** 161 /**
  162 + * Get the depth of the subscription
  163 + *
  164 + * @return boolean the depth of this subscription
  165 + */
  166 + function getWithSubFolders() {
  167 + return $this->bWithSubFolders;
  168 + }
  169 +
  170 + /**
  171 + * Set the depth of the subscription
  172 + *
  173 + * @param boolean new depth status
  174 + */
  175 + function setWithSubFolders($iNewValue) {
  176 + $this->bWithSubFolders = $iNewValue;
  177 + }
  178 +
  179 + /**
158 * Returns the display path to the subscription content 180 * Returns the display path to the subscription content
159 */ 181 */
160 function getContentDisplayPath() { 182 function getContentDisplayPath() {
@@ -217,11 +239,15 @@ class Subscription extends KTEntity { @@ -217,11 +239,15 @@ class Subscription extends KTEntity {
217 } 239 }
218 240
219 function _fieldValues () { 241 function _fieldValues () {
220 - return array( 242 + $fields = array(
221 'user_id' => $this->iUserID, 243 'user_id' => $this->iUserID,
222 $this->sIdFieldName => $this->iExternalID, 244 $this->sIdFieldName => $this->iExternalID,
223 'is_alerted' => KTUtil::anyToBool($this->bIsAlerted), 245 'is_alerted' => KTUtil::anyToBool($this->bIsAlerted),
224 ); 246 );
  247 + if($this->sIdFieldName == 'folder_id'){
  248 + $fields['with_subfolders'] = KTUtil::anyToBool($this->bWithSubFolders);
  249 + }
  250 + return $fields;
225 } 251 }
226 252
227 function _table () { 253 function _table () {
lib/subscriptions/subscriptions.inc.php
@@ -6,31 +6,31 @@ @@ -6,31 +6,31 @@
6 * Document Management Made Simple 6 * Document Management Made Simple
7 * Copyright (C) 2008 KnowledgeTree Inc. 7 * Copyright (C) 2008 KnowledgeTree Inc.
8 * Portions copyright The Jam Warehouse Software (Pty) Limited 8 * Portions copyright The Jam Warehouse Software (Pty) Limited
9 - * 9 + *
10 * This program is free software; you can redistribute it and/or modify it under 10 * This program is free software; you can redistribute it and/or modify it under
11 * the terms of the GNU General Public License version 3 as published by the 11 * the terms of the GNU General Public License version 3 as published by the
12 * Free Software Foundation. 12 * Free Software Foundation.
13 - * 13 + *
14 * This program is distributed in the hope that it will be useful, but WITHOUT 14 * This program is distributed in the hope that it will be useful, but WITHOUT
15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 16 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
17 * details. 17 * details.
18 - * 18 + *
19 * You should have received a copy of the GNU General Public License 19 * You should have received a copy of the GNU General Public License
20 * along with this program. If not, see <http://www.gnu.org/licenses/>. 20 * along with this program. If not, see <http://www.gnu.org/licenses/>.
21 - *  
22 - * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco, 21 + *
  22 + * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco,
23 * California 94120-7775, or email info@knowledgetree.com. 23 * California 94120-7775, or email info@knowledgetree.com.
24 - * 24 + *
25 * The interactive user interfaces in modified source and object code versions 25 * The interactive user interfaces in modified source and object code versions
26 * of this program must display Appropriate Legal Notices, as required under 26 * of this program must display Appropriate Legal Notices, as required under
27 * Section 5 of the GNU General Public License version 3. 27 * Section 5 of the GNU General Public License version 3.
28 - * 28 + *
29 * In accordance with Section 7(b) of the GNU General Public License version 3, 29 * In accordance with Section 7(b) of the GNU General Public License version 3,
30 * these Appropriate Legal Notices must retain the display of the "Powered by 30 * these Appropriate Legal Notices must retain the display of the "Powered by
31 - * KnowledgeTree" logo and retain the original copyright notice. If the display of the 31 + * KnowledgeTree" logo and retain the original copyright notice. If the display of the
32 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices 32 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices
33 - * must display the words "Powered by KnowledgeTree" and retain the original 33 + * must display the words "Powered by KnowledgeTree" and retain the original
34 * copyright notice. 34 * copyright notice.
35 * Contributor( s): ______________________________________ 35 * Contributor( s): ______________________________________
36 * 36 *
@@ -101,55 +101,20 @@ class SubscriptionEvent { @@ -101,55 +101,20 @@ class SubscriptionEvent {
101 101
102 // only useful for folder subscriptions. 102 // only useful for folder subscriptions.
103 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]); 103 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
104 - foreach ($aUsers as $oSubscriber) {  
105 104
106 - // notification object first.  
107 - $aNotificationOptions = array();  
108 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
109 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
110 - $aNotificationOptions['target_name'] = $oAddedFolder->getName();  
111 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
112 - $aNotificationOptions['object_id'] = $oAddedFolder->getId(); // parent folder_id, in this case.  
113 - $aNotificationOptions['event_type'] = "AddFolder";  
114 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
115 -  
116 - // now the email content.  
117 - // FIXME this needs to be handled entirely within notifications from now on.  
118 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
119 - $emailContent = $content->getEmailAlertContent($oNotification);  
120 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
121 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
122 - $oEmail->send();  
123 - }  
124 - } 105 + $parentId = $oParentFolder->getId();
  106 + $this->sendNotification($aUsers, 'AddFolder', $oAddedFolder->getName(), $oAddedFolder->getId(), $parentId);
125 } 107 }
  108 +
126 function AddDocument ($oAddedDocument, $oParentFolder) { 109 function AddDocument ($oAddedDocument, $oParentFolder) {
127 $content = new SubscriptionContent(); // needed for i18n 110 $content = new SubscriptionContent(); // needed for i18n
128 // two parts to this: 111 // two parts to this:
129 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]); 112 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
130 - foreach ($aUsers as $oSubscriber) {  
131 -  
132 - // notification object first.  
133 - $aNotificationOptions = array();  
134 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
135 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null - is this valid?  
136 - $aNotificationOptions['target_name'] = $oAddedDocument->getName();  
137 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
138 - $aNotificationOptions['object_id'] = $oAddedDocument->getId(); // parent folder_id, in this case.  
139 - $aNotificationOptions['event_type'] = "AddDocument";  
140 113
141 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
142 -  
143 - // now the email content.  
144 - // FIXME this needs to be handled entirely within notifications from now on.  
145 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
146 - $emailContent = $content->getEmailAlertContent($oNotification);  
147 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
148 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
149 - $oEmail->send();  
150 - }  
151 - } 114 + $parentId = $oParentFolder->getId();
  115 + $this->sendNotification($aUsers, 'AddDocument', $oAddedDocument->getName(), $oAddedDocument->getId(), $parentId);
152 } 116 }
  117 +
153 function RemoveFolder($oRemovedFolder, $oParentFolder) { 118 function RemoveFolder($oRemovedFolder, $oParentFolder) {
154 $content = new SubscriptionContent(); // needed for i18n 119 $content = new SubscriptionContent(); // needed for i18n
155 // two cases to consider here: 120 // two cases to consider here:
@@ -188,29 +153,11 @@ class SubscriptionEvent { @@ -188,29 +153,11 @@ class SubscriptionEvent {
188 153
189 // now handle (for those who haven't been alerted) users watching the folder. 154 // now handle (for those who haven't been alerted) users watching the folder.
190 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]); 155 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
191 - foreach ($aUsers as $oSubscriber) {  
192 -  
193 - // notification object first.  
194 - $aNotificationOptions = array();  
195 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
196 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
197 - $aNotificationOptions['target_name'] = $oRemovedFolder->getName();  
198 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
199 - $aNotificationOptions['object_id'] = $oParentFolder->getId(); // parent folder_id, since the removed one is removed.  
200 - $aNotificationOptions['event_type'] = "RemoveChildFolder";  
201 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
202 -  
203 - // now the email content.  
204 - // FIXME this needs to be handled entirely within notifications from now on.  
205 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
206 - $emailContent = $content->getEmailAlertContent($oNotification);  
207 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
208 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
209 - $oEmail->send();  
210 - }  
211 - }  
212 156
  157 + $parentId = $oParentFolder->getId();
  158 + $this->sendNotification($aUsers, 'RemoveChildFolder', $oRemovedFolder->getName(), $oParentFolder->getId(), $parentId);
213 } 159 }
  160 +
214 function RemoveDocument($oRemovedDocument, $oParentFolder) { 161 function RemoveDocument($oRemovedDocument, $oParentFolder) {
215 $content = new SubscriptionContent(); // needed for i18n 162 $content = new SubscriptionContent(); // needed for i18n
216 // two cases to consider here: 163 // two cases to consider here:
@@ -249,457 +196,126 @@ class SubscriptionEvent { @@ -249,457 +196,126 @@ class SubscriptionEvent {
249 196
250 // now handle (for those who haven't been alerted) users watching the folder. 197 // now handle (for those who haven't been alerted) users watching the folder.
251 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]); 198 $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
252 - foreach ($aUsers as $oSubscriber) {  
253 -  
254 - // notification object first.  
255 - $aNotificationOptions = array();  
256 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
257 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
258 - $aNotificationOptions['target_name'] = $oRemovedDocument->getName();  
259 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
260 - $aNotificationOptions['object_id'] = $oParentFolder->getId(); // parent folder_id, since the removed one is removed.  
261 - $aNotificationOptions['event_type'] = "RemoveChildDocument";  
262 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
263 -  
264 - // now the email content.  
265 - // FIXME this needs to be handled entirely within notifications from now on.  
266 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
267 - $emailContent = $content->getEmailAlertContent($oNotification);  
268 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
269 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
270 - $oEmail->send();  
271 - }  
272 - }  
273 199
  200 + $parentId = $oParentFolder->getId();
  201 + $this->sendNotification($aUsers, 'RemoveChildDocument', $oRemovedDocument->getName(), $oParentFolder->getId(), $parentId);
274 } 202 }
275 function ModifyDocument($oModifiedDocument, $oParentFolder) { 203 function ModifyDocument($oModifiedDocument, $oParentFolder) {
276 $content = new SubscriptionContent(); // needed for i18n 204 $content = new SubscriptionContent(); // needed for i18n
277 // OK: two actions: document registrants, folder registrants. 205 // OK: two actions: document registrants, folder registrants.
278 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
279 - foreach ($aUsers as $oSubscriber) {  
280 -  
281 - // notification object first.  
282 - $aNotificationOptions = array();  
283 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
284 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
285 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
286 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
287 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
288 - $aNotificationOptions['event_type'] = "ModifyDocument";  
289 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
290 -  
291 - // now the email content.  
292 - // FIXME this needs to be handled entirely within notifications from now on.  
293 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
294 - $emailContent = $content->getEmailAlertContent($oNotification);  
295 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
296 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
297 - $oEmail->send();  
298 - }  
299 - }  
300 - 206 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  207 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  208 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
301 209
302 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
303 - foreach ($aUsers as $oSubscriber) {  
304 -  
305 - // notification object first.  
306 - $aNotificationOptions = array();  
307 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
308 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
309 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
310 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
311 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
312 - $aNotificationOptions['event_type'] = "ModifyDocument";  
313 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
314 -  
315 - // now the email content.  
316 - // FIXME this needs to be handled entirely within notifications from now on.  
317 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
318 - $emailContent = $content->getEmailAlertContent($oNotification);  
319 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
320 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
321 - $oEmail->send();  
322 - }  
323 - } 210 + $parentId = $oParentFolder->getId();
  211 + $this->sendNotification($aUsers, 'ModifyDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
324 } 212 }
325 213
326 function DiscussDocument($oModifiedDocument, $oParentFolder) { 214 function DiscussDocument($oModifiedDocument, $oParentFolder) {
327 $content = new SubscriptionContent(); // needed for i18n 215 $content = new SubscriptionContent(); // needed for i18n
328 // OK: two actions: document registrants, folder registrants. 216 // OK: two actions: document registrants, folder registrants.
329 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
330 - foreach ($aUsers as $oSubscriber) {  
331 -  
332 - // notification object first.  
333 - $aNotificationOptions = array();  
334 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
335 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
336 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
337 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
338 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
339 - $aNotificationOptions['event_type'] = "DiscussDocument";  
340 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions); 217 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  218 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  219 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
341 220
342 - // now the email content.  
343 - // FIXME this needs to be handled entirely within notifications from now on.  
344 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
345 - $emailContent = $content->getEmailAlertContent($oNotification);  
346 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
347 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
348 - $oEmail->send();  
349 - }  
350 - }  
351 -  
352 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
353 - foreach ($aUsers as $oSubscriber) {  
354 -  
355 - // notification object first.  
356 - $aNotificationOptions = array();  
357 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
358 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
359 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
360 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
361 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
362 - $aNotificationOptions['event_type'] = "DiscussDocument";  
363 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
364 -  
365 - // now the email content.  
366 - // FIXME this needs to be handled entirely within notifications from now on.  
367 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
368 - $emailContent = $content->getEmailAlertContent($oNotification);  
369 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
370 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
371 - $oEmail->send();  
372 - }  
373 - } 221 + $parentId = $oParentFolder->getId();
  222 + $this->sendNotification($aUsers, 'DiscussDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
374 } 223 }
375 224
376 function CheckInDocument($oModifiedDocument, $oParentFolder) { 225 function CheckInDocument($oModifiedDocument, $oParentFolder) {
377 $content = new SubscriptionContent(); // needed for i18n 226 $content = new SubscriptionContent(); // needed for i18n
378 // OK: two actions: document registrants, folder registrants. 227 // OK: two actions: document registrants, folder registrants.
379 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
380 - foreach ($aUsers as $oSubscriber) {  
381 -  
382 - // notification object first.  
383 - $aNotificationOptions = array();  
384 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
385 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
386 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
387 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
388 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
389 - $aNotificationOptions['event_type'] = "CheckInDocument";  
390 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
391 -  
392 - // now the email content.  
393 - // FIXME this needs to be handled entirely within notifications from now on.  
394 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
395 - $emailContent = $content->getEmailAlertContent($oNotification);  
396 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
397 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
398 - $oEmail->send();  
399 - }  
400 - }  
401 - 228 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  229 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  230 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
402 231
403 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
404 -  
405 - foreach ($aUsers as $oSubscriber) {  
406 -  
407 - // notification object first.  
408 - $aNotificationOptions = array();  
409 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
410 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
411 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
412 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
413 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
414 - $aNotificationOptions['event_type'] = "CheckInDocument";  
415 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
416 -  
417 - // now the email content.  
418 - // FIXME this needs to be handled entirely within notifications from now on.  
419 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
420 - $emailContent = $content->getEmailAlertContent($oNotification);  
421 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
422 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
423 - $oEmail->send();  
424 -  
425 - }  
426 - } 232 + $parentId = $oParentFolder->getId();
  233 + $this->sendNotification($aUsers, 'CheckInDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
427 } 234 }
  235 +
428 function CheckOutDocument($oModifiedDocument, $oParentFolder) { 236 function CheckOutDocument($oModifiedDocument, $oParentFolder) {
429 $content = new SubscriptionContent(); // needed for i18n 237 $content = new SubscriptionContent(); // needed for i18n
430 // OK: two actions: document registrants, folder registrants. 238 // OK: two actions: document registrants, folder registrants.
431 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
432 -  
433 - foreach ($aUsers as $oSubscriber) {  
434 -  
435 - // notification object first.  
436 - $aNotificationOptions = array();  
437 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
438 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
439 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
440 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
441 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
442 - $aNotificationOptions['event_type'] = "CheckOutDocument";  
443 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
444 -  
445 - // now the email content.  
446 - // FIXME this needs to be handled entirely within notifications from now on.  
447 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
448 - $emailContent = $content->getEmailAlertContent($oNotification);  
449 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
450 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
451 - $oEmail->send();  
452 - }  
453 - }  
454 - 239 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  240 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  241 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
455 242
456 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
457 - foreach ($aUsers as $oSubscriber) {  
458 -  
459 - // notification object first.  
460 - $aNotificationOptions = array();  
461 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
462 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
463 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
464 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
465 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
466 - $aNotificationOptions['event_type'] = "CheckOutDocument";  
467 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
468 -  
469 - // now the email content.  
470 - // FIXME this needs to be handled entirely within notifications from now on.  
471 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
472 - $emailContent = $content->getEmailAlertContent($oNotification);  
473 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
474 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
475 - $oEmail->send();  
476 - }  
477 - } 243 + $parentId = $oParentFolder->getId();
  244 + $this->sendNotification($aUsers, 'CheckOutDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
478 } 245 }
479 246
480 function MoveDocument($oMovedDocument, $oToFolder, $oFromFolder, $moveOrCopy = "MovedDocument") { 247 function MoveDocument($oMovedDocument, $oToFolder, $oFromFolder, $moveOrCopy = "MovedDocument") {
481 $content = new SubscriptionContent(); // needed for i18n 248 $content = new SubscriptionContent(); // needed for i18n
482 // OK: two actions: document registrants, folder registrants. 249 // OK: two actions: document registrants, folder registrants.
483 - $aUsers = $this->_getSubscribers($oMovedDocument->getId(), $this->subscriptionTypes["Document"]);  
484 -  
485 - foreach ($aUsers as $oSubscriber) {  
486 - // notification object first.  
487 - $aNotificationOptions = array();  
488 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
489 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
490 - $aNotificationOptions['target_name'] = $oMovedDocument->getName();  
491 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oToFolder->getId());  
492 - $aNotificationOptions['object_id'] = $oToFolder->getId(); // parent folder_id, in this case.  
493 - $aNotificationOptions['event_type'] = $moveOrCopy;  
494 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
495 -  
496 - // now the email content.  
497 - // FIXME this needs to be handled entirely within notifications from now on.  
498 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
499 - $emailContent = $content->getEmailAlertContent($oNotification);  
500 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
501 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
502 - $oEmail->send();  
503 - }  
504 - }  
505 -  
506 -  
507 - $aUsers = $this->_getSubscribers($oFromFolder->getId(), $this->subscriptionTypes["Folder"]);  
508 -  
509 - foreach ($aUsers as $oSubscriber) {  
510 -  
511 - // notification object first.  
512 - $aNotificationOptions = array();  
513 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
514 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
515 - $aNotificationOptions['target_name'] = $oMovedDocument->getName();  
516 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oToFolder->getId());  
517 - $aNotificationOptions['object_id'] = $oToFolder->getId(); // parent folder_id, in this case.  
518 - $aNotificationOptions['event_type'] = $moveOrCopy;  
519 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
520 -  
521 - // now the email content.  
522 - // FIXME this needs to be handled entirely within notifications from now on.  
523 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
524 - $emailContent = $content->getEmailAlertContent($oNotification);  
525 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
526 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
527 - $oEmail->send();  
528 - }  
529 - }  
530 -  
531 - $aUsers = $this->_getSubscribers($oToFolder->getId(), $this->subscriptionTypes["Folder"]);  
532 - foreach ($aUsers as $oSubscriber) {  
533 -  
534 - // notification object first.  
535 - $aNotificationOptions = array();  
536 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
537 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
538 - $aNotificationOptions['target_name'] = $oMovedDocument->getName();  
539 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oToFolder->getId());  
540 - $aNotificationOptions['object_id'] = $oToFolder->getId(); // parent folder_id, in this case.  
541 - $aNotificationOptions['event_type'] = $moveOrCopy;  
542 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
543 -  
544 - // now the email content.  
545 - // FIXME this needs to be handled entirely within notifications from now on.  
546 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
547 - $emailContent = $content->getEmailAlertContent($oNotification);  
548 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
549 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
550 - $oEmail->send();  
551 - }  
552 - } 250 + $aDocUsers = $this->_getSubscribers($oMovedDocument->getId(), $this->subscriptionTypes["Document"]);
  251 + $aFromUsers = $this->_getSubscribers($oFromFolder->getId(), $this->subscriptionTypes["Folder"]);
  252 + $aFolderUsers = $this->_getSubscribers($oToFolder->getId(), $this->subscriptionTypes["Folder"]);
  253 + $aUsers = array_merge($aDocUsers, $aFromUsers);
  254 + $aUsers = array_merge($aUsers, $aFolderUsers);
  255 +
  256 + $parentId = $oToFolder->getId();
  257 + $this->sendNotification($aUsers, $moveOrCopy, $oMovedDocument->getName(), $oToFolder->getId(), $parentId);
553 } 258 }
554 259
555 function ArchivedDocument($oModifiedDocument, $oParentFolder) { 260 function ArchivedDocument($oModifiedDocument, $oParentFolder) {
556 $content = new SubscriptionContent(); // needed for i18n 261 $content = new SubscriptionContent(); // needed for i18n
557 // OK: two actions: document registrants, folder registrants. 262 // OK: two actions: document registrants, folder registrants.
558 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
559 - foreach ($aUsers as $oSubscriber) { 263 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  264 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  265 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
560 266
561 - // notification object first.  
562 - $aNotificationOptions = array();  
563 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
564 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
565 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
566 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
567 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
568 - $aNotificationOptions['event_type'] = "ArchivedDocument";  
569 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
570 -  
571 - // now the email content.  
572 - // FIXME this needs to be handled entirely within notifications from now on.  
573 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
574 - $emailContent = $content->getEmailAlertContent($oNotification);  
575 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
576 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
577 - $oEmail->send();  
578 - }  
579 - }  
580 -  
581 -  
582 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
583 - foreach ($aUsers as $oSubscriber) {  
584 -  
585 - // notification object first.  
586 - $aNotificationOptions = array();  
587 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
588 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
589 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
590 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
591 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
592 - $aNotificationOptions['event_type'] = "ArchivedDocument";  
593 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
594 -  
595 - // now the email content.  
596 - // FIXME this needs to be handled entirely within notifications from now on.  
597 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
598 - $emailContent = $content->getEmailAlertContent($oNotification);  
599 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
600 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
601 - $oEmail->send();  
602 - }  
603 - } 267 + $parentId = $oParentFolder->getId();
  268 + $this->sendNotification($aUsers, 'ArchivedDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
604 } 269 }
605 270
606 function RestoreDocument($oModifiedDocument, $oParentFolder) { 271 function RestoreDocument($oModifiedDocument, $oParentFolder) {
607 $content = new SubscriptionContent(); // needed for i18n 272 $content = new SubscriptionContent(); // needed for i18n
608 // OK: two actions: document registrants, folder registrants. 273 // OK: two actions: document registrants, folder registrants.
609 - $aUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);  
610 - foreach ($aUsers as $oSubscriber) {  
611 -  
612 - // notification object first.  
613 - $aNotificationOptions = array();  
614 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
615 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
616 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
617 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
618 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
619 - $aNotificationOptions['event_type'] = "RestoreArchivedDocument";  
620 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
621 -  
622 - // now the email content.  
623 - // FIXME this needs to be handled entirely within notifications from now on.  
624 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
625 - $emailContent = $content->getEmailAlertContent($oNotification);  
626 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
627 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
628 - $oEmail->send();  
629 - }  
630 - }  
631 -  
632 -  
633 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);  
634 - foreach ($aUsers as $oSubscriber) { 274 + $aDocUsers = $this->_getSubscribers($oModifiedDocument->getId(), $this->subscriptionTypes["Document"]);
  275 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  276 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
635 277
636 - // notification object first.  
637 - $aNotificationOptions = array();  
638 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
639 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
640 - $aNotificationOptions['target_name'] = $oModifiedDocument->getName();  
641 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
642 - $aNotificationOptions['object_id'] = $oModifiedDocument->getId(); // parent folder_id, in this case.  
643 - $aNotificationOptions['event_type'] = "RestoreArchivedDocument";  
644 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);  
645 -  
646 - // now the email content.  
647 - // FIXME this needs to be handled entirely within notifications from now on.  
648 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
649 - $emailContent = $content->getEmailAlertContent($oNotification);  
650 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
651 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
652 - $oEmail->send();  
653 - }  
654 - } 278 + $parentId = $oParentFolder->getId();
  279 + $this->sendNotification($aUsers, 'RestoreArchivedDocument', $oModifiedDocument->getName(), $oModifiedDocument->getId(), $parentId);
655 } 280 }
656 281
657 function DownloadDocument($oDocument, $oParentFolder) { 282 function DownloadDocument($oDocument, $oParentFolder) {
658 $content = new SubscriptionContent(); // needed for i18n 283 $content = new SubscriptionContent(); // needed for i18n
659 // OK: two actions: document registrants, folder registrants. 284 // OK: two actions: document registrants, folder registrants.
660 - $aUsers = $this->_getSubscribers($oDocument->getId(), $this->subscriptionTypes["Document"]);  
661 - foreach ($aUsers as $oSubscriber) { 285 + $aDocUsers = $this->_getSubscribers($oDocument->getId(), $this->subscriptionTypes["Document"]);
  286 + $aFolderUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]);
  287 + $aUsers = array_merge($aDocUsers, $aFolderUsers);
662 288
663 - // notification object first.  
664 - $aNotificationOptions = array();  
665 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
666 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
667 - $aNotificationOptions['target_name'] = $oDocument->getName();  
668 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
669 - $aNotificationOptions['object_id'] = $oDocument->getId(); // parent folder_id, in this case.  
670 - $aNotificationOptions['event_type'] = "DownloadDocument";  
671 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions); 289 + $parentId = $oParentFolder->getId();
  290 + $this->sendNotification($aUsers, 'DownloadDocument', $oDocument->getName(), $oDocument->getId(), $parentId);
  291 + }
672 292
673 - // now the email content.  
674 - // FIXME this needs to be handled entirely within notifications from now on.  
675 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) {  
676 - $emailContent = $content->getEmailAlertContent($oNotification);  
677 - $emailSubject = $content->getEmailAlertSubject($oNotification);  
678 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent);  
679 - $oEmail->send();  
680 - }  
681 - } 293 + function sendNotification($aUsers, $eventType, $targetName, $objectId, $parentId) {
  294 + $content = new SubscriptionContent(); // needed for i18n
682 295
  296 + //$aUsers = $this->_getSubscribers($oDocument->getId(), $this->subscriptionTypes["Document"]);
683 297
684 - $aUsers = $this->_getSubscribers($oParentFolder->getId(), $this->subscriptionTypes["Folder"]); 298 + $locationName = Folder::generateFullFolderPath($parentId);
  299 + $userId = $_SESSION['userID'];
685 foreach ($aUsers as $oSubscriber) { 300 foreach ($aUsers as $oSubscriber) {
686 301
687 - // notification object first.  
688 - $aNotificationOptions = array();  
689 - $aNotificationOptions['target_user'] = $oSubscriber->getID();  
690 - $aNotificationOptions['actor_id'] = KTUtil::arrayGet($_SESSION,"userID", null); // _won't_ be null.  
691 - $aNotificationOptions['target_name'] = $oDocument->getName();  
692 - $aNotificationOptions['location_name'] = Folder::generateFullFolderPath($oParentFolder->getId());  
693 - $aNotificationOptions['object_id'] = $oDocument->getId(); // parent folder_id, in this case.  
694 - $aNotificationOptions['event_type'] = "DownloadDocument";  
695 - $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions); 302 + $emailAddress = $oSubscriber->getEmail();
  303 + if ($oSubscriber->getEmailNotification() && !empty($emailAddress)) {
696 304
697 - // now the email content.  
698 - // FIXME this needs to be handled entirely within notifications from now on.  
699 - if ($oSubscriber->getEmailNotification() && (strlen($oSubscriber->getEmail()) > 0)) { 305 + // notification object first.
  306 + $aNotificationOptions = array();
  307 + $aNotificationOptions['target_user'] = $oSubscriber->getID();
  308 + $aNotificationOptions['actor_id'] = $userId;
  309 + $aNotificationOptions['target_name'] = $targetName;
  310 + $aNotificationOptions['location_name'] = $locationName;
  311 + $aNotificationOptions['object_id'] = $objectId;
  312 + $aNotificationOptions['event_type'] = $eventType;
  313 + $oNotification =& KTSubscriptionNotification::generateSubscriptionNotification($aNotificationOptions);
  314 +
  315 + // now the email content.
700 $emailContent = $content->getEmailAlertContent($oNotification); 316 $emailContent = $content->getEmailAlertContent($oNotification);
701 $emailSubject = $content->getEmailAlertSubject($oNotification); 317 $emailSubject = $content->getEmailAlertSubject($oNotification);
702 - $oEmail = new EmailAlert($oSubscriber->getEmail(), $emailSubject, $emailContent); 318 + $oEmail = new EmailAlert($emailAddress, $emailSubject, $emailContent);
703 $oEmail->send(); 319 $oEmail->send();
704 } 320 }
705 } 321 }
@@ -729,11 +345,32 @@ class SubscriptionEvent { @@ -729,11 +345,32 @@ class SubscriptionEvent {
729 global $default; // for the logging. 345 global $default; // for the logging.
730 if (KTLOG_CACHE) $default->log->debug("_getSubscribers(id=$iObjectId, type=$iSubType); table=" .Subscription::getTableName($iSubType). "; id=" .Subscription::getIdFieldName($iSubType)); 346 if (KTLOG_CACHE) $default->log->debug("_getSubscribers(id=$iObjectId, type=$iSubType); table=" .Subscription::getTableName($iSubType). "; id=" .Subscription::getIdFieldName($iSubType));
731 347
732 - $aUsers = array();  
733 - $sQuery = "SELECT user_id FROM " . Subscription::getTableName($iSubType) . " WHERE " . Subscription::getIdFieldName($iSubType) . " = ?"; 348 + $aUsers = array();
  349 + $aNewUsers = array();
  350 + $aSubUsers = array();
  351 + $table = Subscription::getTableName($iSubType);
  352 + $field = Subscription::getIdFieldName($iSubType);
  353 +
  354 + // If we're dealing with a folder then get those user who are subscribed to one of the parent folders and want notifications on sub folders
  355 + if($iSubType == $this->subscriptionTypes["Folder"] && $iObjectId != 1){
  356 + // Get parent folder ids
  357 + $query= "SELECT parent_folder_ids FROM folders WHERE id = {$iObjectId}";
  358 + $aParentIds = DBUtil::getResultArrayKey($query, 'parent_folder_ids');
  359 + $parentIds = $aParentIds[0];
  360 +
  361 + // Get those users who have checked the subfolders option on the above folders
  362 + $query = "SELECT user_id FROM {$table} WHERE {$field} IN ({$parentIds}) AND with_subfolders = 1";
  363 + $aSubUsers = DBUtil::getResultArrayKey($query, 'user_id');
  364 + }
  365 +
  366 + $sQuery = "SELECT user_id FROM {$table} WHERE {$field} = ?";
734 $aParams = array($iObjectId); 367 $aParams = array($iObjectId);
735 368
736 - $aNewUsers = DBUtil::getResultArrayKey(array($sQuery, $aParams), "user_id"); 369 + $aNewUsers = DBUtil::getResultArrayKey(array($sQuery, $aParams), 'user_id');
  370 +
  371 + // Add any users from parent folders
  372 + $aNewUsers = array_merge($aNewUsers, $aSubUsers);
  373 + $aNewUsers = array_unique($aNewUsers);
737 374
738 // Remove alerted users 375 // Remove alerted users
739 $aNewUsers = $this->_pruneAlertedUsers($aNewUsers); 376 $aNewUsers = $this->_pruneAlertedUsers($aNewUsers);
plugins/ktstandard/KTSubscriptions.php
@@ -6,31 +6,31 @@ @@ -6,31 +6,31 @@
6 * Document Management Made Simple 6 * Document Management Made Simple
7 * Copyright (C) 2008 KnowledgeTree Inc. 7 * Copyright (C) 2008 KnowledgeTree Inc.
8 * Portions copyright The Jam Warehouse Software (Pty) Limited 8 * Portions copyright The Jam Warehouse Software (Pty) Limited
9 - * 9 + *
10 * This program is free software; you can redistribute it and/or modify it under 10 * This program is free software; you can redistribute it and/or modify it under
11 * the terms of the GNU General Public License version 3 as published by the 11 * the terms of the GNU General Public License version 3 as published by the
12 * Free Software Foundation. 12 * Free Software Foundation.
13 - * 13 + *
14 * This program is distributed in the hope that it will be useful, but WITHOUT 14 * This program is distributed in the hope that it will be useful, but WITHOUT
15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 16 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
17 * details. 17 * details.
18 - * 18 + *
19 * You should have received a copy of the GNU General Public License 19 * You should have received a copy of the GNU General Public License
20 * along with this program. If not, see <http://www.gnu.org/licenses/>. 20 * along with this program. If not, see <http://www.gnu.org/licenses/>.
21 - *  
22 - * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco, 21 + *
  22 + * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco,
23 * California 94120-7775, or email info@knowledgetree.com. 23 * California 94120-7775, or email info@knowledgetree.com.
24 - * 24 + *
25 * The interactive user interfaces in modified source and object code versions 25 * The interactive user interfaces in modified source and object code versions
26 * of this program must display Appropriate Legal Notices, as required under 26 * of this program must display Appropriate Legal Notices, as required under
27 * Section 5 of the GNU General Public License version 3. 27 * Section 5 of the GNU General Public License version 3.
28 - * 28 + *
29 * In accordance with Section 7(b) of the GNU General Public License version 3, 29 * In accordance with Section 7(b) of the GNU General Public License version 3,
30 * these Appropriate Legal Notices must retain the display of the "Powered by 30 * these Appropriate Legal Notices must retain the display of the "Powered by
31 - * KnowledgeTree" logo and retain the original copyright notice. If the display of the 31 + * KnowledgeTree" logo and retain the original copyright notice. If the display of the
32 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices 32 * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices
33 - * must display the words "Powered by KnowledgeTree" and retain the original 33 + * must display the words "Powered by KnowledgeTree" and retain the original
34 * copyright notice. 34 * copyright notice.
35 * Contributor( s): ______________________________________ 35 * Contributor( s): ______________________________________
36 * 36 *
@@ -95,46 +95,94 @@ class KTSubscriptionPortlet extends KTPortlet { @@ -95,46 +95,94 @@ class KTSubscriptionPortlet extends KTPortlet {
95 } 95 }
96 96
97 function render() { 97 function render() {
98 - if (!$this->oDispatcher->oDocument && !$this->oDispatcher->oFolder) { 98 + if ($this->oDispatcher->oUser->isAnonymous()) {
99 return null; 99 return null;
100 } 100 }
101 - if ($this->oDispatcher->oUser->isAnonymous()) { 101 +
  102 + if($this->oDispatcher->oDocument){
  103 + $oObject = $this->oDispatcher->oDocument;
  104 + $type = 'documentsubscriptionaction';
  105 + }else if($this->oDispatcher->oFolder){
  106 + $oObject = $this->oDispatcher->oFolder;
  107 + $type = 'foldersubscriptionaction';
  108 + }else{
  109 + // not in a folder or document
102 return null; 110 return null;
103 } 111 }
104 - if ($this->oDispatcher->oDocument) {  
105 - $oKTActionRegistry =& KTActionRegistry::getSingleton();  
106 - $actions = $oKTActionRegistry->getActions('documentsubscriptionaction');  
107 - foreach ($actions as $aAction) {  
108 - list($sClassName, $sPath) = $aAction;  
109 - if (!empty($sPath)) {  
110 - // require_once(KT_DIR .  
111 - // Or something... 112 +
  113 + global $default;
  114 + $serverName = $default->serverName;
  115 + $base_url = ($default->sslEnabled ? 'https' : 'http') .'://'.$serverName;
  116 + $oUser = $this->oDispatcher->oUser;
  117 + $this->actions = array();
  118 +
  119 + // Get the actions
  120 + $oKTActionRegistry =& KTActionRegistry::getSingleton();
  121 + $actions = $oKTActionRegistry->getActions($type);
  122 +
  123 + foreach ($actions as $aAction){
  124 + list($sClassName, $sPath) = $aAction;
  125 + $oSubscription = new $sClassName($oObject, $oUser);
  126 + $actionInfo = $oSubscription->getInfo();
  127 + if(!empty($actionInfo)){
  128 + if(isset($actionInfo['active']) && $actionInfo['active'] == 'no'){
  129 + $nonActiveUrl = $base_url.$actionInfo['url'];
  130 + $nonActiveName = $actionInfo['name'];
  131 + }else {
  132 + $aInfo = $actionInfo;
112 } 133 }
113 - $oObject =new $sClassName($this->oDispatcher->oDocument, $this->oDispatcher->oUser);  
114 - $this->actions[] = $oObject->getInfo();  
115 } 134 }
116 } 135 }
117 136
118 - if ($this->oDispatcher->oFolder) {  
119 - $oKTActionRegistry =& KTActionRegistry::getSingleton();  
120 - $actions = $oKTActionRegistry->getActions('foldersubscriptionaction');  
121 - foreach ($actions as $aAction) {  
122 - list($sClassName, $sPath) = $aAction;  
123 - if (!empty($sPath)) {  
124 - // require_once(KT_DIR .  
125 - // Or something...  
126 - }  
127 - $oObject =new $sClassName($this->oDispatcher->oFolder, $this->oDispatcher->oUser);  
128 - $this->actions[] = $oObject->getInfo(); 137 + // Create js script
  138 + $url = $base_url.$aInfo['url'];
  139 + $script = '<script type="text/javascript">
  140 + function doSubscribe(action){
  141 + var respDiv = document.getElementById("response");
  142 + var link = document.getElementById("subscribeLink");
  143 +
  144 + Ext.Ajax.request({
  145 + url: "'.$url.'",
  146 + success: function(response) {
  147 + respDiv.innerHTML = response.responseText;
  148 + respDiv.style.display = "block";
  149 + link.style.display = "none";
  150 + if(document.getElementById("subLink")){
  151 + document.getElementById("subLink").style.display = "none";
  152 + }
  153 + },
  154 + failure: function() {
  155 + respDiv.innerHTML = "'._kt('There was a problem with the subscription, please refresh the page and try again.').'";
  156 + respDiv.style.display = "block";
  157 + },
  158 + params: {
  159 + action: action
  160 + }
  161 + });
129 } 162 }
  163 + </script>';
  164 +
  165 + $script .= "<a id='subscribeLink' style='cursor:pointer' onclick='javascript: doSubscribe(\"ajax\")'>{$aInfo['name']}</a>";
  166 +
  167 + $aInfo['js'] = $script;
  168 + $this->actions[] = $aInfo;
  169 +
  170 + if(isset($aInfo['subaction'])){
  171 + $subInfo = array();
  172 + $subInfo['js'] = "<a id='subLink' style='cursor:pointer' onclick='javascript: doSubscribe(\"add_subfolders\")'>{$aInfo['subaction']}</a>";
  173 +
  174 +// $script .= "<br>&nbsp;&nbsp;&nbsp;<input type='checkbox' id='subfolders' /> {$aInfo['subaction']}";
  175 + $this->actions[] = $subInfo;
130 } 176 }
131 177
132 $this->actions[] = array("name" => _kt("Manage subscriptions"), "url" => $this->oPlugin->getPagePath('manage')); 178 $this->actions[] = array("name" => _kt("Manage subscriptions"), "url" => $this->oPlugin->getPagePath('manage'));
  179 + $btn = '<div id="response" style="padding: 2px; margin-right: 10px; margin-left: 10px; word-wrap: normal; background: #CCC; display:none;"></div>';
133 180
134 $oTemplating =& KTTemplating::getSingleton(); 181 $oTemplating =& KTTemplating::getSingleton();
135 $oTemplate = $oTemplating->loadTemplate("kt3/portlets/actions_portlet"); 182 $oTemplate = $oTemplating->loadTemplate("kt3/portlets/actions_portlet");
136 $aTemplateData = array( 183 $aTemplateData = array(
137 - "context" => $this, 184 + 'context' => $this,
  185 + 'btn' => $btn
138 ); 186 );
139 return $oTemplate->render($aTemplateData); 187 return $oTemplate->render($aTemplateData);
140 } 188 }
@@ -150,10 +198,27 @@ class KTDocumentSubscriptionAction extends KTDocumentAction { @@ -150,10 +198,27 @@ class KTDocumentSubscriptionAction extends KTDocumentAction {
150 } 198 }
151 199
152 function getInfo() { 200 function getInfo() {
  201 + $aInfo = parent::getInfo();
153 if (Subscription::exists($this->oUser->getID(), $this->oDocument->getID(), SubscriptionEvent::subTypes('Document'))) { 202 if (Subscription::exists($this->oUser->getID(), $this->oDocument->getID(), SubscriptionEvent::subTypes('Document'))) {
154 - return null; 203 + $aInfo['active'] = 'no';
  204 + }
  205 + return $aInfo;
  206 + }
  207 +
  208 + function do_ajax() {
  209 + $iSubscriptionType = SubscriptionEvent::subTypes('Document');
  210 + if (Subscription::exists($this->oUser->getId(), $this->oDocument->getId(), $iSubscriptionType)) {
  211 + echo _kt('You are already subscribed to that document');
  212 + } else {
  213 + $oSubscription = new Subscription($this->oUser->getId(), $this->oDocument->getId(), $iSubscriptionType);
  214 + $res = $oSubscription->create();
  215 + if ($res) {
  216 + echo _kt('You have been subscribed to this document');
  217 + } else {
  218 + echo _kt('There was a problem subscribing you to this document');
  219 + }
155 } 220 }
156 - return parent::getInfo(); 221 + exit(0);
157 } 222 }
158 223
159 function do_main() { 224 function do_main() {
@@ -184,10 +249,27 @@ class KTDocumentUnsubscriptionAction extends KTDocumentAction { @@ -184,10 +249,27 @@ class KTDocumentUnsubscriptionAction extends KTDocumentAction {
184 } 249 }
185 250
186 function getInfo() { 251 function getInfo() {
187 - if (Subscription::exists($this->oUser->getID(), $this->oDocument->getID(), SubscriptionEvent::subTypes('Document'))) {  
188 - return parent::getInfo(); 252 + $aInfo = parent::getInfo();
  253 + if (!Subscription::exists($this->oUser->getID(), $this->oDocument->getID(), SubscriptionEvent::subTypes('Document'))) {
  254 + $aInfo['active'] = 'no';
  255 + }
  256 + return $aInfo;
  257 + }
  258 +
  259 + function do_ajax() {
  260 + $iSubscriptionType = SubscriptionEvent::subTypes('Document');
  261 + if (!Subscription::exists($this->oUser->getId(), $this->oDocument->getId(), $iSubscriptionType)) {
  262 + echo _kt('You are not subscribed to this document');
  263 + } else {
  264 + $oSubscription = new Subscription($this->oUser->getId(), $this->oDocument->getId(), $iSubscriptionType);
  265 + $res = $oSubscription->create();
  266 + if ($res) {
  267 + echo _kt('You have been unsubscribed from this document');
  268 + } else {
  269 + echo _kt('There was a problem unsubscribing you from this document');
  270 + }
189 } 271 }
190 - return null; 272 + exit(0);
191 } 273 }
192 274
193 function do_main() { 275 function do_main() {
@@ -342,17 +424,53 @@ class KTFolderSubscriptionAction extends KTFolderAction { @@ -342,17 +424,53 @@ class KTFolderSubscriptionAction extends KTFolderAction {
342 } 424 }
343 425
344 function getInfo() { 426 function getInfo() {
  427 + $aInfo = parent::getInfo();
345 if (Subscription::exists($this->oUser->getID(), $this->oFolder->getID(), SubscriptionEvent::subTypes('Folder'))) { 428 if (Subscription::exists($this->oUser->getID(), $this->oFolder->getID(), SubscriptionEvent::subTypes('Folder'))) {
346 // KTFolderUnsubscriptionAction will display instead. 429 // KTFolderUnsubscriptionAction will display instead.
347 - return null; 430 + $aInfo['active'] = 'no';
  431 + }
  432 + // return the url to the action for subfolders - display the Subscribe link, on clicking, display the include subfolders link.
  433 + $aInfo['subaction'] = _kt('Subscribe to folder and subfolders');
  434 + return $aInfo;
  435 + }
  436 +
  437 + function do_ajax() {
  438 + $this->subscribe();
  439 + }
  440 +
  441 + function do_add_subfolders() {
  442 + $this->subscribe(true);
  443 + }
  444 +
  445 + function subscribe($incSubFolders = false) {
  446 + $iSubscriptionType = SubscriptionEvent::subTypes('Folder');
  447 + if (Subscription::exists($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType)) {
  448 + echo _kt('You are already subscribed to this folder');
  449 + } else {
  450 + $oSubscription = new Subscription($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType);
  451 +
  452 + if($incSubFolders){
  453 + $oSubscription->setWithSubFolders(true);
  454 + }
  455 +
  456 + $res = $oSubscription->create();
  457 + if ($res) {
  458 + if($incSubFolders){
  459 + echo _kt('You have been subscribed to this folder and its subfolders');
  460 + }else{
  461 + echo _kt('You have been subscribed to this folder');
  462 + }
  463 + } else {
  464 + echo _kt('There was a problem subscribing you to this folder');
  465 + }
348 } 466 }
349 - return parent::getInfo(); 467 + exit(0);
350 } 468 }
351 469
352 function do_main() { 470 function do_main() {
353 $iSubscriptionType = SubscriptionEvent::subTypes('Folder'); 471 $iSubscriptionType = SubscriptionEvent::subTypes('Folder');
354 if (Subscription::exists($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType)) { 472 if (Subscription::exists($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType)) {
355 - $_SESSION['KTErrorMessage'][] = _kt("You are already subscribed to that folder"); 473 + $_SESSION['KTErrorMessage'][] = _kt("You are already subscribed to this folder");
356 } else { 474 } else {
357 $oSubscription = new Subscription($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType); 475 $oSubscription = new Subscription($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType);
358 $res = $oSubscription->create(); 476 $res = $oSubscription->create();
@@ -377,10 +495,27 @@ class KTFolderUnsubscriptionAction extends KTFolderAction { @@ -377,10 +495,27 @@ class KTFolderUnsubscriptionAction extends KTFolderAction {
377 } 495 }
378 496
379 function getInfo() { 497 function getInfo() {
380 - if (Subscription::exists($this->oUser->getID(), $this->oFolder->getID(), SubscriptionEvent::subTypes('Folder'))) {  
381 - return parent::getInfo(); 498 + $aInfo = parent::getInfo();
  499 + if (!Subscription::exists($this->oUser->getID(), $this->oFolder->getID(), SubscriptionEvent::subTypes('Folder'))) {
  500 + $aInfo['active'] = 'no';
382 } 501 }
383 - return null; 502 + return $aInfo;
  503 + }
  504 +
  505 + function do_ajax() {
  506 + $iSubscriptionType = SubscriptionEvent::subTypes('Folder');
  507 + if (!Subscription::exists($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType)) {
  508 + echo _kt('You were not subscribed to that folder');
  509 + } else {
  510 + $oSubscription = & Subscription::getByIDs($this->oUser->getId(), $this->oFolder->getId(), $iSubscriptionType);
  511 + $res = $oSubscription->delete();
  512 + if ($res) {
  513 + echo _kt('You have been unsubscribed from this folder');
  514 + } else {
  515 + echo _kt('There was a problem unsubscribing you from this folder');
  516 + }
  517 + }
  518 + exit(0);
384 } 519 }
385 520
386 function do_main() { 521 function do_main() {
sql/mysql/install/structure.sql
@@ -511,7 +511,7 @@ CREATE TABLE `document_transaction_types_lookup` ( @@ -511,7 +511,7 @@ CREATE TABLE `document_transaction_types_lookup` (
511 CREATE TABLE `document_transactions` ( 511 CREATE TABLE `document_transactions` (
512 `id` int(11) NOT NULL auto_increment, 512 `id` int(11) NOT NULL auto_increment,
513 `document_id` int(11) default NULL, 513 `document_id` int(11) default NULL,
514 - `version` float default NULL, 514 + `version` varchar(10),
515 `user_id` int(11) default NULL, 515 `user_id` int(11) default NULL,
516 `datetime` datetime NOT NULL default '0000-00-00 00:00:00', 516 `datetime` datetime NOT NULL default '0000-00-00 00:00:00',
517 `ip` varchar(15) default NULL, 517 `ip` varchar(15) default NULL,
@@ -775,6 +775,7 @@ CREATE TABLE `folder_subscriptions` ( @@ -775,6 +775,7 @@ CREATE TABLE `folder_subscriptions` (
775 `user_id` int(11) NOT NULL default '0', 775 `user_id` int(11) NOT NULL default '0',
776 `folder_id` int(11) NOT NULL default '0', 776 `folder_id` int(11) NOT NULL default '0',
777 `is_alerted` tinyint(1) default NULL, 777 `is_alerted` tinyint(1) default NULL,
  778 + `with_subfolders` tinyint(1) NOT NULL default '0',
778 PRIMARY KEY (`id`), 779 PRIMARY KEY (`id`),
779 KEY `user_id` (`user_id`), 780 KEY `user_id` (`user_id`),
780 KEY `folder_id` (`folder_id`), 781 KEY `folder_id` (`folder_id`),
sql/mysql/upgrade/3.5.3/subscriptions.sql 0 → 100644
  1 +ALTER TABLE folder_subscriptions ADD COLUMN with_subfolders TINYINT(1) NOT NULL default 0;
0 \ No newline at end of file 2 \ No newline at end of file
templates/kt3/portlets/actions_portlet.smarty
1 {if $btn} 1 {if $btn}
2 -<div style='width: 100%;'>{$btn}</div> 2 + <div style='width: 100%;'>{$btn}</div>
3 {/if} 3 {/if}
4 <ul class="actionlist"> 4 <ul class="actionlist">
5 -{foreach item=action from=$context->actions }  
6 -{if $action != null}  
7 -<li {if $action.active}class="active"{/if}>  
8 -{if $action.js}  
9 - {$action.js}  
10 -{else}  
11 -{if ($action.url)}  
12 -<a href="{$action.url}" {if $action.description}title="{$action.description}"{/if}>  
13 - {$action.name}  
14 -</a>  
15 -{else}  
16 - {$action.name}  
17 -{/if}</li>  
18 -{/if}  
19 -{/if}  
20 -{/foreach}  
21 -</ul> 5 + {foreach item=action from=$context->actions }
  6 + {if $action != null}
  7 + <li {if $action.active}class="active"{/if}>
  8 + {if $action.js}
  9 + {$action.js}
  10 + {else}
  11 + {if ($action.url)}
  12 + <a href="{$action.url}" {if $action.description}title="{$action.description}"{/if}>
  13 + {$action.name}
  14 + </a>
  15 + {else}
  16 + {$action.name}
  17 + {/if}
  18 + {/if}
  19 + </li>
  20 + {/if}
  21 + {/foreach}
  22 +</ul>
22 \ No newline at end of file 23 \ No newline at end of file