Help

Re: converting an "await input.recordAsync" script to run automatically when record enters

778 0
cancel
Showing results for 
Search instead for 
Did you mean: 
Taylor_Johnston
6 - Interface Innovator
6 - Interface Innovator

Hi, all! 

Can anyone point me in the right direction for how to convert a script (made for me by someone else - I am not a programmer) to run in an automation? It is currently programmed to run via a button click in my base, but I would really like to be able to make it run when a record enters a view. 

I'm not sure if this modification is a simple one, or something that is going to involve reworking the entire script. 
Any advice, tips, or direction would be greatly appreciated! 😊

Here is the original script: 

 

let twoLettersToNumber = {
    "ah": 5,
    "ch": 8,
    "wh": 16,
    "tz": 18,
    "sh": 21,
    "ta": 22,
    "th": 22,
};

let lastLetterToNumber = {
    "m": 12,
    "p": 12,
};

let letterToNumber = {
    "a": 1,
    "b": 2,
    "c": 11,
    "d": 4,
    "e": 5,
    "f": 18,
    "g": 3,
    "h": 5,
    "i": 10,
    "j": 10,
    "k": 19,
    "l": 12,
    "m": 13,
    "n": 14,
    "o": 6,
    "p": 17,
    "q": 19,
    "r": 20,
    "s": 15,
    "t": 9,
    "u": 6,
    "v": 6,
    "w": 6,
    "x": 15,
    "y": 16,
    "z": 7,
};

/**
 * @param {string} token
 * @param {{ ah?: number; ch?: number; wh?: number; tz?: number; sh?: number; ta?: number; th?: number; a?: number; b?: number; c?: number; d?: number; e?: number; f?: number; g?: number; h?: number; i?: number; j?: number; k?: number; l?: number; m?: number; n?: number; o?: number; p?: number; q?: number; r?: number; s?: number; t?: number; u?: number; v?: number; w?: number; x?: number; y?: number; z?: number; }} dict
 * @param {number[]} arr
 */
function tryInsert(token, dict, arr) {
    if (token in dict) {
        arr.push(dict[token]);
        return true;
    }
    return false;
}

/**
 * @param {string} name
 */
function nameToNumbers(name) {
    var result = [];
    for (var current = 0; current < name.length;) {
        var token = name.substr(current, 2);
        if (token.length == 2) {
            if (tryInsert(token, twoLettersToNumber, result)) {
                current += 2;
            } else {
                token = name[current];
                if (tryInsert(token, letterToNumber, result)) {
                    current += 1;
                } else {
                    throw `Invalid character found: ${token}`
                }
            }
        } else {
            if (tryInsert(token, lastLetterToNumber, result)) {
                current += 1;
            } else {
                if (tryInsert(token, letterToNumber, result)) {
                    current += 1;
                } else {
                    throw `Invalid character found: ${token}`
                }
            }
        }
    }
    return result;
}

/**
 * @param {number[]} columns
 * @param {number[]} numbers
 * @param {number} colIndex
 */
function addToColumns(columns, numbers, colIndex) {
    for (let number of numbers) {
        columns[colIndex] += number;
        colIndex += 1;
        colIndex = colIndex % columns.length;
    }
    return colIndex;
}

/**
 * @param {number} number
 */
function sumDigits(number) {
    let total = 0;
    while (number) {
        total += number % 10;
        number = Math.floor(number / 10);
    }
    return total;
}

/**
 * @param {number} number
 * @param {{ (number: number): boolean }} predicate
 */
function reduceUntil(number, predicate) {
    while (predicate(number)) {
        number = sumDigits(number);
    }
    return number;
}

/**
 * @param {number} number
 */
let greaterThan22 = number => number > 22;

/**
 * @param {number} number
 */
let singleDigit = number => number > 9;

/**
 * @param {number} number
 * @param {number} firstNumberTotal
 * @param {number} secondNumberTotal
 */
function reduce(number, firstNumberTotal, secondNumberTotal) {
    number = reduceUntil(number, greaterThan22);
    let firstNumber = number;
    let secondNumber = reduceUntil(number, singleDigit);
    firstNumberTotal += firstNumber;
    secondNumberTotal += secondNumber;
    return { columnValue: `${firstNumber}-${secondNumber}`, fnt: firstNumberTotal, snt: secondNumberTotal };
}

function reduceColumns(columns) {
    var firstNumberTotal = 0;
    var secondNumberTotal = 0;
    for (var i = 0; i < columns.length; i++) {
        var { columnValue, fnt, snt } = reduce(columns[i], firstNumberTotal, secondNumberTotal);
        columns[i] = columnValue;
        firstNumberTotal = fnt;
        secondNumberTotal = snt;
    }
    firstNumberTotal = reduceUntil(firstNumberTotal, greaterThan22);
    secondNumberTotal = reduceUntil(secondNumberTotal, singleDigit);
    columns.push(`${firstNumberTotal}-${secondNumberTotal}`);
    return columns;
}


/**
 * @param {string} firstName
 * @param {string} middleName
 * @param {string} lastName
 */
function computeColumns(firstName, middleName, lastName) {
    if (!firstName && !middleName && !lastName) {
        throw "At least one of first name, middle name or last name should be given"
    }
    firstName = firstName ? firstName.toLowerCase() : "";
    middleName = middleName ? middleName.toLowerCase() : "";
    lastName = lastName ? lastName.toLowerCase() : "";

    var columns = [0, 0, 0, 0, 0, 0];
    var numbers = nameToNumbers(firstName);
    var colIndex = 0;
    colIndex = addToColumns(columns, numbers, colIndex);
    numbers = nameToNumbers(middleName);
    colIndex = addToColumns(columns, numbers, colIndex);
    numbers = nameToNumbers(lastName);
    colIndex = addToColumns(columns, numbers, colIndex);
    return reduceColumns(columns);
}

