You are here

zoomapi.api.inc in Zoom API 7.2

API callbacks for Zoom API module.

File

zoomapi.api.inc
View source
<?php

/**
 * @file
 * API callbacks for Zoom API module.
 */
use ZoomAPI\ZoomAPIClient;

/**
 * Get ZoomAPI client.
 */
function zoomapi_api_client() {
  $api_key = variable_get('zoomapi_key', '');
  $api_secret = variable_get('zoomapi_secret', '');
  try {
    if (empty($api_key) || empty($api_secret)) {
      throw new Exception('Missing Zoom API key or secret.');
    }
    $zoom_client = new ZoomAPIClient($api_key, $api_secret);
    return $zoom_client;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to load Zoom API client library. Error: @e', [
      '@e' => $e
        ->getMessage(),
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Check if email in use.
 *
 * Checks against local table, however option to check against API.
 */
function zoomapi_api_user_email_exists($email) {
  $zoom_client = zoomapi_client();
  $exists = $zoom_client
    ->users()
    ->emailExists($email);
  return $exists;
}

/**
 * Create Zoom user.
 *
 * Simple wrapper to the API so we can track drupal/zoom user account
 * relationship.
 */
function zoomapi_api_create_user($uid, $params) {
  try {
    $zoom_client = zoomapi_client();
    drupal_alter('zoomapi_create_user', $params, $uid);
    $zoom_user = $zoom_client
      ->api('user')
      ->create($params);
    zoomapi_track_user($uid, $zoom_user);
    module_invoke_all('zoomapi_user_create', $zoom_user, $uid);
    return $zoom_user;
  } catch (Exception $e) {
    watchdog(__FUNCTION__, 'Error creating zoom user for uid @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $uid,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Get Zoom users.
 */
function zoomapi_api_get_users() {
  try {
    $zoom_client = zoomapi_client();
    $zoom_users = $zoom_client
      ->users()
      ->fetchAll();
    return $zoom_users;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to retrieve all zoom accounts. Error: @e', [
      '@e' => $e
        ->getMessage(),
    ], WATCHDOG_CRITICAL);
    return [];
  }
}

/**
 * Get Zoom user.
 */
function zoomapi_api_get_user($identifier, $uid = 0) {
  if (!valid_email_address($identifier) && !is_string($identifier)) {
    throw new Exception('Zoom account email or id is required to retrieve zoom account.');
  }
  try {
    $zoom_client = zoomapi_client();
    $zoom_user = $zoom_client
      ->api('user')
      ->fetch($identifier);
    if ($uid) {
      zoomapi_track_user($uid, $zoom_user);
    }
    return $zoom_user;
  } catch (\Exception $e) {
    return [];
  }
}

/**
 * Update Zoom user.
 */
function zoomapi_api_update_user($uid, $zoom_user_id, array $user_info) {
  try {
    drupal_alter('zoomapi_update_user', $user_info, $uid);
    $zoom_client = zoomapi_client();
    $zoom_client
      ->api('user')
      ->update($zoom_user_id, $user_info);
    if (!empty($user_info['email'])) {
      $zoom_user = $zoom_client
        ->api('user')
        ->fetch($zoom_user_id);
      zoomapi_track_user($uid, $zoom_user);
    }
    return TRUE;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to update zoom account @id for user !uid. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $zoom_user_id,
      '!uid' => $uid,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Update Zoom user email.
 *
 * @todo "Domain name doesn't match, please contact Zoom customer support to set
 * managed domains for your account"
 */
function zoomapi_api_update_user_email($zoom_user_id, $email) {
  try {
    $zoom_client = zoomapi_client();
    $zoom_client
      ->api('user')
      ->email($zoom_user_id, $email);
    db_update('zoomapi_users')
      ->fields([
      'zoom_email' => $email,
    ])
      ->condition('zoom_user_id', $zoom_user_id)
      ->condition('realm', zoomapi_realm())
      ->execute();
    return TRUE;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to update zoom email to @email for zoom account @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@email' => $email,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Get Zoom User settings.
 */
function zoomapi_api_get_user_settings($zoom_user_id) {
  try {
    $zoom_client = zoomapi_client();
    $settings = $zoom_client
      ->api('user')
      ->settings($zoom_user_id);
    return $settings;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to retrieve user settings for Zoom account @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $zoom_user_id,
    ], WATCHDOG_CRITICAL);
    return [];
  }
}

/**
 * Update Zoom User settings.
 */
function zoomapi_api_update_user_settings($zoom_user_id, array $settings) {
  try {
    $zoom_client = zoomapi_client();
    $settings = $zoom_client
      ->api('user')
      ->settings($zoom_user_id, $settings);
    return $settings;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to update Zoom account settings for Zoom account @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $zoom_user_id,
    ], WATCHDOG_CRITICAL);
    return [];
  }
}

/**
 * Create Zoom Meeting.
 */
function zoomapi_api_create_meeting($zoom_user_id, array $params, array $context = []) {
  try {
    drupal_alter('zoomapi_create_meeting', $params, $context);
    $params['user_id'] = $zoom_user_id;
    list($entity_type, $entity_id) = zoomapi_extract_entity_info_from_meeting_context($context);
    if (!$entity_id || !$entity_type) {
      throw new Exception('Missing entity ID or type.');
    }
    $zoom_client = zoomapi_client();
    $zoom_meeting = $zoom_client
      ->api('meeting')
      ->create($params);
    zoomapi_track_meeting($zoom_meeting, $entity_type, $entity_id);
    module_invoke_all('zoomapi_meeting_create', $zoom_meeting, $context);
    return $zoom_meeting;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to create meeting for Zoom account @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $zoom_user_id,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Get Meeting.
 */
function zoomapi_api_get_meeting($meeting_id) {
  try {
    $zoom_client = zoomapi_client();
    $zoom_meeting = $zoom_client
      ->api('meeting')
      ->fetch($meeting_id);
    return $zoom_meeting;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to retrieve Zoom meeting @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $meeting_id,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Get User Recordings.
 */
function zoomapi_api_get_user_recordings($zoom_user_id) {
  try {
    $zoom_client = zoomapi_client();
    $params = [
      'user_id' => $zoom_user_id,
    ];
    $recordings = $zoom_client
      ->recordings()
      ->fetchAll($params);
    return $recordings;
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to get recordings for Zoom account @id. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@id' => $zoom_user_id,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  }
}

/**
 * Get Meeting Recordings.
 *
 * Retrieve the Zoom meeting recordings response.
 */
function zoomapi_api_get_meeting_recordings($meeting_id) {
  try {
    $zoom_client = zoomapi_client();
    $zoom_meeting_recordings = $zoom_client
      ->api('recordings')
      ->fetchMeetingRecordings($meeting_id);
  } catch (\Exception $e) {
    $zoom_meeting_recordings = [];
    if ($e
      ->getCode() != 404) {
      watchdog(__FUNCTION__, 'Unable to retrieve recordings for Zoom meeting @id. Error: @e', [
        '@e' => $e
          ->getMessage(),
        '@id' => $meeting_id,
      ], WATCHDOG_CRITICAL);
    }
  }
  return $zoom_meeting_recordings;
}

/**
 * Download Recording.
 *
 * Downloads a zoom recording to the specified destination / filename.
 */
function zoomapi_api_download_recording($zoom_meeting_recording, $destination_directory, $filename = '', $context = []) {
  try {

    // Check that the destination is writable.
    $temporary_directory = 'temporary://';
    if (!file_prepare_directory($temporary_directory, FILE_MODIFY_PERMISSIONS)) {
      $msg = t('The directory %dir is not writable, because it does not have the correct permissions set.', [
        '%dir' => drupal_realpath($temporary_directory),
      ]);
      throw new Exception($msg);
    }
    $file_type = strtolower($zoom_meeting_recording['file_type']);
    $filename = $filename ?: $zoom_meeting_recording['id'] . '_' . strtotime($zoom_meeting_recording['recording_start']) . '.' . $file_type;
    if (empty($context['recording'])) {
      $context['recording'] = $zoom_meeting_recording;
    }
    drupal_alter('zoomapi_recording_filename', $filename, $context);
    if (strtolower(substr($filename, -1 * strlen($file_type))) != $file_type) {
      $filename .= ".{$file_type}";
    }
    $zoom_client = zoomapi_client();
    $url = url($zoom_meeting_recording['download_url'], [
      'query' => [
        'access_token' => $zoom_client
          ->generateJwt(),
      ],
    ]);

    // Check that the destination is writable.
    $mode = variable_get('file_chmod_directory', 0775);

    // This first chmod check is for other systems such as S3, which don't work
    // with file_prepare_directory().
    if (!drupal_chmod($destination_directory, $mode) && !file_prepare_directory($destination_directory, FILE_CREATE_DIRECTORY)) {
      $msg = t('File %file could not be copied, because the destination directory %destination is not configured correctly.', [
        '%file' => $url,
        '%destination' => drupal_realpath($destination_directory),
      ]);
      throw new Exception($msg);
    }

    // Check the headers to make sure it exists and is within the allowed size.
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_HEADER, TRUE);
    curl_setopt($ch, CURLOPT_NOBODY, TRUE);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);

    // Causes a warning if PHP safe mode is on.
    @curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);

    // Set a user agent - some hosts block requests unless header is present.
    $curl_version = curl_version();
    curl_setopt($ch, CURLOPT_USERAGENT, 'PHP-curl/' . $curl_version['version']);
    curl_exec($ch);
    $info = curl_getinfo($ch);
    if ($info['http_code'] != 200) {
      curl_setopt($ch, CURLOPT_HTTPGET, TRUE);
      $file_contents = curl_exec($ch);
      $info = curl_getinfo($ch);
    }
    curl_close($ch);
    if ($info['http_code'] != 200) {
      $replacements = [
        '@filename' => $filename,
        '@code' => $info['http_code'],
      ];
      switch ($info['http_code']) {
        case 403:
          $replacements['reason'] = 'Access to the file was denied.';
          break;
        case 404:
          $replacements['reason'] = 'Not found.';
          break;
      }
      $msg = t('The recording @filename for meeting @meeting_id could not be downloaded. HTTP error (@code). Reason !reason', $replacements);
      throw new Exception($msg);
    }

    // Update the $url variable to reflect any redirects.
    $url = $info['url'];
    $filename = zoomapi_clean_filename($filename);
    $filepath = file_create_filename($filename, $temporary_directory);

    // Set progress bar information.
    $options = [
      'key' => $url,
      'filepath' => $filepath,
    ];
    zoomapi_set_transfer_options($options);
    $transfer_success = FALSE;

    // If we've already downloaded the entire file because the header-retrieval
    // failed, just use the contents we have.
    if (isset($file_contents)) {
      if ($fp = @fopen($filepath, 'w')) {
        fwrite($fp, $file_contents);
        fclose($fp);
        $transfer_success = TRUE;
      }
    }
    else {
      $ch = curl_init();
      curl_setopt($ch, CURLOPT_URL, $url);
      curl_setopt($ch, CURLOPT_HEADER, FALSE);
      curl_setopt($ch, CURLOPT_WRITEFUNCTION, 'zoomapi_download_recording_curl_write');

      // Causes a warning if PHP safe mode is on.
      @curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);

      // Set a user agent - some hosts block requests unless header is present.
      $curl_version = curl_version();
      curl_setopt($ch, CURLOPT_USERAGENT, 'PHP-curl/' . $curl_version['version']);
      $transfer_success = curl_exec($ch);
      curl_close($ch);
    }
    if ($transfer_success) {
      $download_size = filesize($filepath);
      if ($download_size != $zoom_meeting_recording['file_size']) {
        $msg = t('The file size (@new_size) for recording @recording_id of meeting @meeting_id did not match the specified file size (@orig_size).', [
          '@new_size' => $download_size,
          '@recording_id' => $zoom_meeting_recording['id'],
          '@meeting_id' => $zoom_meeting_recording['meeting_id'],
          '@orig_size' => $zoom_meeting_recording['file_size'],
        ]);
        $transfer_success = FALSE;
        throw new Exception($msg);
      }
      $file = zoomapi_save_file($filepath, $destination_directory);
      return (array) $file;
    }
  } catch (\Exception $e) {
    watchdog(__FUNCTION__, 'Unable to download Zoom recording @filename. Error: @e', [
      '@e' => $e
        ->getMessage(),
      '@filename' => $filename,
    ], WATCHDOG_CRITICAL);
    return FALSE;
  } finally {

    // Delete the temporary file.
    if (isset($file) && isset($filepath) && $filepath !== $file->uri) {
      @unlink($filepath);
    }
  }
}

Functions

Namesort descending Description
zoomapi_api_client Get ZoomAPI client.
zoomapi_api_create_meeting Create Zoom Meeting.
zoomapi_api_create_user Create Zoom user.
zoomapi_api_download_recording Download Recording.
zoomapi_api_get_meeting Get Meeting.
zoomapi_api_get_meeting_recordings Get Meeting Recordings.
zoomapi_api_get_user Get Zoom user.
zoomapi_api_get_users Get Zoom users.
zoomapi_api_get_user_recordings Get User Recordings.
zoomapi_api_get_user_settings Get Zoom User settings.
zoomapi_api_update_user Update Zoom user.
zoomapi_api_update_user_email Update Zoom user email.
zoomapi_api_update_user_settings Update Zoom User settings.
zoomapi_api_user_email_exists Check if email in use.