| 1 |
<?php
|
| 2 |
//$Id$
|
| 3 |
|
| 4 |
/*
|
| 5 |
* This module was ripped from views_rss and modified
|
| 6 |
*/
|
| 7 |
|
| 8 |
function views_node_feed_menu($may_cache) {
|
| 9 |
$items = array();
|
| 10 |
if ($may_cache) {
|
| 11 |
$items[] = array(
|
| 12 |
'path' => 'admin/settings/views_node_feed',
|
| 13 |
'title' => t('Views Node Feed'),
|
| 14 |
'description' => t('Manage Different Types of Node Feeds'),
|
| 15 |
'access' => user_access('administer views'),
|
| 16 |
'callback' => 'views_node_feed_admin_settings',
|
| 17 |
'type' => MENU_NORMAL_ITEM,
|
| 18 |
);
|
| 19 |
}
|
| 20 |
else {
|
| 21 |
$items[] = array(
|
| 22 |
'path' => 'admin/settings/views_node_feed/edit/' . arg(4),
|
| 23 |
'title' => t('!op Node Feed', array('!op' => arg(4) === 'new' ? t('Add') : t('Edit'))),
|
| 24 |
'access' => user_access('administer views'),
|
| 25 |
'callback' => 'drupal_get_form',
|
| 26 |
'callback arguments' => array('views_node_feed_edit_form', arg(4)),
|
| 27 |
'type' => MENU_CALLBACK,
|
| 28 |
);
|
| 29 |
$items[] = array(
|
| 30 |
'path' => 'admin/settings/views_node_feed/delete/' . arg(4),
|
| 31 |
'title' => t('Delete Node Feed'),
|
| 32 |
'access' => user_access('administer views'),
|
| 33 |
'callback' => 'drupal_get_form',
|
| 34 |
'callback arguments' => array('views_node_feed_delete_form', arg(4)),
|
| 35 |
'type' => MENU_CALLBACK,
|
| 36 |
);
|
| 37 |
}
|
| 38 |
return $items;
|
| 39 |
}
|
| 40 |
|
| 41 |
|
| 42 |
function views_node_feed_admin_settings() {
|
| 43 |
$feeds = views_node_feed_get_feeds();
|
| 44 |
return theme('views_node_feed_admin', $feeds);
|
| 45 |
}
|
| 46 |
|
| 47 |
function views_node_feed_edit_form($ident) {
|
| 48 |
$new = $ident === 'new';
|
| 49 |
if (!$new) {
|
| 50 |
if (views_node_feed_valid_identifier($ident)) {
|
| 51 |
$feed = views_node_feed_get_feeds($ident);
|
| 52 |
}
|
| 53 |
if (!$feed) {
|
| 54 |
drupal_not_found();
|
| 55 |
exit;
|
| 56 |
}
|
| 57 |
}
|
| 58 |
$form = array();
|
| 59 |
$form['new'] = array(
|
| 60 |
'#type' => 'value',
|
| 61 |
'#value' => $new,
|
| 62 |
);
|
| 63 |
$form['identifier'] = array(
|
| 64 |
'#type' => 'textfield',
|
| 65 |
'#title' => t('Feed identifier'),
|
| 66 |
'#description' => t('Name with which you will identify this node feed. Only letters, numbers and underscores allowed.'),
|
| 67 |
'#maxlength' => 50,
|
| 68 |
'#required' => TRUE,
|
| 69 |
'#default_value' => $new ? '' : $ident,
|
| 70 |
);
|
| 71 |
$form['wrapper'] = array(
|
| 72 |
'#type' => 'textarea',
|
| 73 |
'#title' => t('Wrapper Template'),
|
| 74 |
'#description' => t('Template that will be placed around the list of nodes. Be sure to include the string ***VIEWS_NODE_FEED_ITEMS*** which will automatically be replaced with the necessary items. The variables $view, $nodes, and $type will be available.'),
|
| 75 |
'#default_value' => $new ? '***VIEWS_NODE_FEED_ITEMS***' : $feed['wrapper'],
|
| 76 |
'#required' => FALSE,
|
| 77 |
);
|
| 78 |
$form['node'] = array(
|
| 79 |
'#type' => 'textarea',
|
| 80 |
'#title' => t('Node template'),
|
| 81 |
'#description' => t('Template that will be generated for each node. The variables $view, $nodes, $node, and $type will be available.'),
|
| 82 |
'#default_value' => $new ? '<?php print $node->title; ?><br/>' : $feed['node'],
|
| 83 |
'#required' => FALSE,
|
| 84 |
);
|
| 85 |
$form['submit'] = array(
|
| 86 |
'#type' => 'submit',
|
| 87 |
'#value' => t('Save'),
|
| 88 |
);
|
| 89 |
return $form;
|
| 90 |
}
|
| 91 |
|
| 92 |
function views_node_feed_edit_form_validate($form_id, $form_values) {
|
| 93 |
if (!views_node_feed_valid_identifier($form_values['identifier'])) {
|
| 94 |
form_set_error('identifier', t('Invalid feed identifier'));
|
| 95 |
}
|
| 96 |
$feeds = views_node_feed_get_feeds();
|
| 97 |
if ($form_values['new'] && in_array($form_values['identifier'], $feeds)) {
|
| 98 |
form_set_error('identifier', t('Feed identifier already exists.'));
|
| 99 |
}
|
| 100 |
}
|
| 101 |
|
| 102 |
function views_node_feed_edit_form_submit($form_id, $form_values) {
|
| 103 |
$val = array(
|
| 104 |
'identifier' => $form_values['identifier'],
|
| 105 |
'wrapper' => $form_values['wrapper'],
|
| 106 |
'node' => $form_values['node']
|
| 107 |
);
|
| 108 |
$ident = $form_values['identifier'];
|
| 109 |
$feeds = views_node_feed_get_feeds();
|
| 110 |
$feeds[$ident] = $ident;
|
| 111 |
variable_set("views_node_feed_$ident", $val);
|
| 112 |
variable_set("views_node_feed_feeds", $feeds);
|
| 113 |
|
| 114 |
drupal_set_message('Node feed %feed updated', array('%feed' => $ident));
|
| 115 |
return 'admin/settings/views_node_feed';
|
| 116 |
}
|
| 117 |
|
| 118 |
function views_node_feed_delete_form($ident) {
|
| 119 |
$feeds = views_node_feed_get_feeds();
|
| 120 |
if (!in_array($ident, $feeds)) {
|
| 121 |
drupal_not_found();
|
| 122 |
exit;
|
| 123 |
}
|
| 124 |
$form['identifier'] = array('#type' => 'value', '#value' => $ident);
|
| 125 |
$form['#redirect'] = 'admin/settings/views_node_feed';
|
| 126 |
return confirm_form($form,
|
| 127 |
t('Delete the node feed %feed?', array('%feed' => $ident)),
|
| 128 |
'admin/settings/views_node_feed',
|
| 129 |
t('This will delete the node feed %feed.', array('%feed' => $ident)),
|
| 130 |
t('Delete'), t('Cancel'));
|
| 131 |
}
|
| 132 |
|
| 133 |
function views_node_feed_delete_form_submit($form_id, $form_values) {
|
| 134 |
$feeds = views_node_feed_get_feeds();
|
| 135 |
$ident = $form_values['identifier'];
|
| 136 |
unset($feeds[$ident]);
|
| 137 |
variable_del("views_node_feed_$ident");
|
| 138 |
variable_set("views_node_feed_feeds", $feeds);
|
| 139 |
drupal_set_message(t('Node feed %feed deleted.', t(array('%feed' => $ident))));
|
| 140 |
}
|
| 141 |
|
| 142 |
function views_node_feed_valid_identifier($ident) {
|
| 143 |
$ident = (string)$ident;
|
| 144 |
if (strlen($ident) <=0 || strlen($ident) > 50) {
|
| 145 |
return FALSE;
|
| 146 |
}
|
| 147 |
$new = preg_replace('/[^a-zA-Z0-9_]/', '', $ident);
|
| 148 |
if ($new !== $ident) {
|
| 149 |
return FALSE;
|
| 150 |
}
|
| 151 |
return TRUE;
|
| 152 |
}
|
| 153 |
|
| 154 |
function views_node_feed_get_feeds($ident = NULL) {
|
| 155 |
if ($ident === NULL) {
|
| 156 |
return variable_get("views_node_feed_feeds", array());
|
| 157 |
}
|
| 158 |
else {
|
| 159 |
return variable_get("views_node_feed_$ident", FALSE);
|
| 160 |
}
|
| 161 |
}
|
| 162 |
|
| 163 |
/**
|
| 164 |
* Provide views plugins for the feed types we support.
|
| 165 |
*/
|
| 166 |
function views_node_feed_views_style_plugins() {
|
| 167 |
return array(
|
| 168 |
'views_node_feed' => array(
|
| 169 |
'name' => t('Views Node Feed: Node feed'),
|
| 170 |
'theme' => 'views_node_feed',
|
| 171 |
'needs_table_header' => TRUE,
|
| 172 |
'needs_fields' => TRUE,
|
| 173 |
'even_empty' => TRUE,
|
| 174 |
),
|
| 175 |
);
|
| 176 |
}
|
| 177 |
|
| 178 |
/**
|
| 179 |
* While we support the global selector, some might want to allow
|
| 180 |
* ONLY RSS feeds so we support a stingy selector too
|
| 181 |
*/
|
| 182 |
function views_node_feed_views_arguments() {
|
| 183 |
$feeds = views_node_feed_get_feeds();
|
| 184 |
$arguments = array(
|
| 185 |
'node_feed' => array(
|
| 186 |
'name' => t('Node: Node Feed Selector'),
|
| 187 |
'handler' => 'views_handler_arg_node_feed_feed',
|
| 188 |
'option' => array(
|
| 189 |
'#type' => 'select',
|
| 190 |
'#options' => $feeds,
|
| 191 |
),
|
| 192 |
'help' => t('This argument specifies a specific Node feed selector; it will only select Node feeds, unlike the built-in selector which can select pluggable feeds. You may enter the title the feed will advertise in the title field here, and the description of the feed in the option field here.'),
|
| 193 |
),
|
| 194 |
);
|
| 195 |
return $arguments;
|
| 196 |
}
|
| 197 |
|
| 198 |
/**
|
| 199 |
* handler for our own RSS argument; mimics the feed selector
|
| 200 |
*/
|
| 201 |
function views_handler_arg_node_feed_feed($op, &$query, $argtype, $arg = '') {
|
| 202 |
switch($op) {
|
| 203 |
case 'summary':
|
| 204 |
case 'sort':
|
| 205 |
case 'link':
|
| 206 |
case 'title':
|
| 207 |
break;
|
| 208 |
case 'filter':
|
| 209 |
// This is a clone of the default selector, but it just invokes ours
|
| 210 |
// rather than calling all of them.
|
| 211 |
views_node_feed_views_feed_argument('argument', $GLOBALS['current_view'], $arg, $argtype);
|
| 212 |
}
|
| 213 |
}
|
| 214 |
|
| 215 |
/**
|
| 216 |
* post view for our own op -- mimics the feed selector
|
| 217 |
*/
|
| 218 |
function views_node_feed_views_post_view($view, $items, $output) {
|
| 219 |
foreach ($view->argument as $id => $argument) {
|
| 220 |
if ($argument['type'] == 'node_feed') {
|
| 221 |
$feed = $id;
|
| 222 |
break;
|
| 223 |
}
|
| 224 |
}
|
| 225 |
|
| 226 |
if ($feed !== NULL) {
|
| 227 |
return views_node_feed_views_feed_argument('post_view', $view, 'node_feed');
|
| 228 |
}
|
| 229 |
}
|
| 230 |
|
| 231 |
/**
|
| 232 |
* feed argument hook that will convert us to RSS or display an icon.
|
| 233 |
* the 4th argument isn't part of the hook, but we use it to differentiate
|
| 234 |
* when called as a hook or when called manually from views_rss_views_post_view
|
| 235 |
*/
|
| 236 |
function views_node_feed_views_feed_argument($op, &$view, $arg, $argdata = NULL) {
|
| 237 |
if ($op == 'argument' && $arg == 'node_feed') {
|
| 238 |
$view->page_type = 'views_node_feed';
|
| 239 |
|
| 240 |
if ($argdata['options']) {
|
| 241 |
$view->node_feed_type = $argdata['options'];
|
| 242 |
}
|
| 243 |
|
| 244 |
// reset the 'real url' to the URL without the feed argument.
|
| 245 |
$view_args = array();
|
| 246 |
$max = count($view->args);
|
| 247 |
foreach ($view->args as $id => $view_arg) {
|
| 248 |
++$count;
|
| 249 |
if ($view_arg == $arg && $view->argument[$id]['id'] == $argdata['id']) {
|
| 250 |
if ($count != $max) {
|
| 251 |
$view_args[] = $argdata['wildcard'];
|
| 252 |
}
|
| 253 |
}
|
| 254 |
else {
|
| 255 |
$view_args[] = $view_arg;
|
| 256 |
}
|
| 257 |
}
|
| 258 |
$view->feed_url = views_get_url($view, $view_args);
|
| 259 |
}
|
| 260 |
else if ($op == 'post_view' && $view->build_type != 'block') {
|
| 261 |
$args = views_post_view_make_args($view, $arg, 'node_feed');
|
| 262 |
$url = views_get_url($view, $args);
|
| 263 |
$title = views_get_title($view, 'page', $args);
|
| 264 |
|
| 265 |
if ($view->used_filters) {
|
| 266 |
$filters = drupal_query_string_encode($view->used_filters);
|
| 267 |
}
|
| 268 |
|
| 269 |
}
|
| 270 |
}
|
| 271 |
|
| 272 |
/**
|
| 273 |
* plugin that actually displays an RSS feed
|
| 274 |
*/
|
| 275 |
function theme_views_node_feed($view, $nodes, $type) {
|
| 276 |
if ($type == 'block') {
|
| 277 |
return;
|
| 278 |
}
|
| 279 |
global $base_url;
|
| 280 |
|
| 281 |
$feed = views_node_feed_get_feeds($view->node_feed_type);
|
| 282 |
$node_output = '';
|
| 283 |
//append list of nodes using template and ob
|
| 284 |
foreach ($nodes as $node) {
|
| 285 |
// Load the specified node:
|
| 286 |
$node = node_load($node->nid);
|
| 287 |
ob_start();
|
| 288 |
eval('?>' . $feed['node']);
|
| 289 |
$node_output .= ob_get_contents();
|
| 290 |
ob_end_clean();
|
| 291 |
}
|
| 292 |
ob_start();
|
| 293 |
eval('?>' . $feed['wrapper']);
|
| 294 |
$wrapper_output = ob_get_contents();
|
| 295 |
ob_end_clean();
|
| 296 |
|
| 297 |
//combine wrapper and nodes
|
| 298 |
$output = str_replace('***VIEWS_NODE_FEED_ITEMS***', $node_output, $wrapper_output);
|
| 299 |
|
| 300 |
//drupal_set_header('Content-Type: text/xml; charset=utf-8');
|
| 301 |
print $output;
|
| 302 |
module_invoke_all('exit');
|
| 303 |
exit;
|
| 304 |
}
|
| 305 |
|
| 306 |
function theme_views_node_feed_admin($feeds) {
|
| 307 |
$output = '';
|
| 308 |
$output .= '<p>' . l(t('Add new node feed'), 'admin/settings/views_node_feed/edit/new') . '</p>';
|
| 309 |
|
| 310 |
$output .= '<p>';
|
| 311 |
if (count($feeds) == 0) {
|
| 312 |
$output .= t("No existing node feeds");
|
| 313 |
}
|
| 314 |
else {
|
| 315 |
$header = array(t('Identifier'), t('Actions'));
|
| 316 |
$rows = array();
|
| 317 |
foreach ($feeds as $ident) {
|
| 318 |
$rows[] = array($ident, l(t('Edit'), 'admin/settings/views_node_feed/edit/'.$ident) . ' / ' . l(t('Delete'), 'admin/settings/views_node_feed/delete/'.$ident));
|
| 319 |
}
|
| 320 |
$output .= theme('table', $header, $rows);
|
| 321 |
}
|
| 322 |
$output .= '</p>';
|
| 323 |
|
| 324 |
return $output;
|
| 325 |
}
|