フリーランスの顧客管理をNotion×GASで自動化、対応履歴を自動蓄積

「やり取り、自動で残る。」Gmailのやり取りをGASでNotionの対応履歴DBに自動記録する仕組みのアイキャッチ画像

結論:Gmailでのやり取りを、GASで自動的にNotionの対応履歴DBに記録する仕組みを作りました。継続案件が増えても、誰といつどんな話をしたか思い出せなくなる不安がなくなりました。

この記事でわかること

  • なぜフリーランスにも簡易CRMが必要か
  • Notionでの対応履歴DB設計
  • GmailからNotionへ自動記録する仕組み
  • つまずいたポイント

前回の記事で、案件管理の実運用をまとめました。今回は案件そのものではなく、クライアントとのやり取りの履歴を自動で残す仕組みを作ります。

なぜフリーランスにも簡易CRMが必要か

継続案件のクライアントが増えてくると、「前回何を話したか」「いつ連絡したか」を覚えていられなくなります。企業のように本格的なCRMを導入するほどではなくても、対応履歴が自動で残る仕組みがあれば十分だと考え、今回作ることにしました。

Notionでの対応履歴DB設計

項目内容
件名メールの件名
差出人誰とのやり取りか
日時いつのやり取りか
本文抜粋内容を思い出すための冒頭部分
メールID重複記録を防ぐための識別子

GASでの自動記録の仕組み

Gmail側で「クライアント対応」というラベルを付けたメールだけを対象に、GASで定期的にNotionへ記録します。

const NOTION_TOKEN = 'ここにNotion Integrationのシークレットを入れる';
const HISTORY_DB_ID = 'ここに対応履歴DBのIDを入れる';
const GMAIL_LABEL = 'クライアント対応'; // このラベルを付けたメールだけを対象にする

function syncClientHistory() {
  const threads = GmailApp.search(`label:${GMAIL_LABEL} newer_than:1d`);
  const recordedIds = getRecordedMessageIds_();

  threads.forEach(thread => {
    thread.getMessages().forEach(message => {
      const id = message.getId();
      if (recordedIds.has(id)) return;

      createNotionRecord_({
        subject: message.getSubject(),
        from: message.getFrom(),
        date: message.getDate(),
        snippet: message.getPlainBody().slice(0, 200),
        messageId: id
      });
    });
  });
}

function createNotionRecord_(data) {
  UrlFetchApp.fetch('https://api.notion.com/v1/pages', {
    method: 'post',
    headers: {
      'Authorization': `Bearer ${NOTION_TOKEN}`,
      'Notion-Version': '2022-06-28',
      'Content-Type': 'application/json'
    },
    payload: JSON.stringify({
      parent: { database_id: HISTORY_DB_ID },
      properties: {
        '件名': { title: [{ text: { content: data.subject } }] },
        '差出人': { rich_text: [{ text: { content: data.from } }] },
        '日時': { date: { start: data.date.toISOString() } },
        'メールID': { rich_text: [{ text: { content: data.messageId } }] }
      },
      children: [{
        object: 'block',
        type: 'paragraph',
        paragraph: { rich_text: [{ text: { content: data.snippet } }] }
      }]
    })
  });
}

getRecordedMessageIds_は、既に記録済みのメールIDを取得して重複を防ぐための関数です。トリガーは「時間主導型・時間ベース・1時間おき」程度で設定しています。

つまずいたポイント:最初は毎回Notion DB全体を検索して重複チェックしていましたが、案件が増えるとAPI呼び出しが遅くなりました。PropertiesServiceで直近の記録済みIDだけをキャッシュする方式に変更し、余計な検索を減らしました。

運用してみて

まだ導入したばかりですが、「あのクライアントと最後にいつ連絡を取ったか」をNotionを開くだけで確認できるようになったのは、思っていたより安心感があります。ラベル付けを忘れると記録されないという運用上の弱点はあるので、しばらく使いながら改善していく予定です。

よくある質問

全てのメールが記録されますか?

いいえ。特定のGmailラベル(今回は「クライアント対応」)を付けたメールだけを対象にしているので、プライベートなメールなどが誤って記録されることはありません。

過去のメールも遡って記録できますか?

検索条件のnewer_than:1dの部分を変更すれば、過去分もまとめて取り込めます。ただし件数が多い場合はNotion APIの実行時間制限に注意が必要です。

個人情報の観点で心配はありませんか?

取得するのは自分宛のメールの一部(件名・差出人・本文の冒頭)のみで、Notion上でも自分だけがアクセスできる範囲で運用しています。第三者に共有する設計にはしていません。

次回は、請求書を過去データから一気通貫で自動生成する仕組みを作ります。