Integration Guides
Step-by-step recipes for connecting ShareDoc to the tools you already use. Each guide takes under 10 minutes.
Looking for a specific email or sales platform? See all 25 email & sales integrations →
Slack Notifications
Get a message in Slack the moment someone reads your deck, completes it, or returns for a second look.
Go to api.slack.com/apps → Create New App → Incoming Webhooks → Add to a channel. Copy the webhook URL.
You'll need a small server to receive ShareDoc webhooks and forward them to Slack. Deploy this anywhere (Railway, Vercel, AWS Lambda):
# Python (Flask) — deploy as a serverless function or microservice
from flask import Flask, request, jsonify
import requests, hmac, hashlib
app = Flask(__name__)
SHAREDOC_SECRET = "your_webhook_secret_here"
SLACK_WEBHOOK_URL = "https://hooks.slack.com/services/T.../B.../xxx"
def verify(body, header, secret):
parts = dict(p.split("=", 1) for p in header.split(","))
signed = f"{parts['t']}.".encode() + body
expected = hmac.new(secret.encode(), signed, hashlib.sha256).hexdigest()
return hmac.compare_digest(expected, parts["v1"])
@app.route("/webhook", methods=["POST"])
def handle():
body = request.get_data()
sig = request.headers.get("X-ShareDoc-Signature", "")
if not verify(body, sig, SHAREDOC_SECRET):
return "Invalid signature", 401
event = request.json
data = event["data"]
doc = data["document"]
event_type = event["event"]
if event_type == "document.viewed":
viewer = data["viewer"]
who = viewer.get("email") or "Someone"
text = (f"*{who}* viewed <{doc['url']}|{doc['title']}>\n"
f"Pages: {viewer['pages_viewed']}/{viewer['total_pages']} "
f"({int(viewer['completion']*100)}%) · "
f"Visit #{viewer['visit_number']}")
elif event_type == "document.completed":
viewer = data["viewer"]
who = viewer.get("email") or "Someone"
text = f":white_check_mark: *{who}* read 100% of <{doc['url']}|{doc['title']}>!"
elif event_type == "lead.captured":
lead = data["lead"]
text = (f":email: New lead from <{doc['url']}|{doc['title']}>\n"
f"*{lead['email']}*"
f"{' (' + lead['company_domain'] + ')' if lead.get('company_domain') else ''}")
elif event_type == "viewer.revisited":
viewer = data["viewer"]
who = viewer.get("email") or "A viewer"
text = (f":eyes: *{who}* came back to <{doc['url']}|{doc['title']}> "
f"after {viewer['hours_since_first_view']:.0f}h")
else:
return "ok", 200
requests.post(SLACK_WEBHOOK_URL, json={"text": text})
return "ok", 200
Point ShareDoc's webhook at your server:
curl -X POST https://sharedoc.co/api/v1/webhooks \
-H "Authorization: Bearer bd_live_your_key_here" \
-H "Content-Type: application/json" \
-d '{
"url": "https://your-server.com/webhook",
"events": ["document.viewed", "document.completed", "lead.captured", "viewer.revisited"]
}'
Save the secret from the response — you'll need it for signature verification.
curl -X POST https://sharedoc.co/api/v1/webhooks/test \
-H "Authorization: Bearer bd_live_your_key_here"
You should see a test message in your Slack channel.
Google Sheets
Every lead automatically lands in a spreadsheet. No code required if you use Zapier, or use Apps Script for a free, self-contained solution.
Option A: Google Apps Script (free, no third-party tools)
Add headers in row 1: Email, Name, Company, Document, Pages Read, Captured At
Extensions → Apps Script. Paste this code:
function doPost(e) {
var sheet = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
var payload = JSON.parse(e.postData.contents);
if (payload.event !== "lead.captured") {
return ContentService.createTextOutput("ignored");
}
var data = payload.data;
var lead = data.lead;
var doc = data.document;
sheet.appendRow([
lead.email,
lead.name || "",
lead.company_domain || "",
doc.title,
lead.pages_viewed + "/" + lead.total_pages,
payload.created_at
]);
return ContentService.createTextOutput("ok");
}
Deploy → New deployment → Web app → Execute as "Me" → Access "Anyone". Copy the URL.
curl -X POST https://sharedoc.co/api/v1/webhooks \
-H "Authorization: Bearer bd_live_your_key_here" \
-H "Content-Type: application/json" \
-d '{"url": "https://script.google.com/macros/s/.../exec", "events": ["lead.captured"]}'
Option B: Zapier (see Zapier guide below)
Use the "Webhooks by Zapier" trigger + "Google Sheets" action. Takes 2 minutes, no code.
HubSpot CRM
Create or update HubSpot contacts when leads are captured, and log document views as engagement activities.
Settings → Integrations → Private Apps → Create. Give it crm.objects.contacts.write scope.
# Node.js (Express)
const express = require('express');
const axios = require('axios');
const app = express();
app.use(express.json());
const HUBSPOT_TOKEN = "pat-xxx";
app.post('/webhook', async (req, res) => {
const { event, data } = req.body;
if (event === 'lead.captured') {
const { email, name, company_domain } = data.lead;
const { title } = data.document;
// Create or update contact
await axios.post(
'https://api.hubapi.com/crm/v3/objects/contacts',
{
properties: {
email,
firstname: name.split(' ')[0] || '',
lastname: name.split(' ').slice(1).join(' ') || '',
company: company_domain,
hs_lead_status: 'NEW',
notes_last_contacted: `Viewed "${title}" on ShareDoc`
}
},
{ headers: { Authorization: `Bearer ${HUBSPOT_TOKEN}` } }
).catch(async (err) => {
// Contact exists — update instead
if (err.response?.status === 409) {
const contactId = err.response.data.message.match(/ID: (\d+)/)?.[1];
if (contactId) {
await axios.patch(
`https://api.hubapi.com/crm/v3/objects/contacts/${contactId}`,
{ properties: { notes_last_contacted: `Viewed "${title}" on ShareDoc` } },
{ headers: { Authorization: `Bearer ${HUBSPOT_TOKEN}` } }
);
}
}
});
}
if (event === 'document.completed') {
const viewer = data.viewer;
if (viewer.email) {
// Search for contact by email, then log a note
const search = await axios.post(
'https://api.hubapi.com/crm/v3/objects/contacts/search',
{ filterGroups: [{ filters: [{ propertyName: 'email', operator: 'EQ', value: viewer.email }] }] },
{ headers: { Authorization: `Bearer ${HUBSPOT_TOKEN}` } }
);
if (search.data.total > 0) {
const contactId = search.data.results[0].id;
await axios.post(
'https://api.hubapi.com/crm/v3/objects/notes',
{
properties: {
hs_note_body: `Read 100% of "${data.document.title}" on ShareDoc (${viewer.time_spent_seconds}s)`,
hs_timestamp: new Date().toISOString()
},
associations: [{ to: { id: contactId }, types: [{ associationCategory: 'HUBSPOT_DEFINED', associationTypeId: 202 }] }]
},
{ headers: { Authorization: `Bearer ${HUBSPOT_TOKEN}` } }
);
}
}
}
res.send('ok');
});
app.listen(3000);
curl -X POST https://sharedoc.co/api/v1/webhooks \
-H "Authorization: Bearer bd_live_your_key_here" \
-H "Content-Type: application/json" \
-d '{"url": "https://your-server.com/webhook", "events": ["lead.captured", "document.completed"]}'
Zapier (No-Code)
Connect ShareDoc to 5,000+ apps without writing code. Works with Slack, Google Sheets, HubSpot, Notion, email, and more.
For the trigger, choose Webhooks by Zapier → Catch Hook. Zapier gives you a URL like https://hooks.zapier.com/hooks/catch/123/abc/
curl -X POST https://sharedoc.co/api/v1/webhooks \
-H "Authorization: Bearer bd_live_your_key_here" \
-H "Content-Type: application/json" \
-d '{"url": "https://hooks.zapier.com/hooks/catch/123/abc/", "events": ["lead.captured"]}'
curl -X POST https://sharedoc.co/api/v1/webhooks/test \
-H "Authorization: Bearer bd_live_your_key_here"
Go back to Zapier and click "Test trigger" — it should find the test event.
Now add what happens when a webhook fires. Popular combos:
data.lead.email, data.lead.company_domain, data.document.title to sheet columnsdata.lead.email and data.document.titledata.lead.email and data.lead.company_domain as companyevent = document.completedn8n (Self-Hosted)
Build automations on your own infrastructure. Same concept as Zapier, but open-source and self-hosted.
In n8n, create a new workflow. Add a Webhook trigger node. Set HTTP Method to POST. Copy the production webhook URL (e.g. https://your-n8n.com/webhook/sharedoc).
curl -X POST https://sharedoc.co/api/v1/webhooks \
-H "Authorization: Bearer bd_live_your_key_here" \
-H "Content-Type: application/json" \
-d '{"url": "https://your-n8n.com/webhook/sharedoc"}'
Route by {{ $json.event }}:
lead.captured → Google Sheets node / CRM nodedocument.viewed → Slack nodedocument.completed → Email node (follow-up reminder)viewer.revisited → Slack node (hot lead alert)All webhook data is under {{ $json.data }}. Key fields:
{{ $json.data.document.title }} → Document name
{{ $json.data.lead.email }} → Lead email
{{ $json.data.lead.company_domain }} → Company
{{ $json.data.viewer.completion }} → How much they read (0-1)
{{ $json.data.viewer.visit_number }} → Which visit this is
Common Patterns
Useful patterns that work with any integration platform.
Daily digest: email a summary of yesterday's engagement
Use a cron job (or Zapier Schedule) to poll the portfolio analytics endpoint once a day:
# Get yesterday's stats
curl "https://sharedoc.co/api/v1/analytics/overview?since=2026-04-08&until=2026-04-08" \
-H "Authorization: Bearer bd_live_your_key_here"
# Response includes total views, new leads, top docs —
# format it into an email or Slack digest
Prioritize follow-ups: find who's most engaged
Use the viewers endpoint to rank prospects by engagement:
# Get per-viewer engagement for your investor deck
curl https://sharedoc.co/api/v1/documents/s-ab12cd/viewers \
-H "Authorization: Bearer bd_live_your_key_here"
# Viewers are sorted by engagement (most engaged first)
# Use completion + visits to prioritize who to call next
Find your hottest content
# List only high-interest documents, sorted by views
curl "https://sharedoc.co/api/v1/documents?engagement=high_interest&sort=views" \
-H "Authorization: Bearer bd_live_your_key_here"