將文字合併至文件

Google Docs API 的一個實用應用程式,是將一或多個資料來源的資訊合併至文件中。

本頁面將說明如何從外部來源取得資料,並將資料插入現有的範本文件中。

範本是一種特殊類型的文件,其中包含相同的固定文字,適用於透過範本建立的所有文件,以及可放置其他動態文字的指定預留位置。舉例來說,合約範本可能會包含固定內容,以及收件者的姓名、地址和其他詳細資料。接著,應用程式就能將特定客戶的資料合併至範本,以建立完成的文件。

這種做法有幾個好處:

  • 設計人員可以輕鬆使用 Google 文件編輯器微調文件設計。這比在應用程式中調整參數來設定算繪版面配置來得簡單。

  • 將內容與呈現方式分開是眾所皆知的設計原則,且有許多好處。

合併作業的概念圖。

基本食譜

以下是使用 Docs API 將資料合併至文件的範例:

  1. 使用預留位置內容建立文件,以利設計和格式設定。系統會保留要取代的文字格式。

  2. 針對要插入的每個元素,請將預留位置內容替換為標記。請務必使用平常不太可能出現的字串。例如,{{account-holder-name}} 可能是一個不錯的標記。

  3. 在程式碼中使用 Google 雲端硬碟 API 建立文件副本。

  4. 在程式碼中,使用 Docs API 的 batchUpdate() 方法搭配文件名稱,並納入 ReplaceAllTextRequest

文件 ID 會參照文件,可從網址衍生

https://docs.google.com/document/d/documentId/edit

範例

請參考下列範例,其中會將範本所有分頁中的 2 個欄位替換為實際值,以產生完成的文件。

如要執行此合併作業,您可以使用下列程式碼。

Java

String customerName = "Alice";
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy/MM/dd");
String date = formatter.format(LocalDate.now());

List<Request> requests = new ArrayList<>();
// One option for replacing all text is to specify all tab IDs.
requests.add(new Request()
        .setReplaceAllText(new ReplaceAllTextRequest()
                .setContainsText(new SubstringMatchCriteria()
                        .setText("{{customer-name}}")
                        .setMatchCase(true))
                .setReplaceText(customerName)
                .setTabsCriteria(new TabsCriteria()
                        .addTabIds(TAB_ID_1)
                        .addTabIds(TAB_ID_2)
                        .addTabIds(TAB_ID_3))));
// Another option is to omit TabsCriteria if you are replacing across all tabs.
requests.add(new Request()
        .setReplaceAllText(new ReplaceAllTextRequest()
                .setContainsText(new SubstringMatchCriteria()
                        .setText("{{date}}")
                        .setMatchCase(true))
                .setReplaceText(date)));

BatchUpdateDocumentRequest body = new BatchUpdateDocumentRequest();
service.documents().batchUpdate(documentId, body.setRequests(requests)).execute();

Node.js

  let customerName = 'Alice';
  let date = yyyymmdd()
  let requests = [
    // One option for replacing all text is to specify all tab IDs.
    {
      replaceAllText: {
        containsText: {
          text: '{{customer-name}}',
          matchCase: true,
        },
        replaceText: customerName,
        tabsCriteria: {
          tabIds: [TAB_ID_1, TAB_ID_2, TAB_ID_3],
        },
      },
    },
    // Another option is to omit TabsCriteria if you are replacing across all tabs.
    {
      replaceAllText: {
        containsText: {
          text: '{{date}}',
          matchCase: true,
        },
        replaceText: date,
      },
    },
  ];

  google.options({auth: auth});
  google
      .discoverAPI(
          'https://docs.googleapis.com/$discovery/rest?version=v1&key={YOUR_API_KEY}')
      .then(function(docs) {
        docs.documents.batchUpdate(
            {
              documentId: '1yBx6HSnu_gbV2sk1nChJOFo_g3AizBhr-PpkyKAwcTg',
              resource: {
                requests,
              },
            },
            (err, {data}) => {
              if (err) return console.log('The API returned an error: ' + err);
              console.log(data);
            });
      });

Python

customer_name = 'Alice'
date = datetime.datetime.now().strftime("%y/%m/%d")

requests = [
        # One option for replacing all text is to specify all tab IDs.
        {
        'replaceAllText': {
            'containsText': {
                'text': '{{customer-name}}',
                'matchCase':  'true'
            },
            'replaceText': customer_name,
            'tabsCriteria': {
                'tabIds': [TAB_ID_1, TAB_ID_2, TAB_ID_3],
            },
        }},
        # Another option is to omit TabsCriteria if you are replacing across all tabs.
        {
        'replaceAllText': {
            'containsText': {
                'text': '{{date}}',
                'matchCase':  'true'
            },
            'replaceText': str(date),
        }
    }
]

result = service.documents().batchUpdate(
    documentId=document_id, body={'requests': requests}).execute()

管理範本

針對應用程式定義及擁有的範本文件,請使用代表應用程式的專屬帳戶建立範本。服務帳戶是個不錯的選擇,可避免因 Google Workspace 限制分享的政策而造成複雜情況。

使用範本建立文件執行個體時,請務必使用終端使用者憑證。這樣一來,使用者就能完全控管產生的文件,並避免因雲端硬碟中的每位使用者限制而導致的縮放問題。

如要使用服務帳戶建立範本,請使用應用程式憑證執行下列步驟:

  1. 使用 Docs API 中的 documents.create 建立文件。
  2. 更新權限,允許文件收件者使用 Drive API 中的 permissions.create 讀取文件。
  3. 更新權限,允許範本作者使用 Drive API 中的 permissions.create 寫入範本。
  4. 視需要編輯範本。

如要建立文件的例項,請使用使用者憑證執行下列步驟:

  1. 使用 Drive API 中的 files.copy 建立範本副本。
  2. 使用 Docs API 中的 documents.batchUpdate 取代值。