PageRenderTime 57ms CodeModel.GetById 20ms RepoModel.GetById 0ms app.codeStats 0ms

/lib/net/nemein/rss/manage.php

https://github.com/nemein/openpsa
PHP | 415 lines | 255 code | 54 blank | 106 comment | 21 complexity | 0ed59d83ddc34a8c96db0025c6fb2235 MD5 | raw file
  1. <?php
  2. /**
  3. * @package net.nemein.rss
  4. * @author The Midgard Project, http://www.midgard-project.org
  5. * @copyright The Midgard Project, http://www.midgard-project.org
  6. * @license http://www.gnu.org/licenses/lgpl.html GNU Lesser General Public License
  7. */
  8. /**
  9. * Feed management class.
  10. *
  11. * @package net.nemein.rss
  12. */
  13. class net_nemein_rss_manage extends midcom_baseclasses_components_plugin
  14. {
  15. public function _on_initialize()
  16. {
  17. // Ensure we get the correct styles
  18. midcom::get('style')->prepend_component_styledir('net.nemein.rss');
  19. $this->_request_data['node'] = $this->_topic;
  20. }
  21. /**
  22. * @param mixed $handler_id The ID of the handler.
  23. * @param Array $args The argument list.
  24. * @param Array &$data The local request data.
  25. */
  26. public function _handler_opml($handler_id, array $args, array &$data)
  27. {
  28. midcom::get('cache')->content->content_type("text/xml; charset=UTF-8");
  29. midcom::get()->header("Content-type: text/xml; charset=UTF-8");
  30. midcom::get()->skip_page_style = true;
  31. $qb = net_nemein_rss_feed_dba::new_query_builder();
  32. $qb->add_order('title');
  33. $qb->add_constraint('node', '=', $this->_topic->id);
  34. $data['feeds'] = $qb->execute();
  35. midcom::get('componentloader')->load_library('de.bitfolge.feedcreator');
  36. }
  37. /**
  38. *
  39. * @param mixed $handler_id The ID of the handler.
  40. * @param array &$data The local request data.
  41. */
  42. public function _show_opml($handler_id, array &$data)
  43. {
  44. $opml = new OPMLCreator();
  45. $opml->title = $this->_topic->extra;
  46. foreach ($data['feeds'] as $feed)
  47. {
  48. $item = new FeedItem();
  49. $item->title = $feed->title;
  50. $item->xmlUrl = $feed->url;
  51. $opml->addItem($item);
  52. }
  53. echo $opml->createFeed();
  54. }
  55. /**
  56. * @param mixed $handler_id The ID of the handler.
  57. * @param Array $args The argument list.
  58. * @param Array &$data The local request data.
  59. */
  60. public function _handler_list($handler_id, array $args, array &$data)
  61. {
  62. $qb = net_nemein_rss_feed_dba::new_query_builder();
  63. $qb->add_order('title');
  64. $qb->add_constraint('node', '=', $this->_topic->id);
  65. $data['feeds'] = $qb->execute();
  66. $this->_update_breadcrumb_line($handler_id);
  67. }
  68. /**
  69. *
  70. * @param mixed $handler_id The ID of the handler.
  71. * @param array &$data The local request data.
  72. */
  73. public function _show_list($handler_id, array &$data)
  74. {
  75. $data['folder'] = $this->_topic;
  76. midcom_show_style('net-nemein-rss-feeds-list-header');
  77. foreach ($data['feeds'] as $feed)
  78. {
  79. $data['feed'] = $feed;
  80. $data['feed_category'] = 'feed:' . md5($feed->url);
  81. $data['topic'] = $this->_topic;
  82. midcom_show_style('net-nemein-rss-feeds-list-item');
  83. }
  84. midcom_show_style('net-nemein-rss-feeds-list-footer');
  85. }
  86. private function _subscribe_feed($feed_url, $feed_title = null)
  87. {
  88. // Try to fetch the new feed
  89. $rss = net_nemein_rss_fetch::raw_fetch($feed_url);
  90. // TODO: display error on invalid feed
  91. if (!$feed_title)
  92. {
  93. // If we didn't get the channel title preset
  94. $feed_title = '';
  95. if ($rss)
  96. {
  97. // Get the channel title from the feed
  98. if (isset($rss->channel['title']))
  99. {
  100. $feed_title = $rss->channel['title'];
  101. }
  102. }
  103. }
  104. // Find out if the URL is already subscribed, and update it in that case
  105. $qb = net_nemein_rss_feed_dba::new_query_builder();
  106. $qb->add_constraint('node', '=', $this->_topic->id);
  107. $qb->add_constraint('url', '=', $feed_url);
  108. $feeds = $qb->execute();
  109. if (count($feeds) > 0)
  110. {
  111. // If we're updating existing feed
  112. $feed = $feeds[0];
  113. $feed->title = $feed_title;
  114. if ($feed->update())
  115. {
  116. $this->_request_data['feeds_updated'][$feed->id] = $feed->url;
  117. return true;
  118. }
  119. return false;
  120. }
  121. else
  122. {
  123. // Otherwise create new feed
  124. $feed = new net_nemein_rss_feed_dba();
  125. $feed->node = $this->_topic->id;
  126. $feed->url = $feed_url;
  127. $feed->title = $feed_title;
  128. if ($feed->create())
  129. {
  130. $this->_request_data['feeds_subscribed'][$feed->id] = $feed->url;
  131. return true;
  132. }
  133. return false;
  134. }
  135. }
  136. /**
  137. * @param mixed $handler_id The ID of the handler.
  138. * @param Array $args The argument list.
  139. * @param Array &$data The local request data.
  140. */
  141. public function _handler_subscribe($handler_id, array $args, array &$data)
  142. {
  143. $this->_topic->require_do('midgard:create');
  144. // Arrays for containing data on subscribed and updated feeds
  145. $data['feeds_subscribed'] = array();
  146. $data['feeds_updated'] = array();
  147. // Single feed addition
  148. if ( array_key_exists('net_nemein_rss_manage_newfeed', $_POST)
  149. && $_POST['net_nemein_rss_manage_newfeed']['url'])
  150. {
  151. $this->_subscribe_feed($_POST['net_nemein_rss_manage_newfeed']['url']);
  152. // TODO: display error messages
  153. // TODO: redirect user to edit page if creation succeeded
  154. return new midcom_response_relocate('feeds/list/');
  155. }
  156. // OPML subscription list import support
  157. if ( array_key_exists('net_nemein_rss_manage_opml', $_FILES)
  158. && is_uploaded_file($_FILES['net_nemein_rss_manage_opml']['tmp_name']))
  159. {
  160. $opml_file = $_FILES['net_nemein_rss_manage_opml']['tmp_name'];
  161. // We have OPML file, parse it
  162. $opml_handle = fopen($opml_file, 'r');
  163. $opml_data = fread($opml_handle, filesize($opml_file));
  164. fclose($opml_handle);
  165. unlink($opml_file);
  166. $opml_parser = xml_parser_create();
  167. xml_parse_into_struct($opml_parser, $opml_data, $opml_values );
  168. foreach ($opml_values as $opml_element)
  169. {
  170. if ($opml_element['tag'] === 'OUTLINE')
  171. {
  172. // Subscribe to found channels
  173. if (isset($opml_element['attributes']['TITLE']))
  174. {
  175. $this->_subscribe_feed($opml_element['attributes']['XMLURL'], $opml_element['attributes']['TITLE']);
  176. }
  177. else
  178. {
  179. $this->_subscribe_feed($opml_element['attributes']['XMLURL']);
  180. }
  181. }
  182. }
  183. xml_parser_free($opml_parser);
  184. return new midcom_response_relocate('feeds/list/');
  185. }
  186. $this->_update_breadcrumb_line($handler_id);
  187. }
  188. /**
  189. *
  190. * @param mixed $handler_id The ID of the handler.
  191. * @param array &$data The local request data.
  192. */
  193. public function _show_subscribe($handler_id, array &$data)
  194. {
  195. $data['folder'] = $this->_topic;
  196. midcom_show_style('net-nemein-rss-feeds-subscribe');
  197. }
  198. private function _load_controller(&$data)
  199. {
  200. $data['schemadb'] = midcom_helper_datamanager2_schema::load_database($this->_config->get('schemadb_feed'));
  201. $data['controller'] = midcom_helper_datamanager2_controller::create('simple');
  202. $data['controller']->schemadb =& $data['schemadb'];
  203. $data['controller']->set_storage($data['feed']);
  204. if (! $data['controller']->initialize())
  205. {
  206. throw new midcom_error("Failed to initialize a DM2 controller instance for feed {$data['feed']->id}.");
  207. }
  208. }
  209. /**
  210. * @param mixed $handler_id The ID of the handler.
  211. * @param Array $args The argument list.
  212. * @param Array &$data The local request data.
  213. */
  214. public function _handler_edit($handler_id, array $args, array &$data)
  215. {
  216. $data['feed'] = new net_nemein_rss_feed_dba($args[0]);
  217. $data['feed']->require_do('midgard:update');
  218. $this->_load_controller($data);
  219. switch ($data['controller']->process_form())
  220. {
  221. case 'save':
  222. // TODO: Fetch the feed here?
  223. // *** FALL-THROUGH ***
  224. case 'cancel':
  225. return new midcom_response_relocate('feeds/list/');
  226. }
  227. midcom::get('metadata')->set_request_metadata($data['feed']->metadata->revised, $data['feed']->guid);
  228. $this->bind_view_to_object($data['feed']);
  229. $this->_update_breadcrumb_line($handler_id);
  230. }
  231. /**
  232. *
  233. * @param mixed $handler_id The ID of the handler.
  234. * @param array &$data The local request data.
  235. */
  236. public function _show_edit($handler_id, array &$data)
  237. {
  238. midcom_show_style('net-nemein-rss-feed-edit');
  239. }
  240. /**
  241. * Displays a downloadpage delete confirmation view.
  242. *
  243. * Note, that the downloadpage for non-index mode operation is automatically determined in the can_handle
  244. * phase.
  245. *
  246. * If create privileges apply, we relocate to the index creation downloadpage
  247. *
  248. * @param mixed $handler_id The ID of the handler.
  249. * @param Array $args The argument list.
  250. * @param Array &$data The local request data.
  251. */
  252. public function _handler_delete($handler_id, array $args, array &$data)
  253. {
  254. $data['feed'] = new net_nemein_rss_feed_dba($args[0]);
  255. $data['feed']->require_do('midgard:delete');
  256. $this->_load_controller($data);
  257. if (array_key_exists('net_nemein_rss_deleteok', $_REQUEST))
  258. {
  259. // Deletion confirmed.
  260. if (!$data['feed']->delete())
  261. {
  262. throw new midcom_error("Failed to delete feed {$args[0]}, last Midgard error was: " . midcom_connection::get_error_string());
  263. }
  264. // Delete ok, relocating to welcome.
  265. return new midcom_response_relocate('feeds/list/');
  266. }
  267. if (array_key_exists('net_nemein_rss_deletecancel', $_REQUEST))
  268. {
  269. // Redirect to view page.
  270. return new midcom_response_relocate('feeds/list/');
  271. }
  272. midcom::get('metadata')->set_request_metadata($data['feed']->metadata->revised, $data['feed']->guid);
  273. $this->_view_toolbar->bind_to($data['feed']);
  274. midcom::get('head')->set_pagetitle("{$this->_topic->extra}: {$data['feed']->title}");
  275. $this->_update_breadcrumb_line($handler_id);
  276. }
  277. /**
  278. * Shows the loaded downloadpage.
  279. *
  280. * @param mixed $handler_id The ID of the handler.
  281. * @param array &$data The local request data.
  282. */
  283. public function _show_delete ($handler_id, array &$data)
  284. {
  285. midcom_show_style('net-nemein-rss-feed-delete');
  286. }
  287. /**
  288. * @param mixed $handler_id The ID of the handler.
  289. * @param Array $args The argument list.
  290. * @param Array &$data The local request data.
  291. */
  292. public function _handler_fetch($handler_id, array $args, array &$data)
  293. {
  294. $this->_topic->require_do('midgard:create');
  295. midcom::get('cache')->content->enable_live_mode();
  296. //Disable limits
  297. @ini_set('memory_limit', $GLOBALS['midcom_config']['midcom_max_memory']);
  298. @ini_set('max_execution_time', 0);
  299. if ($handler_id == 'feeds_fetch')
  300. {
  301. $data['feed'] = new net_nemein_rss_feed_dba($args[0]);
  302. $fetcher = new net_nemein_rss_fetch($data['feed']);
  303. $data['items'] = $fetcher->import();
  304. midcom::get('metadata')->set_request_metadata($data['feed']->metadata->revised, $data['feed']->guid);
  305. $this->bind_view_to_object($data['feed']);
  306. }
  307. else
  308. {
  309. $data['items'] = array();
  310. $qb = net_nemein_rss_feed_dba::new_query_builder();
  311. $qb->add_order('title');
  312. $qb->add_constraint('node', '=', $this->_topic->id);
  313. $data['feeds'] = $qb->execute();
  314. foreach ($data['feeds'] as $feed)
  315. {
  316. $fetcher = new net_nemein_rss_fetch($feed);
  317. $items = $fetcher->import();
  318. $data['items'] = array_merge($data['items'], $items);
  319. }
  320. }
  321. $this->_update_breadcrumb_line($handler_id);
  322. }
  323. /**
  324. *
  325. * @param mixed $handler_id The ID of the handler.
  326. * @param array &$data The local request data.
  327. */
  328. public function _show_fetch($handler_id, array &$data)
  329. {
  330. midcom_show_style('net-nemein-rss-feed-fetch');
  331. }
  332. /**
  333. * Helper, updates the context so that we get a complete breadcrumb line towards the current
  334. * location.
  335. *
  336. * @param string $handler_id The current handler's ID
  337. */
  338. private function _update_breadcrumb_line($handler_id)
  339. {
  340. $this->add_breadcrumb("feeds/list/", $this->_l10n->get('manage feeds'));
  341. switch ($handler_id)
  342. {
  343. case 'feeds_subscribe':
  344. $this->add_breadcrumb("feeds/subscribe/", $this->_l10n->get('subscribe feeds'));
  345. break;
  346. case 'feeds_edit':
  347. $this->add_breadcrumb("feeds/edit/{$this->_request_data['feed']->guid}/", $this->_l10n_midcom->get('edit'));
  348. break;
  349. case 'feeds_delete':
  350. $this->add_breadcrumb("feeds/delete/{$this->_request_data['feed']->guid}/", $this->_l10n_midcom->get('delete'));
  351. break;
  352. case 'feeds_fetch_all':
  353. $this->add_breadcrumb("feeds/fetch/all/", $this->_l10n->get('refresh all feeds'));
  354. break;
  355. case 'feeds_fetch':
  356. $this->add_breadcrumb("feeds/fetch/{$this->_request_data['feed']->guid}/", $this->_l10n->get('refresh feed'));
  357. break;
  358. }
  359. }
  360. }
  361. ?>