Projet

Général

Profil

Paste
Télécharger (14,6 ko) Statistiques
| Branche: | Révision:

root / drupal7 / sites / all / modules / sweaver / drush / sweaver.drush.inc @ 76df55b7

1 85ad3d82 Assos Assos
<?php
2
3
/**
4
 * @file
5
 * Sweaver Drush functions.
6
 *
7
 * While this is crazy and probably not something that will be
8
 * used a lot, it's jolly good fun to program this :).
9
 */
10
11
/**
12
 * Implementation of hook_drush_help().
13
 */
14
function sweaver_drush_help($section) {
15
  switch ($section) {
16
    case 'drush:sweaver-edit':
17
      return dt('Edit a style known by Sweaver. With no arguments, the command will list all available styles, after that just add the id as an argument.');
18
    case 'drush:sweaver-variables':
19
      return dt('Set some variables for Sweaver. With no arguments, the command will list the default values. Supply "type" and "value" as arguments. You can currently set the editor and the warning message to your likings (defaults to vi and true).');
20
  }
21
}
22
23
24
/**
25
 * Implementation of hook_drush_command().
26
 */
27
function sweaver_drush_command() {
28
  $items = array();
29
30
  $items['sweaver-edit'] = array(
31
    'callback' => 'sweaver_drush_style',
32
    'description' => dt('Edit the style with your favorite Editor.'),
33
    'arguments' => array(
34
      'style_id' => dt('A style ID'),
35
    ),
36
    'aliases' => array('swe'),
37
  );
38
39
  $items['sweaver-variables'] = array(
40
    'callback' => 'sweaver_drush_variables',
41
    'description' => dt('Set variables for running Sweaver with drush.'),
42
    'arguments' => array(
43
      'type' => dt('The type of variable to store. Currenlty only "editor" or "warning".'),
44
      'value' => dt('The value of the variable. Currently your favorite editor command (+ any arguments if needed) or "true" or "false" for the warning message.'),
45
    ),
46
    'aliases' => array('swv'),
47
  );
48
49
  return $items;
50
}
51
52
/**
53
 * Edit a style via drush.
54
 *
55
 * @param $args
56
 *   Arguments passed by the CLI.
57
 *
58
 * @return $mixed
59
 *   Either a list of styles or start up the editor functionality.
60
 */
61
function sweaver_drush_style() {
62
  $args = func_get_args();
63
  $styles = sweaver_drush_list_styles();
64
  $action = sweaver_drush_verify($args);
65
66
  switch ($action) {
67
    case 'list':
68
      return sweaver_drush_print_styles($styles);
69
      break;
70
    case 'edit':
71
      if (isset($styles[$args[0]])) {
72
        sweaver_drush_verify_edit($styles[$args[0]]);
73
        return sweaver_drush_edit_style($styles[$args[0]]);
74
      }
75
      drush_print(dt('Style id does not exists.'));
76
  }
77
}
78
79
/**
80
 * Edit a style.
81
 *
82
 * @param $style
83
 *   A style object from the Database.
84
 */
