PluginProbe
FeedWordPress / 2011.0721
FeedWordPress v2011.0721
trunk 0.8 0.9 0.91 0.95 0.96 0.97 0.98 0.981 0.99 0.991 0.992 0.993 2008.1030 2008.1101 2008.1105 2008.1214 2009.0612 2009.0613 2009.0618 2009.0707 2009.1111 2009.1112 2010.0127 2010.0528 All 65 releases
feedwordpress / feeds-page.php

feeds-page.php in FeedWordPress 2011.0721, at feeds-page.php

981 lines 37.6 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 require_once(dirname(__FILE__) . '/admin-ui.php');
3 require_once(dirname(__FILE__) . '/magpiemocklink.class.php');
4 require_once(dirname(__FILE__) . '/feedfinder.class.php');
5 require_once(dirname(__FILE__) . '/updatedpostscontrol.class.php');
6
7 class FeedWordPressFeedsPage extends FeedWordPressAdminPage {
8 var $HTTPStatusMessages = array (
9 200 => 'OK. FeedWordPress had no problems retrieving the content at this URL but the content does not seem to be a feed, and does not seem to include links to any feeds.',
10 201 => 'Created',
11 202 => 'Accepted',
12 203 => 'Non-Authoritative information',
13 204 => 'No Content',
14 205 => 'Reset Content',
15 206 => 'Partial Content',
16 300 => 'Multiple Choices',
17 301 => 'Moved Permanently',
18 302 => 'Found',
19 303 => 'See Other',
20 304 => 'Not Modified',
21 305 => 'Use Proxy',
22 307 => 'Temporary Redirect',
23 400 => 'Bad Request',
24 401 => 'Unauthorized. This URL probably needs a username and password for you to access it.',
25 402 => 'Payment Required',
26 403 => 'Forbidden. The URL is not made available for the machine that FeedWordPress is running on.',
27 404 => 'Not Found. There is nothing at this URL. Have you checked the address for typos?',
28 405 => 'Method Not Allowed',
29 406 => 'Not Acceptable',
30 407 => 'Proxy Authentication Required',
31 408 => 'Request Timeout',
32 409 => 'Conflict',
33 410 => 'Gone. This URL is no longer available on this server and no forwarding address is known.',
34 411 => 'Length Required',
35 412 => 'Precondition Failed',
36 413 => 'Request Entity Too Large',
37 414 => 'Request URI Too Long',
38 415 => 'Unsupported Media Type',
39 416 => 'Requested Range Not Satisfiable',
40 417 => 'Expectation Failed',
41 500 => 'Internal Server Error. Something unexpected went wrong with the configuration of the server that hosts this URL. You might try again later to see if this issue has been resolved.',
42 501 => 'Not Implemented',
43 502 => 'Bad Gateway',
44 503 => 'Service Unavailable. The server is currently unable to handle the request due to a temporary overloading or maintenance of the server that hosts this URL. This is probably a temporary condition and you should try again later to see if the issue has been resolved.',
45 504 => 'Gateway Timeout',
46 505 => 'HTTP Version Not Supported',
47 );
48 var $updatedPosts = NULL;
49
50 var $special_settings = array ( /* Regular expression syntax is OK here */
51 'cats',
52 'cat_split',
53 'fetch timeout',
54 'freeze updates',
55 'hardcode name',
56 'hardcode url',
57 'hardcode description',
58 'hardcode categories', /* Deprecated */
59 'comment status',
60 'terms',
61 'map authors',
62 'munge permalink',
63 'ping status',
64 'post status',
65 'postmeta',
66 'query parameters',
67 'resolve relative',
68 'syndicated post type',
69 'tags',
70 'unfamiliar author',
71 'unfamliar categories', /* Deprecated */
72 'unfamiliar category',
73 'unfamiliar post_tag',
74 'add/.*',
75 'update/.*',
76 'feed/.*',
77 'link/.*',
78 'match/.*',
79 );
80
81 /**
82 * Constructs the Feeds page object
83 *
84 * @param mixed $link An object of class {@link SyndicatedLink} if created for one feed's settings, NULL if created for global default settings
85 */
86 function FeedWordPressFeedsPage ($link = -1) {
87 if (is_numeric($link) and -1 == $link) :
88 $link = FeedWordPressAdminPage::submitted_link();
89 endif;
90
91 FeedWordPressAdminPage::FeedWordPressAdminPage('feedwordpressfeeds', $link);
92
93 $this->dispatch = 'feedwordpress_admin_page_feeds';
94 $this->pagenames = array(
95 'default' => 'Feeds',
96 'settings-update' => 'Syndicated feed',
97 'open-sheet' => 'Feed and Update',
98 );
99 $this->filename = __FILE__;
100 $this->updatedPosts = new UpdatedPostsControl($this);
101
102 $this->special_settings = apply_filters('syndicated_feed_special_settings', $this->special_settings, $this);
103 } /* FeedWordPressFeedsPage constructor */
104
105 function display () {
106 global $fwp_post;
107 global $post_source;
108
109 $this->boxes_by_methods = array(
110 'feed_information_box' => __('Feed Information'),
111 'global_feeds_box' => __('Update Scheduling'),
112 'updated_posts_box' => __('Updated Posts'),
113 'custom_settings_box' => __('Custom Feed Settings (for use in templates)'),
114 'fetch_settings_box' => __('Settings for Fetching Feeds (Advanced)'),
115 );
116 if ($this->for_default_settings()) :
117 unset($this->boxes_by_methods['custom_settings_box']);
118 endif;
119
120 // Allow overriding of normal source for FeedFinder, which may
121 // be called from multiple points.
122 if (isset($post_source) and !is_null($post_source)) :
123 $source = $post_source;
124 else :
125 $source = $this->dispatch;
126 endif;
127
128 if (isset($_REQUEST['feedfinder'])
129 or (isset($_REQUEST['action']) and $_REQUEST['action']=='feedfinder')
130 or (isset($_REQUEST['action']) and $_REQUEST['action']==FWP_SYNDICATE_NEW)) :
131 // If this is a POST, validate source and user credentials
132 FeedWordPressCompatibility::validate_http_request(/*action=*/ $source, /*capability=*/ 'manage_links');
133
134 return $this->display_feedfinder(); // re-route to Feed Finder page
135 endif;
136
137 parent::display();
138 return false; // Don't continue
139 } /* FeedWordPressFeedsPage::display() */
140
141 function ajax_interface_js () {
142 FeedWordPressAdminPage::ajax_interface_js();
143 ?>
144
145 jQuery(document).ready( function () {
146 contextual_appearance('automatic-updates-selector', 'cron-job-explanation', null, 'no');
147 contextual_appearance('time-limit', 'time-limit-box', null, 'yes');
148 contextual_appearance('use-default-update-window-no', 'update-scheduling-note', null, null, 'block', true);
149 jQuery('#use-default-update-window-yes, #use-default-update-window-no').click( function () {
150 contextual_appearance('use-default-update-window-no', 'update-scheduling-note', null, null, 'block', true);
151 } );
152
153 var els = ['name', 'description', 'url'];
154 for (var i = 0; i < els.length; i++) {
155 contextual_appearance(
156 /*item=*/ 'basics-hardcode-'+els[i],
157 /*appear=*/ 'basics-'+els[i]+'-view',
158 /*disappear=*/ 'basics-'+els[i]+'-edit',
159 /*value=*/ 'no',
160 /*visibleStyle=*/ 'block',
161 /*checkbox=*/ true
162 );
163 } /* for */
164 } );
165
166 <?php
167 }
168
169 /*static*/ function updated_posts_box ($page, $box = NULL) {
170 ?>
171 <table class="edit-form">
172 <?php $page->updatedPosts->display(); ?>
173 </table>
174 <?php
175 } /* FeedWordPressFeedsPage::updated_posts_box() */
176
177 /*static*/ function global_feeds_box ($page, $box = NULL) {
178 global $feedwordpress;
179 $automatic_updates = $feedwordpress->automatic_update_hook(array('setting only' => true));
180 $update_time_limit = (int) get_option('feedwordpress_update_time_limit');
181
182 // Hey, ho, let's go...
183 ?>
184
185 <table class="edit-form">
186 <?php if ($page->for_default_settings()) : ?>
187
188 <tr>
189 <th scope="row">Updates:</th>
190 <td><select id="automatic-updates-selector" name="automatic_updates" size="1" onchange="contextual_appearance('automatic-updates-selector', 'cron-job-explanation', null, 'no');">
191 <option value="shutdown"<?php echo ($automatic_updates=='shutdown')?' selected="selected"':''; ?>>automatically check for updates after pages load</option>
192 <option value="init"<?php echo ($automatic_updates=='init')?' selected="selected"':''; ?>>automatically check for updates before pages load</option>
193 <option value="no"<?php echo (!$automatic_updates)?' selected="selected"':''; ?>>cron job or manual updates</option>
194 </select>
195 <div id="cron-job-explanation" class="setting-description">
196 <p>If you want to use a cron job,
197 you can perform scheduled updates by sending regularly-scheduled
198 requests to <a href="<?php bloginfo('home'); ?>?update_feedwordpress=1"><code><?php bloginfo('url') ?>?update_feedwordpress=1</code></a>
199 For example, inserting the following line in your crontab:</p>
200 <pre style="font-size: 0.80em"><code>*/10 * * * * /usr/bin/curl --silent <?php bloginfo('url'); ?>?update_feedwordpress=1</code></pre>
201 <p class="setting-description">will check in every 10 minutes
202 and check for updates on any feeds that are ready to be polled for updates.</p>
203 </div>
204 </td>
205 </tr>
206
207 <?php else : /* Feed-specific settings */ ?>
208
209 <tr>
210 <th scope="row"><?php _e('Last update') ?>:</th>
211 <td><?php
212 if (isset($page->link->settings['update/last'])) :
213 echo fwp_time_elapsed($page->link->settings['update/last'])." ";
214 else :
215 echo " none yet";
216 endif;
217 ?></td></tr>
218
219 <tr><th><?php _e('Next update') ?>:</th>
220 <td><?php
221 $holdem = (isset($page->link->settings['update/hold']) ? $page->link->settings['update/hold'] : 'scheduled');
222 ?>
223 <select name="update_schedule">
224 <option value="scheduled"<?php echo ($holdem=='scheduled')?' selected="selected"':''; ?>>update on schedule <?php
225 echo " (";
226 if (isset($page->link->settings['update/ttl']) and is_numeric($page->link->settings['update/ttl'])) :
227 if (isset($page->link->settings['update/timed']) and $page->link->settings['update/timed']=='automatically') :
228 echo 'next: ';
229 $next = $page->link->settings['update/last'] + ((int) $page->link->settings['update/ttl'] * 60);
230 if (strftime('%x', time()) != strftime('%x', $next)) :
231 echo strftime('%x', $next)." ";
232 endif;
233 echo strftime('%X', $page->link->settings['update/last']+((int) $page->link->settings['update/ttl']*60));
234 else :
235 echo "every ".$page->link->settings['update/ttl']." minute".(($page->link->settings['update/ttl']!=1)?"s":"");
236 endif;
237 else:
238 echo "next scheduled update";
239 endif;
240 echo ")";
241 ?></option>
242 <option value="next"<?php echo ($holdem=='next')?' selected="selected"':''; ?>>update ASAP</option>
243 <option value="ping"<?php echo ($holdem=='ping')?' selected="selected"':''; ?>>update only when pinged</option>
244 </select></td></tr>
245
246 <?php endif; ?>
247
248 <tr>
249 <th scope="row"><?php print __('Update scheduling:') ?></th>
250 <td><p style="margin-top:0px">How long should FeedWordPress wait between updates before it considers this feed ready to be polled for updates again?</p>
251 <?php
252
253 $this->setting_radio_control(
254 'update/window', 'update_window',
255 array(&$this, 'update_window_edit_box'),
256 array(
257 'global-setting-default' => DEFAULT_UPDATE_PERIOD,
258 'default-input-name' => 'use_default_update_window',
259 'default-input-id' => 'use-default-update-window-yes',
260 'default-input-id-no' => 'use-default-update-window-no',
261 'labels' => array(&$this, 'update_window_currently'),
262 )
263 );
264 ?></td>
265 </tr>
266
267 <tr>
268 <th scope="row"><?php print __('Minimum Interval:'); ?></th>
269 <td><p style="margin-top:0px">Some feeds include standard elements that
270 request a specific update schedule. If the interval requested by the
271 feed provider is <em>longer</em> than FeedWordPress's normal scheduling,
272 FeedWordPress will always respect their request to slow down. But what
273 should it do if the update interval is <em>shorter</em> than the schedule set above?</p>
274 <?php
275 $this->setting_radio_control(
276 'update/minimum', 'update_minimum',
277 /*options=*/ array(
278 'no' => 'Speed up and accept the interval from the feed provider',
279 'yes' => 'Keep pace and use the longer scheduling from FeedWordPress',
280 ),
281 /*params=*/ array(
282 'setting-default' => NULL,
283 'global-setting-default' => 'no',
284 'default-input-value' => 'default',
285 )
286 );
287 ?>
288 </td>
289 </tr>
290
291 <?php if ($this->for_default_settings()) : ?>
292
293 <tr>
294 <th scope="row"><?php print __('Time limit on updates'); ?>:</th>
295 <td><select id="time-limit" name="update_time_limit" size="1" onchange="contextual_appearance('time-limit', 'time-limit-box', null, 'yes');">
296 <option value="no"<?php echo ($update_time_limit>0)?'':' selected="selected"'; ?>>no time limit on updates</option>
297 <option value="yes"<?php echo ($update_time_limit>0)?' selected="selected"':''; ?>>limit updates to no more than...</option>
298 </select>
299 <span id="time-limit-box"><label><input type="text" name="time_limit_seconds" value="<?php print $update_time_limit; ?>" size="5" /> seconds</label></span>
300 </tr>
301
302 <?php endif; ?>
303
304 </table>
305
306 <?php
307 } /* FeedWordPressFeedsPage::global_feeds_box() */
308
309 function update_window_edit_box ($updateWindow, $defaulted, $params) {
310 if (!is_numeric($updateWindow)) :
311 $updateWindow = DEFAULT_UPDATE_PERIOD;
312 endif;
313 ?>
314 <p>Wait <input type="text" name="update_window" value="<?php print $updateWindow; ?>" size="4" /> minutes between polling.</p>
315 <div class="setting-description" id="update-scheduling-note">
316 <p<?php if ($updateWindow<50) : ?> style="color: white; background-color: #703030; padding: 1.0em;"<?php endif; ?>><strong>Recommendation.</strong> Unless you are positive that you have the webmaster's permission, you generally should not set FeedWordPress to poll feeds more frequently than once every 60 minutes. Many webmasters consider more frequent automated polling to be abusive, and may complain to your web host, or ban your IP address, as retaliation for hammering their servers too hard.</p>
317 <p><strong>Note.</strong> This is a default setting that FeedWordPress uses to schedule updates when the feed does not provide any scheduling requests. If this feed does provide update scheduling information (through elements such as <code>&lt;rss:ttl&gt;</code> or <code>&lt;sy:updateFrequency&gt;</code>), FeedWordPress will respect the feed's request.</p>
318 </div>
319 <?php
320 } /* FeedWordPressFeedsPage::update_window_edit_box () */
321
322 function update_window_currently ($updateWindow, $defaulted, $params) {
323 $updateWindow = (int) $updateWindow;
324 if (1==$updateWindow) :
325 $caption = 'wait %d minute between polling';
326 else :
327 $caption = 'wait %d minutes between polling';
328 endif;
329 return sprintf(__($caption), $updateWindow);
330 } /* FeedWordPressFeedsPage::update_window_currently () */
331
332 function fetch_timeout_setting ($setting, $defaulted, $params) {
333 $timeout = intval($this->setting('fetch timeout', FEEDWORDPRESS_FETCH_TIMEOUT_DEFAULT));
334
335 if ($this->for_feed_settings()) :
336 $article = 'this';
337 else :
338 $article = 'a';
339 endif;
340 ?>
341 <p>Wait no more than
342 than <input name="fetch_timeout" type="number" min="0" size="3" value="<?php print $timeout; ?>" />
343 second(s) when trying to fetch <?php print $article; ?> feed to check for updates.</p>
344 <p>If <?php print $article; ?> source's web server does not respond before time runs
345 out, FeedWordPress will skip over the source and try again during
346 the next update cycle.</p>
347 <?php
348 }
349 function fetch_timeout_setting_value ($setting, $defaulted, $params) {
350 print number_format(intval($setting)) . " " . (($setting==1) ? "second" : "seconds");
351 }
352
353 function fetch_settings_box ($page, $box = NULL) {
354 $this->setting_radio_control(
355 'fetch timeout', 'fetch_timeout',
356 array(&$this, 'fetch_timeout_setting'),
357 array(
358 'global-setting-default' => FEEDWORDPRESS_FETCH_TIMEOUT_DEFAULT,
359 'input-name' => 'fetch_timeout',
360 'default-input-name' => 'fetch_timeout_default',
361 'labels' => array(&$this, 'fetch_timeout_setting_value'),
362 )
363 );
364 } /* FeedWordPressFeedsPage::fetch_settings_box () */
365
366 function feed_information_box ($page, $box = NULL) {
367 global $wpdb;
368 $link_rss_params = maybe_unserialize($page->setting('query parameters', ''));
369 if (!is_array($link_rss_params)) :
370 $link_rss_params = array();
371 endif;
372
373 if ($page->for_feed_settings()) :
374 $info['name'] = esc_html($page->link->link->link_name);
375 $info['description'] = esc_html($page->link->link->link_description);
376 $info['url'] = esc_html($page->link->link->link_url);
377 $rss_url = $page->link->link->link_rss;
378
379 $hardcode['name'] = $page->link->hardcode('name');
380 $hardcode['description'] = $page->link->hardcode('description');
381 $hardcode['url'] = $page->link->hardcode('url');
382 else :
383 $cat_id = FeedWordPress::link_category_id();
384
385 $params = array();
386 if (FeedWordPressCompatibility::test_version(FWP_SCHEMA_USES_ARGS_TAXONOMY)) :
387 $params['taxonomy'] = 'link_category';
388 else :
389 $params['type'] = 'link';
390 endif;
391 $params['hide_empty'] = false;
392 $results = get_categories($params);
393
394 // Guarantee that the Contributors category will be in the drop-down chooser, even if it is empty.
395 $found_link_category_id = false;
396 foreach ($results as $row) :
397 // Normalize case
398 if (!isset($row->cat_id)) : $row->cat_id = $row->cat_ID; endif;
399
400 if ($row->cat_id == $cat_id) : $found_link_category_id = true; endif;
401 endforeach;
402
403 if (!$found_link_category_id) :
404 $results[] = get_category($cat_id);
405 endif;
406
407 $info = array();
408 $rss_url = null;
409
410 $hardcode['name'] = get_option('feedwordpress_hardcode_name');
411 $hardcode['description'] = get_option('feedwordpress_hardcode_description');
412 $hardcode['url'] = get_option('feedwordpress_hardcode_url');
413 endif;
414
415 // Hey ho, let's go
416 ?>
417 <table class="edit-form">
418
419 <?php if ($page->for_feed_settings()) : ?>
420
421 <tr>
422 <th scope="row"><?php _e('Feed URL:') ?></th>
423 <td><a href="<?php echo esc_html($rss_url); ?>"><?php echo esc_html($rss_url); ?></a>
424 (<a href="<?php echo FEEDVALIDATOR_URI; ?>?url=<?php echo urlencode($rss_url); ?>"
425 title="Check feed &lt;<?php echo esc_html($rss_url); ?>&gt; for validity">validate</a>)
426 <input type="submit" name="feedfinder" value="switch &rarr;" style="font-size:smaller" />
427
428 <table id="link-rss-params">
429 <tbody>
430 <?php
431 $link_rss_params['new'] = array('', '');
432 $i = 0;
433 foreach ($link_rss_params as $index => $pair) :
434 ?>
435 <tr class="link-rss-params-row" id="link-rss-params-<?php print $index; ?>">
436 <td><label>Parameter: <input type="text" class="link_params_key"
437 name="link_rss_params_key[<?php print $index; ?>]" value="<?php print esc_html($pair[0]); ?>"
438 size="5" style="width: 5em" placeholder="name" /></label></td>
439 <td class="link-rss-params-value-cell"><label class="link_params_value_label">= <input type="text" class="link_params_value"
440 name="link_rss_params_value[<?php print $index; ?>]" value="<?php print esc_html($pair[1]); ?>"
441 size="8" placeholder="value" /></label></td>
442 </tr>
443 <?php
444 $i++;
445 endforeach;
446 ?>
447 </tbody>
448 </table>
449
450 <div><input type="hidden" id="link-rss-params-num" name="link_rss_params_num" value="<?php print $i; ?>" /></div>
451
452 <script type="text/javascript">
453 function linkParamsRowRemove (element) {
454 jQuery(element).closest('tr').fadeOut('slow', function () {
455 jQuery(this).remove();
456 } );
457 }
458
459 jQuery('<td><a href="#" class="add-remove link-rss-params-remove"><span class="x">(X)</span> Remove</a></td>').insertAfter('.link-rss-params-value-cell');
460
461 jQuery('#link-rss-params-new').hide();
462 jQuery('<a class="add-remove" id="link-rss-params-add" href="#">+ Add a query parameter</a>').insertAfter('#link-rss-params');
463 jQuery('#link-rss-params-add').click( function () {
464 var next = jQuery('#link-rss-params-num').val();
465 var newRow = jQuery('#link-rss-params-new').clone().attr('id', 'link-rss-params-'+next);
466 newRow.find('.link_params_key').attr('name', 'link_rss_params_key['+next+']');
467 newRow.find('.link_params_value').attr('name', 'link_rss_params_value['+next+']');
468
469 newRow.find('.link-rss-params-remove').click( function () {
470 linkParamsRowRemove(this);
471 return false;
472 } );
473
474 newRow.appendTo('#link-rss-params');
475 newRow.show();
476
477 // Update counter for next row.
478 next++;
479 jQuery('#link-rss-params-num').val(next);
480
481 return false;
482 } );
483 jQuery('.link-rss-params-remove').click( function () {
484 linkParamsRowRemove(this);
485 return false;
486 } );
487 </script>
488 </td>
489 </tr>
490
491 <?php
492 $rows = array(
493 "name" => __('Link Name'),
494 "description" => __('Short Description'),
495 "url" => __('Homepage'),
496 );
497 foreach ($rows as $what => $label) :
498 ?>
499 <tr>
500 <th scope="row"><?php print $label ?></th>
501 <td>
502 <div id="basics-<?php print $what; ?>-edit"><input type="text" name="link<?php print $what; ?>"
503 value="<?php echo $info[$what]; ?>" style="width: 95%" /></div>
504 <div id="basics-<?php print $what; ?>-view">
505 <?php if ($what=='url') : ?><a href="<?php print $info[$what]; ?>"><?php else : ?><strong><?php endif; ?>
506 <?php print (strlen(trim($info[$what])) > 0) ? $info[$what] : '(none provided)'; ?>
507 <?php if ($what=='url') : ?></a><?php else : ?></strong><?php endif; ?></div>
508
509 <div>
510 <label><input id="basics-hardcode-<?php print $what; ?>"
511 type="radio" name="hardcode_<?php print $what; ?>" value="no"
512 <?php echo (($hardcode[$what]=='yes')?'':' checked="checked"');?>
513 onchange="contextual_appearance('basics-hardcode-<?php print $what; ?>', 'basics-<?php print $what; ?>-view', 'basics-<?php print $what; ?>-edit', 'no', 'block', /*checkbox=*/ true)"
514 /> Update automatically from feed</label>
515 <label><input type="radio" name="hardcode_<?php print $what; ?>" value="yes"
516 <?php echo (($hardcode[$what]!='yes')?'':' checked="checked"');?>
517 onchange="contextual_appearance('basics-hardcode-<?php print $what; ?>', 'basics-<?php print $what; ?>-view', 'basics-<?php print $what; ?>-edit', 'no', 'block', /*checkbox=*/ true)"
518 /> Edit manually</label>
519 </div>
520 </td>
521 </tr>
522 <?php
523 endforeach;
524 ?>
525
526 <?php else : ?>
527
528 <tr>
529 <th scope="row">Syndicated Link category:</th>
530 <td><p><select name="syndication_category" size="1">
531 <?php
532 foreach ($results as $row) :
533 // Normalize case
534 if (!isset($row->cat_id)) : $row->cat_id = $row->cat_ID; endif;
535
536 echo "\n\t<option value=\"$row->cat_id\"";
537 if ($row->cat_id == $cat_id) :
538 echo " selected='selected'";
539 endif;
540 echo ">$row->cat_id: ".esc_html($row->cat_name);
541 echo "</option>\n";
542 endforeach;
543 ?></select></p>
544 <p class="setting-description">FeedWordPress will syndicate the
545 links placed under this link category.</p>
546 </td>
547 </tr>
548
549 <tr>
550 <th scope="row">Link Names:</th>
551 <td><label><input type="checkbox" name="hardcode_name" value="no"<?php echo (($hardcode['name']=='yes')?'':' checked="checked"');?>/> Update contributor titles automatically when the feed title changes</label></td>
552 </tr>
553
554 <tr>
555 <th scope="row">Short descriptions:</th>
556 <td><label><input type="checkbox" name="hardcode_description" value="no"<?php echo (($hardcode['description']=='yes')?'':' checked="checked"');?>/> Update contributor descriptions automatically when the feed tagline changes</label></td>
557 </tr>
558
559 <tr>
560 <th scope="row">Homepages:</th>
561 <td><label><input type="checkbox" name="hardcode_url" value="no"<?php echo (($hardcode['url']=='yes')?'':' checked="checked"');?>/> Update contributor homepages automatically when the feed link changes</label></td>
562 </tr>
563
564 <?php endif; ?>
565
566 </table>
567 <?php
568 } /* FeedWordPressFeedsPage::feed_information_box() */
569
570 function custom_settings_box ($page, $box = NULL) {
571 ?>
572 <p class="setting-description">These custom settings are special fields for the <strong>feed</strong> you are
573 syndicating, to be retrieved in templates using the <code>get_feed_meta()</code> function. They do not create
574 custom fields on syndicated <strong>posts</strong>. If you want to create custom fields that are applied to each
575 individual post from this feed, set up the settings in <a href="admin.php?page=<?php print $GLOBALS['fwp_path'] ?>/posts-page.php&amp;link_id=<?php print $page->link->id; ?>">Syndicated Posts</a>.</p>
576
577 <div id="postcustomstuff">
578 <table id="meta-list" cellpadding="3">
579 <tr>
580 <th>Key</th>
581 <th>Value</th>
582 <th>Action</th>
583 </tr>
584
585 <?php
586 $i = 0;
587 foreach ($page->link->settings as $key => $value) :
588 if (!preg_match("\007^((".implode(')|(', $page->special_settings)."))$\007i", $key)) :
589 ?>
590 <tr style="vertical-align:top">
591 <th width="30%" scope="row"><input type="hidden" name="notes[<?php echo $i; ?>][key0]" value="<?php echo esc_html($key); ?>" />
592 <input id="notes-<?php echo $i; ?>-key" name="notes[<?php echo $i; ?>][key1]" value="<?php echo esc_html($key); ?>" /></th>
593 <td width="60%"><textarea rows="2" cols="40" id="notes-<?php echo $i; ?>-value" name="notes[<?php echo $i; ?>][value]"><?php echo esc_html($value); ?></textarea></td>
594 <td width="10%"><select name="notes[<?php echo $i; ?>][action]">
595 <option value="update">save changes</option>
596 <option value="delete">delete this setting</option>
597 </select></td>
598 </tr>
599 <?php
600 $i++;
601 endif;
602 endforeach;
603 ?>
604 <tr>
605 <th scope="row"><input type="text" size="10" name="notes[<?php echo $i; ?>][key1]" value="" /></th>
606 <td><textarea name="notes[<?php echo $i; ?>][value]" rows="2" cols="40"></textarea></td>
607 <td><em>add new setting...</em><input type="hidden" name="notes[<?php echo $i; ?>][action]" value="update" /></td>
608 </tr>
609 </table>
610 </div> <!-- id="postcustomstuff" -->
611 <?php
612 }
613
614 function display_feedfinder () {
615 global $wpdb;
616
617 $lookup = (isset($_REQUEST['lookup']) ? $_REQUEST['lookup'] : NULL);
618
619 $feeds = array(); $feedSwitch = false; $current = null;
620 if ($this->for_feed_settings()) : // Existing feed?
621 $feedSwitch = true;
622 if (is_null($lookup)) :
623 // Switch Feed without a specific feed yet suggested
624 // Go to the human-readable homepage to look for
625 // auto-detection links
626 $lookup = $this->link->link->link_url;
627
628 // Guarantee that you at least have the option to
629 // stick with what works.
630 $current = $this->link->link->link_rss;
631 $feeds[] = $current;
632 endif;
633 $name = esc_html($this->link->link->link_name);
634 else: // Or a new subscription to add?
635 $name = "Subscribe to <code>".esc_html(feedwordpress_display_url($lookup))."</code>";
636 endif;
637 ?>
638 <div class="wrap" id="feed-finder">
639 <h2>Feed Finder: <?php echo $name; ?></h2>
640
641 <?php
642 if ($feedSwitch) :
643 $this->display_alt_feed_box($lookup);
644 endif;
645
646 $finder = array();
647 if (!is_null($current)) :
648 $finder[$current] = new FeedFinder($current);
649 endif;
650 $finder[$lookup] = new FeedFinder($lookup);
651
652 foreach ($finder as $url => $ff) :
653 $feeds = array_merge($feeds, $ff->find());
654 endforeach;
655
656 $feeds = array_values( // Renumber from 0..(N-1)
657 array_unique( // Eliminate duplicates
658 $feeds
659 )
660 );
661
662 if (count($feeds) > 0):
663 if ($feedSwitch) :
664 ?>
665 <h3>Feeds Found</h3>
666 <?php
667 endif;
668
669 if (count($feeds) > 1) :
670 $option_template = 'Option %d: ';
671 $form_class = ' class="multi"';
672 ?>
673 <p><strong>This web page provides at least <?php print count($feeds); ?> different feeds.</strong> These feeds may provide the same information
674 in different formats, or may track different items. (You can check the Feed Information and the
675 Sample Item for each feed to get an idea of what the feed provides.) Please select the feed that you'd like to subscribe to.</p>
676 <?php
677 else :
678 $option_template = '';
679 $form_class = '';
680 endif;
681
682 foreach ($feeds as $key => $f):
683 $pie = FeedWordPress::fetch($f);
684 $rss = (is_wp_error($pie) ? $pie : new MagpieFromSimplePie($pie));
685
686 if ($rss and !is_wp_error($rss)):
687 $feed_link = (isset($rss->channel['link'])?$rss->channel['link']:'');
688 $feed_title = (isset($rss->channel['title'])?$rss->channel['title']:$feed_link);
689 $feed_type = ($rss->feed_type ? $rss->feed_type : 'Unknown');
690 $feed_version_template = '%.1f';
691 $feed_version = $rss->feed_version;
692 else :
693 // Give us some sucky defaults
694 $feed_title = feedwordpress_display_url($lookup);
695 $feed_link = $lookup;
696 $feed_type = 'Unknown';
697 $feed_version_template = '';
698 $feed_version = '';
699 endif;
700 ?>
701 <form<?php print $form_class; ?> action="admin.php?page=<?php print $GLOBALS['fwp_path'] ?>/syndication.php" method="post">
702 <div class="inside"><?php FeedWordPressCompatibility::stamp_nonce('feedwordpress_switchfeed'); ?>
703
704 <?php
705 $classes = array('feed-found'); $currentFeed = '';
706 if (!is_null($current) and $current==$f) :
707 $classes[] = 'current';
708 $currentFeed = ' (currently subscribed)';
709 endif;
710 if ($key%2) :
711 $classes[] = 'alt';
712 endif;
713 ?>
714 <fieldset class="<?php print implode(" ", $classes); ?>">
715 <legend><?php printf($option_template, ($key+1)); print $feed_type." "; printf($feed_version_template, $feed_version); ?> feed<?php print $currentFeed; ?></legend>
716
717 <?php
718 $this->stamp_link_id();
719
720 // No feed specified = add new feed; we
721 // need to pass along a starting title
722 // and homepage URL for the new Link.
723 if (!$this->for_feed_settings()):
724 ?>
725 <input type="hidden" name="feed_title" value="<?php echo esc_html($feed_title); ?>" />
726 <input type="hidden" name="feed_link" value="<?php echo esc_html($feed_link); ?>" />
727 <?php
728 endif;
729 ?>
730
731 <input type="hidden" name="feed" value="<?php echo esc_html($f); ?>" />
732 <input type="hidden" name="action" value="switchfeed" />
733
734 <div>
735 <div class="feed-sample">
736 <?php
737 $link = NULL;
738 $post = NULL;
739 if (!is_wp_error($rss) and count($rss->items) > 0):
740 // Prepare to display Sample Item
741 $link = new MagpieMockLink(array('simplepie' => $pie, 'magpie' => $rss), $f);
742 $post = new SyndicatedPost(array('simplepie' => $rss->originals[0], 'magpie' => $rss->items[0]), $link);
743 ?>
744 <h3>Sample Item</h3>
745 <ul>
746 <li><strong>Title:</strong> <a href="<?php echo $post->post['meta']['syndication_permalink']; ?>"><?php echo $post->post['post_title']; ?></a></li>
747 <li><strong>Date:</strong> <?php print date('d-M-y g:i:s a', $post->published()); ?></li>
748 </ul>
749 <div class="entry">
750 <?php print $post->post['post_content']; ?>
751 </div>
752 <?php
753 do_action('feedwordpress_feed_finder_sample_item', $f, $post, $link);
754 else:
755 if (is_wp_error($rss)) :
756 print '<div class="feed-problem">';
757 print "<h3>Problem:</h3>\n";
758 print "<p>FeedWordPress encountered the following error
759 when trying to retrieve this feed:</p>";
760 print '<p style="margin: 1.0em 3.0em"><code>'.$rss->get_error_message().'</code></p>';
761 print "<p>If you think this is a temporary problem, you can still force FeedWordPress to add the subscription. FeedWordPress will not be able to find any syndicated posts until this problem is resolved.</p>";
762 print "</div>";
763 endif;
764 ?>
765 <h3>No Items</h3>
766 <p>FeedWordPress found no posts on this feed.</p>
767 <?php
768 endif;
769 ?>
770 </div>
771
772 <div>
773 <h3>Feed Information</h3>
774 <ul>
775 <li><strong>Homepage:</strong> <a href="<?php echo $feed_link; ?>"><?php echo is_null($feed_title)?'<em>Unknown</em>':$feed_title; ?></a></li>
776 <li><strong>Feed URL:</strong> <a title="<?php echo esc_html($f); ?>" href="<?php echo esc_html($f); ?>"><?php echo esc_html(feedwordpress_display_url($f, 40, 10)); ?></a> (<a title="Check feed &lt;<?php echo esc_html($f); ?>&gt; for validity" href="http://feedvalidator.org/check.cgi?url=<?php echo urlencode($f); ?>">validate</a>)</li>
777 <li><strong>Encoding:</strong> <?php echo isset($rss->encoding)?esc_html($rss->encoding):"<em>Unknown</em>"; ?></li>
778 <li><strong>Description:</strong> <?php echo isset($rss->channel['description'])?esc_html($rss->channel['description']):"<em>Unknown</em>"; ?></li>
779 </ul>
780 <?php do_action('feedwordpress_feedfinder_form', $f, $post, $link, $this->for_feed_settings()); ?>
781 <div class="submit"><input type="submit" class="button-primary" name="Use" value="&laquo; Use this feed" />
782 <input type="submit" class="button" name="Cancel" value="× Cancel" /></div>
783 </div>
784 </div>
785 </fieldset>
786 </div> <!-- class="inside" -->
787 </form>
788 <?php
789 unset($link);
790 unset($post);
791 endforeach;
792 else:
793 foreach ($finder as $url => $ff) :
794 $url = esc_html($url);
795 print "<h3>Searched for feeds at ${url}</h3>\n";
796 print "<p><strong>".__('Error').":</strong> ".__("FeedWordPress couldn't find any feeds at").' <code><a href="'.htmlspecialchars($lookup).'">'.htmlspecialchars($lookup).'</a></code>';
797 print ". ".__('Try another URL').".</p>";
798
799 // Diagnostics
800 print "<div class=\"updated\" style=\"margin-left: 3.0em; margin-right: 3.0em;\">\n";
801 print "<h3>".__('Diagnostic information')."</h3>\n";
802 if (!is_null($ff->error()) and strlen($ff->error()) > 0) :
803 print "<h4>".__('HTTP request failure')."</h4>\n";
804 print "<p>".$ff->error()."</p>\n";
805 else :
806 print "<h4>".__('HTTP request completed')."</h4>\n";
807 print "<p><strong>Status ".$ff->status().":</strong> ".$this->HTTPStatusMessages[(int) $ff->status()]."</p>\n";
808 endif;
809
810 // Do some more diagnostics if the API for it is available.
811 if (function_exists('_wp_http_get_object')) :
812 $httpObject = _wp_http_get_object();
813 $transports = $httpObject->_getTransport();
814
815 print "<h4>".__('HTTP Transports available').":</h4>\n";
816 print "<ol>\n";
817 print "<li>".implode("</li>\n<li>", array_map('get_class', $transports))."</li>\n";
818 print "</ol>\n";
819 print "</div>\n";
820 endif;
821 endforeach;
822 endif;
823
824 if (!$feedSwitch) :
825 $this->display_alt_feed_box($lookup, /*alt=*/ true);
826 endif;
827 ?>
828 </div> <!-- class="wrap" -->
829 <?php
830 return false; // Don't continue
831 } /* FeedWordPressFeedsPage::display_feedfinder() */
832
833 function display_alt_feed_box ($lookup, $alt = false) {
834 global $fwp_post;
835 ?>
836 <form action="admin.php?page=<?php print $GLOBALS['fwp_path'] ?>/<?php echo basename(__FILE__); ?>" method="post">
837 <div class="inside"><?php
838 FeedWordPressCompatibility::stamp_nonce($this->dispatch);
839 ?>
840 <fieldset class="alt"
841 <?php if (!$alt): ?>style="margin: 1.0em 3.0em; font-size: smaller;"<?php endif; ?>>
842 <legend><?php if ($alt) : ?>Alternative feeds<?php else: ?>Find feeds<?php endif; ?></legend>
843 <?php if ($alt) : ?><h3>Use a different feed</h3><?php endif; ?>
844 <div><label>Address:
845 <input type="text" name="lookup" id="use-another-feed"
846 placeholder="URL"
847 <?php if (is_null($lookup)) : ?>
848 value="URL"
849 <?php else : ?>
850 value="<?php print esc_html($lookup); ?>"
851 <?php endif; ?>
852 size="64" style="max-width: 80%" /></label>
853 <?php if (is_null($lookup)) : ?>
854 <?php FeedWordPressSettingsUI::magic_input_tip_js('use-another-feed'); ?>
855 <?php endif; ?>
856 <?php $this->stamp_link_id('link_id'); ?>
857 <input type="hidden" name="action" value="feedfinder" />
858 <input type="submit" class="button<?php if ($alt): ?>-primary<?php endif; ?>" value="Check &raquo;" /></div>
859 <p>This can be the address of a feed, or of a website. FeedWordPress
860 will try to automatically detect any feeds associated with a
861 website.</p>
862 </div> <!-- class="inside" -->
863 </fieldset></form>
864
865 <?php
866 } /* FeedWordPressFeedsPage::display_alt_feed_box() */
867
868 function save_settings ($post) {
869 if ($this->for_feed_settings()) :
870 if (isset($post['link_rss_params_key'])) :
871 $qp = array();
872 foreach ($post['link_rss_params_key'] as $index => $key) :
873 if (strlen($key) > 0) :
874 if (isset($post['link_rss_params_value'][$index])
875 and strlen($post['link_rss_params_value'][$index])) :
876 $value = $post['link_rss_params_value'][$index];
877 $qp[] = array($key, $value);
878 endif;
879 endif;
880 endforeach;
881 $this->update_setting('query parameters', serialize($qp));
882 endif;
883
884 // custom feed settings first
885 foreach ($post['notes'] as $mn) :
886 $mn['key0'] = (isset($mn['key0']) ? trim($mn['key0']) : NULL);
887 $mn['key1'] = trim($mn['key1']);
888 if (preg_match("\007^(("
889 .implode(')|(',$this->special_settings)
890 ."))$\007i",
891 $mn['key1'])) :
892 $mn['key1'] = 'user/'.$mn['key1'];
893 endif;
894
895 if (strlen($mn['key0']) > 0) :
896 unset($this->link->settings[$mn['key0']]); // out with the old
897 endif;
898
899 if (($mn['action']=='update') and (strlen($mn['key1']) > 0)) :
900 $this->link->settings[$mn['key1']] = $mn['value']; // in with the new
901 endif;
902 endforeach;
903
904 // now stuff through the web form
905 // hardcoded feed info
906
907 foreach (array('name', 'description', 'url') as $what) :
908 // We have a checkbox for "No," so if it's unchecked, mark as "Yes."
909 $this->link->settings["hardcode {$what}"] = (isset($post["hardcode_{$what}"]) ? $post["hardcode_{$what}"] : 'yes');
910 if (FeedWordPress::affirmative($this->link->settings, "hardcode {$what}")) :
911 $this->link->link->{'link_'.$what} = $post['link'.$what];
912 endif;
913 endforeach;
914
915 // Update scheduling
916 if (isset($post['update_schedule'])) :
917 $this->link->settings['update/hold'] = $post['update_schedule'];
918 endif;
919
920 if (isset($post['use_default_update_window']) and strtolower($post['use_default_update_window'])=='yes') :
921 unset($this->link->settings['update/window']);
922 elseif (isset($post['update_window'])):
923 if ((int) $post['update_window'] > 0) :
924 $this->link->settings['update/window'] = (int) $post['update_window'];
925 endif;
926 endif;
927
928 else :
929 // Global
930 update_option('feedwordpress_cat_id', $post['syndication_category']);
931
932 if (!isset($post['automatic_updates']) or !in_array($post['automatic_updates'], array('init', 'shutdown'))) :
933 $automatic_updates = NULL;
934 else :
935 $automatic_updates = $post['automatic_updates'];
936 endif;
937 update_option('feedwordpress_automatic_updates', $automatic_updates);
938
939 if (isset($post['update_window'])):
940 if ((int) $post['update_window'] > 0) :
941 update_option('feedwordpress_update_window', (int) $post['update_window']);
942 endif;
943 endif;
944
945 update_option('feedwordpress_update_time_limit', ($post['update_time_limit']=='yes')?(int) $post['time_limit_seconds']:0);
946
947 foreach (array('name', 'description', 'url') as $what) :
948 // We have a checkbox for "No," so if it's unchecked, mark as "Yes."
949 $hardcode = (isset($post["hardcode_{$what}"]) ? $post["hardcode_{$what}"] : 'yes');
950 update_option("feedwordpress_hardcode_{$what}", $hardcode);
951 endforeach;
952
953 endif;
954
955 if (isset($post['fetch_timeout'])) :
956 if (isset($post['fetch_timeout_default']) and $post['fetch_timeout_default']=='yes') :
957 $timeout = NULL;
958 else :
959 $timeout = $post['fetch_timeout'];
960 endif;
961
962 if (is_int($timeout)) :
963 $timeout = intval($timeout);
964 endif;
965 $this->update_setting('fetch timeout', $timeout);
966 endif;
967
968 if (isset($post['update_minimum'])) :
969 $this->update_setting('update/minimum', $post['update_minimum']);
970 endif;
971
972 $this->updatedPosts->accept_POST($post);
973 parent::save_settings($post);
974 } /* FeedWordPressFeedsPage::save_settings() */
975
976 } /* class FeedWordPressFeedsPage */
977
978 $feedsPage = new FeedWordPressFeedsPage;
979 $feedsPage->display();
980
981