//--------------------Airtable specific code-----------------

let columnNames = ["PK", "SK", "PT", "ST", "PG", "SG", "SD"];

const config = input.config({
    title: 'Numerology Script',
    items: [
        input.config.table('namesTable', {
            label: 'Names table',
            description: 'The table in which you track names'
        }),
        input.config.field('firstNameField', {
            label: 'First name field',
            parentTable: 'namesTable',
        }),
        input.config.field('middleNameField', {
            label: 'Middle name field',
            parentTable: 'namesTable',
        }),
        input.config.field('lastNameField', {
            label: 'Last name field',
            parentTable: 'namesTable',
        }),
        input.config.field('pkField', {
            label: 'PK field',
            parentTable: 'namesTable',
        }),
        input.config.field('skField', {
            label: 'SK field',
            parentTable: 'namesTable',
        }),
        input.config.field('ptField', {
            label: 'PT field',
            parentTable: 'namesTable',
        }),
        input.config.field('stField', {
            label: 'ST field',
            parentTable: 'namesTable',
        }),
        input.config.field('pgField', {
            label: 'PG field',
            parentTable: 'namesTable',
        }),
        input.config.field('sgField', {
            label: 'SG field',
            parentTable: 'namesTable',
        }),
        input.config.field('sdField', {
            label: 'SD field',
            parentTable: 'namesTable',
        }),
        input.config.table('linkedTable', {
            label: 'Templates table',
            description: "The table which the names table's PK, SK, PT, ST, PG, SG and SD fields link to"
        }),
        input.config.field('linkedTableNameField', {
            label: 'Templates table attributes field',
            description: 'Templates table field containing the values 13-4, 5-5 etc.',
            parentTable: 'linkedTable',
        }),
        input.config.field('aspectField', {
            label: 'Templates table aspect field',
            description: 'Templates table field containing the values "Physical Karma", "Spiritual Karma" etc.',
            parentTable: 'linkedTable',
        }),
    ]
});

async function createLinkedRecordDict() {
    let dict = {};
    let query = await config.linkedTable.selectRecordsAsync({
        fields: [config.linkedTableNameField.name, config.aspectField.name]
    });
    for (let r of query.records) {
        let name = r.getCellValueAsString(config.linkedTableNameField.name);
        let aspect = r.getCellValueAsString(config.aspectField.name);
        var key = `${name}${aspect}`;
        key = key.trim();
        dict[key] = r.id;
    }
    return dict;
}

let dict = await createLinkedRecordDict();

function findLinkedRecordId(attribute, aspect) {
    var key = `${attribute}${aspect}`;
    return dict[key];
}

let record = await input.recordAsync('Pick a record', config.namesTable);
if (record) {
    let firstName = record.getCellValueAsString(config.firstNameField.name);
    let middleName = record.getCellValueAsString(config.middleNameField.name);
    let lastName = record.getCellValueAsString(config.lastNameField.name);
    let columns = computeColumns(firstName, middleName, lastName);

    var error = false;
    let pkLinkedRecordId = findLinkedRecordId(columns[0], 'Physical Karma');
    if (!pkLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[0]} and aspect Physical Karma in ${config.linkedTable.name} table`);
        error = true;
    }
    let skLinkedRecordId = findLinkedRecordId(columns[1], 'Spiritual Karma');
    if (!skLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[1]} and aspect Spiritual Karma in ${config.linkedTable.name} table`);
        error = true;
    }
    let ptLinkedRecordId = findLinkedRecordId(columns[2], 'Physical Talents');
    if (!ptLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[2]} and aspect Physical Talents in ${config.linkedTable.name} table`);
        error = true;
    }
    let stLinkedRecordId = findLinkedRecordId(columns[3], 'Spiritual Talents');
    if (!stLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[3]} and aspect Spiritual Talents in ${config.linkedTable.name} table`);
        error = true;
    }
    let pgLinkedRecordId = findLinkedRecordId(columns[4], 'Physical Goals');
    if (!pgLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[4]} and aspect Physical Goals in ${config.linkedTable.name} table`);
        error = true;
    }
    let sgLinkedRecordId = findLinkedRecordId(columns[5], 'Spiritual Goals');
    if (!sgLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[5]} and aspect Spiritual Goals in ${config.linkedTable.name} table`);
        error = true;
    }
    let sdLinkedRecordId = findLinkedRecordId(columns[6], 'Soul Destiny');
    if (!sdLinkedRecordId) {
        console.error(`Failed to find a record with name ${columns[6]} and aspect Soul Destiny in ${config.linkedTable.name} table`);
        error = true;
    }

    if (!error) {
        await config.namesTable.updateRecordAsync(record, {
            [config.pkField.name]: [{ id: pkLinkedRecordId }],
            [config.skField.name]: [{ id: skLinkedRecordId }],
            [config.ptField.name]: [{ id: ptLinkedRecordId }],
            [config.stField.name]: [{ id: stLinkedRecordId }],
            [config.pgField.name]: [{ id: pgLinkedRecordId }],
            [config.sgField.name]: [{ id: sgLinkedRecordId }],
            [config.sdField.name]: [{ id: sdLinkedRecordId }],
        });

        output.text(`Updated columns for ${firstName} ${middleName} ${lastName}`);
    }
} else {
    output.text('Please pick a record');
}

 

 
1 Reply 1

I recommend that you go back to the original author of the script and ask him or her to rework it to run from an automation. Because your script uses both script settings and output, several lines of code will need to change--every line with input.config and output.text. These are not difficult change for someone experienced with code who also understands the differences between scripting extension and an automation script.