Skip to main content

Is it possible to embed a calendar view in an automated email?

I don't know if this will match your use case, but you can use this script in automation to output calendar HTML.

Code:

const { month, year, recordIds } = input.config();



// Please specify the table name

const tableName = "table name";



// Caption format for year and month

const caption = `${year} / ${month}`;



// Whether to link to records true or false

const recordLink = true;



// URL up to tbl~ or viw~

const linkURL = "https://airtable.com/app~/tbl~/viw~";



// Common style

const style = "border:1px solid #ddd; padding:4px; width: 14.2857%; min-height:100px;";



function generateCalendar(year, month, records) {

const firstDay = new Date(year, month - 1, 1);

const lastDay = new Date(year, month, 0);

const daysInMonth = lastDay.getDate();



let calendarHTML = `<h3 style="text-align:center;">${caption}</h3><table>`;

calendarHTML += '<tr><th style="width: 14.2857%">Sun</th><th style="width: 14.2857%">Mon</th><th style="width: 14.2857%">Tue</th><th style="width: 14.2857%">Wed</th><th style="width: 14.2857%">thu</th><th style="width: 14.2857%">Fri</th><th style="width: 14.2857%">Sat</th></tr>';

calendarHTML += '';



let dayCounter = 1;

for (let i = 0; i < 6; i++) {

calendarHTML += '<tr>';

let bgColor = "#ffffff";

for (let j = 0; j < 7; j++) {

if (j === 0 || j === 6) {

bgColor = "#efefef";

} else {

bgColor = "#ffffff";

}

if (i === 0 && j < firstDay.getDay()) {

// Empty cells before the first day of the month

calendarHTML += `<td style="${style} background-color:${bgColor};"></td>`;

} else if (dayCounter <= daysInMonth) {

const cellDate = new Date(year, month - 1, dayCounter);

const matchingRecords = records.filter(record => {

const recordDate = new Date(record.date);

return cellDate.toISOString().split('T')[0] === recordDate.toISOString().split('T')[0];

});



const cellContent = matchingRecords.map(record => {

let content = '<span style="display: inline-block; height: 100%; overflow: hidden; text-overflow: clip; border:1px solid #ddd;">';

if(recordLink === true){

content += `<a href="${linkURL}/${record.id}?blocks=hide&date=${record.date}&mode=month">${record.name}</a></span><br>`;

} else {

content += `${record.name}</span><br>`;

}

return content;

});

calendarHTML += `<td style="${style} background-color:${bgColor};">${dayCounter}<br>`;

calendarHTML += cellContent.join(``);

calendarHTML += "</td>";

dayCounter++;

} else {

calendarHTML += `<td style="${style} background-color:${bgColor};"></td>`; // Empty cells after the last day of the month

}

}

calendarHTML += '</tr>';

}



calendarHTML += '</table>';

return calendarHTML;

}



const genYear = parseInt(year, 10);

const genMonth = parseInt(month, 10);



// Filtering by specified year and month

const queryRecords = await base.getTable(tableName).selectRecordsAsync({

recordIds: recordIds

});

let records = queryRecords.records.map(record => {

let name = record.getCellValueAsString("Name");

let date = record.getCellValue("Date");

return {name: name, date: date, id:record.id};

})

const calendarHTML = generateCalendar(genYear, genMonth, records);



// Setting the generated HTML to the 'Calendar' field

output.set('Calendar', calendarHTML);

Automation is set up like this:

Preview:


Reply