Dịch vụ Lịch nâng cao

Dịch vụ Lịch nâng cao cho phép bạn sử dụng API Lịch Google trong Apps Script. Giống như dịch vụ Lịch tích hợp của Apps Script, API này cho phép các tập lệnh truy cập và sửa đổi Lịch Google của người dùng, bao gồm lịch bổ sung mà người dùng đã đăng ký. Trong hầu hết các trường hợp, hàm tích hợp sẵn dịch vụ này dễ sử dụng hơn nhưng dịch vụ nâng cao này cung cấp thêm các tính năng mới, bao gồm cả việc đặt màu nền cho từng sự kiện.

Tài liệu tham khảo

Để biết thông tin chi tiết về dịch vụ này, hãy xem tài liệu tham khảo cho công chúng API Lịch Google. Giống như tất cả các dịch vụ nâng cao trong Apps Script, Dịch vụ Lịch sử dụng các đối tượng, phương thức và thông số giống như chế độ công khai API. Để biết thêm thông tin, hãy xem bài viết Cách xác định chữ ký phương thức.

Để báo cáo sự cố và tìm hỗ trợ khác, hãy xem Hướng dẫn hỗ trợ về Lịch.

Tiêu đề của yêu cầu HTTP

Dịch vụ Lịch nâng cao có thể chấp nhận tiêu đề của yêu cầu HTTP If-MatchIf-None-Match. Để biết chi tiết, hãy xem tài liệu tham khảo.

Mã mẫu

Mã mẫu bên dưới sử dụng phiên bản 3 của API.

Tạo sự kiện

Ví dụ sau đây minh hoạ cách tạo một sự kiện theo mặc định của người dùng lịch.

advanced/calendar.gs
/**
 * Creates an event in the user's default calendar.
 * @see https://developers.google.com/calendar/api/v3/reference/events/insert
 */
function createEvent() {
  const calendarId = 'primary';
  const start = getRelativeDate(1, 12);
  const end = getRelativeDate(1, 13);
  // event details for creating event.
  let event = {
    summary: 'Lunch Meeting',
    location: 'The Deli',
    description: 'To discuss our plans for the presentation next week.',
    start: {
      dateTime: start.toISOString()
    },
    end: {
      dateTime: end.toISOString()
    },
    attendees: [
      {email: 'gduser1@workspacesample.dev'},
      {email: 'gduser2@workspacesample.dev'}
    ],
    // Red background. Use Calendar.Colors.get() for the full list.
    colorId: 11
  };
  try {
    // call method to insert/create new event in provided calandar
    event = Calendar.Events.insert(event, calendarId);
    console.log('Event ID: ' + event.id);
  } catch (err) {
    console.log('Failed with error %s', err.message);
  }
}

/**
 * Helper function to get a new Date object relative to the current date.
 * @param {number} daysOffset The number of days in the future for the new date.
 * @param {number} hour The hour of the day for the new date, in the time zone
 *     of the script.
 * @return {Date} The new date.
 */
function getRelativeDate(daysOffset, hour) {
  const date = new Date();
  date.setDate(date.getDate() + daysOffset);
  date.setHours(hour);
  date.setMinutes(0);
  date.setSeconds(0);
  date.setMilliseconds(0);
  return date;
}

Lịch danh sách

Ví dụ sau minh hoạ cách truy xuất thông tin chi tiết về lịch hiển thị trong danh sách lịch của người dùng.

advanced/calendar.gs
/**
 * Lists the calendars shown in the user's calendar list.
 * @see https://developers.google.com/calendar/api/v3/reference/calendarList/list
 */
function listCalendars() {
  let calendars;
  let pageToken;
  do {
    calendars = Calendar.CalendarList.list({
      maxResults: 100,
      pageToken: pageToken

    });
    if (!calendars.items || calendars.items.length === 0) {
      console.log('No calendars found.');
      return;
    }
    // Print the calendar id and calendar summary
    for (const calendar of calendars.items) {
      console.log('%s (ID: %s)', calendar.summary, calendar.id);
    }
    pageToken = calendars.nextPageToken;
  } while (pageToken);
}

