forena.admin.inc 26.1 KB
Newer Older
1
<?php
metzlerd's avatar
metzlerd committed
2
// $Id$
metzlerd's avatar
metzlerd committed
3
4
/**
 * @file
metzlerd's avatar
metzlerd committed
5
 * Report administration forms and functions.
metzlerd's avatar
metzlerd committed
6
 */
metzlerd's avatar
metzlerd committed
7
require_once('forena.common.inc');
8

9
10
11
12
13
/**
 * Display reports to edit for admins in the structure menu
 * Enter description here ...
 */
function forena_admin_reports() {
14
  GLOBAL $language;
15
  $data = array();
16
  $output = '';
17
  $content = drupal_get_form('forena_sync_form');
18
  $sync_form = drupal_render($content);
19
  $links[] = array('href' => 'reports/add', 'title' => 'Create New Report' );
20
  $output .= theme('links',
21
22
23
24
    array(
      'links' => $links,
      'attributes' => array('class' => 'action-links'),
    )
metzlerd's avatar
metzlerd committed
25
  );
26
  // Add Data tables if it exists.
27
28
  $headers = array(t('category'), t('title'), t('name'), t('operation'));
  $result = Frx::File()->allReports();
29
  foreach ($result as $row) {
30
    $rpt = str_replace('/', '.', $row->name);
31
32
33
34
35
36
    if ($row->include) {
      $edit = l(t('Override'), 'reports/' . $rpt . '/edit');
    }
    else {
      $edit = l(t('Edit'), 'reports/' . $rpt . '/edit');
    }
metzlerd's avatar
metzlerd committed
37
    $clone = l(t('Clone'), 'reports/add/' . $rpt);
38
39
40
41
42
43
44
45
46
47
48
    // Determine the nature of the report delete link.
    if ($row->override) {
      $delete = l(t('Revert'), 'reports/' . $rpt . '/delete', array('query' => array('destination' => 'admin/structure/forena')));
    }
    else if (!$row->include) {
      $delete = l(t('Delete'), 'reports/' . $rpt . '/delete', array('query' => array('destination' => 'admin/structure/forena')));
    }
    else {
      $delete = '';
    }

49
50
    $title = l(t($row->cache['title']), 'reports/' . $rpt);
    $data[] = array($row->cache['category'], $title, $row->name, $edit . ' ' . $clone . ' ' . $delete);
51
  }
52
  $output .= '<div id="forena-reports-list">';
53
  $output .= theme('forena_data_table', array('header' => $headers, 'rows' => $data));
54
  $output .= '</div>';
55
  $output .= $sync_form;
56
57
58
  return $output;
}

59

60

metzlerd's avatar
metzlerd committed
61

62
63


64
function forena_filter_element($fmt, $name) {
metzlerd's avatar
metzlerd committed
65
66
67
68
  global $user;
  $element['format'] =  array(
    '#type' => 'fieldset',
    '#collapsible' => TRUE,
69
    '#collapsed' => $fmt!='',
metzlerd's avatar
metzlerd committed
70
71
    '#title' => t('Input formats'),
  );
72
  if (!$fmt) $fmt='full_html';
metzlerd's avatar
metzlerd committed
73
  // Get a list of formats that the current user has access to.
metzlerd's avatar
metzlerd committed
74
75
76
77
78
  $formats = filter_formats($user);
  foreach ($formats as $format) {
    $options[$format->format] = $format->name;
    $element['format']['guidelines'][$format->format] = array(
      '#theme' => 'filter_guidelines',
79
      '#required' => TRUE,
metzlerd's avatar
metzlerd committed
80
81
82
83
84
      '#format' => $format,
    );
  }
  $element['format']['guidelines']['#weight']=12;

85
  $element['format'][$name] = array(
metzlerd's avatar
metzlerd committed
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
    '#type' => 'select',
    '#title' => t('Text format'),
    '#options' => $options,
    '#default_value' => $fmt,
    '#access' => count($formats) > 1,
    '#weight' => 10,
    '#attributes' => array('class' => array('filter-list')),
  );

  $element['format']['help'] = array(
    '#type' => 'container',
    '#theme' => 'filter_tips_more_info',
    '#attributes' => array('class' => array('filter-help')),
    '#weight' => 11,
  );
metzlerd's avatar
metzlerd committed
101
  return $element['format'];
metzlerd's avatar
metzlerd committed
102
}
103

metzlerd's avatar
metzlerd committed
104
105


106
/**
107
108
109
 * Report syncronization form
 * @param $formid
 * @param $form_state
110
 */
