Skip to main content

Automatically create RelayCam projects from Google Calendar Events

A one-time, 15-minute setup that turns new Google Calendar appointments into RelayCam projects, with the address filled in.

Written by Rhet Porter

What this does: when your office books an appointment in Google Calendar, RelayCam creates a project for it automatically, with the address already filled in. No more typing addresses twice.

You only set this up once, and it takes about 15 minutes. You don't need to be good with computers. You'll copy, paste and click a few buttons, and every step tells you exactly what to click.

Would you rather have help? Just message us and we'll do it with you on a quick call.

What you'll need

  • A computer (Windows or Mac). This can't be done on a phone or tablet.

  • The Google account your office books your appointments into. This is the Gmail address and password for that calendar.

  • Your RelayCam admin login.

  • About 15 minutes.

Part 1: Get your RelayCam connection key

RelayCam gives you a private connection key. It's called an "API key." Think of it like a spare house key: it lets your Google Calendar add projects to your RelayCam account.

Keep it private. Treat your key like a password and don't share it with anyone.

  1. Log in to RelayCam. On your computer, open your web browser (Chrome, Safari, Edge or Firefox) and go to web.relaycam.com.

  2. Open your menu. Click your name in the bottom-left corner of the screen. It says Personal Settings underneath.

  3. Go to Developer. A menu pops up. Click Developer.

    Don't see Developer? Only a company admin can create a key. Ask the person who manages your RelayCam account to do Part 1, or to make you an admin.

  4. Start a new key. Click the green New Secret API Key button in the top-right corner.

  5. Name it. A box pops up asking for a name. Type Google Calendar and click Create API Key.

  6. Find your key. Your new key appears in the list, with a green Copy button next to it. The key is a long string of letters and numbers starting with ck_.

    Leave this browser tab open. You'll come back to copy the key in Part 2.

Part 2: Set it up in Google

  1. Open Google's setup page. Open a new browser tab and go to script.google.com. If it asks you to sign in, use the Google account your office books your appointments into. If you see a page with a Start Scripting button, click it.

  2. Start a new project. Click the New project button in the top-left corner. A page opens with a large white typing area that already has a few lines of text in it.

    If small boxes pop up, such as one saying which account you're signed in as or one offering a tip, click OK or Got it to close them.

  3. Clear the white area. Click once anywhere inside the white area. Press the Ctrl and A keys together (on a Mac, Command and A). All the text turns highlighted. Press the Delete key. The white area is now empty.

  4. Copy the setup text. Scroll to the end of this article, to the gray box under The setup text to copy. Click just before the very first character in the box, hold down the Shift key, and click just after the very last character. Everything in the box turns highlighted. Press Ctrl and C together (on a Mac, Command and C).

  5. Paste it into Google. Go back to the Google tab. Click inside the empty white area and press Ctrl and V together (on a Mac, Command and V). The text appears.

  6. Copy your RelayCam key. Go to the RelayCam tab from Part 1 and click the green Copy button next to your key. If that doesn't work, highlight the key with your mouse and press Ctrl and C (on a Mac, Command and C).

  7. Put your key in. Go back to the Google tab. Near the top of the text, find this line:

    const RELAYCAM_API_KEY = 'PASTE_YOUR_API_KEY_HERE';

    Double-click the words PASTE_YOUR_API_KEY_HERE so they turn highlighted. Press Ctrl and V (on a Mac, Command and V). Your key replaces those words.

    Make sure the small quote marks are still on both sides of your key, like this example:

    const RELAYCAM_API_KEY = 'a1b2c3d4e5f6';

  8. Name it. At the very top of the page, click the words Untitled project. A box pops up. Type RelayCam Calendar Sync and click Rename.

  9. Save it. Click the Save button just above the white area. It's a small picture of a floppy disk. You can also press Ctrl and S (on a Mac, Command and S).

  10. Turn it on. Just above the white area there's a Run button, a Debug button, and next to them a box with a word in it. Make sure that box says setup. If it says something else, click it and choose setup from the list. Then click Run.

  11. Give Google permission. A box appears that says Authorization required. Click Review permissions, then click your Google account.

  12. Get past Google's warning. You'll probably see a screen that says Google hasn't verified this app. Click the small Advanced link at the bottom left, then click Go to RelayCam Calendar Sync (unsafe) at the bottom.

    This warning is normal and expected. Google shows it for any setup that hasn't been through Google's own review, and small setups like this one never are. It runs only inside your own Google account, and the email address it mentions is your own, because you're the one who set this up.

  13. Allow access. On the next screen, scroll down a little and click Select all if you see checkboxes. Then click Allow (on some screens the button says Continue).

    Google lists everything a setup like this could do with your calendar, so the wording sounds bigger than it is. This setup only reads new appointments. It never changes or deletes anything on your calendar.

  14. Check that it worked. A box called Execution log appears at the bottom of the page. Wait a few seconds. When you see a line that starts with All set!, you're finished. It also says how many appointments were already on your calendar and skipped; that's normal.

    If you see red text instead, see If something goes wrong below.