Sự kiện trang thông tin

Ví dụ sau minh hoạ cách liệt kê 10 sự kiện sắp tới tiếp theo trong lịch mặc định của người dùng.

advanced/calendar.gs
/**
 * Lists the next 10 upcoming events in the user's default calendar.
 * @see https://developers.google.com/calendar/api/v3/reference/events/list
 */
function listNext10Events() {
  const calendarId = 'primary';
  const now = new Date();
  const events = Calendar.Events.list(calendarId, {
    timeMin: now.toISOString(),
    singleEvents: true,
    orderBy: 'startTime',
    maxResults: 10
  });
  if (!events.items || events.items.length === 0) {
    console.log('No events found.');
    return;
  }
  for (const event of events.items) {
    if (event.start.date) {
      // All-day event.
      const start = new Date(event.start.date);
      console.log('%s (%s)', event.summary, start.toLocaleDateString());
      continue;
    }
    const start = new Date(event.start.dateTime);
    console.log('%s (%s)', event.summary, start.toLocaleString());
  }
}

Sửa đổi sự kiện có điều kiện

Ví dụ sau đây cho biết cách cập nhật một sự kiện trên Lịch theo điều kiện bằng cách sử dụng tiêu đề If-Match. Tập lệnh tạo một sự kiện mới, đợi 30 giây, sau đó chỉ cập nhật sự kiện nếu không có thông tin chi tiết nào về sự kiện thay đổi kể từ khi sự kiện diễn ra đã tạo.

advanced/calendar.gs
/**
 * Creates an event in the user's default calendar, waits 30 seconds, then
 * attempts to update the event's location, on the condition that the event
 * has not been changed since it was created.  If the event is changed during
 * the 30-second wait, then the subsequent update will throw a 'Precondition
 * Failed' error.
 *
 * The conditional update is accomplished by setting the 'If-Match' header
 * to the etag of the new event when it was created.
 */
function conditionalUpdate() {
  const calendarId = 'primary';
  const start = getRelativeDate(1, 12);
  const end = getRelativeDate(1, 13);
  let event = {
    summary: 'Lunch Meeting',
    location: 'The Deli',
    description: 'To discuss our plans for the presentation next week.',
    start: {
      dateTime: start.toISOString()
    },
    end: {
      dateTime: end.toISOString()
    },
    attendees: [
      {email: 'gduser1@workspacesample.dev'},
      {email: 'gduser2@workspacesample.dev'}
    ],
    // Red background. Use Calendar.Colors.get() for the full list.
    colorId: 11
  };
  event = Calendar.Events.insert(event, calendarId);
  console.log('Event ID: ' + event.getId());
  // Wait 30 seconds to see if the event has been updated outside this script.
  Utilities.sleep(30 * 1000);
  // Try to update the event, on the condition that the event state has not
  // changed since the event was created.
  event.location = 'The Coffee Shop';
  try {
    event = Calendar.Events.update(
        event,
        calendarId,
        event.id,
        {},
        {'If-Match': event.etag}
    );
    console.log('Successfully updated event: ' + event.id);
  } catch (e) {
    console.log('Fetch threw an exception: ' + e);
  }
}

Truy xuất có điều kiện một sự kiện

Ví dụ sau đây cho thấy cách tìm nạp một sự kiện Lịch theo điều kiện bằng cách sử dụng tiêu đề If-None-Match. Tập lệnh này tạo một sự kiện mới, sau đó thăm dò ý kiến về sự kiện đó để biết các thay đổi trong 30 giây. Bất cứ khi nào sự kiện thay đổi, phiên bản mới sẽ được tìm nạp.

advanced/calendar.gs
/**
 * Creates an event in the user's default calendar, then re-fetches the event
 * every second, on the condition that the event has changed since the last
 * fetch.
 *
 * The conditional fetch is accomplished by setting the 'If-None-Match' header
 * to the etag of the last known state of the event.
 */
