处理日期和时间

AdWords 脚本经常需要处理日期和时间。常见的使用情形包括检索特定日期范围的报告,安排广告系列或广告组在特定时间投放,以及将脚本上次运行时间输出到电子表格。本指南介绍了在 AdWords 脚本中处理日期和时间的重要概念以及常见问题和推荐的解决方式。

基本概念

要在 AdWords 脚本中处理日期和时间,需要使用 JavaScript 的内置日期对象。JavaScript 日期对象代表特定时刻。有几种方法创建新的日期对象:

// Create a date object for the current date and time.
var now = new Date();

// Create a date object for a past date and time using a formatted string.
var date = new Date('February 17, 2016 13:00:00 -0500');

// Create a copy of an existing date object.
var copy = new Date(date);

新脚本用户常常困惑于日期对象对时区的处理方式。日期对象很自然地被认为是单个时区内的时钟时间,然而这并不正确。例如,在上面的代码段中,某些用户误以为 date 只对与创建它的时区时差为 -5 小时的那一个时区有效。按照这种错误的观点,在其他时区中使用时,需要对 date 进行“转换”。

对日期对象的正确认知方式是,它是独立于任何时区的特定时刻。虽然特定时刻在不同时区时钟上的显示不同,但是是同一时刻。例如,考虑这一代码段:

// Create two date objects with different times and timezone offsets.
var date1 = new Date('February 17, 2016 13:00:00 -0500');
var date2 = new Date('February 17, 2016 10:00:00 -0800');

// getTime() returns the number of milliseconds since the beginning of
// January 1, 1970 UTC.
// True, as the dates represent the same moment in time.
Logger.log(date1.getTime() == date2.getTime());

// False, as the dates are separate objects, though they happen to
// represent the same moment in time.
Logger.log(date1 == date2);

因为日期对象代表时间中的特定时刻,所以不需要进行跨时区的“转换”。相反,它可以被输出为针对特定时区的带格式字符串。

要以特定格式和时区的字符串输出日期,请使用 Utilities.formatDate(date, timeZone, format)。例如:

var date = new Date('February 17, 2016 13:00:00 -0500');

// February 17, 2016 13:00:00 -0500
Logger.log(Utilities.formatDate(date, 'America/New_York', 'MMMM dd, yyyy HH:mm:ss Z'));

// February 17, 2016 10:00:00 -0800
Logger.log(Utilities.formatDate(date, 'America/Los_Angeles', 'MMMM dd, yyyy HH:mm:ss Z'));

// 2016-02-17T18:00:00.000Z
Logger.log(Utilities.formatDate(date, 'Etc/GMT', 'yyyy-MM-dd\'T\'HH:mm:ss.SSS\'Z\''));

这些示例直接使用时区 ID指定时区。要检索与运行脚本的 AdWords 帐户相关联的时区,请使用 AdWordsApp.currentAccount().getTimeZone()

常见问题

记录日期对象时的默认时区

使用 Logger.log() 直接记录日期对象时,将使用默认格式和时区进行输出。例如:

var date = new Date('February 17, 2016 13:00:00 -0500');

// Wed Feb 17 10:00:00 GMT-08:00 2016
Logger.log(date);

与 AdWords 帐户的关联时区无关,默认时区为美国/洛杉矶(太平洋时间)。要使用自定义格式和时区将日期对象输出为字符串,以用于记录或其他目标,请务必使用 Utilities.formatDate(date, timeZone, format)

创建日期对象时的默认时区

如果使用不提供时区偏移量的字符串创建日期对象,则与 AdWords 帐户的关联时区无关,时区将被认定为美国/洛杉矶(太平洋时间)。例如:

// Create a date without specifying the timezone offset.
var date = new Date('February 17, 2016 13:00:00');

// Wed Feb 17 13:00:00 GMT-08:00 2016
Logger.log(date);

如果使用字符串创建日期对象,则一定要加入时区偏移量,以确保日期对象表示您真正需要的时刻。

日期对象方法的默认时区

