]> git.wh0rd.org - tt-rss.git/blame - classes/pref/feeds.php
since dojo dropdowns won't work in article content because of html escaping trick...
[tt-rss.git] / classes / pref / feeds.php
CommitLineData
afcfe6ca 1<?php
369dbc19 2class Pref_Feeds extends Handler_Protected {
8484ce22
AD
3
4 function csrf_ignore($method) {
f6cd767b 5 $csrf_ignored = array("index", "getfeedtree", "add", "editcats", "editfeed",
bc6fa236 6 "savefeedorder", "uploadicon", "feedswitherrors", "inactivefeeds");
8484ce22
AD
7
8 return array_search($method, $csrf_ignored) !== false;
9 }
10
afcfe6ca
AD
11 function batch_edit_cbox($elem, $label = false) {
12 print "<input type=\"checkbox\" title=\"".__("Check to enable field")."\"
13 onchange=\"dijit.byId('feedEditDlg').toggleField(this, '$elem', '$label')\">";
14 }
15
16 function renamecat() {
3972bf59
AD
17 $title = db_escape_string($this->link, $_REQUEST['title']);
18 $id = db_escape_string($this->link, $_REQUEST['id']);
afcfe6ca
AD
19
20 if ($title) {
21 db_query($this->link, "UPDATE ttrss_feed_categories SET
22 title = '$title' WHERE id = '$id' AND owner_uid = " . $_SESSION["uid"]);
23 }
24 return;
25 }
26
2a060a94 27 private function get_category_items($cat_id) {
6e0ee833
AD
28
29 if ($_REQUEST['mode'] != 2)
30 $search = $_SESSION["prefs_feed_search"];
31 else
32 $search = "";
17c755f0
AD
33
34 if ($search) $search_qpart = " AND LOWER(title) LIKE LOWER('%$search%')";
35
f393dc6f 36 $show_empty_cats = $_REQUEST['mode'] != 2 && !$search &&
fbf85cf6 37 get_pref($this->link, '_PREFS_SHOW_EMPTY_CATS');
2a060a94
AD
38
39 $items = array();
40
88918ca6 41 $result = db_query($this->link, "SELECT id, title FROM ttrss_feed_categories
2a060a94
AD
42 WHERE owner_uid = " . $_SESSION["uid"] . " AND parent_cat = '$cat_id' ORDER BY order_id, title");
43
44 while ($line = db_fetch_assoc($result)) {
45
46 $cat = array();
47 $cat['id'] = 'CAT:' . $line['id'];
2ecd2df5 48 $cat['bare_id'] = (int)$line['id'];
2a060a94
AD
49 $cat['name'] = $line['title'];
50 $cat['items'] = array();
51 $cat['checkbox'] = false;
52 $cat['type'] = 'category';
2ecd2df5 53 $cat['unread'] = 0;
2c5f231e 54 $cat['child_unread'] = 0;
2a060a94
AD
55
56 $cat['items'] = $this->get_category_items($line['id']);
57
f5c1fef9 58 $cat['param'] = vsprintf(ngettext('(%d feed)', '(%d feeds)', count($cat['items'])), count($cat['items']));
2a060a94
AD
59
60 if (count($cat['items']) > 0 || $show_empty_cats)
61 array_push($items, $cat);
62
63 }
64
65 $feed_result = db_query($this->link, "SELECT id, title, last_error,
66 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
67 FROM ttrss_feeds
68 WHERE cat_id = '$cat_id' AND owner_uid = ".$_SESSION["uid"].
69 "$search_qpart ORDER BY order_id, title");
70
71 while ($feed_line = db_fetch_assoc($feed_result)) {
72 $feed = array();
73 $feed['id'] = 'FEED:' . $feed_line['id'];
2ecd2df5 74 $feed['bare_id'] = (int)$feed_line['id'];
2a060a94
AD
75 $feed['name'] = $feed_line['title'];
76 $feed['checkbox'] = false;
2ecd2df5 77 $feed['unread'] = 0;
2a060a94
AD
78 $feed['error'] = $feed_line['last_error'];
79 $feed['icon'] = getFeedIcon($feed_line['id']);
80 $feed['param'] = make_local_datetime($this->link,
81 $feed_line['last_updated'], true);
82
83 array_push($items, $feed);
84 }
85
86 return $items;
87 }
88
afcfe6ca
AD
89 function getfeedtree() {
90
6e0ee833
AD
91 if ($_REQUEST['mode'] != 2)
92 $search = $_SESSION["prefs_feed_search"];
93 else
94 $search = "";
afcfe6ca
AD
95
96 if ($search) $search_qpart = " AND LOWER(title) LIKE LOWER('%$search%')";
97
98 $root = array();
99 $root['id'] = 'root';
100 $root['name'] = __('Feeds');
101 $root['items'] = array();
102 $root['type'] = 'category';
103
2ecd2df5
AD
104 $enable_cats = get_pref($this->link, 'ENABLE_FEED_CATS');
105
106 if ($_REQUEST['mode'] == 2) {
107
108 if ($enable_cats) {
88918ca6 109 $cat = $this->feedlist_init_cat(-1);
2ecd2df5
AD
110 } else {
111 $cat['items'] = array();
112 }
113
5417fbd7 114 foreach (array(-4, -3, -1, -2, 0, -6) as $i) {
2ecd2df5
AD
115 array_push($cat['items'], $this->feedlist_init_feed($i));
116 }
117
a413f53e
AD
118 /* Plugin feeds for -1 */
119
120 global $pluginhost;
121
122 $feeds = $pluginhost->get_feeds(-1);
123
124 if ($feeds) {
125 foreach ($feeds as $feed) {
126 $feed_id = PluginHost::pfeed_to_feed_id($feed['id']);
127
128 $item = array();
129 $item['id'] = 'FEED:' . $feed_id;
130 $item['bare_id'] = (int)$feed_id;
131 $item['name'] = $feed['title'];
132 $item['checkbox'] = false;
133 $item['error'] = '';
134 $item['icon'] = $feed['icon'];
135
136 $item['param'] = '';
137 $item['unread'] = 0; //$feed['sender']->get_unread($feed['id']);
138 $item['type'] = 'feed';
139
140 array_push($cat['items'], $item);
141 }
142 }
143
2ecd2df5
AD
144 if ($enable_cats) {
145 array_push($root['items'], $cat);
146 } else {
147 $root['items'] = array_merge($root['items'], $cat['items']);
148 }
afcfe6ca 149
2ecd2df5
AD
150 $result = db_query($this->link, "SELECT * FROM
151 ttrss_labels2 WHERE owner_uid = ".$_SESSION['uid']." ORDER by caption");
152
153 if (db_num_rows($result) > 0) {
154
155 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
88918ca6 156 $cat = $this->feedlist_init_cat(-2);
2ecd2df5
AD
157 } else {
158 $cat['items'] = array();
159 }
160
161 while ($line = db_fetch_assoc($result)) {
162
f822a8e5 163 $label_id = label_to_feed_id($line['id']);
2ecd2df5 164
88918ca6 165 $feed = $this->feedlist_init_feed($label_id, false, 0);
2ecd2df5
AD
166
167 $feed['fg_color'] = $line['fg_color'];
168 $feed['bg_color'] = $line['bg_color'];
169
170 array_push($cat['items'], $feed);
171 }
172
173 if ($enable_cats) {
174 array_push($root['items'], $cat);
175 } else {
176 $root['items'] = array_merge($root['items'], $cat['items']);
177 }
178 }
179 }
180
181 if ($enable_cats) {
f393dc6f 182 $show_empty_cats = $_REQUEST['mode'] != 2 && !$search &&
2ecd2df5
AD
183 get_pref($this->link, '_PREFS_SHOW_EMPTY_CATS');
184
88918ca6 185 $result = db_query($this->link, "SELECT id, title FROM ttrss_feed_categories
2a060a94 186 WHERE owner_uid = " . $_SESSION["uid"] . " AND parent_cat IS NULL ORDER BY order_id, title");
afcfe6ca
AD
187
188 while ($line = db_fetch_assoc($result)) {
189 $cat = array();
190 $cat['id'] = 'CAT:' . $line['id'];
2ecd2df5 191 $cat['bare_id'] = (int)$line['id'];
afcfe6ca
AD
192 $cat['name'] = $line['title'];
193 $cat['items'] = array();
194 $cat['checkbox'] = false;
195 $cat['type'] = 'category';
2ecd2df5 196 $cat['unread'] = 0;
2c5f231e 197 $cat['child_unread'] = 0;
afcfe6ca 198
2a060a94 199 $cat['items'] = $this->get_category_items($line['id']);
afcfe6ca 200
f5c1fef9 201 $cat['param'] = vsprintf(ngettext('(%d feed)', '(%d feeds)', count($cat['items'])), count($cat['items']));
afcfe6ca 202
5b7bd238 203 if (count($cat['items']) > 0 || $show_empty_cats)
afcfe6ca
AD
204 array_push($root['items'], $cat);
205
206 $root['param'] += count($cat['items']);
207 }
208
209 /* Uncategorized is a special case */
210
211 $cat = array();
212 $cat['id'] = 'CAT:0';
213 $cat['bare_id'] = 0;
214 $cat['name'] = __("Uncategorized");
215 $cat['items'] = array();
216 $cat['type'] = 'category';
217 $cat['checkbox'] = false;
2ecd2df5 218 $cat['unread'] = 0;
2c5f231e 219 $cat['child_unread'] = 0;
afcfe6ca
AD
220
221 $feed_result = db_query($this->link, "SELECT id, title,last_error,
222 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
223 FROM ttrss_feeds
224 WHERE cat_id IS NULL AND owner_uid = ".$_SESSION["uid"].
225 "$search_qpart ORDER BY order_id, title");
226
227 while ($feed_line = db_fetch_assoc($feed_result)) {
228 $feed = array();
229 $feed['id'] = 'FEED:' . $feed_line['id'];
2ecd2df5 230 $feed['bare_id'] = (int)$feed_line['id'];
afcfe6ca
AD
231 $feed['name'] = $feed_line['title'];
232 $feed['checkbox'] = false;
233 $feed['error'] = $feed_line['last_error'];
234 $feed['icon'] = getFeedIcon($feed_line['id']);
235 $feed['param'] = make_local_datetime($this->link,
236 $feed_line['last_updated'], true);
2ecd2df5
AD
237 $feed['unread'] = 0;
238 $feed['type'] = 'feed';
afcfe6ca
AD
239
240 array_push($cat['items'], $feed);
241 }
242
f5c1fef9 243 $cat['param'] = vsprintf(ngettext('(%d feed)', '(%d feeds)', count($cat['items'])), count($cat['items']));
afcfe6ca 244
5b7bd238 245 if (count($cat['items']) > 0 || $show_empty_cats)
afcfe6ca
AD
246 array_push($root['items'], $cat);
247
248 $root['param'] += count($cat['items']);
f5c1fef9 249 $root['param'] = vsprintf(ngettext('(%d feed)', '(%d feeds)', count($cat['items'])), count($cat['items']));
afcfe6ca
AD
250
251 } else {
252 $feed_result = db_query($this->link, "SELECT id, title, last_error,
253 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
254 FROM ttrss_feeds
255 WHERE owner_uid = ".$_SESSION["uid"].
256 "$search_qpart ORDER BY order_id, title");
257
258 while ($feed_line = db_fetch_assoc($feed_result)) {
259 $feed = array();
260 $feed['id'] = 'FEED:' . $feed_line['id'];
2ecd2df5 261 $feed['bare_id'] = (int)$feed_line['id'];
afcfe6ca
AD
262 $feed['name'] = $feed_line['title'];
263 $feed['checkbox'] = false;
264 $feed['error'] = $feed_line['last_error'];
265 $feed['icon'] = getFeedIcon($feed_line['id']);
266 $feed['param'] = make_local_datetime($this->link,
267 $feed_line['last_updated'], true);
2ecd2df5
AD
268 $feed['unread'] = 0;
269 $feed['type'] = 'feed';
afcfe6ca
AD
270
271 array_push($root['items'], $feed);
272 }
273
f5c1fef9 274 $root['param'] = vsprintf(ngettext('(%d feed)', '(%d feeds)', count($cat['items'])), count($cat['items']));
afcfe6ca
AD
275 }
276
277 $fl = array();
278 $fl['identifier'] = 'id';
279 $fl['label'] = 'name';
2ecd2df5
AD
280
281 if ($_REQUEST['mode'] != 2) {
282 $fl['items'] = array($root);
283 } else {
284 $fl['items'] =& $root['items'];
285 }
afcfe6ca
AD
286
287 print json_encode($fl);
288 return;
289 }
290
291 function catsortreset() {
292 db_query($this->link, "UPDATE ttrss_feed_categories
293 SET order_id = 0 WHERE owner_uid = " . $_SESSION["uid"]);
294 return;
295 }
296
297 function feedsortreset() {
298 db_query($this->link, "UPDATE ttrss_feeds
299 SET order_id = 0 WHERE owner_uid = " . $_SESSION["uid"]);
300 return;
301 }
302
5b7bd238
AD
303 function togglehiddenfeedcats() {
304 set_pref($this->link, '_PREFS_SHOW_EMPTY_CATS',
305 (get_pref($this->link, '_PREFS_SHOW_EMPTY_CATS') ? 'false' : 'true'));
306 }
307
95ee44b3
AD
308 private function process_category_order(&$data_map, $item_id, $parent_id = false, $nest_level = 0) {
309 $debug = isset($_REQUEST["debug"]);
310
311 $prefix = "";
312 for ($i = 0; $i < $nest_level; $i++)
313 $prefix .= " ";
314
315 if ($debug) _debug("$prefix C: $item_id P: $parent_id");
316
317 $bare_item_id = substr($item_id, strpos($item_id, ':')+1);
2a060a94
AD
318
319 if ($item_id != 'root') {
320 if ($parent_id && $parent_id != 'root') {
321 $parent_bare_id = substr($parent_id, strpos($parent_id, ':')+1);
3972bf59 322 $parent_qpart = db_escape_string($this->link, $parent_bare_id);
2a060a94
AD
323 } else {
324 $parent_qpart = 'NULL';
325 }
326
327 db_query($this->link, "UPDATE ttrss_feed_categories
95ee44b3 328 SET parent_cat = $parent_qpart WHERE id = '$bare_item_id' AND
2a060a94
AD
329 owner_uid = " . $_SESSION["uid"]);
330 }
331
332 $order_id = 0;
333
334 $cat = $data_map[$item_id];
335
336 if ($cat && is_array($cat)) {
337 foreach ($cat as $item) {
338 $id = $item['_reference'];
339 $bare_id = substr($id, strpos($id, ':')+1);
340
95ee44b3 341 if ($debug) _debug("$prefix [$order_id] $id/$bare_id");
2a060a94
AD
342
343 if ($item['_reference']) {
344
345 if (strpos($id, "FEED") === 0) {
346
95ee44b3 347 $cat_id = ($item_id != "root") ?
3972bf59 348 db_escape_string($this->link, $bare_item_id) : "NULL";
95ee44b3 349
49b2401e
AD
350 $cat_qpart = ($cat_id != 0) ? "cat_id = '$cat_id'" :
351 "cat_id = NULL";
352
2a060a94 353 db_query($this->link, "UPDATE ttrss_feeds
49b2401e 354 SET order_id = $order_id, $cat_qpart
95ee44b3 355 WHERE id = '$bare_id' AND
2a060a94
AD
356 owner_uid = " . $_SESSION["uid"]);
357
358 } else if (strpos($id, "CAT:") === 0) {
95ee44b3
AD
359 $this->process_category_order($data_map, $item['_reference'], $item_id,
360 $nest_level+1);
2a060a94
AD
361
362 if ($item_id != 'root') {
3972bf59 363 $parent_qpart = db_escape_string($this->link, $bare_id);
2a060a94
AD
364 } else {
365 $parent_qpart = 'NULL';
366 }
367
368 db_query($this->link, "UPDATE ttrss_feed_categories
369 SET order_id = '$order_id' WHERE id = '$bare_id' AND
370 owner_uid = " . $_SESSION["uid"]);
371 }
372 }
373
374 ++$order_id;
375 }
376 }
377 }
378
afcfe6ca
AD
379 function savefeedorder() {
380 $data = json_decode($_POST['payload'], true);
381
2a060a94
AD
382 #file_put_contents("/tmp/saveorder.json", $_POST['payload']);
383 #$data = json_decode(file_get_contents("/tmp/saveorder.json"), true);
a26f57e6 384
95ee44b3
AD
385 if (!is_array($data['items']))
386 $data['items'] = json_decode($data['items'], true);
387
388# print_r($data['items']);
2a060a94 389
afcfe6ca
AD
390 if (is_array($data) && is_array($data['items'])) {
391 $cat_order_id = 0;
392
393 $data_map = array();
2a060a94 394 $root_item = false;
afcfe6ca
AD
395
396 foreach ($data['items'] as $item) {
397
2a060a94 398# if ($item['id'] != 'root') {
afcfe6ca
AD
399 if (is_array($item['items'])) {
400 if (isset($item['items']['_reference'])) {
401 $data_map[$item['id']] = array($item['items']);
402 } else {
403 $data_map[$item['id']] =& $item['items'];
404 }
405 }
2a060a94
AD
406 if ($item['id'] == 'root') {
407 $root_item = $item['id'];
afcfe6ca
AD
408 }
409 }
410
d04f8c82 411 $this->process_category_order($data_map, $root_item);
2a060a94
AD
412
413 /* foreach ($data['items'][0]['items'] as $item) {
afcfe6ca
AD
414 $id = $item['_reference'];
415 $bare_id = substr($id, strpos($id, ':')+1);
416
417 ++$cat_order_id;
418
419 if ($bare_id > 0) {
420 db_query($this->link, "UPDATE ttrss_feed_categories
421 SET order_id = '$cat_order_id' WHERE id = '$bare_id' AND
422 owner_uid = " . $_SESSION["uid"]);
423 }
424
425 $feed_order_id = 0;
426
427 if (is_array($data_map[$id])) {
428 foreach ($data_map[$id] as $feed) {
429 $id = $feed['_reference'];
430 $feed_id = substr($id, strpos($id, ':')+1);
431
432 if ($bare_id != 0)
433 $cat_query = "cat_id = '$bare_id'";
434 else
435 $cat_query = "cat_id = NULL";
436
437 db_query($this->link, "UPDATE ttrss_feeds
438 SET order_id = '$feed_order_id',
439 $cat_query
440 WHERE id = '$feed_id' AND
441 owner_uid = " . $_SESSION["uid"]);
442
443 ++$feed_order_id;
444 }
445 }
2a060a94 446 } */
afcfe6ca
AD
447 }
448
449 return;
450 }
451
452 function removeicon() {
3972bf59 453 $feed_id = db_escape_string($this->link, $_REQUEST["feed_id"]);
afcfe6ca
AD
454
455 $result = db_query($this->link, "SELECT id FROM ttrss_feeds
456 WHERE id = '$feed_id' AND owner_uid = ". $_SESSION["uid"]);
457
458 if (db_num_rows($result) != 0) {
459 unlink(ICONS_DIR . "/$feed_id.ico");
460 }
461
462 return;
463 }
464
465 function uploadicon() {
350e3944
AD
466 header("Content-type: text/html");
467
afcfe6ca 468 $icon_file = $_FILES['icon_file']['tmp_name'];
3972bf59 469 $feed_id = db_escape_string($this->link, $_REQUEST["feed_id"]);
afcfe6ca
AD
470
471 if (is_file($icon_file) && $feed_id) {
472 if (filesize($icon_file) < 20000) {
473
474 $result = db_query($this->link, "SELECT id FROM ttrss_feeds
475 WHERE id = '$feed_id' AND owner_uid = ". $_SESSION["uid"]);
476
477 if (db_num_rows($result) != 0) {
478 unlink(ICONS_DIR . "/$feed_id.ico");
479 move_uploaded_file($icon_file, ICONS_DIR . "/$feed_id.ico");
480 $rc = 0;
481 } else {
482 $rc = 2;
483 }
484 } else {
485 $rc = 1;
486 }
487 } else {
488 $rc = 2;
489 }
490
491 print "<script type=\"text/javascript\">";
492 print "parent.uploadIconHandler($rc);";
493 print "</script>";
494 return;
495 }
496
497 function editfeed() {
498 global $purge_intervals;
499 global $update_intervals;
afcfe6ca 500
3972bf59 501 $feed_id = db_escape_string($this->link, $_REQUEST["id"]);
afcfe6ca
AD
502
503 $result = db_query($this->link,
504 "SELECT * FROM ttrss_feeds WHERE id = '$feed_id' AND
505 owner_uid = " . $_SESSION["uid"]);
506
507 $title = htmlspecialchars(db_fetch_result($result,
508 0, "title"));
509
510 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"id\" value=\"$feed_id\">";
511 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"op\" value=\"pref-feeds\">";
512 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"method\" value=\"editSave\">";
513
514 print "<div class=\"dlgSec\">".__("Feed")."</div>";
515 print "<div class=\"dlgSecCont\">";
516
517 /* Title */
518
519 print "<input dojoType=\"dijit.form.ValidationTextBox\" required=\"1\"
520 placeHolder=\"".__("Feed Title")."\"
521 style=\"font-size : 16px; width: 20em\" name=\"title\" value=\"$title\">";
522
523 /* Feed URL */
524
525 $feed_url = db_fetch_result($result, 0, "feed_url");
526 $feed_url = htmlspecialchars(db_fetch_result($result,
527 0, "feed_url"));
528
529 print "<hr/>";
530
531 print __('URL:') . " ";
532 print "<input dojoType=\"dijit.form.ValidationTextBox\" required=\"1\"
533 placeHolder=\"".__("Feed URL")."\"
534 regExp='^(http|https)://.*' style=\"width : 20em\"
535 name=\"feed_url\" value=\"$feed_url\">";
536
537 $last_error = db_fetch_result($result, 0, "last_error");
538
539 if ($last_error) {
540 print "&nbsp;<span title=\"".htmlspecialchars($last_error)."\"
541 class=\"feed_error\">(error)</span>";
542
543 }
544
545 /* Category */
546
547 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
548
549 $cat_id = db_fetch_result($result, 0, "cat_id");
550
551 print "<hr/>";
552
553 print __('Place in category:') . " ";
554
555 print_feed_cat_select($this->link, "cat_id", $cat_id,
556 'dojoType="dijit.form.Select"');
557 }
558
559 print "</div>";
560
561 print "<div class=\"dlgSec\">".__("Update")."</div>";
562 print "<div class=\"dlgSecCont\">";
563
564 /* Update Interval */
565
566 $update_interval = db_fetch_result($result, 0, "update_interval");
567
568 print_select_hash("update_interval", $update_interval, $update_intervals,
569 'dojoType="dijit.form.Select"');
570
19b3992b 571 /* Purge intl */
afcfe6ca
AD
572
573 $purge_interval = db_fetch_result($result, 0, "purge_interval");
574
afcfe6ca
AD
575 print "<hr/>";
576 print __('Article purging:') . " ";
577
578 print_select_hash("purge_interval", $purge_interval, $purge_intervals,
579 'dojoType="dijit.form.Select" ' .
580 ((FORCE_ARTICLE_PURGE == 0) ? "" : 'disabled="1"'));
581
582 print "</div>";
583 print "<div class=\"dlgSec\">".__("Authentication")."</div>";
584 print "<div class=\"dlgSecCont\">";
585
586 $auth_login = htmlspecialchars(db_fetch_result($result, 0, "auth_login"));
587
588 print "<input dojoType=\"dijit.form.TextBox\" id=\"feedEditDlg_login\"
589 placeHolder=\"".__("Login")."\"
590 name=\"auth_login\" value=\"$auth_login\"><hr/>";
591
592 $auth_pass = htmlspecialchars(db_fetch_result($result, 0, "auth_pass"));
593
594 print "<input dojoType=\"dijit.form.TextBox\" type=\"password\" name=\"auth_pass\"
595 placeHolder=\"".__("Password")."\"
596 value=\"$auth_pass\">";
597
598 print "<div dojoType=\"dijit.Tooltip\" connectId=\"feedEditDlg_login\" position=\"below\">
599 ".__('<b>Hint:</b> you need to fill in your login information if your feed requires authentication, except for Twitter feeds.')."
600 </div>";
601
602 print "</div>";
603 print "<div class=\"dlgSec\">".__("Options")."</div>";
604 print "<div class=\"dlgSecCont\">";
605
606 $private = sql_bool_to_bool(db_fetch_result($result, 0, "private"));
607
608 if ($private) {
609 $checked = "checked=\"1\"";
610 } else {
611 $checked = "";
612 }
613
614 print "<input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" name=\"private\" id=\"private\"
615 $checked>&nbsp;<label for=\"private\">".__('Hide from Popular feeds')."</label>";
616
afcfe6ca
AD
617 $include_in_digest = sql_bool_to_bool(db_fetch_result($result, 0, "include_in_digest"));
618
619 if ($include_in_digest) {
620 $checked = "checked=\"1\"";
621 } else {
622 $checked = "";
623 }
624
625 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"include_in_digest\"
626 name=\"include_in_digest\"
627 $checked>&nbsp;<label for=\"include_in_digest\">".__('Include in e-mail digest')."</label>";
628
629
630 $always_display_enclosures = sql_bool_to_bool(db_fetch_result($result, 0, "always_display_enclosures"));
631
632 if ($always_display_enclosures) {
633 $checked = "checked";
634 } else {
635 $checked = "";
636 }
637
638 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"always_display_enclosures\"
639 name=\"always_display_enclosures\"
640 $checked>&nbsp;<label for=\"always_display_enclosures\">".__('Always display image attachments')."</label>";
641
bfd61d3f
AD
642 $hide_images = sql_bool_to_bool(db_fetch_result($result, 0, "hide_images"));
643
644 if ($hide_images) {
645 $checked = "checked=\"1\"";
646 } else {
647 $checked = "";
648 }
649
650 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"hide_images\"
651 name=\"hide_images\"
652 $checked>&nbsp;<label for=\"hide_images\">".
653 __('Do not embed images')."</label>";
afcfe6ca
AD
654
655 $cache_images = sql_bool_to_bool(db_fetch_result($result, 0, "cache_images"));
656
657 if ($cache_images) {
658 $checked = "checked=\"1\"";
659 } else {
660 $checked = "";
661 }
662
3c696512
AD
663 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"cache_images\"
664 name=\"cache_images\"
afcfe6ca 665 $checked>&nbsp;<label for=\"cache_images\">".
3c696512 666 __('Cache images locally')."</label>";
afcfe6ca
AD
667
668 $mark_unread_on_update = sql_bool_to_bool(db_fetch_result($result, 0, "mark_unread_on_update"));
669
670 if ($mark_unread_on_update) {
671 $checked = "checked";
672 } else {
673 $checked = "";
674 }
675
676 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"mark_unread_on_update\"
677 name=\"mark_unread_on_update\"
678 $checked>&nbsp;<label for=\"mark_unread_on_update\">".__('Mark updated articles as unread')."</label>";
679
afcfe6ca
AD
680 print "</div>";
681
682 /* Icon */
683
684 print "<div class=\"dlgSec\">".__("Icon")."</div>";
685 print "<div class=\"dlgSecCont\">";
686
687 print "<iframe name=\"icon_upload_iframe\"
688 style=\"width: 400px; height: 100px; display: none;\"></iframe>";
689
690 print "<form style='display : block' target=\"icon_upload_iframe\"
691 enctype=\"multipart/form-data\" method=\"POST\"
692 action=\"backend.php\">
693 <input id=\"icon_file\" size=\"10\" name=\"icon_file\" type=\"file\">
694 <input type=\"hidden\" name=\"op\" value=\"pref-feeds\">
695 <input type=\"hidden\" name=\"feed_id\" value=\"$feed_id\">
696 <input type=\"hidden\" name=\"method\" value=\"uploadicon\">
697 <button dojoType=\"dijit.form.Button\" onclick=\"return uploadFeedIcon();\"
698 type=\"submit\">".__('Replace')."</button>
699 <button dojoType=\"dijit.form.Button\" onclick=\"return removeFeedIcon($feed_id);\"
700 type=\"submit\">".__('Remove')."</button>
701 </form>";
702
703 print "</div>";
704
705 $title = htmlspecialchars($title, ENT_QUOTES);
706
707 print "<div class='dlgButtons'>
708 <div style=\"float : left\">
709 <button dojoType=\"dijit.form.Button\" onclick='return unsubscribeFeed($feed_id, \"$title\")'>".
710 __('Unsubscribe')."</button>";
711
712 if (PUBSUBHUBBUB_ENABLED) {
713 $pubsub_state = db_fetch_result($result, 0, "pubsub_state");
714 $pubsub_btn_disabled = ($pubsub_state == 2) ? "" : "disabled=\"1\"";
715
716 print "<button dojoType=\"dijit.form.Button\" id=\"pubsubReset_Btn\" $pubsub_btn_disabled
717 onclick='return resetPubSub($feed_id, \"$title\")'>".__('Resubscribe to push updates').
718 "</button>";
719 }
720
721 print "</div>";
722
723 print "<div dojoType=\"dijit.Tooltip\" connectId=\"pubsubReset_Btn\" position=\"below\">".
724 __('Resets PubSubHubbub subscription status for push-enabled feeds.')."</div>";
725
726 print "<button dojoType=\"dijit.form.Button\" onclick=\"return dijit.byId('feedEditDlg').execute()\">".__('Save')."</button>
727 <button dojoType=\"dijit.form.Button\" onclick=\"return dijit.byId('feedEditDlg').hide()\">".__('Cancel')."</button>
728 </div>";
729
730 return;
731 }
732
733 function editfeeds() {
734 global $purge_intervals;
735 global $update_intervals;
46da73c2 736
3972bf59 737 $feed_ids = db_escape_string($this->link, $_REQUEST["ids"]);
afcfe6ca 738
ca6a0741
AD
739 print "<div class=\"dialogNotice\">" . __("Enable the options you wish to apply using checkboxes on the right:") . "</div>";
740
afcfe6ca
AD
741 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"ids\" value=\"$feed_ids\">";
742 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"op\" value=\"pref-feeds\">";
743 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"method\" value=\"batchEditSave\">";
744
745 print "<div class=\"dlgSec\">".__("Feed")."</div>";
746 print "<div class=\"dlgSecCont\">";
747
748 /* Title */
749
750 print "<input dojoType=\"dijit.form.ValidationTextBox\"
751 disabled=\"1\" style=\"font-size : 16px; width : 20em;\" required=\"1\"
752 name=\"title\" value=\"$title\">";
753
754 $this->batch_edit_cbox("title");
755
756 /* Feed URL */
757
758 print "<br/>";
759
760 print __('URL:') . " ";
761 print "<input dojoType=\"dijit.form.ValidationTextBox\" disabled=\"1\"
762 required=\"1\" regExp='^(http|https)://.*' style=\"width : 20em\"
763 name=\"feed_url\" value=\"$feed_url\">";
764
765 $this->batch_edit_cbox("feed_url");
766
767 /* Category */
768
769 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
770
771 print "<br/>";
772
773 print __('Place in category:') . " ";
774
775 print_feed_cat_select($this->link, "cat_id", $cat_id,
776 'disabled="1" dojoType="dijit.form.Select"');
777
778 $this->batch_edit_cbox("cat_id");
779
780 }
781
782 print "</div>";
783
784 print "<div class=\"dlgSec\">".__("Update")."</div>";
785 print "<div class=\"dlgSecCont\">";
786
787 /* Update Interval */
788
789 print_select_hash("update_interval", $update_interval, $update_intervals,
790 'disabled="1" dojoType="dijit.form.Select"');
791
792 $this->batch_edit_cbox("update_interval");
793
afcfe6ca
AD
794 /* Purge intl */
795
796 if (FORCE_ARTICLE_PURGE == 0) {
797
798 print "<br/>";
799
800 print __('Article purging:') . " ";
801
802 print_select_hash("purge_interval", $purge_interval, $purge_intervals,
803 'disabled="1" dojoType="dijit.form.Select"');
804
805 $this->batch_edit_cbox("purge_interval");
806 }
807
808 print "</div>";
809 print "<div class=\"dlgSec\">".__("Authentication")."</div>";
810 print "<div class=\"dlgSecCont\">";
811
812 print "<input dojoType=\"dijit.form.TextBox\"
813 placeHolder=\"".__("Login")."\" disabled=\"1\"
814 name=\"auth_login\" value=\"$auth_login\">";
815
816 $this->batch_edit_cbox("auth_login");
817
818 print "<br/><input dojoType=\"dijit.form.TextBox\" type=\"password\" name=\"auth_pass\"
819 placeHolder=\"".__("Password")."\" disabled=\"1\"
820 value=\"$auth_pass\">";
821
822 $this->batch_edit_cbox("auth_pass");
823
824 print "</div>";
825 print "<div class=\"dlgSec\">".__("Options")."</div>";
826 print "<div class=\"dlgSecCont\">";
827
828 print "<input disabled=\"1\" type=\"checkbox\" name=\"private\" id=\"private\"
829 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"private_l\" class='insensitive' for=\"private\">".__('Hide from Popular feeds')."</label>";
830
831 print "&nbsp;"; $this->batch_edit_cbox("private", "private_l");
832
afcfe6ca
AD
833 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"include_in_digest\"
834 name=\"include_in_digest\"
835 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"include_in_digest_l\" class='insensitive' for=\"include_in_digest\">".__('Include in e-mail digest')."</label>";
836
837 print "&nbsp;"; $this->batch_edit_cbox("include_in_digest", "include_in_digest_l");
838
839 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"always_display_enclosures\"
840 name=\"always_display_enclosures\"
841 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"always_display_enclosures_l\" class='insensitive' for=\"always_display_enclosures\">".__('Always display image attachments')."</label>";
842
843 print "&nbsp;"; $this->batch_edit_cbox("always_display_enclosures", "always_display_enclosures_l");
844
bfd61d3f
AD
845 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"hide_images\"
846 name=\"hide_images\"
847 dojoType=\"dijit.form.CheckBox\">&nbsp;<label class='insensitive' id=\"hide_images_l\"
848 for=\"hide_images\">".
849 __('Do not embed images')."</label>";
850
851 print "&nbsp;"; $this->batch_edit_cbox("hide_images", "hide_images_l");
852
3c696512
AD
853 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"cache_images\"
854 name=\"cache_images\"
855 dojoType=\"dijit.form.CheckBox\">&nbsp;<label class='insensitive' id=\"cache_images_l\"
856 for=\"cache_images\">".
857 __('Cache images locally')."</label>";
afcfe6ca 858
3c696512 859 print "&nbsp;"; $this->batch_edit_cbox("cache_images", "cache_images_l");
afcfe6ca
AD
860
861 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"mark_unread_on_update\"
862 name=\"mark_unread_on_update\"
863 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"mark_unread_on_update_l\" class='insensitive' for=\"mark_unread_on_update\">".__('Mark updated articles as unread')."</label>";
864
865 print "&nbsp;"; $this->batch_edit_cbox("mark_unread_on_update", "mark_unread_on_update_l");
866
afcfe6ca
AD
867 print "</div>";
868
869 print "<div class='dlgButtons'>
870 <button dojoType=\"dijit.form.Button\"
871 onclick=\"return dijit.byId('feedEditDlg').execute()\">".
872 __('Save')."</button>
873 <button dojoType=\"dijit.form.Button\"
874 onclick=\"return dijit.byId('feedEditDlg').hide()\">".
875 __('Cancel')."</button>
876 </div>";
877
878 return;
879 }
880
881 function batchEditSave() {
3a76e2a2 882 return $this->editsaveops(true);
afcfe6ca 883 }
46da73c2 884
afcfe6ca 885 function editSave() {
3a76e2a2 886 return $this->editsaveops(false);
afcfe6ca 887 }
46da73c2
AD
888
889 function editsaveops($batch) {
890
3972bf59
AD
891 $feed_title = db_escape_string($this->link, trim($_POST["title"]));
892 $feed_link = db_escape_string($this->link, trim($_POST["feed_url"]));
893 $upd_intl = (int) db_escape_string($this->link, $_POST["update_interval"]);
894 $purge_intl = (int) db_escape_string($this->link, $_POST["purge_interval"]);
895 $feed_id = (int) db_escape_string($this->link, $_POST["id"]); /* editSave */
896 $feed_ids = db_escape_string($this->link, $_POST["ids"]); /* batchEditSave */
897 $cat_id = (int) db_escape_string($this->link, $_POST["cat_id"]);
898 $auth_login = db_escape_string($this->link, trim($_POST["auth_login"]));
899 $auth_pass = db_escape_string($this->link, trim($_POST["auth_pass"]));
900 $private = checkbox_to_sql_bool(db_escape_string($this->link, $_POST["private"]));
afcfe6ca 901 $include_in_digest = checkbox_to_sql_bool(
3972bf59 902 db_escape_string($this->link, $_POST["include_in_digest"]));
afcfe6ca 903 $cache_images = checkbox_to_sql_bool(
3972bf59 904 db_escape_string($this->link, $_POST["cache_images"]));
bfd61d3f 905 $hide_images = checkbox_to_sql_bool(
3972bf59 906 db_escape_string($this->link, $_POST["hide_images"]));
afcfe6ca 907 $always_display_enclosures = checkbox_to_sql_bool(
3972bf59 908 db_escape_string($this->link, $_POST["always_display_enclosures"]));
afcfe6ca
AD
909
910 $mark_unread_on_update = checkbox_to_sql_bool(
3972bf59 911 db_escape_string($this->link, $_POST["mark_unread_on_update"]));
afcfe6ca 912
afcfe6ca
AD
913 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
914 if ($cat_id && $cat_id != 0) {
915 $category_qpart = "cat_id = '$cat_id',";
916 $category_qpart_nocomma = "cat_id = '$cat_id'";
917 } else {
918 $category_qpart = 'cat_id = NULL,';
919 $category_qpart_nocomma = 'cat_id = NULL';
920 }
921 } else {
922 $category_qpart = "";
923 $category_qpart_nocomma = "";
924 }
925
3a76e2a2 926 if (!$batch) {
afcfe6ca
AD
927
928 $result = db_query($this->link, "UPDATE ttrss_feeds SET
929 $category_qpart
930 title = '$feed_title', feed_url = '$feed_link',
931 update_interval = '$upd_intl',
932 purge_interval = '$purge_intl',
933 auth_login = '$auth_login',
934 auth_pass = '$auth_pass',
935 private = $private,
87764a50 936 cache_images = $cache_images,
bfd61d3f 937 hide_images = $hide_images,
afcfe6ca
AD
938 include_in_digest = $include_in_digest,
939 always_display_enclosures = $always_display_enclosures,
5321e775 940 mark_unread_on_update = $mark_unread_on_update
19b3992b 941 WHERE id = '$feed_id' AND owner_uid = " . $_SESSION["uid"]);
afcfe6ca 942
3a76e2a2 943 } else {
afcfe6ca
AD
944 $feed_data = array();
945
946 foreach (array_keys($_POST) as $k) {
947 if ($k != "op" && $k != "method" && $k != "ids") {
948 $feed_data[$k] = $_POST[$k];
949 }
950 }
951
952 db_query($this->link, "BEGIN");
953
954 foreach (array_keys($feed_data) as $k) {
955
956 $qpart = "";
957
958 switch ($k) {
959 case "title":
960 $qpart = "title = '$feed_title'";
961 break;
962
963 case "feed_url":
964 $qpart = "feed_url = '$feed_link'";
965 break;
966
967 case "update_interval":
968 $qpart = "update_interval = '$upd_intl'";
969 break;
970
971 case "purge_interval":
972 $qpart = "purge_interval = '$purge_intl'";
973 break;
974
975 case "auth_login":
976 $qpart = "auth_login = '$auth_login'";
977 break;
978
979 case "auth_pass":
980 $qpart = "auth_pass = '$auth_pass'";
981 break;
982
983 case "private":
a498d18b 984 $qpart = "private = $private";
afcfe6ca
AD
985 break;
986
987 case "include_in_digest":
a498d18b 988 $qpart = "include_in_digest = $include_in_digest";
afcfe6ca
AD
989 break;
990
991 case "always_display_enclosures":
a498d18b 992 $qpart = "always_display_enclosures = $always_display_enclosures";
afcfe6ca
AD
993 break;
994
995 case "mark_unread_on_update":
a498d18b 996 $qpart = "mark_unread_on_update = $mark_unread_on_update";
afcfe6ca
AD
997 break;
998
afcfe6ca 999 case "cache_images":
a498d18b 1000 $qpart = "cache_images = $cache_images";
afcfe6ca
AD
1001 break;
1002
bfd61d3f
AD
1003 case "hide_images":
1004 $qpart = "hide_images = $hide_images";
1005 break;
1006
afcfe6ca
AD
1007 case "cat_id":
1008 $qpart = $category_qpart_nocomma;
1009 break;
1010
1011 }
1012
1013 if ($qpart) {
1014 db_query($this->link,
1015 "UPDATE ttrss_feeds SET $qpart WHERE id IN ($feed_ids)
1016 AND owner_uid = " . $_SESSION["uid"]);
1017 print "<br/>";
1018 }
1019 }
1020
1021 db_query($this->link, "COMMIT");
1022 }
1023 return;
1024 }
1025
1026 function resetPubSub() {
1027
3972bf59 1028 $ids = db_escape_string($this->link, $_REQUEST["ids"]);
afcfe6ca
AD
1029
1030 db_query($this->link, "UPDATE ttrss_feeds SET pubsub_state = 0 WHERE id IN ($ids)
1031 AND owner_uid = " . $_SESSION["uid"]);
1032
1033 return;
1034 }
1035
1036 function remove() {
1037
3972bf59 1038 $ids = split(",", db_escape_string($this->link, $_REQUEST["ids"]));
afcfe6ca
AD
1039
1040 foreach ($ids as $id) {
efc6553d 1041 Pref_Feeds::remove_feed($this->link, $id, $_SESSION["uid"]);
afcfe6ca
AD
1042 }
1043
1044 return;
1045 }
1046
1047 function clear() {
3972bf59 1048 $id = db_escape_string($this->link, $_REQUEST["id"]);
87d7e850 1049 $this->clear_feed_articles($this->link, $id);
afcfe6ca
AD
1050 }
1051
1052 function rescore() {
92c14e9d
AD
1053 require_once "rssfuncs.php";
1054
3972bf59 1055 $ids = split(",", db_escape_string($this->link, $_REQUEST["ids"]));
afcfe6ca
AD
1056
1057 foreach ($ids as $id) {
1058
1059 $filters = load_filters($this->link, $id, $_SESSION["uid"], 6);
1060
1061 $result = db_query($this->link, "SELECT
1062 title, content, link, ref_id, author,".
1063 SUBSTRING_FOR_DATE."(updated, 1, 19) AS updated
1064 FROM
1065 ttrss_user_entries, ttrss_entries
1066 WHERE ref_id = id AND feed_id = '$id' AND
1067 owner_uid = " .$_SESSION['uid']."
1068 ");
1069
1070 $scores = array();
1071
1072 while ($line = db_fetch_assoc($result)) {
1073
1074 $tags = get_article_tags($this->link, $line["ref_id"]);
1075
1076 $article_filters = get_article_filters($filters, $line['title'],
1077 $line['content'], $line['link'], strtotime($line['updated']),
1078 $line['author'], $tags);
1079
1080 $new_score = calculate_article_score($article_filters);
1081
1082 if (!$scores[$new_score]) $scores[$new_score] = array();
1083
1084 array_push($scores[$new_score], $line['ref_id']);
1085 }
1086
1087 foreach (array_keys($scores) as $s) {
1088 if ($s > 1000) {
1089 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
1090 marked = true WHERE
1091 ref_id IN (" . join(',', $scores[$s]) . ")");
1092 } else if ($s < -500) {
1093 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
1094 unread = false WHERE
1095 ref_id IN (" . join(',', $scores[$s]) . ")");
1096 } else {
1097 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s' WHERE
1098 ref_id IN (" . join(',', $scores[$s]) . ")");
1099 }
1100 }
1101 }
1102
1103 print __("All done.");
1104
1105 }
1106
1107 function rescoreAll() {
1108
1109 $result = db_query($this->link,
1110 "SELECT id FROM ttrss_feeds WHERE owner_uid = " . $_SESSION['uid']);
1111
1112 while ($feed_line = db_fetch_assoc($result)) {
1113
1114 $id = $feed_line["id"];
1115
1116 $filters = load_filters($this->link, $id, $_SESSION["uid"], 6);
1117
1118 $tmp_result = db_query($this->link, "SELECT
1119 title, content, link, ref_id, author,".
1120 SUBSTRING_FOR_DATE."(updated, 1, 19) AS updated
1121 FROM
1122 ttrss_user_entries, ttrss_entries
1123 WHERE ref_id = id AND feed_id = '$id' AND
1124 owner_uid = " .$_SESSION['uid']."
1125 ");
1126
1127 $scores = array();
1128
1129 while ($line = db_fetch_assoc($tmp_result)) {
1130
1131 $tags = get_article_tags($this->link, $line["ref_id"]);
1132
1133 $article_filters = get_article_filters($filters, $line['title'],
1134 $line['content'], $line['link'], strtotime($line['updated']),
1135 $line['author'], $tags);
1136
1137 $new_score = calculate_article_score($article_filters);
1138
1139 if (!$scores[$new_score]) $scores[$new_score] = array();
1140
1141 array_push($scores[$new_score], $line['ref_id']);
1142 }
1143
1144 foreach (array_keys($scores) as $s) {
1145 if ($s > 1000) {
1146 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
1147 marked = true WHERE
1148 ref_id IN (" . join(',', $scores[$s]) . ")");
1149 } else {
1150 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s' WHERE
1151 ref_id IN (" . join(',', $scores[$s]) . ")");
1152 }
1153 }
1154 }
1155
1156 print __("All done.");
1157
1158 }
1159
afcfe6ca 1160 function categorize() {
3972bf59 1161 $ids = split(",", db_escape_string($this->link, $_REQUEST["ids"]));
afcfe6ca 1162
3972bf59 1163 $cat_id = db_escape_string($this->link, $_REQUEST["cat_id"]);
afcfe6ca
AD
1164
1165 if ($cat_id == 0) {
1166 $cat_id_qpart = 'NULL';
1167 } else {
1168 $cat_id_qpart = "'$cat_id'";
1169 }
1170
1171 db_query($this->link, "BEGIN");
1172
1173 foreach ($ids as $id) {
1174
1175 db_query($this->link, "UPDATE ttrss_feeds SET cat_id = $cat_id_qpart
1176 WHERE id = '$id'
1177 AND owner_uid = " . $_SESSION["uid"]);
1178
1179 }
1180
1181 db_query($this->link, "COMMIT");
1182 }
1183
28537341 1184 function removeCat() {
3972bf59 1185 $ids = split(",", db_escape_string($this->link, $_REQUEST["ids"]));
28537341 1186 foreach ($ids as $id) {
a6a9b812 1187 $this->remove_feed_category($this->link, $id, $_SESSION["uid"]);
28537341
AD
1188 }
1189 }
1190
1191 function addCat() {
3972bf59 1192 $feed_cat = db_escape_string($this->link, trim($_REQUEST["cat"]));
28537341
AD
1193
1194 add_feed_category($this->link, $feed_cat);
1195 }
1196
afcfe6ca
AD
1197 function index() {
1198
1199 print "<div dojoType=\"dijit.layout.AccordionContainer\" region=\"center\">";
1200 print "<div id=\"pref-feeds-feeds\" dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Feeds')."\">";
1201
1202 $result = db_query($this->link, "SELECT COUNT(id) AS num_errors
1203 FROM ttrss_feeds WHERE last_error != '' AND owner_uid = ".$_SESSION["uid"]);
1204
1205 $num_errors = db_fetch_result($result, 0, "num_errors");
1206
1207 if ($num_errors > 0) {
1208
1209 $error_button = "<button dojoType=\"dijit.form.Button\"
1210 onclick=\"showFeedsWithErrors()\" id=\"errorButton\">" .
1211 __("Feeds with errors") . "</button>";
1212 }
1213
1214 if (DB_TYPE == "pgsql") {
1215 $interval_qpart = "NOW() - INTERVAL '3 months'";
1216 } else {
1217 $interval_qpart = "DATE_SUB(NOW(), INTERVAL 3 MONTH)";
1218 }
1219
1220 $result = db_query($this->link, "SELECT COUNT(*) AS num_inactive FROM ttrss_feeds WHERE
1221 (SELECT MAX(updated) FROM ttrss_entries, ttrss_user_entries WHERE
1222 ttrss_entries.id = ref_id AND
1223 ttrss_user_entries.feed_id = ttrss_feeds.id) < $interval_qpart AND
1224 ttrss_feeds.owner_uid = ".$_SESSION["uid"]);
1225
1226 $num_inactive = db_fetch_result($result, 0, "num_inactive");
1227
1228 if ($num_inactive > 0) {
1229 $inactive_button = "<button dojoType=\"dijit.form.Button\"
1230 onclick=\"showInactiveFeeds()\">" .
1231 __("Inactive feeds") . "</button>";
1232 }
1233
3972bf59 1234 $feed_search = db_escape_string($this->link, $_REQUEST["search"]);
afcfe6ca
AD
1235
1236 if (array_key_exists("search", $_REQUEST)) {
1237 $_SESSION["prefs_feed_search"] = $feed_search;
1238 } else {
1239 $feed_search = $_SESSION["prefs_feed_search"];
1240 }
1241
1242 print '<div dojoType="dijit.layout.BorderContainer" gutters="false">';
1243
1244 print "<div region='top' dojoType=\"dijit.Toolbar\">"; #toolbar
1245
1246 print "<div style='float : right; padding-right : 4px;'>
1247 <input dojoType=\"dijit.form.TextBox\" id=\"feed_search\" size=\"20\" type=\"search\"
1248 value=\"$feed_search\">
1249 <button dojoType=\"dijit.form.Button\" onclick=\"updateFeedList()\">".
1250 __('Search')."</button>
1251 </div>";
1252
1253 print "<div dojoType=\"dijit.form.DropDownButton\">".
1254 "<span>" . __('Select')."</span>";
1255 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1256 print "<div onclick=\"dijit.byId('feedTree').model.setAllChecked(true)\"
1257 dojoType=\"dijit.MenuItem\">".__('All')."</div>";
1258 print "<div onclick=\"dijit.byId('feedTree').model.setAllChecked(false)\"
1259 dojoType=\"dijit.MenuItem\">".__('None')."</div>";
1260 print "</div></div>";
1261
1262 print "<div dojoType=\"dijit.form.DropDownButton\">".
1263 "<span>" . __('Feeds')."</span>";
1264 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1265 print "<div onclick=\"quickAddFeed()\"
1266 dojoType=\"dijit.MenuItem\">".__('Subscribe to feed')."</div>";
1267 print "<div onclick=\"editSelectedFeed()\"
1268 dojoType=\"dijit.MenuItem\">".__('Edit selected feeds')."</div>";
1269 print "<div onclick=\"resetFeedOrder()\"
1270 dojoType=\"dijit.MenuItem\">".__('Reset sort order')."</div>";
33f0fdd0
AD
1271 print "<div onclick=\"batchSubscribe()\"
1272 dojoType=\"dijit.MenuItem\">".__('Batch subscribe')."</div>";
afcfe6ca
AD
1273 print "</div></div>";
1274
1275 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
1276 print "<div dojoType=\"dijit.form.DropDownButton\">".
1277 "<span>" . __('Categories')."</span>";
1278 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
5ef071e0
AD
1279 print "<div onclick=\"createCategory()\"
1280 dojoType=\"dijit.MenuItem\">".__('Add category')."</div>";
5b7bd238
AD
1281 print "<div onclick=\"toggleHiddenFeedCats()\"
1282 dojoType=\"dijit.MenuItem\">".__('(Un)hide empty categories')."</div>";
afcfe6ca
AD
1283 print "<div onclick=\"resetCatOrder()\"
1284 dojoType=\"dijit.MenuItem\">".__('Reset sort order')."</div>";
fd26d5bf
AD
1285 print "<div onclick=\"removeSelectedCategories()\"
1286 dojoType=\"dijit.MenuItem\">".__('Remove selected')."</div>";
afcfe6ca
AD
1287 print "</div></div>";
1288
1289 }
1290
1291 print $error_button;
1292 print $inactive_button;
1293
1294 print "<button dojoType=\"dijit.form.Button\" onclick=\"removeSelectedFeeds()\">"
1295 .__('Unsubscribe')."</button dojoType=\"dijit.form.Button\"> ";
1296
1297 if (defined('_ENABLE_FEED_DEBUGGING')) {
1298
1299 print "<select id=\"feedActionChooser\" onchange=\"feedActionChange()\">
1300 <option value=\"facDefault\" selected>".__('More actions...')."</option>";
1301
1302 if (FORCE_ARTICLE_PURGE == 0) {
1303 print
1304 "<option value=\"facPurge\">".__('Manual purge')."</option>";
1305 }
1306
1307 print "
1308 <option value=\"facClear\">".__('Clear feed data')."</option>
1309 <option value=\"facRescore\">".__('Rescore articles')."</option>";
1310
1311 print "</select>";
1312
1313 }
1314
1315 print "</div>"; # toolbar
1316
1317 //print '</div>';
1318 print '<div dojoType="dijit.layout.ContentPane" region="center">';
1319
1320 print "<div id=\"feedlistLoading\">
1321 <img src='images/indicator_tiny.gif'>".
1322 __("Loading, please wait...")."</div>";
1323
1324 print "<div dojoType=\"fox.PrefFeedStore\" jsId=\"feedStore\"
1325 url=\"backend.php?op=pref-feeds&method=getfeedtree\">
1326 </div>
1327 <div dojoType=\"lib.CheckBoxStoreModel\" jsId=\"feedModel\" store=\"feedStore\"
1328 query=\"{id:'root'}\" rootId=\"root\" rootLabel=\"Feeds\"
1329 childrenAttrs=\"items\" checkboxStrict=\"false\" checkboxAll=\"false\">
1330 </div>
1331 <div dojoType=\"fox.PrefFeedTree\" id=\"feedTree\"
1332 dndController=\"dijit.tree.dndSource\"
1333 betweenThreshold=\"5\"
1334 model=\"feedModel\" openOnClick=\"false\">
1335 <script type=\"dojo/method\" event=\"onClick\" args=\"item\">
1336 var id = String(item.id);
1337 var bare_id = id.substr(id.indexOf(':')+1);
1338
1339 if (id.match('FEED:')) {
1340 editFeed(bare_id);
1341 } else if (id.match('CAT:')) {
1342 editCat(bare_id, item);
1343 }
1344 </script>
1345 <script type=\"dojo/method\" event=\"onLoad\" args=\"item\">
1346 Element.hide(\"feedlistLoading\");
1347 </script>
1348 </div>";
1349
ba5296a1
AD
1350# print "<div dojoType=\"dijit.Tooltip\" connectId=\"feedTree\" position=\"below\">
1351# ".__('<b>Hint:</b> you can drag feeds and categories around.')."
1352# </div>";
afcfe6ca
AD
1353
1354 print '</div>';
1355 print '</div>';
1356
1357 print "</div>"; # feeds pane
1358
6c2637d9 1359 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('OPML')."\">";
afcfe6ca 1360
566faa14 1361 print "<p>" . __("Using OPML you can export and import your feeds, filters, labels and Tiny Tiny RSS settings.") . " ";
afcfe6ca 1362
566faa14 1363 print __("Only main settings profile can be migrated using OPML.") . "</p>";
afcfe6ca 1364
55f34b81 1365 print "<iframe id=\"upload_iframe\"
afcfe6ca
AD
1366 name=\"upload_iframe\" onload=\"opmlImportComplete(this)\"
1367 style=\"width: 400px; height: 100px; display: none;\"></iframe>";
1368
1369 print "<form name=\"opml_form\" style='display : block' target=\"upload_iframe\"
1370 enctype=\"multipart/form-data\" method=\"POST\"
55f34b81 1371 action=\"backend.php\">
afcfe6ca
AD
1372 <input id=\"opml_file\" name=\"opml_file\" type=\"file\">&nbsp;
1373 <input type=\"hidden\" name=\"op\" value=\"dlg\">
c4c74732 1374 <input type=\"hidden\" name=\"method\" value=\"importOpml\">
afcfe6ca 1375 <button dojoType=\"dijit.form.Button\" onclick=\"return opmlImport();\" type=\"submit\">" .
a1159c01 1376 __('Import my OPML') . "</button>";
afcfe6ca 1377
a1159c01 1378 print "<hr>";
afcfe6ca
AD
1379
1380 print "<p>" . __('Filename:') .
1381 " <input type=\"text\" id=\"filename\" value=\"TinyTinyRSS.opml\" />&nbsp;" .
a1159c01 1382 __('Include settings') . "<input type=\"checkbox\" id=\"settings\" checked=\"1\"/>";
afcfe6ca 1383
a1159c01 1384 print "</p><button dojoType=\"dijit.form.Button\"
afcfe6ca 1385 onclick=\"gotoExportOpml(document.opml_form.filename.value, document.opml_form.settings.checked)\" >" .
a1159c01 1386 __('Export OPML') . "</button></p></form>";
afcfe6ca 1387
a1159c01 1388 print "<hr>";
afcfe6ca
AD
1389
1390 print "<p>".__('Your OPML can be published publicly and can be subscribed by anyone who knows the URL below.') . " ";
1391
566faa14 1392 print __("Published OPML does not include your Tiny Tiny RSS settings, feeds that require authentication or feeds hidden from Popular feeds.") . "</p>";
afcfe6ca
AD
1393
1394 print "<button dojoType=\"dijit.form.Button\" onclick=\"return displayDlg('pubOPMLUrl')\">".
a1159c01 1395 __('Display published OPML URL')."</button> ";
afcfe6ca 1396
699daf58
AD
1397 global $pluginhost;
1398 $pluginhost->run_hooks($pluginhost::HOOK_PREFS_TAB_SECTION,
1399 "hook_prefs_tab_section", "prefFeedsOPML");
1400
afcfe6ca
AD
1401 print "</div>"; # pane
1402
1403 if (strpos($_SERVER['HTTP_USER_AGENT'], "Firefox") !== false) {
1404
1405 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Firefox integration')."\">";
1406
1407 print "<p>" . __('This Tiny Tiny RSS site can be used as a Firefox Feed Reader by clicking the link below.') . "</p>";
1408
1409 print "<p>";
1410
1411 print "<button onclick='window.navigator.registerContentHandler(" .
1412 "\"application/vnd.mozilla.maybe.feed\", " .
1413 "\"" . add_feed_url() . "\", " . " \"Tiny Tiny RSS\")'>" .
1414 __('Click here to register this site as a feed reader.') .
1415 "</button>";
1416
1417 print "</p>";
1418
1419 print "</div>"; # pane
1420 }
1421
e95e7819 1422 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Published & shared articles / Generated feeds')."\">";
afcfe6ca
AD
1423
1424 print "<h3>" . __("Published articles and generated feeds") . "</h3>";
1425
1426 print "<p>".__('Published articles are exported as a public RSS feed and can be subscribed by anyone who knows the URL specified below.')."</p>";
1427
1428 $rss_url = '-2::' . htmlspecialchars(get_self_url_prefix() .
1429 "/public.php?op=rss&id=-2&view-mode=all_articles");;
1430
1431 print "<button dojoType=\"dijit.form.Button\" onclick=\"return displayDlg('generatedFeed', '$rss_url')\">".
1432 __('Display URL')."</button> ";
1433
1434 print "<button dojoType=\"dijit.form.Button\" onclick=\"return clearFeedAccessKeys()\">".
1435 __('Clear all generated URLs')."</button> ";
1436
1437 print "<h3>" . __("Articles shared by URL") . "</h3>";
1438
1439 print "<p>" . __("You can disable all articles shared by unique URLs here.") . "</p>";
1440
1441 print "<button dojoType=\"dijit.form.Button\" onclick=\"return clearArticleAccessKeys()\">".
1442 __('Unshare all articles')."</button> ";
1443
699daf58
AD
1444 global $pluginhost;
1445 $pluginhost->run_hooks($pluginhost::HOOK_PREFS_TAB_SECTION,
1446 "hook_prefs_tab_section", "prefFeedsPublishedGenerated");
1447
afcfe6ca
AD
1448 print "</div>"; #pane
1449
6065f3ad 1450 global $pluginhost;
de612e7a 1451
6065f3ad
AD
1452 $pluginhost->run_hooks($pluginhost::HOOK_PREFS_TAB,
1453 "hook_prefs_tab", "prefFeeds");
1454
afcfe6ca 1455 print "</div>"; #container
afcfe6ca 1456 }
2ecd2df5 1457
88918ca6 1458 private function feedlist_init_cat($cat_id) {
2ecd2df5
AD
1459 $obj = array();
1460 $cat_id = (int) $cat_id;
1461
1462 if ($cat_id > 0) {
1463 $cat_unread = ccache_find($this->link, $cat_id, $_SESSION["uid"], true);
1464 } else if ($cat_id == 0 || $cat_id == -2) {
1465 $cat_unread = getCategoryUnread($this->link, $cat_id);
1466 }
1467
1468 $obj['id'] = 'CAT:' . $cat_id;
1469 $obj['items'] = array();
1470 $obj['name'] = getCategoryTitle($this->link, $cat_id);
1471 $obj['type'] = 'category';
1472 $obj['unread'] = (int) $cat_unread;
2ecd2df5
AD
1473 $obj['bare_id'] = $cat_id;
1474
1475 return $obj;
1476 }
1477
1478 private function feedlist_init_feed($feed_id, $title = false, $unread = false, $error = '', $updated = '') {
1479 $obj = array();
1480 $feed_id = (int) $feed_id;
1481
1482 if (!$title)
1483 $title = getFeedTitle($this->link, $feed_id, false);
1484
1485 if ($unread === false)
1486 $unread = getFeedUnread($this->link, $feed_id, false);
1487
1488 $obj['id'] = 'FEED:' . $feed_id;
1489 $obj['name'] = $title;
1490 $obj['unread'] = (int) $unread;
1491 $obj['type'] = 'feed';
1492 $obj['error'] = $error;
1493 $obj['updated'] = $updated;
1494 $obj['icon'] = getFeedIcon($feed_id);
1495 $obj['bare_id'] = $feed_id;
1496
1497 return $obj;
1498 }
1499
bc6fa236
AD
1500 function inactiveFeeds() {
1501
1502 if (DB_TYPE == "pgsql") {
1503 $interval_qpart = "NOW() - INTERVAL '3 months'";
1504 } else {
1505 $interval_qpart = "DATE_SUB(NOW(), INTERVAL 3 MONTH)";
1506 }
1507
1508 $result = db_query($this->link, "SELECT ttrss_feeds.title, ttrss_feeds.site_url,
1509 ttrss_feeds.feed_url, ttrss_feeds.id, MAX(updated) AS last_article
1510 FROM ttrss_feeds, ttrss_entries, ttrss_user_entries WHERE
1511 (SELECT MAX(updated) FROM ttrss_entries, ttrss_user_entries WHERE
1512 ttrss_entries.id = ref_id AND
1513 ttrss_user_entries.feed_id = ttrss_feeds.id) < $interval_qpart
1514 AND ttrss_feeds.owner_uid = ".$_SESSION["uid"]." AND
1515 ttrss_user_entries.feed_id = ttrss_feeds.id AND
1516 ttrss_entries.id = ref_id
1517 GROUP BY ttrss_feeds.title, ttrss_feeds.id, ttrss_feeds.site_url, ttrss_feeds.feed_url
1518 ORDER BY last_article");
1519
1520 print "<div class=\"dialogNotice\">" . __("These feeds have not been updated with new content for 3 months (oldest first):") . "</div>";
1521
1522 print "<div dojoType=\"dijit.Toolbar\">";
1523 print "<div dojoType=\"dijit.form.DropDownButton\">".
1524 "<span>" . __('Select')."</span>";
1525 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1526 print "<div onclick=\"selectTableRows('prefInactiveFeedList', 'all')\"
1527 dojoType=\"dijit.MenuItem\">".__('All')."</div>";
1528 print "<div onclick=\"selectTableRows('prefInactiveFeedList', 'none')\"
1529 dojoType=\"dijit.MenuItem\">".__('None')."</div>";
1530 print "</div></div>";
1531 print "</div>"; #toolbar
1532
1533 print "<div class=\"inactiveFeedHolder\">";
1534
1535 print "<table width=\"100%\" cellspacing=\"0\" id=\"prefInactiveFeedList\">";
1536
1537 $lnum = 1;
1538
1539 while ($line = db_fetch_assoc($result)) {
1540
1541 $class = ($lnum % 2) ? "even" : "odd";
1542 $feed_id = $line["id"];
1543 $this_row_id = "id=\"FUPDD-$feed_id\"";
1544
1545 # class needed for selectTableRows()
1546 print "<tr class=\"placeholder\" $this_row_id>";
1547
1548 $edit_title = htmlspecialchars($line["title"]);
1549
1550 # id needed for selectTableRows()
1551 print "<td width='5%' align='center'><input
1552 onclick='toggleSelectRow2(this);' dojoType=\"dijit.form.CheckBox\"
1553 type=\"checkbox\" id=\"FUPDC-$feed_id\"></td>";
1554 print "<td>";
1555
1556 print "<a class=\"visibleLink\" href=\"#\" ".
1557 "title=\"".__("Click to edit feed")."\" ".
1558 "onclick=\"editFeed(".$line["id"].")\">".
1559 htmlspecialchars($line["title"])."</a>";
1560
1561 print "</td><td class=\"insensitive\" align='right'>";
1562 print make_local_datetime($this->link, $line['last_article'], false);
1563 print "</td>";
1564 print "</tr>";
1565
1566 ++$lnum;
1567 }
1568
1569 print "</table>";
1570 print "</div>";
1571
1572 print "<div class='dlgButtons'>";
1573 print "<div style='float : left'>";
1574 print "<button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('inactiveFeedsDlg').removeSelected()\">"
1575 .__('Unsubscribe from selected feeds')."</button> ";
1576 print "</div>";
1577
1578 print "<button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('inactiveFeedsDlg').hide()\">".
1579 __('Close this window')."</button>";
1580
1581 print "</div>";
1582
1583 }
1584
1585 function feedsWithErrors() {
1586 print "<div class=\"dialogNotice\">" . __("These feeds have not been updated because of errors:") . "</div>";
1587
1588 $result = db_query($this->link, "SELECT id,title,feed_url,last_error,site_url
1589 FROM ttrss_feeds WHERE last_error != '' AND owner_uid = ".$_SESSION["uid"]);
1590
1591 print "<div dojoType=\"dijit.Toolbar\">";
1592 print "<div dojoType=\"dijit.form.DropDownButton\">".
1593 "<span>" . __('Select')."</span>";
1594 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1595 print "<div onclick=\"selectTableRows('prefErrorFeedList', 'all')\"
1596 dojoType=\"dijit.MenuItem\">".__('All')."</div>";
1597 print "<div onclick=\"selectTableRows('prefErrorFeedList', 'none')\"
1598 dojoType=\"dijit.MenuItem\">".__('None')."</div>";
1599 print "</div></div>";
1600 print "</div>"; #toolbar
1601
1602 print "<div class=\"inactiveFeedHolder\">";
1603
1604 print "<table width=\"100%\" cellspacing=\"0\" id=\"prefErrorFeedList\">";
1605
1606 $lnum = 1;
1607
1608 while ($line = db_fetch_assoc($result)) {
1609
1610 $class = ($lnum % 2) ? "even" : "odd";
1611 $feed_id = $line["id"];
1612 $this_row_id = "id=\"FERDD-$feed_id\"";
1613
1614 # class needed for selectTableRows()
1615 print "<tr class=\"placeholder\" $this_row_id>";
1616
1617 $edit_title = htmlspecialchars($line["title"]);
1618
1619 # id needed for selectTableRows()
1620 print "<td width='5%' align='center'><input
1621 onclick='toggleSelectRow2(this);' dojoType=\"dijit.form.CheckBox\"
1622 type=\"checkbox\" id=\"FERDC-$feed_id\"></td>";
1623 print "<td>";
1624
1625 print "<a class=\"visibleLink\" href=\"#\" ".
1626 "title=\"".__("Click to edit feed")."\" ".
1627 "onclick=\"editFeed(".$line["id"].")\">".
1628 htmlspecialchars($line["title"])."</a>: ";
1629
1630 print "<span class=\"insensitive\">";
1631 print htmlspecialchars($line["last_error"]);
1632 print "</span>";
1633
1634 print "</td>";
1635 print "</tr>";
1636
1637 ++$lnum;
1638 }
1639
1640 print "</table>";
1641 print "</div>";
1642
1643 print "<div class='dlgButtons'>";
1644 print "<div style='float : left'>";
1645 print "<button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('errorFeedsDlg').removeSelected()\">"
1646 .__('Unsubscribe from selected feeds')."</button> ";
1647 print "</div>";
1648
1649 print "<button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('errorFeedsDlg').hide()\">".
1650 __('Close this window')."</button>";
1651
1652 print "</div>";
1653 }
1654
87d7e850
AD
1655 /**
1656 * Purge a feed contents, marked articles excepted.
1657 *
1658 * @param mixed $link The database connection.
1659 * @param integer $id The id of the feed to purge.
1660 * @return void
1661 */
1662 private function clear_feed_articles($link, $id) {
1663
1664 if ($id != 0) {
1665 $result = db_query($link, "DELETE FROM ttrss_user_entries
1666 WHERE feed_id = '$id' AND marked = false AND owner_uid = " . $_SESSION["uid"]);
1667 } else {
1668 $result = db_query($link, "DELETE FROM ttrss_user_entries
1669 WHERE feed_id IS NULL AND marked = false AND owner_uid = " . $_SESSION["uid"]);
1670 }
1671
1672 $result = db_query($link, "DELETE FROM ttrss_entries WHERE
1673 (SELECT COUNT(int_id) FROM ttrss_user_entries WHERE ref_id = id) = 0");
1674
1675 ccache_update($link, $id, $_SESSION['uid']);
1676 } // function clear_feed_articles
1677
a6a9b812
AD
1678 private function remove_feed_category($link, $id, $owner_uid) {
1679
1680 db_query($link, "DELETE FROM ttrss_feed_categories
1681 WHERE id = '$id' AND owner_uid = $owner_uid");
1682
1683 ccache_remove($link, $id, $owner_uid, true);
1684 }
1685
efc6553d 1686 static function remove_feed($link, $id, $owner_uid) {
a6a9b812
AD
1687
1688 if ($id > 0) {
1689
1690 /* save starred articles in Archived feed */
1691
1692 db_query($link, "BEGIN");
1693
1694 /* prepare feed if necessary */
1695
1696 $result = db_query($link, "SELECT id FROM ttrss_archived_feeds
1697 WHERE id = '$id'");
1698
1699 if (db_num_rows($result) == 0) {
1700 db_query($link, "INSERT INTO ttrss_archived_feeds
1701 (id, owner_uid, title, feed_url, site_url)
1702 SELECT id, owner_uid, title, feed_url, site_url from ttrss_feeds
1703 WHERE id = '$id'");
1704 }
1705
1706 db_query($link, "UPDATE ttrss_user_entries SET feed_id = NULL,
1707 orig_feed_id = '$id' WHERE feed_id = '$id' AND
1708 marked = true AND owner_uid = $owner_uid");
1709
1710 /* Remove access key for the feed */
1711
1712 db_query($link, "DELETE FROM ttrss_access_keys WHERE
1713 feed_id = '$id' AND owner_uid = $owner_uid");
1714
1715 /* remove the feed */
1716
1717 db_query($link, "DELETE FROM ttrss_feeds
1718 WHERE id = '$id' AND owner_uid = $owner_uid");
1719
1720 db_query($link, "COMMIT");
1721
1722 if (file_exists(ICONS_DIR . "/$id.ico")) {
1723 unlink(ICONS_DIR . "/$id.ico");
1724 }
1725
1726 ccache_remove($link, $id, $owner_uid);
1727
1728 } else {
f822a8e5
AD
1729 label_remove($link, feed_to_label_id($id), $owner_uid);
1730 //ccache_remove($link, $id, $owner_uid); don't think labels are cached
a6a9b812
AD
1731 }
1732 }
87d7e850 1733
afcfe6ca
AD
1734}
1735?>