Project

General

Profile

Paste
Download (7.7 KB) Statistics
| Branch: | Revision:

root / drupal7 / sites / all / modules / views_data_export / views_data_export.module @ f0456308

1
<?php
2

    
3
/**
4
 * @file
5
 * Provides the ability to export to specific
6
 */
7

    
8
define('VIEWS_DATA_EXPORT_HEADER', 'header');
9
define('VIEWS_DATA_EXPORT_BODY', 'body');
10
define('VIEWS_DATA_EXPORT_FOOTER', 'footer');
11
define('VIEWS_DATA_EXPORT_FINISHED', 'finished');
12

    
13
define('VIEWS_DATA_EXPORT_INDEX_TABLE_PREFIX', 'views_data_export_index_');
14

    
15
/**
16
 * Implements hook_init().
17
 */
18
function views_data_export_init() {
19
  // We have to include our theme preprocessors here until:
20
  // http://drupal.org/node/1096770 is fixed.
21
  module_load_include('inc', 'views_data_export', 'theme/views_data_export.theme');
22
}
23

    
24
/**
25
 * Implementation of hook_views_api().
26
 */
27
function views_data_export_views_api() {
28
  return array(
29
    'api' => 2,
30
  );
31
}
32

    
33
/**
34
 * Implementation of hook_theme().
35
 */
36
function views_data_export_theme() {
37
  // Make sure that views picks up the preprocess functions.
38
  module_load_include('inc', 'views_data_export', 'theme/views_data_export.theme');
39
  $hooks = array();
40
  $hooks['views_data_export_feed_icon'] = array(
41
    'pattern' => 'views_data_export_feed_icon__',
42
    'variables' => array(
43
      'image_path' => NULL,
44
      'url' => NULL,
45
      'query' => '',
46
      'text' => '',
47
    ),
48
    'file' => 'theme/views_data_export.theme.inc',
49
  );
50

    
51
  $hooks['views_data_export_complete_page'] = array (
52
    'variables' => array(
53
      'file' => '',
54
      'errors' => array(),
55
      'return_url'=> '',
56
    ),
57
    'file' => 'theme/views_data_export.theme.inc',
58
  );
59

    
60
  $hooks['views_data_export_message'] = array (
61
    'variables' => array(
62
      'message' => '',
63
      'type' => 'info',
64
    ),
65
    'file' => 'theme/views_data_export.theme.inc',
66
  );
67

    
68
  return $hooks;
69
}
70

    
71

    
72
/**
73
 * Implementation of hook_cron().
74
 */
75
function views_data_export_cron() {
76
  views_data_export_garbage_collect();
77
}
78

    
79
/**
80
 * Removes any temporary index tables that have been left
81
 * behind. This is caused by batch processes which are
82
 * started but never finished.
83
 *
84
 * Removes all trace of exports from the database that
85
 * were created more than $expires seconds ago
86
 *
87
 * @param $expires
88
 *   Seconds ago. Defaults to that given in the settings.
89
 * @param $chunk
90
 *   The number of tables to test for and delete.
91
 *   Defaults to that given in the settings. Pass -1
92
 *   for this setting to remove any restriction and to
93
 *   garbage collect all exports.
94
 */
95
function views_data_export_garbage_collect($expires = NULL, $chunk = NULL) {
96
  if (lock_acquire('views_data_export_gc')) {
97
    if (!isset($expires)) {
98
      $expires = variable_get('views_data_export_gc_expires', 604800); // one week
99
    }
100
    if (!isset($chunk)) {
101
      $chunk = variable_get('views_data_export_gc_chunk', 30);
102
    }
103

    
104
    if ($chunk == -1) {
105
      $result = db_query("SELECT eid FROM {views_data_export} WHERE time_stamp <= :timestamp ORDER BY time_stamp ASC", array(':timestamp' => REQUEST_TIME - $expires));
106
    }
107
    else {
108
      $result = db_query_range("SELECT eid FROM {views_data_export} WHERE time_stamp <= :timestamp ORDER BY time_stamp ASC", 0, $chunk, array(':timestamp' => REQUEST_TIME - $expires));
109
    }
110

    
111
    $eids_to_clear = array();
112
    foreach ($result as $row) {
113
      $eids_to_clear[] = $row->eid;
114
    }
115

    
116
    // We do two things to exports we want to garbage collect
117
    // 1. Delete the index table for it, if it is still around
118
    // 2. Delete the row from the exports table
119
    // 3. Delete the view from the object_cache
120
    if (count($eids_to_clear)) {
121
      foreach ($eids_to_clear as $eid) {
122
        // 1. Delete index table, if it is still around for some reason
123
        $table = VIEWS_DATA_EXPORT_INDEX_TABLE_PREFIX . $eid;
124
        if (db_table_exists($table)) {
125
          db_drop_table($table);
126
        }
127
      }
128

    
129
      // 2. Delete the entries in the exports table.
130
      db_delete('views_data_export')
131
        ->condition('eid', $eids_to_clear, 'IN')
132
        ->execute();
133

    
134
      // 3. Clear the cached views
135
      views_data_export_view_clear($eids_to_clear);
136
    }
137

    
138
    lock_release('views_data_export_gc');
139
  }
140
}
141

    
142

    
143
/**
144
 * Batch API callback.
145
 * Handles all batching operations by executing the appropriate view.
146
 */
147
function _views_data_export_batch_process($export_id, $display_id, $exposed_input, &$context) {
148
  // Don't show the admin menu on batch page, some people don't like it.
149
  if (module_exists('admin_menu')) {
150
    module_invoke('admin_menu', 'suppress');
151
  }
152

    
153
  // Fetch the view in question from our cache
154
  $view = views_data_export_view_retrieve($export_id);
155
  $view->set_display($display_id);
156
  if (!empty($exposed_input)) {
157
    $view->set_exposed_input($exposed_input);
158
  }
159
  // Inform the data_export display which export it corresponds to and execute
160
  if (!isset($view->display_handler->batched_execution_state)) {
161
    $view->display_handler->batched_execution_state = new stdClass();
162
  }
163
  $view->display_handler->batched_execution_state->eid = $export_id;
164
  $view->display_handler->views_data_export_cached_view_loaded = TRUE;
165
  $view->execute_display($display_id);
166

    
167
  // Update batch api progress information
168
  $sandbox = $view->display_handler->batched_execution_state->sandbox;
169
  $context['finished'] = $sandbox['finished'];
170
  $context['message'] = $sandbox['message'];
171

    
172
  views_data_export_view_store($export_id, $view);
173
}
174

    
175

    
176

    
177
/**********/
178
/** CRUD **/
179
/**********/
180

    
181
/**
182
 * Save a new export into the database.
183
 */
184
function views_data_export_new($view_name, $view_display_id, $file) {
185
  // Insert new row into exports table
186
  $record = (object) array(
187
    'view_name' => $view_name,
188
    'view_display_id' => $view_display_id,
189
    'time_stamp' => REQUEST_TIME,
190
    'fid' => $file,
191
    'batch_state' => VIEWS_DATA_EXPORT_HEADER,
192
    'sandbox' => array(),
193
  );
194
  drupal_write_record('views_data_export', $record);
195
  return $record;
196
}
197

    
198

    
199
/**
200
 * Update an export row in the database
201
 */
202
function views_data_export_update($state) {
203
  // Note, drupal_write_record handles serializing
204
  // the sandbox field as per our schema definition
205
  drupal_write_record('views_data_export', $state, 'eid');
206
}
207

    
208

    
209

    
210
/**
211
 * Get the information about a previous export.
212
 */
213
function views_data_export_get($export_id) {
214
  $object = db_query("SELECT * FROM {views_data_export} WHERE eid = :eid", array(':eid' => (int)$export_id))->fetch();
215
  if ($object) {
216
    $object->sandbox = unserialize($object->sandbox);
217
  }
218
  return $object;
219
}
220

    
221
/**
222
 * Remove the information about an export.
223
 */
224
function views_data_export_clear($export_id) {
225
  db_delete('views_data_export')
226
    ->condition('eid', $export_id)
227
    ->execute();
228
  views_data_export_view_clear($export_id);
229
}
230

    
231

    
232
/**
233
 * Store a view in the object cache.
234
 */
235
function views_data_export_view_store($export_id, $view) {
236
  // Store a clean copy of the view.
237
  $_view = $view->clone_view();
238

    
239
  views_data_export_view_clear($export_id);
240
  $record = array(
241
    'eid' => $export_id,
242
    'data' => $_view,
243
    'updated' => REQUEST_TIME,
244
  );
245
  drupal_write_record('views_data_export_object_cache', $record);
246
}
247

    
248
/**
249
 * Retrieve a view from the object cache.
250
 */
251
function views_data_export_view_retrieve($export_id) {
252
  views_include('view');
253
  $data = db_query("SELECT * FROM {views_data_export_object_cache} WHERE eid = :eid", array(':eid' => $export_id))->fetch();
254
  if ($data) {
255
    $view = unserialize($data->data);
256
  }
257
  return $view;
258
}
259

    
260
/**
261
 * Clear a view from the object cache.
262
 *
263
 * @param $export_id
264
 *   An export ID or an array of export IDs to clear from the object cache.
265
 */
266
function views_data_export_view_clear($export_id) {
267
  db_delete('views_data_export_object_cache')
268
    ->condition('eid', $export_id)
269
    ->execute();
270
}
271

    
272
/**
273
 * Implements hook_file_presave().
274
 */
275
function views_data_export_file_presave($file) {
276
  // Ensure temporary files really are temporary.
277
  // @see: https://drupal.org/node/2198399
278
  if (strpos($file->filename, 'views_data_export') === 0) {
279
    // There is no FILE_STATUS_TEMPORARY.
280
    $file->status = 0;
281
  }
282
}