85
function sweaver_drush_edit_style($style) {
86
87
  $warning = variable_get('sweaver_drush_warning_edit', 'true');
88
  $editor = variable_get('sweaver_drush_editor', 'vi');
89
90
  // Display the warning text if needed.
91
  if ($warning == 'true') {
92
    $return = drush_confirm(sweaver_drush_warning_text());
93
    if (!$return) {
94
      // Bail out.
95
      drush_set_context("DRUSH_EXECUTION_COMPLETED", TRUE);
96
      drush_print(dt('Editing of style aborted.'));
97
      exit();
98
    }
99
  }
100
101
  // Prepare the css variable from the editor.
102
  $css = json_decode($style->css);
103
  $css = (!empty($css)) ? sweaver_drush_json_to_css($css) : '';
104
105
  // Create a static $data variable with CTools.
106
  $data = &drupal_static('sweaver_drush_style_data' , array());
107
  $data = array(
108
    'style' => $style,
109
    'editor' => $editor,
110
    'ts_enabled' => FALSE,
111
  );
112
113
  // Get some plugins.
114
  $sweaver = Sweaver::get_instance();
115
  $sweaver_cs = $sweaver->get_plugin('sweaver_plugin_customcss');
116
  $sweaver_ts = $sweaver->get_plugin('sweaver_plugin_themesettings');
117
118
  // Create steps array.
119
  $steps = array(
120
    'css' => $css
121
  );
122
  // Add custom css if enabled.
123
  if ($sweaver_cs) {
124
    $steps['customcss'] = $style->customcss;
125
  }
126
  // Add themesettings if enabled.
127
  if ($sweaver_ts) {
128
    $data['ts_enabled'] = TRUE;
129
    $steps['themesettings'] = sweaver_drush_array_to_string($style->themesettings);
130
  }
131
  $data['steps'] = $steps;
132
133
  // Step through.
134
  foreach ($steps as $step => $step_value) {
135
136
    // Ask confirmation first.
137
    $edit = drush_confirm(dt('Do you want to edit the @step ?', array('@step' => $step)));
138
139
    if ($edit) {
140
      $temp_file = drush_save_data_to_temp_file($step_value);
141
      $data['tempfiles'][$step] = $temp_file;
142
      $data['current_step'] = $step;
143
      $edit_command = $editor .' '. $temp_file;
144
      $pipes = array();
145
146
      // Opend the editor.
147
      proc_close(proc_open($edit_command, array(0 => STDIN, 1 => STDOUT, 2 => STDERR), $pipes));
148
149
      // We need to save the new content already here, because we lose the temporary data file.
150
      $step = $data['current_step'];
151
      $temp_file = $data['tempfiles'][$step];
152
      if ($content = file_exists($temp_file)) {
153
        switch ($step) {
154
          case 'css':
155
            $css = file_get_contents($temp_file);
156
            $style->write_css = $css;
157
            $style->css = sweaver_drush_css_to_json($css);
158
            break;
159
          case 'customcss':
160
            $data['style']->customcss = file_get_contents($temp_file);
161
            break;
162
          case 'themesettings':
163
            $data['style']->themesettings = serialize(sweaver_drush_array_lines_to_array_key_values(file($temp_file)));
164
            break;
165
        }
166
      }
167
    }
168
  }
169
170
  // Get the variables again.
171
  $style = $data['style'];
172
  $steps = $data['steps'];
173
174
  // Do we want to save ?
175
  $message = 'Do you want to save all changes ?';
176
  if (isset($style->active) && $style->active) {
177
    $message = 'Do you want to save all changes ? All changes will be visible for your visitors.';
178
  }
179
  $save = drush_confirm(dt($message));
180
181
  // No save.
182
  if (!$save) {
183
    drush_print(dt('Saving aborted, but was\'t this jolly good fun ? :)'));
184
  }
185
186
  // Let's save!
187
  else {
188
    // Get sweaver plugin styles.
189
    $sweaver_styles = $sweaver->get_plugin('sweaver_plugin_styles');
190
191
    // Save into database.
192
    $update = array('style_id');
193
194
    // Create stylesheet.
195
    $stylesheet = $style->write_css;
196
    $stylesheet .= "\n". $style->customcss;
197
198
    // Save draft version.
199
    if (!isset($style->active)) {
200
      drupal_write_record('sweaver_style_draft', $style, $update);
201
      $sweaver_styles->sweaver_export_file($stylesheet, $style);
202
      drush_print(dt('Draft version has been saved.'));
203
    }
204
205
    // Save live version.
206
    if (isset($style->active)) {
207
      drupal_write_record('sweaver_style', $style, $update);
208
      drush_print(dt('Live version has been saved.'));
209
    }
210
211
    // Export css files and set themesettings.
212
    if (isset($style->active)) {
213
      $sweaver_styles->sweaver_export_file($stylesheet, $style, 'live');
214
      if ($data['ts_enabled']) {
215
        $theme_settings_var = str_replace('/', '_', 'theme_'. $style->theme .'_settings');
216
        variable_set($theme_settings_var, unserialize($style->themesettings));
217
      }
218
    }
219
220
    // Flush cache.
221
    sweaver_clear_cache();
222
  }
223
}
224
225
/**
226
 * Print a list of styles.
227
 *
228
 * @param $styles
229
 *   A collection of draft styles.
230
 */
231
function sweaver_drush_print_styles($styles) {
232
  if (empty($styles)) {
233
    drush_print('No styles found in the system');
234
  }
235
  else {
236
    foreach ($styles as $key => $style) {
237
      unset($styles[$key]->css);
238
      unset($styles[$key]->customcss);
239
      unset($styles[$key]->themesettings);
240
      $style->style_id = $key;
241
      if (isset($style->active)) {
242
        $style->style = $style->style .' '. dt('(live)');
243
        unset($style->active);
244
      }
245
    }
246
    $rows = array(0 => array(dt('ID'), dt('Theme'), dt('Name')));
247
    $rows += $styles;
248
    drush_print_table($rows, TRUE);
249
  }
250
}
251
252
/**
253
 * Get the styles available in the system.
254
 */
255
function sweaver_drush_list_styles() {
256
  $styles = array();
257
258
  if (module_exists('sweaver')) {
259
260
    $i = 1;
261
262
    // Draft versions.
263
    $results = db_query("SELECT * FROM {sweaver_style_draft}")->fetchAll();
264
    foreach ($results as $row) {
265
      $styles[$i] = $row;
266
      $i++;
267
    }
268
269
    // Live versions.
270
    $results = db_query("SELECT * FROM {sweaver_style} where active = 1")->fetchAll();
271
    foreach ($results as $row) {
272
      $styles[$i] = $row;
273
      $i++;
274
    }
275
  }
276
  else {
277
    drush_set_context("DRUSH_EXECUTION_COMPLETED", TRUE);
278
    drush_print('Sweaver is not installed.');
279
    exit();
280
  }
281
282
  return $styles;
283
}
284
285
/**
286
 * Set Sweaver variables via Drush.
287
 *
288
 * @param $args
289
 *   Arguments passed by the CLI.
290
 *
291
 * @return $mixed
292
 *   Either a list of styles or start up the editor functionality.
293
 */
294
function sweaver_drush_variables() {
295
  $args = func_get_args();
296
  $action = sweaver_drush_verify($args, 'variables');
297
298
  switch ($action) {
299
    case 'list':
300
      drush_print(dt('Your favorite editor is currently @editor.', array('@editor' => variable_get('sweaver_drush_editor', 'vi'))));
301
      drush_print(dt('Warning message currently set to @warning.', array('@warning' => variable_get('sweaver_drush_warning_edit', 'true'))));
302
      break;
303
304
    case 'save':
305
      if ($args[0] == 'tmp') {
306
        variable_set('sweaver_drush_editor', $args[1]);
307
        drush_print(dt('Temporary directory set to @tmp.', array('@tmp' => $args[1])));
308
      }
309
      elseif ($args[0] == 'warning') {
310
        variable_set('sweaver_drush_warning_edit', $args[1]);
311
        drush_print(dt('Style warning set to @warning.', array('@warning' => $args[1])));
312
      }
313
      else {
314
        drush_print(dt('The first argument can only be "editor" or "warning"'));
315
      }
316
      break;
317
  }
318
}
319
320
/**
321
 * Verify arguments.
322
 *
323
 * @param $args
324
 *   A collection of arguments passed by cli.
325
 * @param $type
326
 *   Whether we need to verify styles or variables.
327
 * @return $string
328
 *   Which action to undertake.
329
 */
330
function sweaver_drush_verify($args, $type = 'styles') {
331
  if (empty($args)) {
332
    return 'list';
333
  }
334
335
  if ($type == 'styles' && isset($args[0]) && is_numeric($args[0])) {
336
    return 'edit';
337
  }
338
339
  if ($type == 'variables' && isset($args[0]) && is_string($args[0]) && isset($args[1]) && is_string($args[1])) {
340
    return 'save';
341
  }
342
  else {
343
    drush_print(dt('Wrong variables supplied.'));
344
  }
345
}
346
347
/**
348
 * Verify if drush can write into the sweaver files directory.
349
 */
350
function sweaver_drush_verify_edit($style) {
351
  $write = TRUE;
352
  $public_path = variable_get('file_public_path', conf_path() . '/files');
353
  $draft_file = $public_path . '/sweaver/sweaver_' . $style->theme .'_' . $style->style_id . '_draft.css';
354
  $live_file = $public_path . '/sweaver/sweaver_' . $style->theme .'_' . $style->style_id . '_live.css';
355
  $touch_file = (isset($style->active)) ? $live_file : $draft_file;
356
  $write = @touch($touch_file);
357
358
  if (!$write) {
359
    drush_set_context("DRUSH_EXECUTION_COMPLETED", TRUE);
360
    drush_print(dt('The drush user is not able to overwrite the files in the sweaver directory. Either change the permissions (best option) of those files or run Drush with sudo permissions (might conflict later on when editing the style again from the interface.)'));
361
    exit();
362
  }
363
}
364
365
/**
366
 * Convert the properties which are collected by the editor.
367
 * They are saved in the database as a JSON object but all
368
 * properties do not have their pre- and/or suffix on them.
369
 *
370
 * @param $css
371
 *   A collection of properties and values configured by the editor.
372
 * $return $new_css
373
 */
374
function sweaver_drush_json_to_css($css) {
375
  ctools_include('css');
376
377
  $new_css = clone($css);
378
  $sweaver_properties = sweaver_object_load(NULL, 'property');
379
380
  foreach ($css as $selector => $properties) {
381
    foreach ($properties as $property => $value) {
382
      if (isset($sweaver_properties[$property])) {
383
384
        // Get the property.
385
        $sp = $sweaver_properties[$property];
386
387
        // Add prefixes and suffixes, but skip special cases.
388
        if (($property == 'background-color' && $value == 'transparent') || ($property == 'background-image' && $value == 'none')) {
389
          continue;
390
        }
391
        $new_value = $sp->property_prefix . $value . $sp->property_suffix;
392
        $new_css->$selector->$property = $new_value;
393
      }
394
    }
395
  }
396
397
  return ctools_css_assemble($new_css);
398
}
399
400
/**
401
 * Convert the stylesheet back to JSON format.
402
 *
403
 * @param $css
404
 *   A stylesheet.
405
 * $return $json_css
406
 */
407
function sweaver_drush_css_to_json($css) {
408
  ctools_include('css');
409
410
  $json_css = new stdClass;
411
  $ctools_css = ctools_css_disassemble($css);
412
  $sweaver_properties = sweaver_object_load(NULL, 'property');
413
414
  foreach ($ctools_css as $selector => $properties) {
415
    foreach ($properties as $property => $value) {
416
      if (isset($sweaver_properties[$property])) {
417
418
        // Get the property.
419
        $sp = $sweaver_properties[$property];
420
        // Use str replaces to remove prefixes, suffixes and ;
421
        $new_value = str_replace(array($sp->property_prefix, $sp->property_suffix, ';'), '', $value);
422
        $json_css->$selector->$property = $new_value;
423
      }
424
    }
425
  }
426
427
  return json_encode($json_css);
428
}
429
430
/**
431
 * Convert an array to string.
432
 *
433
 * @param $array
434
 *   A collection of key value pairs.
435
 * @return $string
436
 */
437
function sweaver_drush_array_to_string($array) {
438
  $string = '';
439
440
  if (is_string($array)) {
441
    $array = unserialize($array);
442
  }
443
444
  if (is_array($array) && !empty($array)) {
445
    foreach ($array as $key => $value) {
446
      $string .= "$key : $value\n";
447
    }
448
  }
449
450
  return $string;
451
}
452
453
/**
454
 * Convert a string to array.
455
 *
456
 * @param $array
457
 *   A collection of key value pairs where the value should be exploded.
458
 * @return $array
459
 */
460
function sweaver_drush_array_lines_to_array_key_values($array) {
461
  $new_array = array();
462
463
  foreach ($array as $key => $line) {
464
    $key_value = explode(":", $line);
465
    $new_array_key = trim(array_shift($key_value));
466
    $new_array_value = trim(implode('', $key_value));
467
    $new_array[$new_array_key] = $new_array_value;
468
  }
469
470
  return $new_array;
471
}
472
473
/**
474
 * Warning text.
475
 *
476
 * @return $warning
477
 *   The warning text before editing a style.
478
 */
479
function sweaver_drush_warning_text() {
480
  $warning = '
481
/////////////////////////////
482
/// IMPORTANT, PLEASE READ //
483
/////////////////////////////
484
485
You are about to edit a style. This happens in a few steps. You
486
will get a confirmation question for each step available.
487
You can remove this warning by typing "drush swv warning false".
488
489
Step 1
490
------
491
Edit the general css which has been created by the style editor.
492
Due to the nature that the editor works, not all css properties are
493
valid, most regareding properties which can take multiple arguments like
494
margin, padding and border. For instance o do not use padding: 0 3 4 1, but
495
padding-x: 0; instead. You can always use the custom css of course where
496
you are free to enter what you like.
497
498
Step 2
499
------
500
Edit the custom css. You can edit this like a normal stylesheet.
501
502
Step 3
503
------
504
Edit the themesettings when the themesettings plugin is enabled.
505
Some values are booleans in the database. So: 0 = false, set to 1 to become true.
506
It will be presented like this. Do not remove the colons.
507
$key : $value
508
509
Step 4
510
------
511
Save the changes you have just performed. Editing a live style will immediately
512
affect the site for your visitors and will also overwrite the draft version of the style.
513
514
Type "y" to continue, "n" to abort.
515
';
516
517
  return dt($warning);
518
}