JavaScript 日期对象有几种认定默认时区的方法,包括 getFullYear()getMonth()getDate()getDay()getHours()getMinutes() 及其对应的 set___() 方法和 getTimezoneOffet()。在 AdWords 脚本中,与 AdWords 帐户的关联时区无关,默认时区为美国/洛杉矶(太平洋时间)。因此,除非您的 AdWords 帐户是在这个时区,否则一般而言,您应避免使用这些方法。

相反,要在您的帐户时区中检索日期对象的年、月、日期、星期、小时或分钟,请一定以您需要的指定日期或时间部分的格式使用 Utilities.formatDate(date, timeZone, format),并使用 AdWordsApp.currentAccount().getTimeZone() 检索帐户的时区。

从已设置格式的日期字符串创建日期对象

可以将已设置格式的日期字符串传递到日期构造函数,从而创建日期对象。例如:

var date = new Date('February 17, 2016 13:00:00 -0500');

构造函数只能解析特定日期字符串格式。为了确保您的日期字符串被正确解析,请务必采用 MMMM dd, yyyy HH:mm:ss Z 格式提供时。

例如,以下代码为当前帐户时区今天中午构造日期对象:

var now = new Date();
var timeZone = AdWordsApp.currentAccount().getTimeZone();
var noonString = Utilities.formatDate(now, timeZone,
                                      'MMMM dd, yyyy 12:00:00 Z')
var noon = new Date(noonString);

不要使用“z”模式来创建将传递给日期构造函数的日期字符串,原因是构造函数不一定始终能够对其进行解析。只使用“Z”模式。

日期数学运算

一些脚本需要对日期进行简单的数学运算,如找到给定日期之前或之后 X 天的日期。执行日期数学运算时,请一定使用 getTime()。对日期对象调用 getTime() 将返回自 UTC 1970 年 1 月 1 日起的毫秒数。您可以对这个值执行数学运算,然后使用 setTime() 将新的数值应用于某个日期对象,或在创建新的日期对象时将其作为参数提供。

例如:

var MILLIS_PER_DAY = 1000 * 60 * 60 * 24;
var now = new Date();
var yesterday = new Date(now.getTime() - MILLIS_PER_DAY);

在这个例子中,yesterday 是恰好 24 小时前。

报告

当使用 AdWordsApp.report(query, optArgs) 检索报告时,该 AWQL 查询要求将日期指定为 8 位整数 (YYYYMMDD)。同样,许多 AdWords 脚本对象中提供的 getStatsFor() 方法要求将日期指定为 8 位整数。使用 Utilities.formatDate(date, timeZone, format),采用这种格式来设置日期对象的格式。

例如,要检索一至三天前的报告:

var MILLIS_PER_DAY = 1000 * 60 * 60 * 24;
var now = new Date();
var from = new Date(now.getTime() - 3 * MILLIS_PER_DAY);
var to = new Date(now.getTime() - 1 * MILLIS_PER_DAY);

var timeZone = AdWordsApp.currentAccount().getTimeZone();
var report = AdWordsApp.report(
  'SELECT CampaignName, Clicks ' +
  'FROM   CAMPAIGN_PERFORMANCE_REPORT ' +
  'DURING ' + Utilities.formatDate(from, timeZone, 'yyyyMMdd') + ','
            + Utilities.formatDate(to, timeZone, 'yyyyMMdd'));

电子表格

AdWords 脚本经常将输出写到电子表格,包括日期对象。当通过传递日期对象在电子表格中设置单元格时,将使用电子表格的时区来解释该日期。例如,假设我们有一个电子表格的时区设置为太平洋时间:

// Suppose today is February 17, 2016 13:00:00 -0500 (Eastern Time)
var now = new Date();
spreadsheet.getRange('A1').setValue(now);

A1 的值将是 17-Feb-16 10:00:00。

为了确保将日期对象写入您所需的电子表格,请将电子表格的时区设置为与您 AdWords 帐户的时区一致:

spreadsheet.setSpreadsheetTimeZone(AdWordsApp.currentAccount().getTimeZone());

您也可以手动设置电子表格的时间

发送以下问题的反馈:

此网页
AdWords Scripts
AdWords Scripts
需要帮助?请访问我们的支持页面