You can close the Google tab now. It keeps working on its own, even when your computer is turned off. You never need to open it again unless you want to turn it off.

Only run setup once. If you run setup again later, anything already on your calendar at that moment is skipped, including a test appointment you just made.

Part 3: Try it out

  1. Open your Google Calendar and create a new appointment for tomorrow.

  2. For the title, type Test RelayCam.

  3. In the Location box (it may say Add location), type your office address and pick it from the suggestions that pop up. Save the appointment.

  4. Wait 10 minutes, then open RelayCam. You should see a new project called Test RelayCam with your office address.

  5. Delete the test appointment from your calendar and the test project from RelayCam.

Don't want to wait 10 minutes? Go to the Google script page. Click the box next to the Run button and choose checkCalendar. Make sure the box says checkCalendar, not setup, then click Run. The Execution log at the bottom should say Created RelayCam project: followed by your appointment's title.

If you clicked Run while the box said setup by mistake, your test appointment was skipped. Just create a new test appointment and try again.

If the project still doesn't show up after 15 minutes, see If something goes wrong below.

What creates a new project

Every 10 minutes, the setup checks the main calendar of the Google account you used in Part 2. It creates a new RelayCam project for an appointment when all three of these are true:

  • It's new. It was added after you finished the setup.

  • It has an address in the Location box.

  • It's within the next 6 months.

Here's what goes into the project:

On the appointment

In the RelayCam project

Title

Project name

Location

Project address

Date, time and notes

Project description

These do not create or change a project:

  • Appointments that were already on your calendar before you did the setup.

  • Appointments with no address. If an address is added later, the project is created at the next check.

  • Editing an appointment after its project exists. Make the change in RelayCam too.

  • Deleting an appointment. The project stays in RelayCam; delete it there if you need to.

  • Appointments on other calendars, such as a shared team calendar.

  • A repeating appointment creates one project, not one for every visit.

Tips for whoever books your appointments: always fill in the Location box and pick the address from the suggestions that pop up. Use a clear title, like Smith – Roof Inspection, since it becomes the project name.

How to turn it off

  1. Go to script.google.com and sign in with the same Google account you used in Part 2.

  2. Click RelayCam Calendar Sync in your list of projects.

  3. Just above the white area, click the box next to the Run button (it probably says setup) and choose stop.

  4. Click Run. The Execution log at the bottom says Stopped.

No new projects are created after that. Projects that were already created stay in RelayCam.

To turn it back on, do the same steps but choose setup instead of stop. Appointments added while it was off won't become projects; only ones added after you turn it back on will.

If something goes wrong

What you see

What to do

Red text saying Paste your RelayCam API key at the top of the script

Your key wasn't put in. Do Part 2, steps 6 and 7 again, click Save, and click Run again.

Red text saying RelayCam did not accept the API key

The key was copied wrong. Do Part 2, steps 6 and 7 again, click Save, and click Run again.

You can't find the Advanced link on the permission screen

It's small and gray, at the bottom left of the box. Scroll down inside the box if you don't see it.

The test project doesn't show up after 15 minutes

Check the test appointment has an address in Location. If it does, message us and we'll take a look with you.

Anything else

Take a screenshot of what you see and send it to us. We'll sort it out.

The setup text to copy

This is the text for Part 2, step 4. Copy all of it, from the first line to the last. You don't need to understand it or change anything except your key in step 7.

// RelayCam Calendar Sync
// Turns new Google Calendar appointments into RelayCam projects.

// ===== STEP 1: PASTE YOUR RELAYCAM API KEY BETWEEN THE QUOTES =====
const RELAYCAM_API_KEY = 'PASTE_YOUR_API_KEY_HERE';

// ===== Optional settings (you can leave these alone) =====
const CALENDAR_ID = ''; // Leave blank to use your main calendar
const DAYS_AHEAD = 180; // How far ahead to look for appointments
const CHECK_EVERY_MINUTES = 10; // Must be 1, 5, 10, 15 or 30

// ===== Do not change anything below this line =====

const API_BASE = 'https://api.relaycam.com/v1';