111
function forena_sync_form($formid, &$form_state) {
112
113
114
115

  $form['sync_overwrite'] = array(
    '#type' => 'checkbox',
    '#title' => t('Revert all delivered reports to orignial'),
116
    '#required' => TRUE,
117
118
119
    '#description' => t('All customizations to module delivered reports will be lost.')
  );

120
121
  $form['sync'] = array(
    '#type' => 'submit',
122
    '#value' => t('Revert'),
123
124
    '#submit' => array('forena_settings_sync_submit'),
  );
125
126

  return $form;
127
128
129
130
131
132
133
134

}

/**
 * Forena admin settings form
 *
 */
function forena_settings() {
135
  $skins = Frx::File()->skins();
136
137
138

  $report_path = forena_report_path();

139

140
141
142
  $form['forena_report_repos'] = array(
    '#type' => 'textfield',
    '#title' => t('Report Repository'),
metzlerd's avatar
metzlerd committed
143
144
145
146
147
148
    '#description' => t('Indicate the directory that you want to use for your reports.  In order for you to ' .
                        'to be able to save reports, this directory should be writable by the web user. Relative' .
                        'paths should be entered relative to the base path of your drupal installation.'),
    '#default_value' => $report_path,
  );

149
150
  $form['forena_last_report_path'] = array(
    '#type' => 'value',
151
    '#value' => variable_get('forena_report_repos', '')
metzlerd's avatar
metzlerd committed
152
153
  );

154
155
156
157
158
159
160
161
162
163
164
165
166
  if (module_exists('forena_query')) {
      $form['forena_query_data_path'] = array(
        '#type' => 'textfield',
        '#title' => t('Custom Data Block Repository'),
        '#description' => t('Indicate the directory that you want to use to save custom created data blocks using
            the forena query builder tool.  These will override any module delivered data blocks.  This needs to
            be a directory that is writable by the web user but should not be browsable by the web.  It defaults to
            '),
        '#default_value' => Frx::DataFile()->dir,
      );

      $form['forena_last_query_data_path'] = array(
          '#type' => 'value',
167
          '#value' =>  variable_get('forena_query_data_path', '')
168
169
170
      );

  }
171

172
  $form['forena_input_format'] = forena_filter_element(variable_get('forena_input_format', filter_default_format()), 'forena_input_format');
173
  $form['forena_default_form'] = array(
174
    '#type' => 'select',
175
    '#title' => t('Default report skin'),
176
    '#options' => $skins,
177
    '#description' => t('Specify the default skin to be used.   New skins can be created by creating .skinfo files in your reports directory.'
metzlerd's avatar
metzlerd committed
178
    . ' Skins are basically css and javascript libraries added to your report.'),
metzlerd's avatar
metzlerd committed
179
    '#default_value' => variable_get('forena_default_form', ''),
metzlerd's avatar
metzlerd committed
180
    );
metzlerd's avatar
metzlerd committed
181

metzlerd's avatar
metzlerd committed
182
183
    $form =  system_settings_form($form);
    return $form;
metzlerd's avatar
metzlerd committed
184

185
}
186
187

function forena_settings_validate($form, &$form_state) {
metzlerd's avatar
metzlerd committed
188
  $values = $form_state['values'];
189
  $path = $values['forena_report_repos'];
190
  if ($path != $values['forena_last_report_path']) {
191
192
193
    if (!file_exists($path)) {
      try {
        if (file_exists($path)) {
194
          drupal_set_message(t('Created directory %s', array('%s' => $path))) ;
195
196
        }
        mkdir($path);
197

198
      } catch (Exception $e) {
199
        Frx::error(t('Unable to create report directory'), $e->getMessage());
200
201
      }
    }
metzlerd's avatar
metzlerd committed
202
  }
203
204
205
206
207
208
209
210
211
212
213
  if (!file_exists($path) || !is_writable($path)) {
    form_set_error('forena_report_repos', 'Report Directory must be writable by the web user');
  }
  if ($values['forena_query_data_path']) {
    $path = $values['forena_query_data_path'];
    if ($path != $values['forena_last_query_data_path']) {
      if (!file_exists($path)) {
        try {

          mkdir($path);
          if (file_exists($path)) {
214
            drupal_set_message(t('Created directory %s', array('%s' => $path))) ;
215
216
217
          }

        } catch (Exception $e) {
218
          Frx::error(t('Unable to create data directory'), $e->getMessage());
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
        }
      }
    }
    if (!file_exists($path) || !is_writable($path)) {
      form_set_error('forena_query_data_path', 'Data Directory must be writable by the web user');
    }
  }


}


/**
 * Added submit handler to create directories and clear menu cache
 *
 * @param unknown_type $form
 * @param unknown_type $form_state
 */
function forena_settings_submit($form, &$form_state) {
238
}
metzlerd's avatar
metzlerd committed
239

240
function forena_settings_sync_submit($form, &$form_state) {
241
  forena_sync_reports($form_state['values']['sync_overwrite']);
242
}
243

metzlerd's avatar
metzlerd committed
244
245
246
247
248
/**
 * Form function for the edit report form
 * @param $form_state
 * @return the form
 */
249
250


251
252
253
254
255
/**
 * Handle delete buttons from edit forms.
 * @return unknown_type
 */
function forena_edit_delete_submit($form, &$form_state) {
metzlerd's avatar
metzlerd committed
256
  $link = 'reports/' . $form_state['values']['name_in'] ;
257
258
259
260
261
262
263
264
265
  $destination = '';
  if (isset($_REQUEST['destination'])) {
    $destination = drupal_get_destination();
    unset($_REQUEST['destination']);
  }
  $form_state['redirect'] = array('path' => $link . '/delete', 'query' => array('destination' => $destination));
}


266
function forena_create_trans_form($formid, $form_state, $report_name) {
267
268
269
  $name = '';
  $filename = '';
  $format = '';
metzlerd's avatar
metzlerd committed
270
  $desc = Frx::Menu()->parseURL($report_name);
metzlerd's avatar
metzlerd committed
271
272


273
274
  $form = array();
  global $language;
275
  $languages = language_list();
276
277
  //determine if this is an add new report request

metzlerd's avatar
metzlerd committed
278
279
  $r = Frx::Editor($report_name, FALSE);
  $base_name = $r->desc['base_name'];
280
  $title = (string)$r->title;
metzlerd's avatar
metzlerd committed
281
  $lang = @$_GET['target_language'];
282
  if ($lang) {
metzlerd's avatar
metzlerd committed
283
    $language = $languages[$lang];
284
285
286
287
288
289
290
291
292
  }
  $form['base_name'] = array(
    '#type' => 'value',
    '#value' => $base_name
  );
  $form['report_name'] = array(
    '#type' => 'value',
    '#value' => $name,
  );
293

metzlerd's avatar
metzlerd committed
294
  foreach ($languages as $key => $obj) {
295
    $languages[$key] = $obj->native;
296
  }
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
  $form['report_lang'] = array(
    '#type' => 'value',
    '#value' => $lang,
  );
  $def_lang = $lang ? $lang : 'en';
  $form['save_report_language'] = array(
    '#type' => 'select',
    '#title' => t('Language'),
    '#options' => $languages,
    '#default_value' => $def_lang,
  );


  $form['title'] = array(
    '#type' => 'textfield',
    '#title' => t('Title'),
    '#default_value' => $title,
metzlerd's avatar
metzlerd committed
314
    '#required' => TRUE,
315
316
317
318
319
320
321
322
323
  );


  $form['save'] = array(
    '#type' => 'submit',
    '#value' => 'Create',
  );
  return $form;

324
325
326
}

function forena_create_trans_form_submit($form, &$form_state) {
metzlerd's avatar
metzlerd committed
327
328
  global $language;
  $language = language_default();
329
  $values = $form_state['values'];
330
  $base_name = $values['base_name'];
metzlerd's avatar
metzlerd committed
331
  $new_name = $values['save_report_language'] . '/' . $base_name;
metzlerd's avatar
metzlerd committed
332
333
  $r = Frx::Editor($base_name, TRUE);
  $link = $r->report_link;
334

metzlerd's avatar
metzlerd committed
335
  // Determine new fielname
metzlerd's avatar
metzlerd committed
336
  $desc = Frx::Menu()->parseURL($new_name);
337
338
  $filename = $desc['filename'];
  $report_name = $desc['name'];
339

metzlerd's avatar
metzlerd committed
340
  //determine redirection.
341

342
  if (Frx::File()->exists($filename, FALSE)) {
metzlerd's avatar
metzlerd committed
343
    drupal_set_message(t('Report %s already exists', array('%s' => $new_name)), 'error');
344
    return;
metzlerd's avatar
metzlerd committed
345
  }
David Metzler's avatar
David Metzler committed
346
  else {
metzlerd's avatar
metzlerd committed
347
348
349
    // Title and category
    $r->setTitle($values['title']);
    $r->update();
David Metzler's avatar
David Metzler committed
350
351
    $r->rename($new_name);
    drupal_set_message(t('Translation,  %s has been created. Switch languages to translate.', array('%s' => $values['title'])));
metzlerd's avatar
metzlerd committed
352
353
354
    //$r->cancel();
    $r->save();
    $form_state['redirect']= $link . '/edit';
David Metzler's avatar
David Metzler committed
355
  }
metzlerd's avatar
metzlerd committed
356

357
  //if this is a new report then redirect to data blocks
358
}
359

360
361


362
363
364
365
/*
 * administer the settings for document format options
 */
function forena_doc_formats_settings() {
366
  // Invoke doc_type hook to see which document types are there.
367
  $supported_doctypes = Frx::documentTypes();
368

369
370
  $form['forena_doc_formats'] = array(
    '#type' => 'checkboxes',
371
    '#title' => t('Allowed Document Formats'),
372
373
374
375
    '#default_value' => variable_get('forena_doc_formats', $supported_doctypes),
    '#description' => t('check your desired document format'),
    '#options' => $supported_doctypes,
  );
376
377
378
379

  $form['forena_doc_defaults'] = array(
    '#type' => 'checkboxes',
    '#title' => t('Default Document Formats'),
380
    '#default_value' => variable_get('forena_doc_defaults', array()),
381
382
383
384
    '#description' => t('check your desired document format'),
    '#options' => $supported_doctypes,
  );

385
386
387
  $form['forena_email_override'] = array(
    '#type' => 'checkbox',
    '#title' => 'Run email merges in test mode' ,
metzlerd's avatar
metzlerd committed
388
    '#default_value' => variable_get('forena_email_override', FALSE),
389
390
    '#description' => t('When this box is checked emails are sent to the currently logged in user.  Useful for testing environments.'),
  );
391
  $form['forena_email_input_format'] = forena_filter_element(variable_get('forena_email_input_format', 'full_text'), 'forena_email_input_format');
392
  $form['forena_email_input_format']['#title'] = t('Email Input Format');
393

394
395
  return system_settings_form($form);
}
396

397
398
399
400
/*
 * administer the settings for document format options
 */
function forena_data_settings() {
401
  $repos = Frx::RepoMan()->repositories;
402
  $r_list = array();
metzlerd's avatar
metzlerd committed
403
404
  $headers = array(t('Name'), t('Description'), t('Path'), t('Operation'));
  foreach ($repos as $name => $r) {
405
    $r_list[] = array(
metzlerd's avatar
metzlerd committed
406
407
408
409
    $name,
    $r['title'],
    $r['path'],
    l(t('configure'), 'admin/config/content/forena/data/configure/' . $name)
410
411
412
413
    );

  }

metzlerd's avatar
metzlerd committed
414
415
  $output = '<ul class="action-links"><li>' . l(t('Add data source'), 'admin/config/content/forena/data/add') . '</li></ul>';
  $output .= theme_table(array('header' => $headers, 'rows' => $r_list, 'attributes' => array(), 'caption' => '', 'sticky' => TRUE, 'colgroups' => array(), 'empty' => ''));
416
417
418
419
  return $output;
}

function forena_data_settings_edit($form, &$form_state, $source=-1) {
420
  global $databases;
421
422
423
424
425
426
427
428
429
  $adding = ($source === -1);
  if (!@$form_state['storage']) {
    if ($adding) {
      $form_state['storage'] = array(
        'name' => '',
        'title' => '',
        'path' => '',
        'config' => array(
          'source' => 'user',
davidmetzler's avatar
davidmetzler committed
430
          'data provider' => 'FrxDrupal',
431
          'database' => 'default',
432
433
          'access callback' => 'user_access',
          'user callback' => 'forena_current_user_id'
metzlerd's avatar
metzlerd committed
434
435
          ),
          );
436
437
    }
    else {
438
439
      Frx::RepoMan()->repository($source);
      $repos = Frx::RepoMan()->repositories;
440
      $r = $repos[$source];
davidmetzler's avatar
davidmetzler committed
441
      // Remove teh object from the data.
442
      unset($r['data']);
443
444
445
      $form_state['storage'] = array(
        'name' => $source,
        'title' => $r['title'],
davidmetzler's avatar
davidmetzler committed
446
        'path' => @$r['path'],
447
        'config' => $r,
448
449
450
451
452
453
      );

    }
  }
  $data = $form_state['storage'];
  $config = $data['config'];
davidmetzler's avatar
davidmetzler committed
454

davidmetzler's avatar
davidmetzler committed
455
  $locked = !($adding || (@$config['source'] == 'user'));
456
457
458
459
460
461
462
463
464
  $values = @$form_state['values'];

  $form['name'] = array(
    '#type' => 'textfield',
    '#title' => t('Name'),
    '#description' => t('Machine readable name.  Used in referencing all data used by this source. must should not contain any special characters or spaces.'),
    '#disabled' => !$adding,
    '#default_value' => $data['name'],
    '#required' => TRUE,
metzlerd's avatar
metzlerd committed
465
  );
466
467
468
469

  $form['title'] = array(
    '#type' => 'textfield',
    '#title' => t('Title'),
davidmetzler's avatar
davidmetzler committed
470
    '#required' => TRUE,
471
472
473
474
475
476
477
478
479
480
481
    '#description' => t('Human readable name that describes the data source.  This primarily occurs in error messages where the data source cannot be accessed.'),
    '#default_value' => $data['title'],
  );

  $form['enabled'] = array(
    '#type' => 'checkbox',
    '#title' => t('Enabled'),
    '#description' => t('Disabling will cause all queries to return no data.'),
    '#default_value' => @$data['enabled']!==0,
  );

davidmetzler's avatar
davidmetzler committed
482
483
484
485
486
487
488
  $form['debug'] = array(
    '#type' => 'checkbox',
    '#title' => t('Debug'),
    '#description' => t('Write information to the screen and logs for each query executed.'),
    '#default_value' => @$config['debug'],
  );

489
490
491
  $form['path'] = array(
    '#type' => 'textfield',
    '#title' => t('Path'),
davidmetzler's avatar
davidmetzler committed
492
    '#required' => TRUE,
493
    '#disabled' => $locked,
494
495
496
497
    '#description' => t('Directory containing data block files.'),
    '#default_value' => @$data['path'],
  );

davidmetzler's avatar
davidmetzler committed
498
499
500
501
502
503
504
505
506
  $user_options = array(
    '' => 'None',
    'forena_current_user_id' => 'UID',
    'forena_current_user_name' => 'User name',
  );

  $form['user_callback'] = array(
    '#type' => 'select',
    '#title' =>  'Current user',
507
    '#disabled' => $locked,
davidmetzler's avatar
davidmetzler committed
508
509
    '#description' => t('Can be refererenced as :current_user in each data block.'),
    '#options' => $user_options,
510
    '#default_value' => @$config['user callback'],
davidmetzler's avatar
davidmetzler committed
511
512
513
514
    '#disabled' => $locked,
  );


515
516
  // Access method list
  $access = array(
davidmetzler's avatar
davidmetzler committed
517
    'callback' => t('Use drupal permissions'),
metzlerd's avatar
metzlerd committed
518
    'block' => t('Match values provided by a data block.'),
519
520
521
522
523
  );

  $form['access_method'] = array(
    '#type' => 'select',
    '#options' => $access,
524
    '#disabled' => $locked,
davidmetzler's avatar
davidmetzler committed
525
526
    '#title' => t('Data security method'),
    '#default_value' => empty($config['access block']) ? 'callback' : 'block',
metzlerd's avatar
metzlerd committed
527
    '#description' => t('Specify how the ACCESS defined for a data block is to be interpreted.'),
528
529
530
    '#ajax' => array(
      'callback' => 'forena_access_info_callback',
      'wrapper' => 'access-details',
metzlerd's avatar
metzlerd committed
531
  ),
532
533
534
535
536
537
  );

  $form['access_details'] = array(
    '#type' => 'fieldset',
    '#prefix' => '<div id="access-details">',
    '#suffix' => '</div>',
davidmetzler's avatar
davidmetzler committed
538
    '#title' => t('Details'),
539
540
541
  ) ;

  switch (!empty($values['access_method']) ? $values['access_method'] : $form['access_method']['#default_value']) {
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
    case 'block':
      $form['access_details']['access_block'] = array(
        '#type' => 'textfield',
        '#title' => 'Data block providing permissions list',
        '#disabled' => $locked,
        '#autocomplete_path' => 'forena/data_block/autocomplete',
        '#description' => t('The datablock to be used to interpret permissions.  This should return a single column of permissions based on the current user.   May be provided by another repository.'),
        '#default_value' => @$config['access block'],
      );
      break;
    default:
      $form['access_details']['access_callback'] = array(
        '#type' => 'item',
        '#title' => 'Access callback',
        '#disabled' => $locked,
        '#markup' => @$config['access callback'],
      );
559
560
561
562
563
564
565
566
  }



  // Driver list
  $drivers = array(
    'FrxDrupal' => t('Drupal'),
    'FrxOracle' => t('Oracle Database'),
metzlerd's avatar
metzlerd committed
567
    'FrxPDO' => t('PDO other than Drupal'),
568
569
570
571
572
    'FrxPostgres' => t('Postgres Database'),
    'FrxMSSQL' => t('MSSQL Database'),
    'FrxFiles' => t('XML Files'),
  );

davidmetzler's avatar
davidmetzler committed
573
  $form['data_provider'] = array(
574
575
576
577
578
    '#type' => 'select',
    '#title' => t('Driver'),
    '#description' => t('Forena data connection type'),
    '#options' => $drivers,
    '#disabled' => $locked,
davidmetzler's avatar
davidmetzler committed
579
    '#default_value' => $config['data provider'],
580
581
582
    '#ajax' => array(
      'callback' => 'forena_connection_info_callback',
      'wrapper' => 'conn-div',
metzlerd's avatar
metzlerd committed
583
  ),
584
585
586
587
  );

  $form['connection'] = array(
    '#type' => 'fieldset',
davidmetzler's avatar
davidmetzler committed
588
    '#tree' => TRUE,
589
590
591
592
    '#title' => 'Connection info',
   '#prefix' =>  '<div id="conn-div">',
   '#suffix' => '</div>',
  );
davidmetzler's avatar
davidmetzler committed
593
  $data_provider = (!empty($form_state['values']['data_provider']) ? $form_state['values']['data_provider'] : $config['data provider']);
594

davidmetzler's avatar
davidmetzler committed
595
596
597
598
599
  // Common controls used in mulitple providers.
  $uri = array(
    '#type' => 'textfield',
    '#title' => t('uri'),
    '#descripton' => t('Connection string: see appropriate php documentation for more details.'),
600
    '#default_value' => @$config['uri'],
davidmetzler's avatar
davidmetzler committed
601
602
603
604
605
606
607
608
609
610
611
612
    '#required' => TRUE,
  );

  $user = array(
    '#type' => 'textfield',
    '#title' => t('User'),
    '#default_value' => @$config['user'],
  );
  $password= array(
    '#type' => 'password',
    '#title' => t('Password'),
    '#default_value' => @$config['password'],
metzlerd's avatar
metzlerd committed
613
  );
davidmetzler's avatar
davidmetzler committed
614

davidmetzler's avatar
davidmetzler committed
615
  switch ($data_provider) {
davidmetzler's avatar
davidmetzler committed
616
    case 'FrxDrupal':
617
618
619
620
      $db_list = array_combine(array_keys($databases), array_keys($databases));
      $form['connection']['database'] = array(
        '#type' => 'select',
        '#title' => t('Database'),
621
        '#disabled' => $locked,
622
623
        '#default_value' => @$config['database'],
        '#options' => $db_list,
davidmetzler's avatar
davidmetzler committed
624
625
626
627
        '#markup' => 'Determined by Drupal settings.php file',
      );
      break;
    case 'FrxMSSQL':
628
629
630
      $form['connection']['uri'] = $uri;
      $form['connection']['user'] = $user;
      $form['connection']['new_password'] = $password;
631
632
633
634
635
636
637
      $form['connection']['database'] = array(
        '#type' => 'textfield',
        '#disabled' => $locked,
        '#title' => t('Database'),
        '#default_value' => $config['database'],
        '#required' => TRUE,
      );
davidmetzler's avatar
davidmetzler committed
638
639
640
641
642
643
644
      $form['connection']['mssql_xml'] = array(
        '#type' => 'checkbox',
        '#disabled' => $locked,
        '#title' => t('Microsoft SQL native XML'),
        '#description' => t('Use for XML auto queries to generate XML.'),
        '#default_value' => $config['mssql_xml'],
      );
metzlerd's avatar
metzlerd committed
645
      break;
davidmetzler's avatar
davidmetzler committed
646
    case 'FrxOracle':
647
      $form['connection']['uri'] = $uri;
davidmetzler's avatar
davidmetzler committed
648
649
      $form['connection']['user'] = $user;
      $form['connection']['new_password'] = $password;
650
651
652
653
654
655
656
657
      $form['connection']['character_set'] = array(
        '#type' => 'textfield',
        '#title' => t('Character Set'),
        '#disabled' => $locked,
        '#description' => t('Leave blank for default character set'),
        '#default_value' => @$config['character_set'],

      );
davidmetzler's avatar
davidmetzler committed
658
659
660
661
662
      $form['connection']['oracle_xml'] = array(
        '#type' => 'checkbox',
        '#title' => t('Oracle native XML'),
        '#disabled' => $locked,
        '#description' => t('Use the function provided with Forena to generate XML.  Requires installing a function into the database'),
663
        '#default_value' => @$config['oracle_xml'],
davidmetzler's avatar
davidmetzler committed
664
665
666
667
      );
      break;
    case 'FrxPDO':
      $form['connection']['uri'] = $uri;
metzlerd's avatar
metzlerd committed
668
669
670
      $form['connection']['user'] = $user;
      $form['connection']['new_password'] = $password;
      break;
davidmetzler's avatar
davidmetzler committed
671
    case 'FrxPostgres':
672
673
      $form['connection']['uri'] = $uri;
      $form['connection']['new_password'] = $password;
davidmetzler's avatar
davidmetzler committed
674
675
676
677
678
679
680
681
682
683
      $form['connection']['postgres_xml'] = array(
        '#type' => 'checkbox',
        '#title' => t('Postgres native XML'),
        '#disabled' => $locked,
        '#default_value' => @$config['postgres_xml'],
        '#description' => t('Use Postgres native XML support.  Requires Posgres 8.3 or better'),
      );

    default:
      $form['connection']['uri'] = $uri;
684
685
686
687
688
  }

  $form['save'] = array(
    '#type' => 'submit',
    '#value' => t('Save'),
689
    '#submit' => array('forena_data_settings_save'),
davidmetzler's avatar
davidmetzler committed
690
691
  );

692

davidmetzler's avatar
davidmetzler committed
693
694
695
696
  $form['delete'] = array(
    "#type" => 'submit',
    '#value' => t('Delete'),
    '#submit' => array('forena_data_settings_delete'),
697
698
699
700
701
  );

  return $form;
}

702
703


davidmetzler's avatar
davidmetzler committed
704
705
706
707
708
/**
 * Submit handler to cause save events to happen.
 * Enter description here ...
 */
function forena_data_settings_save($form, &$form_state) {
709
710
  $values = $form_state['values'];
  $name = $values['name'];
davidmetzler's avatar
davidmetzler committed
711
  $config = $form_state['storage']['config'];
davidmetzler's avatar
davidmetzler committed
712
713
714
  $config['path'] = @$values['path'];
  $config['data provider'] = $values['data_provider'];
  $config['user callback'] = $values['user_callback'];
davidmetzler's avatar
davidmetzler committed
715
716
  $config['debug'] = $values['debug'];
  if (@$values['connection']['new_password']) {
717
    $values['connection']['password'] = $values['connection']['new_password'];
davidmetzler's avatar
davidmetzler committed
718
719
  }
  if (isset($values['connection']['new_password'])) unset($values['connection']['new_password']);
720
  if (is_array(@$values['connection'])) $config = array_merge($config, @$values['connection']);
metzlerd's avatar
metzlerd committed
721
  if ($values['access_method']=='callback') {
722
    $config['access callback'] = empty($values['access_callback']) ? 'user_access' : $values['access_callback'];
metzlerd's avatar
metzlerd committed
723
    if (isset($config['access block'])) unset($config['access block']);
davidmetzler's avatar
davidmetzler committed
724
725
  }
  else {
726
    $config['access block'] = $values['access_block'];
davidmetzler's avatar
davidmetzler committed
727
728
  }
  $config_str = serialize($config);
davidmetzler's avatar
davidmetzler committed
729
  $result = db_query('SELECT * FROM {forena_repositories} WHERE repository = :name', array(':name' => $name));
davidmetzler's avatar
davidmetzler committed
730
731

  if ($result) drupal_set_message(t('Data connection settings saved'));
davidmetzler's avatar
davidmetzler committed
732
733
  if ($repos = $result->fetchObject()) {
    db_update('forena_repositories')
metzlerd's avatar
metzlerd committed
734
    ->fields(array(
davidmetzler's avatar
davidmetzler committed
735
736
        'title' => $values['title'],
        'enabled' => $values['enabled'],
davidmetzler's avatar
davidmetzler committed
737
        'config' => $config_str,
metzlerd's avatar
metzlerd committed
738
739
740
    ))
    ->condition('repository', $name, '=')
    ->execute();
741
742
  }
  else {
743
    $form_state['#redirect'] = 'admin/forena/content/data';
davidmetzler's avatar
davidmetzler committed
744
    db_insert('forena_repositories')
metzlerd's avatar
metzlerd committed
745
    ->fields(array(
davidmetzler's avatar
davidmetzler committed
746
747
748
        'repository' => $name,
        'title' => $values['title'],
        'enabled' => $values['enabled'],
davidmetzler's avatar
davidmetzler committed
749
        'config' => $config_str,
metzlerd's avatar
metzlerd committed
750
751
    ))
    ->execute();
752
  }
davidmetzler's avatar
davidmetzler committed
753
754
755
756
757
758
759
760
761
762
  $form_state['redirect'] = 'admin/config/content/forena/data';
}

/**
 * Delete the function
 * Enter description here ...
 * @param unknown_type $form
 * @param unknown_type $form_state
 */
function forena_data_settings_delete($form, &$form_state) {
763
764
765
  if (!@$form_state['storage]']['locked']) {
    $form_state['redirect'] = 'admin/config/content/forena/data';
    db_delete('forena_repositories')
metzlerd's avatar
metzlerd committed
766
767
    ->condition('repository', $form_state['values']['name'], '=')
    ->execute();
768
  }
davidmetzler's avatar
davidmetzler committed
769

770
771
772
773
774
775
776
777
778
779
780
781
}

/**
 * Generates the controls for external databases.
 * Enter description here ...
 */
function forena_connection_info_callback($form, $form_state) {
  return $form['connection'];

}

function forena_access_info_callback($form, $form_state) {
782
  return $form['access_details'];
783
784
}

785

786

787
/**
metzlerd's avatar
metzlerd committed
788
 * Clean xhtml
789
790
791
792
 *
 * @param unknown_type $xhtml
 * @return unknown
 */
metzlerd's avatar
metzlerd committed
793
794
795
796
function forena_clean_xhtml($xhtml) {
  $ret = $xhtml;
  // If tidy is installed lets clean the html using that.
  if (is_callable('tidy_repair_string')) {
797
    $config = array(
metzlerd's avatar
metzlerd committed
798
      'doctype'            => 'omit',
metzlerd's avatar
metzlerd committed
799
      'indent-spaces'             => 2,
metzlerd's avatar
metzlerd committed
800
801
802
      'indent' => 'auto',
      'input-xml'          => TRUE,
      'output-xml'         => TRUE,
metzlerd's avatar
metzlerd committed
803
      'indent-attributes'  => FALSE,
804
      'indent-spaces'      => 2,
metzlerd's avatar
metzlerd committed
805
      'add-xml-space'      => TRUE,
806
807
      'wrap'               => 135 );
    $ret = tidy_repair_string($xhtml, $config, 'utf8');
metzlerd's avatar
metzlerd committed
808
809
  }
  else {
810
    $ret = str_replace('&nbsp;', '&#160;', $ret);
811
  }
metzlerd's avatar
metzlerd committed
812
  return $ret;
813
}
814

metzlerd's avatar
metzlerd committed
815
/**
816
817
818
819
 *  Prettifies an XML string into a human-readable and indented work of art
 *  @param string $xml The XML as a string
 *  @param boolean $html_output True if the output should be escaped (for use in HTML)
 */
metzlerd's avatar
metzlerd committed
820
function forena_xmlpp($xml, $html_output=FALSE) {
metzlerd's avatar
metzlerd committed
821
822
823
824
  $xml_obj = new SimpleXMLElement($xml);
  $level = 4;
  $indent = 0; // current indentation level
  $pretty = array();
metzlerd's avatar
metzlerd committed
825

metzlerd's avatar
metzlerd committed
826
827
  // get an array containing each XML element
  $xml = explode("\n", preg_replace('/>\s*</', ">\n<", $xml_obj->asXML()));
828

metzlerd's avatar
metzlerd committed
829
830
831
832
  // shift off opening XML tag if present
  if (count($xml) && preg_match('/^<\?\s*xml/', $xml[0])) {
    $pretty[] = array_shift($xml);
  }
metzlerd's avatar
metzlerd committed
833

metzlerd's avatar
metzlerd committed
834
835
836
837
838
839
840
841
842
  foreach ($xml as $el) {
    if (preg_match('/^<([\w])+[^>\/]*>$/U', $el)) {
      // opening tag, increase indent
      $pretty[] = str_repeat(' ', $indent) . $el;
      $indent += $level;
    }
    else {
      if (preg_match('/^<\/.+>$/', $el)) {
        $indent -= $level;  // closing tag, decrease indent
metzlerd's avatar
metzlerd committed
843
      }
metzlerd's avatar
metzlerd committed
844
845
      if ($indent < 0) {
        $indent += $level;
846
      }
metzlerd's avatar
metzlerd committed
847
      $pretty[] = str_repeat(' ', $indent) . $el;
metzlerd's avatar
metzlerd committed
848
    }
metzlerd's avatar
metzlerd committed
849
850
851
  }
  $xml = implode("\n", $pretty);
  return ($html_output) ? htmlentities($xml) : $xml;
852
}
metzlerd's avatar
metzlerd committed
853
854
855
856

/**
 * Auto complete function for categories
 * Checks access for security as well.
metzlerd's avatar
metzlerd committed
857
 *
metzlerd's avatar
metzlerd committed
858
859
860
861
 * @param $string = string to be matched against categories
 * @return An array containing all matching categories
 */
function forena_get_categories($string='') {
862
  $data = Frx::File()->reportsByCategory();
863
864
865
866
867
868
869
870
871
872
873
874
875
  if ($string) {
    $categories = array();
    foreach (array_keys($data) as $cat) {
      if (strpos(strtolower($cat), strtolower(trim($string))) === 0) {
        $categories[] = $cat;
      }
    }

  }
  else {
    $categories = array_keys($data);
  }
  $categories = array_combine($categories, $categories);
metzlerd's avatar
metzlerd committed
876
  return $categories;
metzlerd's avatar
metzlerd committed
877
}
metzlerd's avatar
metzlerd committed
878

879
function forena_template_ajax(&$form_element) {
metzlerd's avatar
metzlerd committed
880
  $form_element['#ajax'] = array(
metzlerd's avatar
metzlerd committed
881
882
        'callback' => 'forena_template_info_callback',
        'wrapper' => 'template-wrapper',
metzlerd's avatar
metzlerd committed
883
  );
metzlerd's avatar
metzlerd committed
884
885
886
887
888
889
}

function forena_query_string($var) {
  return drupal_http_build_query($var);
}

metzlerd's avatar
metzlerd committed
890