Skip to content

Instantly share code, notes, and snippets.

@kentcdodds
Created August 9, 2021 20:34
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save kentcdodds/504d57d0ef110f651499a6b24dabd718 to your computer and use it in GitHub Desktop.
Save kentcdodds/504d57d0ef110f651499a6b24dabd718 to your computer and use it in GitHub Desktop.
Tag subscribers of a ConvertKit sequence with a tag
const fetch = require('make-fetch-happen').defaults({
cacheManager: './node_modules/.cache/make-fetch-happen',
})
// add a .env file that has this in it:
// CONVERT_KIT_API_KEY=some_api_key
// CONVERT_KIT_API_SECRET=some_api_secret
require('dotenv').config()
const {CONVERT_KIT_API_KEY, CONVERT_KIT_API_SECRET} = process.env
async function addTag(email) {
return fetch(`https://api.convertkit.com/v3/tags/2551512/subscribe`, {
method: 'POST',
headers: {'content-type': 'application/json'},
body: JSON.stringify({
api_key: CONVERT_KIT_API_KEY,
api_secret: CONVERT_KIT_API_SECRET,
email,
}),
}).then(r => r.json())
}
async function getConvertKitSequencePage(sequenceId, page) {
const url = new URL(
`https://api.convertkit.com/v3/sequences/${sequenceId}/subscriptions`,
)
url.searchParams.set('api_secret', CONVERT_KIT_API_SECRET)
url.searchParams.set('subscriber_state', 'active')
url.searchParams.set('page', page.toString())
const resp = await fetch(url.toString())
const json = await resp.json()
return json
}
let page = 1
let totalPages = 2
const allSubscribers = []
async function updateSequenceSubs() {
const newsletterSequenceId = '372244'
while (page < totalPages) {
// eslint-disable-next-line no-await-in-loop
const result = await getConvertKitSequencePage(newsletterSequenceId, page)
const subs = result.subscriptions.map(s => s.subscriber)
for (const sub of subs) {
allSubscribers.push(sub)
await addTag(sub.email_address)
}
totalPages = result.total_pages
page = result.page + 1
console.log({
totalPages,
page,
totalSubscriptions: result.total_subscriptions,
subsSoFar: allSubscribers.length,
})
}
}
function makeGo() {
updateSequenceSubs().then(
() => {
console.log('All done')
},
error => {
if (error.stack?.includes?.('Unexpected token R in JSON at position 0')) {
console.log('rate limited... wait a minute then continue.')
setTimeout(() => {
makeGo()
}, 61 * 1000)
}
console.error(error.stack)
},
)
}
makeGo()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment