BambooHR technical integration
Connect BambooHR to Tallyfy and your HR events can start the right process on their own. Hire someone, and Tallyfy kicks off an onboarding run. Change their job, and it starts a role-change run. When they leave, it handles offboarding. Tallyfy pulls the person’s details straight from BambooHR, so no one re-types names, emails, or start dates. (For the plain overview, see the BambooHR integration page.)
You can set this up three ways: have your system call BambooHR’s API directly, listen for BambooHR’s webhooks1, or check for changes on a schedule. Rather not write code? No-code tools like Zapier, Make, Merge, and Finch can connect the two for you.
(Skip this unless you’re setting up the technical side.)
Fetch employee data from BambooHR, then launch a Tallyfy process with that data:
const handleBambooHREmployee = async (employeeId) => { // Fetch employee from BambooHR const employee = await fetch( `https://api.bamboohr.com/api/gateway.php/${subdomain}/v1/employees/${employeeId}`, { headers: { 'Authorization': `Basic ${Buffer.from(apiKey + ':x').toString('base64')}`, 'Accept': 'application/json' } } ).then(res => res.json());
// Launch a Tallyfy process (run) for this employee const run = await fetch( `https://go.tallyfy.com/api/organizations/${orgId}/runs`, { method: 'POST', headers: { 'Authorization': 'Bearer YOUR_TALLYFY_TOKEN', 'X-Tallyfy-Client': 'APIClient', 'Content-Type': 'application/json' }, body: JSON.stringify({ checklist_id: 'your_onboarding_template_id', name: `Onboarding - ${employee.firstName} ${employee.lastName}`, data: { employee_id: employee.id, full_name: `${employee.firstName} ${employee.lastName}`, email: employee.workEmail, department: employee.department, location: employee.location, job_title: employee.jobTitle, manager: employee.supervisor, start_date: employee.hireDate } }) } );
return run.json();};BambooHR webhooks use SHA-256 HMAC signatures. You’ll need to verify every incoming request before processing it:
const express = require('express');const crypto = require('crypto');const app = express();
app.post('/bamboohr-webhook', express.raw({ type: '*/*' }), async (req, res) => { const signature = req.headers['x-bamboohr-signature']; const expected = crypto .createHmac('sha256', process.env.BAMBOOHR_WEBHOOK_SECRET) .update(req.body) .digest('hex');
if (signature !== expected) { return res.status(401).send('Invalid signature'); }
const { type, employees } = JSON.parse(req.body);
for (const employeeId of employees) { switch (type) { case 'employee': await launchOnboardingWorkflow(employeeId); break; case 'job_information': await launchRoleChangeWorkflow(employeeId); break; case 'employment_status': await handleStatusChange(employeeId); break; } }
res.status(200).send('OK');});If your system can’t receive webhooks, BambooHR supports change reports you can poll on a schedule:
const pollBambooHRChanges = async () => { const since = new Date(Date.now() - 24 * 60 * 60 * 1000).toISOString();
const changes = await fetch( `https://api.bamboohr.com/api/gateway.php/${subdomain}/v1/employees/changed?since=${since}`, { headers: { 'Authorization': `Basic ${Buffer.from(apiKey + ':x').toString('base64')}`, 'Accept': 'application/json' } } ).then(res => res.json());
for (const employee of changes.employees) { await processEmployeeChange(employee.id, employee.action); }};Common BambooHR fields mapped to Tallyfy form field variables:
| BambooHR field | Tallyfy variable | Notes |
|---|---|---|
id | employee_id | Record ID |
firstName + lastName | full_name | Combined name |
workEmail | email | Work email |
department | department | Department |
division | division | Division |
location | location | Work location |
jobTitle | job_title | Title |
supervisor | manager | Direct manager name |
supervisorEmail | manager_email | Manager’s email |
hireDate | start_date | Hire date |
employmentHistoryStatus | status | Employment status |
BambooHR uses HTTP Basic auth - the API key is the username and x is the password:
const getBambooHRHeaders = () => ({ 'Authorization': `Basic ${Buffer.from(process.env.BAMBOOHR_API_KEY + ':x').toString('base64')}`, 'Accept': 'application/json'});BambooHR webhooks can fire on these field changes:
- Employee created - new employee added
- Job information - title, department, or location changed
- Employment status - active, terminated, or on leave
- Compensation - salary or pay rate changed
- Time off - requests or balances changed
If you’d rather not build a direct API integration:
- Merge API - unified HRIS API that includes BambooHR
- Finch - employment system API
- Zapier - pre-built BambooHR triggers and actions
- Make - visual workflow builder with a BambooHR connector
Paylocity > Paylocity technical integration
Open Api > API integration guide
Netsuite > NetSuite technical integration
-
Webhooks are automatic messages BambooHR sends to your system the moment something changes, so you don’t have to keep asking. ↩
Was this helpful?
- 2026 Tallyfy, Inc.
- Privacy Policy
- Terms of Use
- Report Issue
- Trademarks