AMAZING! Thank you so much! That worked! I will leave the code below for anyone that finds this in the future. Thank you so much Hannah!
/*****************************************************************************************************
Name: Same Table Back Links
Date: July 9, 2021
Author: Kuovonne Vorderbruggen
Website: https://atmosphere.kuovonne.com
Description
Create backlinks for a table with same-table linked records
Usage
- Copy and paste this script into Scripting App.
- Click the “settings gear” for Scripting app and set the table and fields. No code changes necessary.
- Click the “run” button for the script.
license
This script is provided “as is”, without warranty of any kind. Liability of the
author will be limited to a maximum of the original purchase price of the script.
The author will not be liable for any general, special, incidental, or consequential
damages.
*/
/*******************************************************************************
Script Configuration Settings
*/
const inputConfig = input.config({
title: ‘Create back links for same-table links’,
items: [
input.config.table(‘table’, {
label: ‘Table with same-table links’,
}),
input.config.field(‘fldLinkAuthority’, {
label: ‘Original Link’,
description: ‘This linked record field is the “source of truth” for links. Its values will not be changed.’,
parentTable: ‘table’,
}),
input.config.field(‘fldBackLink’, {
label: ‘Back Link field’,
description: ‘This linked record field will be updated to match information in the original link field.’,
parentTable: ‘table’,
}),
]
});
/*******************************************************************************
Main function for the script
*/
await main()
output.markdown("## Done")
/*******************************************************************************/
async function main() {
if (!checkSettings()) { return }
const userContinue = await input.buttonsAsync(Update backlinks in ${inputConfig.table.name}?
, [“Continue”, “Cancel”])
if (userContinue == “Cancel”) {
return
}
const queryResult = await inputConfig.table.selectRecordsAsync({fields: [
inputConfig.fldLinkAuthority,
inputConfig.fldBackLink,
]})
output.markdown(Records to examine: ${queryResult.records.length}
)
// setup map of backlinks by recordId
let linkMap = {}
for (const record of queryResult.records) {
const currentBacklinks = record.getCellValue(inputConfig.fldBackLink)
linkMap[record.id] = {
currentBacklinkIds: (currentBacklinks ? currentBacklinks.map(obj => obj.id) : ),
newBacklinkIds: , // to be filled in later in script
}
}
// fill in newBacklinkIds
for (const record of queryResult.records) {
const linkedValue = record.getCellValue(inputConfig.fldLinkAuthority)
if (!linkedValue) {continue}
for (const obj of linkedValue) {
linkMap[obj.id].newBacklinkIds.push(record.id)
}
}
// figure out which records need updating
let recordsToUpdate =
for (const recordId of Object.keys(linkMap)) {
const currentBacklinkIds = linkMap[recordId].currentBacklinkIds
const newBacklinkIds = linkMap[recordId].newBacklinkIds
if ( (currentBacklinkIds.length == newBacklinkIds.length) && currentBacklinkIds.every(value => newBacklinkIds.includes(value))) {
continue // this recordId doesn’t need updating
}
recordsToUpdate.push({
id: recordId,
fields: {
[inputConfig.fldBackLink.name]: newBacklinkIds.map(id => ({id: id}))
}
})
}
output.markdown(Records to update: ${recordsToUpdate.length}
)
while (recordsToUpdate.length > 0) {
await inputConfig.table.updateRecordsAsync(recordsToUpdate.slice(0, 50));
recordsToUpdate = recordsToUpdate.slice(50);
}
}
/*******************************************************************************/
function checkSettings() {
if (
(inputConfig.fldLinkAuthority.type != “multipleRecordLinks”)
|| (inputConfig.fldBackLink.type != “multipleRecordLinks”)
|| (inputConfig.fldLinkAuthority.options.linkedTableId != inputConfig.table.id)
|| (inputConfig.fldBackLink.options.linkedTableId != inputConfig.table.id)
|| (inputConfig.fldBackLink.id == inputConfig.fldLinkAuthority.id)
) {
output.markdown(“Check fields in settings.”)
return false
}
return true
}
/*******************************************************************************
END OF SCRIPT
*/