Вставка записей Календаря Google с сервисной учетной записью

Я пытаюсь использовать служебную учетную запись для создания записей в календаре Google. Я очень близок к этому, но самая последняя строка не сработает. Я получаю 500 Internal Service Error когда я позволю этому бежать. В противном случае программа работает без ошибок, чего бы это ни стоило.

Calendar.php содержимое файла можно найти здесь. insert() метод, который я пытаюсь вызвать, начинается в строке 1455 этого файла.

<?php

function calendarize ($title, $desc, $ev_date, $cal_id) {

    session_start();

    /************************************************
    Make an API request authenticated with a service
    account.
    ************************************************/
    set_include_path( '../google-api-php-client/src/');

    require_once 'Google/Client.php';
    require_once 'Google/Service/Calendar.php';

    // (not real keys)
    $client_id = '843319906820-jarm3f5ctbtjj9b7lp5qdcqal54p1he6.apps.googleusercontent.com';
    $service_account_name = '843319906820-jarm3f5ctbtjj7b7lp5qdcqal54p1he6@developer.gserviceaccount.com';
    $key_file_location = '../google-api-php-client/calendar-249226a7a27a.p12';

//    echo pageHeader("Service Account Access");
    if (!strlen($service_account_name) || !strlen($key_file_location))
        echo missingServiceAccountDetailsWarning();

    $client = new Google_Client();
    $client->setApplicationName("xxxx Add Google Calendar Entries");

    if (isset($_SESSION['service_token'])) {
        $client->setAccessToken($_SESSION['service_token']);
    }

    $key = file_get_contents($key_file_location);
    $cred = new Google_Auth_AssertionCredentials(
        $service_account_name, 
        array('https://www.googleapis.com/auth/calendar'), 
        $key
    );
    $client->setAssertionCredentials($cred);
    if($client->getAuth()->isAccessTokenExpired()) {
        $client->getAuth()->refreshTokenWithAssertion($cred);
    }
    $_SESSION['service_token'] = $client->getAccessToken();

    // Prior to this, the code has mostly come from Google's example
    //     google-api-php-client / examples / service-account.php
    // and relates to getting the access tokens. 

    // The rest of this is about setting up the calendar entry.
    //Set the Event data
    $event = new Google_Service_Calendar_Event();
    $event->setSummary($title);
    $event->setDescription($desc);

    $start = new Google_Service_Calendar_EventDateTime();
    $start->setDate($ev_date);
    $event->setStart($start);

    $end = new Google_Service_Calendar_EventDateTime();
    $end->setDate($ev_date);     
    $event->setEnd($end);

    $calendarService = new Google_Service_Calendar($client);
    $calendarList = $calendarService->calendarList;

    $events = $calendarService->events;

    // if I leave this line, my code won't crash (but it won't do anything, either)
    //echo "here"; die(); 

    $events.insert($cal_id, $event, false);
} 

?>

2 ответа

Решение

Я понял это. Поскольку я не вижу полных примеров использования учетных записей служб с API v3, я просто опубликую свое полное решение для справки. Однако есть несколько вещей, которые вы должны сделать в дополнение к реализации кода:

1) Вам нужно зайти в консоль разработчика Google и пометить свою учетную запись как "учетную запись службы". Это будет отличать его от веб-приложения. Важным отличием является то, что никому не будет предложено войти в свою учетную запись до добавления событий, поскольку учетная запись будет принадлежать вашему приложению, а не конечному пользователю. Для получения дополнительной информации см. Эту статью, начиная со страницы 5.

2) Вам необходимо создать пару открытый / закрытый ключ. В консоли разработчика нажмите "Учетные данные". Под учетной записью службы нажмите "Создать новый ключ P12". Вы должны будете хранить это где-нибудь. Это местоположение файла становится $key_file_location переменная строка в коде ниже.

3) Также из консоли разработчика вам необходимо включить Calendar API. Из вашего проекта на левом поле вы увидите APIs, Выберите это и найдите Calendar API. Нажмите его, примите условия обслуживания и убедитесь, что он отображается в разделе Enabled APIs со статусом On

4) В Календаре Google, в который вы хотите добавить события, в разделе "Настройки" нажмите "Настройки календаря", а затем "Общий доступ к этому календарю" вверху. В поле "Поделиться с определенными людьми" в поле "Персона" введите адрес электронной почты из учетных данных учетной записи службы. Измените настройки разрешений на "Внести изменения в события". Не забудьте сохранить изменения.

Затем реализуйте этот код где-нибудь.

Прокомментируйте, если что-то сбивает с толку или опущено. Удачи!

<?php

