You are here

support.install in Support Ticketing System 7

Same filename and directory in other branches
  1. 6 support.install

Install, update and uninstall functions for the ._support module.

File

support.install
View source
<?php

/**
 * @file
 * Install, update and uninstall functions for the ._support module.
 *
 */

/**
 * Helpdesk / support ticket tracking system database schema.
 */

/**
 * Support database schema definition.
 */
function support_schema() {
  $schema['support_client'] = array(
    'description' => 'Stores information about support clients.',
    'fields' => array(
      'clid' => array(
        'type' => 'serial',
        'not null' => TRUE,
        'unsigned' => TRUE,
      ),
      'name' => array(
        'type' => 'varchar',
        'length' => 128,
        'not null' => TRUE,
        'default' => '',
      ),
      'path' => array(
        'type' => 'varchar',
        'length' => 32,
        'not null' => TRUE,
        'default' => '',
      ),
      'status' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'default' => 0,
      ),
      'parent' => array(
        'type' => 'int',
        'not null' => TRUE,
        'default' => 0,
      ),
      'integrate_email' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'default' => 0,
      ),
      'server_name' => array(
        'type' => 'varchar',
        'length' => 64,
        'not null' => TRUE,
        'default' => '',
      ),
      'server_username' => array(
        'type' => 'varchar',
        'length' => 64,
        'not null' => TRUE,
        'default' => '',
      ),
      'server_password' => array(
        'type' => 'varchar',
        'length' => 64,
        'not null' => TRUE,
        'default' => '',
      ),
      'mailfrom' => array(
        'type' => 'varchar',
        'length' => 64,
        'not null' => TRUE,
        'default' => '',
      ),
      'mailbox' => array(
        'type' => 'varchar',
        'length' => 64,
        'not null' => TRUE,
        'default' => '',
      ),
      'protocol' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'extra' => array(
        'type' => 'varchar',
        'length' => 128,
        'not null' => TRUE,
        'default' => '',
      ),
      'port' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'autoassign' => array(
        'type' => 'varchar',
        'length' => 255,
        'not null' => TRUE,
        'default' => '',
        'description' => 'Optionally assign new tickets to this user.',
      ),
      'autosubscribe' => array(
        'type' => 'text',
      ),
      'domains' => array(
        'type' => 'text',
        'size' => 'big',
      ),
      'notes' => array(
        'type' => 'text',
        'size' => 'big',
      ),
      'thread_subject' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'default' => 0,
        'description' => 'Optionally configure per-client subject threading settings.',
      ),
      'user_creation' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'default' => 0,
        'description' => 'Optionally configure per-client user creation settings.',
      ),
    ),
    'primary key' => array(
      'clid',
    ),
    'indexes' => array(
      'status' => array(
        'status',
      ),
      'autoassign' => array(
        'autoassign',
      ),
    ),
    'unique keys' => array(
      'name' => array(
        'name',
      ),
    ),
  );
  $schema['support_ticket'] = array(
    'description' => 'Stores information about support tickets.',
    'fields' => array(
      'nid' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'message_id' => array(
        'type' => 'varchar',
        'length' => 255,
        'not null' => TRUE,
        'default' => '',
      ),
      'state' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'priority' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'client' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'assigned' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
    ),
    'primary key' => array(
      'nid',
    ),
    'indexes' => array(
      'message_id' => array(
        'message_id',
      ),
      'state' => array(
        'state',
      ),
    ),
  );
  $schema['support_ticket_comment'] = array(
    'description' => 'Stores information about support ticket comments.',
    'fields' => array(
      'cid' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'message_id' => array(
        'type' => 'varchar',
        'length' => 255,
        'not null' => TRUE,
        'default' => '',
      ),
      'state' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'priority' => array(
        'type' => 'int',
        'size' => 'small',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'client' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'assigned' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
    ),
    'primary key' => array(
      'cid',
    ),
    'indexes' => array(
      'message_id' => array(
        'message_id',
      ),
    ),
  );
  $schema['support_assigned'] = array(
    'description' => 'Stores information about who tickets are assigned to.',
    'fields' => array(
      'nid' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'uid' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
    ),
    'primary key' => array(
      'nid',
      'uid',
    ),
    'indexes' => array(
      'support_assigned_uid' => array(
        'uid',
      ),
    ),
  );
  $schema['support_states'] = array(
    'description' => 'All available support states.',
    'fields' => array(
      'sid' => array(
        'type' => 'serial',
        'not null' => TRUE,
        'unsigned' => TRUE,
      ),
      'state' => array(
        'type' => 'varchar',
        'length' => 32,
        'not null' => TRUE,
      ),
      'phase1' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'phase2' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'isdefault' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'isclosed' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'weight' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
    ),
    'primary key' => array(
      'sid',
    ),
    'indexes' => array(
      'weight_state' => array(
        'weight',
        'state',
      ),
      'isdefault' => array(
        'isdefault',
      ),
      'isclosed' => array(
        'isclosed',
      ),
    ),
  );
  $schema['support_priority'] = array(
    'description' => 'All available support priorities.',
    'fields' => array(
      'pid' => array(
        'type' => 'serial',
        'not null' => TRUE,
        'unsigned' => TRUE,
      ),
      'priority' => array(
        'type' => 'varchar',
        'length' => 32,
        'not null' => TRUE,
      ),
      'isdefault' => array(
        'type' => 'int',
        'size' => 'tiny',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
      'weight' => array(
        'type' => 'int',
        'not null' => TRUE,
        'unsigned' => TRUE,
        'default' => 0,
      ),
    ),
    'primary key' => array(
      'pid',
    ),
    'indexes' => array(
      'weight_priority' => array(
        'weight',
        'priority',
      ),
      'isdefault' => array(
        'isdefault',
      ),
    ),
  );
  return $schema;
}

/**
 * Install support database schema.
 */
function support_install() {

  // State: new
  db_insert('support_states')
    ->fields(array(
    'state' => 'new',
    'weight' => 0,
    'phase1' => 1,
    'phase2' => 0,
    'isdefault' => 1,
  ))
    ->execute();

  // State: active
  db_insert('support_states')
    ->fields(array(
    'state' => 'active',
    'weight' => 1,
    'phase1' => 0,
    'phase2' => 1,
  ))
    ->execute();

  // State: pending
  db_insert('support_states')
    ->fields(array(
    'state' => 'pending',
    'weight' => 2,
    'phase1' => 0,
    'phase2' => 1,
  ))
    ->execute();

  // State: closed
  db_insert('support_states')
    ->fields(array(
    'state' => 'closed',
    'weight' => 3,
    'phase1' => 0,
    'phase2' => 1,
    'isclosed' => 1,
  ))
    ->execute();

  // Priority: low
  db_insert('support_priority')
    ->fields(array(
    'priority' => 'low',
    'weight' => 0,
  ))
    ->execute();

  // Priority: normal
  db_insert('support_priority')
    ->fields(array(
    'priority' => 'normal',
    'weight' => 1,
    'isdefault' => 1,
  ))
    ->execute();

  // Priority: high
  db_insert('support_priority')
    ->fields(array(
    'priority' => 'high',
    'weight' => 2,
  ))
    ->execute();

  // Priority: critical
  db_insert('support_priority')
    ->fields(array(
    'priority' => 'critical',
    'weight' => 3,
  ))
    ->execute();

  // default comment settings
  variable_set('comment_default_mode_support_ticket', COMMENT_MODE_THREADED);

  // TODO: Is there a replacement for this

  //variable_set('comment_default_order_support_ticket', COMMENT_ORDER_OLDEST_FIRST);

  // Set default weight
  db_update('system')
    ->fields(array(
    'weight' => 10,
  ))
    ->condition('name', 'support')
    ->execute();

  // Add body field to support_ticket type.
  node_types_rebuild();
  $types = node_type_get_types();
  node_add_body_field($types['support_ticket']);

  // Set up a file field for uploads.
  _support_ensure_upload_field();
}

/**
 * Cleanup; remove all support_ticket content.
 */
function support_uninstall() {

  // Remove support content type.
  node_type_delete('support_ticket');

  // Delete all support tickets.
  $tickets = db_select('node', 'n')
    ->fields('n', array(
    'nid',
  ))
    ->condition('n.type', 'support_ticket')
    ->execute();
  foreach ($tickets as $ticket) {
    node_delete($ticket->nid);
  }

  // Cleanup old support module permissions.
  db_delete('role_permission')
    ->condition('module', 'support')
    ->execute();

  // Cleanup old support module variables.
  foreach (array(
    'support_admin_notify',
    'support_autoassign_ticket',
    'support_autocomplete_limit',
    'support_autocreate_users',
    'support_autosubscribe_assigned',
    'support_autosubscribe_creator',
    'support_autosubscribe_force',
    'support_cron_download_mail',
    'support_default_sort_order',
    'support_default_sort_tickets',
    'support_disable_comment_reply',
    'support_disable_post_comment',
    'support_display_user_links',
    'support_global_domains',
    'support_global_mailfrom',
    'support_notifications',
    'support_override_block',
    'support_override_theme',
    'support_remove_tickets',
    'support_require_comment',
    'support_secondary_sort_order',
    'support_secondary_sort_tickets',
    'support_thread_by_mail_headers',
    'support_thread_by_subject',
    'support_use_aliased_urls',
    'support_key',
    'support_mail_ticket_comment_new_body',
    'support_mail_ticket_comment_new_subject',
    'support_mail_ticket_deny_body',
    'support_mail_ticket_deny_subject',
    'support_mail_ticket_new_body',
    'support_mail_ticket_new_subject',
  ) as $variable) {
    variable_del($variable);
  }
}

/**
 * Remove unnecessary 'active' field from {support_assigned} table.
 */
function support_update_6008() {

  // Remove inactive entries from table.
  db_delete('support_assigned')
    ->condition('active', 0)
    ->execute();

  // Remove unnecessary status field.
  db_drop_field('support_assigned', 'active');
}

/**
 * Update 6009 skipped in Drupal 7.
 */

/*
function support_update_6009() {
}
*/

/**
 * Make sure support_ticket has a field available for node and comment file attachments.
 */
function _support_ensure_upload_field() {

  // Force the file module to be enabled.
  module_enable(array(
    'file',
  ));

  // If you want to migrate from the comment_upload data in D6 but don't want
  // to use this automatically created field, create a file field manually
  // and set this variable to the field name.
  $field_name = variable_get('support_mail_upload_field', 'support_ticket_upload');
  $info = field_info_field($field_name);
  if (!$info) {

    // Field is missing, create it.
    $field = array(
      'field_name' => $field_name,
      'type' => 'file',
      'module' => 'file',
      'locked' => FALSE,
      'cardinality' => FIELD_CARDINALITY_UNLIMITED,
      'translatable' => FALSE,
      'settings' => array(
        'display_field' => 1,
        'display_default' => variable_get('upload_list_default', 1),
        'uri_scheme' => file_default_scheme(),
        'default_file' => 0,
      ),
    );
    field_create_field($field);
  }
  $upload_size = variable_get('upload_uploadsize_default', 1);

  // Base instance.
  $base_instance = array(
    'field_name' => $field_name,
    'entity_type' => NULL,
    'bundle' => NULL,
    'label' => 'File attachments',
    'required' => 0,
    'description' => '',
    'widget' => array(
      'weight' => '1',
      'settings' => array(
        'progress_indicator' => 'throbber',
      ),
      'type' => 'file_generic',
    ),
    'settings' => array(
      'max_filesize' => $upload_size ? $upload_size . ' MB' : '',
      'file_extensions' => variable_get('upload_extensions_default', 'jpg jpeg gif png txt doc xls pdf ppt pps odt ods odp'),
      'file_directory' => 'support',
      // @@@ I think this is a good idea personally but need a second opinion.
      'description_field' => 1,
    ),
    'display' => array(
      'default' => array(
        'label' => 'hidden',
        'type' => 'file_table',
        'settings' => array(),
        'weight' => 0,
        'module' => 'file',
      ),
    ),
  );
  if (!$info || !isset($info['bundles']['comment']) || !in_array('comment_node_support_ticket', $info['bundles']['comment'])) {

    // Field isn't associated with support_ticket comments, attach it.
    $instance = $base_instance;
    $instance['entity_type'] = 'comment';
    $instance['bundle'] = 'comment_node_support_ticket';
    $instance['display']['full'] = $instance['display']['default'];
    field_create_instance($instance);
  }
  if (!$info || !isset($info['bundles']['node']) || !in_array('support_ticket', $info['bundles']['node'])) {

    // Additionally check if the 'upload' field is available -- we support falling back to that
    // if the field is missing, so users with 6.x sites don't end up with 2 fields.
    $info2 = field_info_field('upload');
    if (!$info2 || !isset($info2['bundles']['node']) || !in_array('support_ticket', $info2['bundles']['node'])) {

      // Field isn't associated with support_ticket nodes and there wasn't a legacy upload field, attach it.
      $instance = $base_instance;
      $instance['entity_type'] = 'node';
      $instance['bundle'] = 'support_ticket';
      $instance['display']['full'] = $instance['display']['default'];
      $instance['display']['rss'] = $instance['display']['default'];
      $instance['display']['teaser'] = $instance['display']['default'];
      $instance['display']['teaser']['type'] = 'hidden';
      field_create_instance($instance);
    }
  }
}

/**
 * Convert support mail variables to HTML.
 */
function support_update_7000() {

  // Note: Other modules have to fix up their own variables.
  $vars = array(
    'support_mail_ticket_comment_new_body',
    'support_mail_ticket_comment_new_subject',
    'support_mail_ticket_deny_body',
    'support_mail_ticket_deny_subject',
    'support_mail_ticket_new_body',
    'support_mail_ticket_new_subject',
  );
  foreach ($vars as $var) {
    $fixed = str_replace(array(
      "\r\n",
      "\n\r",
      "\n",
      "\r",
    ), "<br />\n", variable_get($var, ''));
    if (!empty($fixed)) {
      variable_set($var, $fixed);
    }
  }
}

/**
 * Ensure an upload field is created for uploading to comments.
 */
function support_update_7001() {
  _support_ensure_upload_field();
}

/**
 * Migrate comment_upload data for support.module to a file.module field.
 */
function support_update_7002(&$sandbox) {

  // Code was heavily based on system_update_7061().
  if (!db_table_exists('comment_upload')) {
    return;
  }
  $fieldname = variable_get('support_mail_upload_field', 'support_ticket_upload');
  if (!isset($sandbox['progress'])) {

    // Initialize batch update information.
    $sandbox['progress'] = 0;
    $sandbox['last_cid_processed'] = -1;
    $sandbox['max'] = db_query("SELECT COUNT(*) FROM {comment_upload} u INNER JOIN {node} n ON u.nid = n.nid WHERE n.type = 'support_ticket'")
      ->fetchField();
  }

  // Determine cids for this batch.
  // Process all files attached to a given comment during the same batch.
  $limit = variable_get('upload_update_batch_size', 100);
  $cids = db_query_range("SELECT u.cid FROM {comment_upload} u INNER JOIN {node} n ON u.nid = n.nid WHERE n.type = 'support_ticket' AND u.cid > :lastcid ORDER BY cid", 0, $limit, array(
    ':lastcid' => $sandbox['last_cid_processed'],
  ))
    ->fetchCol();

  // Retrieve information on all the files attached to these comments.
  if (!empty($cids)) {
    $comments = array();
    $result = db_query('SELECT c.fid, c.nid, c.cid, c.description, c.list, c.weight FROM {comment_upload} c WHERE c.cid IN (:cids) ORDER BY c.cid, c.weight, c.fid', array(
      ':cids' => $cids,
    ));
    foreach ($result as $record) {

      // For each uploaded file, retrieve the corresponding data from the old
      // files table (since comment_upload doesn't know about the new entry in the
      // file_managed table).
      $file = db_select('files', 'f')
        ->fields('f', array(
        'fid',
        'uid',
        'filename',
        'filepath',
        'filemime',
        'filesize',
        'status',
        'timestamp',
      ))
        ->condition('f.fid', $record->fid)
        ->execute()
        ->fetchAssoc();
      if (!$file) {
        continue;
      }

      // Add in the file information from the upload table.
      $file['description'] = $record->description;
      $file['display'] = $record->list;

      // Create one record for each revision that contains all the uploaded
      // files.
      $comments[$record->cid]['cid'] = $record->cid;
      $comments[$record->cid]['file'][LANGUAGE_NONE][] = $file;
    }

    // Now that we know which files belong to which comments, update the
    // files'// database entries, and save a reference to each file in the
    // upload field on their node revisions.
    $basename = variable_get('file_directory_path', conf_path() . '/files');
    $scheme = file_default_scheme() . '://';
    foreach ($comments as $cid => $comment) {
      foreach ($comment['file'][LANGUAGE_NONE] as $delta => $file) {

        // We will convert filepaths to uri using the default scheme
        // and stripping off the existing file directory path.
        $file['uri'] = $scheme . str_replace($basename, '', $file['filepath']);
        $file['uri'] = file_stream_wrapper_uri_normalize($file['uri']);
        unset($file['filepath']);

        // Insert into the file_managed table.
        // Each fid should only be stored once in file_managed.
        db_merge('file_managed')
          ->key(array(
          'fid' => $file['fid'],
        ))
          ->fields(array(
          'uid' => $file['uid'],
          'filename' => $file['filename'],
          'uri' => $file['uri'],
          'filemime' => $file['filemime'],
          'filesize' => $file['filesize'],
          'status' => $file['status'],
          'timestamp' => $file['timestamp'],
        ))
          ->execute();

        // Add the usage entry for the file.
        $file = (object) $file;
        file_usage_add($file, 'file', 'comment', $comment['cid']);

        // Update the comment's upload file field with the file data.
        $comment['file'][LANGUAGE_NONE][$delta] = array(
          'fid' => $file->fid,
          'display' => $file->display,
          'description' => $file->description,
        );
      }

      // Write the comment's upload field data into the field_upload tables.
      $comment = (object) $comment;
      _update_7000_field_sql_storage_write('comment', 'comment_node_support_ticket', $comment->cid, $comment->cid, $fieldname, $comment->file);

      // Update our progress information for the batch update.
      $sandbox['progress']++;
      $sandbox['last_cid_processed'] = $cid;
    }
  }

  // If less than limit comments were processed, the update process is
  // finished.
  if (count($cids) < $limit) {
    $finished = TRUE;
  }

  // If there's no max value then there's nothing to update and we're finished.
  if (empty($sandbox['max']) || isset($finished)) {

    // Remove our processed migrated files while leaving the table (as people may be using comment_upload for other things as well)
    $fids = db_query("SELECT fid FROM {comment_upload} c INNER JOIN {node} n ON c.nid = n.nid WHERE n.type = 'support_ticket'")
      ->fetchCol();
    db_delete('comment_upload')
      ->condition('fid', $fids, 'IN')
      ->execute();
    return t('Comment Upload data associated with Support tickets has been migrated to File module.');
  }
  else {

    // Indicate our current progress to the batch update system.
    $sandbox['#finished'] = $sandbox['progress'] / $sandbox['max'];
  }
}

/**
 * Ensure support_update_6008 has run: Remove unnecessary 'active' field from {support_assigned} table.
 */
function support_update_7003() {
  if (db_field_exists('support_assigned', 'active')) {
    support_update_6008();
  }
}

/**
 * Fix a performance issue with the primary key on {support_assigned}.
 */
function support_update_7004() {
  db_drop_primary_key('support_assigned');
  db_add_primary_key('support_assigned', array(
    'nid',
    'uid',
  ));
}

/**
 * Add an index on uid to {support_assigned}.
 */
function support_update_7005() {
  db_add_index('support_assigned', 'support_assigned_uid', array(
    'uid',
  ));
}

/**
 * Convert old built in add, edit, and delete permissions to those provided by Drupal 7 core node module.
 */
function support_update_7006() {
  $permissions = array(
    'create tickets' => 'create support_ticket content',
    'delete any ticket' => 'delete any support_ticket content',
    'delete own tickets' => 'delete own support_ticket content',
    'edit any ticket' => 'edit any support_ticket content',
    'edit own tickets' => 'edit own support_ticket content',
  );
  foreach ($permissions as $old => $new) {
    $old_permission = db_select('role_permission', 'r')
      ->fields('r', array(
      'rid',
    ))
      ->condition('r.permission', $old)
      ->condition('r.module', 'support')
      ->execute()
      ->fetchObject();

    // Convert old permissions to new permissions.
    if (is_object($old_permission) && isset($old_permission->rid)) {
      user_role_grant_permissions($old_permission->rid, array(
        $new,
      ));
      user_role_revoke_permissions($old_permission->rid, array(
        $old,
      ));
      $role = user_role_load($old_permission->rid);
      drupal_set_message(t('Updated %role role %old permission to %new.', array(
        '%role' => $role->name,
        '%old' => $old,
        '%new' => $new,
      )));
    }
  }
}

Functions

Namesort descending Description
support_install Install support database schema.
support_schema Support database schema definition.
support_uninstall Cleanup; remove all support_ticket content.
support_update_6008 Remove unnecessary 'active' field from {support_assigned} table.
support_update_7000 Convert support mail variables to HTML.
support_update_7001 Ensure an upload field is created for uploading to comments.
support_update_7002 Migrate comment_upload data for support.module to a file.module field.
support_update_7003 Ensure support_update_6008 has run: Remove unnecessary 'active' field from {support_assigned} table.
support_update_7004 Fix a performance issue with the primary key on {support_assigned}.
support_update_7005 Add an index on uid to {support_assigned}.
support_update_7006 Convert old built in add, edit, and delete permissions to those provided by Drupal 7 core node module.
_support_ensure_upload_field Make sure support_ticket has a field available for node and comment file attachments.