function conditionalFetch() {
  const calendarId = 'primary';
  const start = getRelativeDate(1, 12);
  const end = getRelativeDate(1, 13);
  let event = {
    summary: 'Lunch Meeting',
    location: 'The Deli',
    description: 'To discuss our plans for the presentation next week.',
    start: {
      dateTime: start.toISOString()
    },
    end: {
      dateTime: end.toISOString()
    },
    attendees: [
      {email: 'gduser1@workspacesample.dev'},
      {email: 'gduser2@workspacesample.dev'}
    ],
    // Red background. Use Calendar.Colors.get() for the full list.
    colorId: 11
  };
  try {
    // insert event
    event = Calendar.Events.insert(event, calendarId);
    console.log('Event ID: ' + event.getId());
    // Re-fetch the event each second, but only get a result if it has changed.
    for (let i = 0; i < 30; i++) {
      Utilities.sleep(1000);
      event = Calendar.Events.get(calendarId, event.id, {}, {'If-None-Match': event.etag});
      console.log('New event description: ' + event.start.dateTime);
    }
  } catch (e) {
    console.log('Fetch threw an exception: ' + e);
  }
}

Sự kiện đồng bộ hoá

Ví dụ sau minh hoạ cách truy xuất các sự kiện bằng mã thông báo đồng bộ hoá. Khi bạn đưa mã thông báo đồng bộ hoá vào yêu cầu dịch vụ nâng cao của Lịch, kết quả phản hồi chỉ bao gồm các mục đã thay đổi kể từ mã thông báo đó đã được tạo, cho phép xử lý hiệu quả hơn. Xem Đồng bộ hoá tài nguyên hiệu quả để biết thêm thông tin chi tiết về quá trình đồng bộ hoá.

Ví dụ sau đây sử dụng cùng một getRelativeDate(daysOffset, hour) xác định trong các ví dụ ở trên.

advanced/calendar.gs
/**
 * Retrieve and log events from the given calendar that have been modified
 * since the last sync. If the sync token is missing or invalid, log all
 * events from up to a month ago (a full sync).
 *
 * @param {string} calendarId The ID of the calender to retrieve events from.
 * @param {boolean} fullSync If true, throw out any existing sync token and
 *        perform a full sync; if false, use the existing sync token if possible.
 */
function logSyncedEvents(calendarId, fullSync) {
  const properties = PropertiesService.getUserProperties();
  const options = {
    maxResults: 100
  };
  const syncToken = properties.getProperty('syncToken');
  if (syncToken && !fullSync) {
    options.syncToken = syncToken;
  } else {
    // Sync events up to thirty days in the past.
    options.timeMin = getRelativeDate(-30, 0).toISOString();
  }
  // Retrieve events one page at a time.
  let events;
  let pageToken;
  do {
    try {
      options.pageToken = pageToken;
      events = Calendar.Events.list(calendarId, options);
    } catch (e) {
      // Check to see if the sync token was invalidated by the server;
      // if so, perform a full sync instead.
      if (e.message === 'Sync token is no longer valid, a full sync is required.') {
        properties.deleteProperty('syncToken');
        logSyncedEvents(calendarId, true);
        return;
      }
      throw new Error(e.message);
    }
    if (events.items && events.items.length === 0) {
      console.log('No events found.');
      return;
    }
    for (const event of events.items) {
      if (event.status === 'cancelled') {
        console.log('Event id %s was cancelled.', event.id);
        return;
      }
      if (event.start.date) {
        const start = new Date(event.start.date);
        console.log('%s (%s)', event.summary, start.toLocaleDateString());
        return;
      }
      // Events that don't last all day; they have defined start times.
      const start = new Date(event.start.dateTime);
      console.log('%s (%s)', event.summary, start.toLocaleString());
    }
    pageToken = events.nextPageToken;
  } while (pageToken);
  properties.setProperty('syncToken', events.nextSyncToken);
}