function calendarize ($title, $desc, $ev_date, $cal_id) {

    session_start();

    /************************************************
    Make an API request authenticated with a service
    account.
    ************************************************/
    set_include_path( '../google-api-php-client/src/');

    require_once 'Google/Client.php';
    require_once 'Google/Service/Calendar.php';

    //obviously, insert your own credentials from the service account in the Google Developer's console
    $client_id = '843319906820-xxxxxxxxxxxxxxxxxxxdcqal54p1he6.apps.googleusercontent.com';
    $service_account_name = '843319906820-xxxxxxxxxxxxxxxxxxxdcqal54p1he6@developer.gserviceaccount.com';
    $key_file_location = '../google-api-php-client/calendar-xxxxxxxxxxxx.p12';

    if (!strlen($service_account_name) || !strlen($key_file_location))
        echo missingServiceAccountDetailsWarning();

    $client = new Google_Client();
    $client->setApplicationName("Whatever the name of your app is");

    if (isset($_SESSION['service_token'])) {
        $client->setAccessToken($_SESSION['service_token']);
    }

    $key = file_get_contents($key_file_location);
    $cred = new Google_Auth_AssertionCredentials(
        $service_account_name, 
        array('https://www.googleapis.com/auth/calendar'), 
        $key
    );
    $client->setAssertionCredentials($cred);
    if($client->getAuth()->isAccessTokenExpired()) {
        $client->getAuth()->refreshTokenWithAssertion($cred);
    }
    $_SESSION['service_token'] = $client->getAccessToken();

    $calendarService = new Google_Service_Calendar($client);
    $calendarList = $calendarService->calendarList;

    //Set the Event data
    $event = new Google_Service_Calendar_Event();
    $event->setSummary($title);
    $event->setDescription($desc);

    $start = new Google_Service_Calendar_EventDateTime();
    $start->setDateTime($ev_date);
    $event->setStart($start);

    $end = new Google_Service_Calendar_EventDateTime();
    $end->setDateTime($ev_date);
    $event->setEnd($end);

    $createdEvent = $calendarService->events->insert($cal_id, $event);

    echo $createdEvent->getId();
} 

?>

Некоторые полезные ресурсы:
Пример Github для сервисных аккаунтов
Консоль разработчика Google для вставки событий в API v3
Использование OAuth 2.0 для доступа к API Google

Вот способ Google API Client 2.0 сделать

Следуйте ответу Алекса. Перейдите в консоль разработчика Google, чтобы создать учетную запись службы, но создайте учетные данные в формате JSON.

Следуйте Руководству по обновлению клиента Google API, установите его композитором и включите в

 require_once 'vendor/autoload.php';

Следуйте ответу Алекса, чтобы перейти в Календарь Google, чтобы открыть календарь с идентификатором учетной записи

xxxxx@yyyy.iam.gserviceaccount.com 

Возьмите Ref. ниже кодирования и наиболее важным является идентификатор календаря должен быть адрес электронной почты создателя календаря, но не основной

<?php


require_once __DIR__.'/vendor/autoload.php';
   session_start();     


$client = new Google_Client();
$application_creds = __DIR__.'/secret.json';  //the Service Account generated cred in JSON
$credentials_file = file_exists($application_creds) ? $application_creds : false;
define("APP_NAME","Google Calendar API PHP");   //whatever
$client->setAuthConfig($credentials_file);
$client->setApplicationName(APP_NAME);
$client->addScope(Google_Service_Calendar::CALENDAR);
$client->addScope(Google_Service_Calendar::CALENDAR_READONLY);

//Setting Complete

//Go Google Calendar to set "Share with ..."  Created in Service Account (xxxxxxx@sustained-vine-198812.iam.gserviceaccount.com)

//Example of Use of API
$service = new Google_Service_Calendar($client);  


$calendarId = 'xxxx@gmail.com';   //NOT primary!! , but the email of calendar creator that you want to view
$optParams = array(
  'maxResults' => 10,
  'orderBy' => 'startTime',
  'singleEvents' => TRUE,
  'timeMin' => date('c'),
);
$results = $service->events->listEvents($calendarId, $optParams);

if (count($results->getItems()) == 0) {
  print "No upcoming events found.\n";
} else {
  echo "Upcoming events:";
  echo "<hr>";
  echo "<table>";
  foreach ($results->getItems() as $event) {
    $start = $event->start->dateTime;
    if (empty($start)) {
      $start = $event->start->date;
    }
    echo "<tr>";
    echo"<td>".$event->getSummary()."</td>";
    echo"<td>".$start."</td>";
    echo "</tr>";
  }
  echo "</table>";
}  
Другие вопросы по тегам