// Run once to turn the sync on. Safe to run again.
function setup() {
if (!RELAYCAM_API_KEY || RELAYCAM_API_KEY === 'PASTE_YOUR_API_KEY_HERE') {
throw new Error('Paste your RelayCam API key at the top of the script, click Save, then run setup again.');
}
checkApiKey_();
removeTriggers_();

// Existing appointments are skipped so only new bookings become projects.
const props = PropertiesService.getScriptProperties();
const events = getUpcomingEvents_();
events.forEach(function (e) {
if (!props.getProperty(key_(e))) props.setProperty(key_(e), 'skipped');
});

ScriptApp.newTrigger('checkCalendar').timeBased().everyMinutes(CHECK_EVERY_MINUTES).create();
Logger.log('All set! ' + events.length + ' existing appointments were skipped. ' +
'New appointments with an address will become RelayCam projects within about ' +
CHECK_EVERY_MINUTES + ' minutes.');
}

// Run to turn the sync off.
function stop() {
removeTriggers_();
Logger.log('Stopped. New appointments will no longer create RelayCam projects.');
}

// Runs automatically every few minutes once setup is done.
function checkCalendar() {
const lock = LockService.getScriptLock();
if (!lock.tryLock(5000)) return; // another check is already running
try {
const props = PropertiesService.getScriptProperties();
const failures = [];
getUpcomingEvents_().forEach(function (e) {
const k = key_(e);
if (props.getProperty(k)) return; // already handled
const location = (e.getLocation() || '').trim();
if (!location) return; // no address yet; check again next time
const result = createProject_(e, location);
if (result.ok) {
props.setProperty(k, 'created');
} else {
failures.push(result.message);
}
});
if (failures.length) {
throw new Error('Some projects could not be created:\n' + failures.join('\n'));
}
} finally {
lock.releaseLock();
}
}

function getCalendar_() {
const cal = CALENDAR_ID ? CalendarApp.getCalendarById(CALENDAR_ID) : CalendarApp.getDefaultCalendar();
if (!cal) throw new Error('Calendar not found. Check CALENDAR_ID at the top of the script.');
return cal;
}

function getUpcomingEvents_() {
const now = Date.now();
const start = new Date(now - 24 * 60 * 60 * 1000);
const end = new Date(now + DAYS_AHEAD * 24 * 60 * 60 * 1000);
return getCalendar_().getEvents(start, end);
}

function key_(e) {
return 'event_' + e.getId();
}

function createProject_(e, location) {
const tz = getCalendar_().getTimeZone();
const when = e.isAllDayEvent()
? Utilities.formatDate(e.getAllDayStartDate(), tz, 'EEE, MMM d, yyyy') + ' (all day)'
: Utilities.formatDate(e.getStartTime(), tz, "EEE, MMM d, yyyy 'at' h:mm a");
const notes = cleanText_(e.getDescription());
const description = ['Appointment: ' + when, notes, 'Created from Google Calendar']
.filter(function (s) { return s; })
.join('\n\n');
const name = (e.getTitle() || '').trim() || location;

const body = {
name: name.slice(0, 200),
location: location.slice(0, 500),
description: description.slice(0, 5000)
};

const res = UrlFetchApp.fetch(API_BASE + '/projects', {
method: 'post',
contentType: 'application/json',
headers: { Authorization: 'Bearer ' + RELAYCAM_API_KEY },
payload: JSON.stringify(body),
muteHttpExceptions: true
});
const code = res.getResponseCode();
if (code === 200 || code === 201) {
Logger.log('Created RelayCam project: ' + body.name);
return { ok: true };
}
return { ok: false, message: '"' + body.name + '": error ' + code + ' ' + res.getContentText() };
}

function checkApiKey_() {
const res = UrlFetchApp.fetch(API_BASE + '/health', {
headers: { Authorization: 'Bearer ' + RELAYCAM_API_KEY },
muteHttpExceptions: true
});
const code = res.getResponseCode();
if (code === 401) {
throw new Error('RelayCam did not accept the API key. Copy it again, paste it at the top, click Save, and run setup again.');
}
if (code !== 200) {
throw new Error('Could not reach RelayCam (error ' + code + '). Try again in a few minutes.');
}
}

function removeTriggers_() {
ScriptApp.getProjectTriggers().forEach(function (t) {
if (t.getHandlerFunction() === 'checkCalendar') ScriptApp.deleteTrigger(t);
});
}

function cleanText_(text) {
return (text || '')
.replace(/<br\s*\/?>/gi, '\n')
.replace(/<\/p>/gi, '\n')
.replace(/<[^>]+>/g, '')
.replace(/&nbsp;/g, ' ')
.replace(/&amp;/g, '&')
.replace(/&lt;/g, '<')
.replace(/&gt;/g, '>')
.replace(/&quot;/g, '"')
.replace(/&#39;/g, "'")
.trim();
}
Did this answer your question?