/** * Roboliq: Automation for liquid-handling robots * @copyright 2017, ETH Zurich, Ellis Whitehead * @license GPL-3.0 */ /** * Module for Evoware commands. * In order to use Evoware commands in Roboliq, you'll need to calls these * functions in your robot configuration file. * @module */ import _ from 'lodash'; import commandHelper from 'roboliq-processor/dist/commandHelper.js'; import expect from 'roboliq-processor/dist/expect.js'; import yaml from 'yamljs'; /** * Create an instruction for Evoware execute an external command. * @static * @param {string} agentName - Agent identifier * @param {string} path - path to command to execute * @param {array} args - array of arguments to pass * @param {boolean} wait - true if evoware should wait for the command to complete execution * @return {object} an object representing an Evoware 'Execute' instruction. */ function makeEvowareExecute(agentName, path, args, wait) { return { command: "evoware._execute", agent: agentName, path, args, wait }; } /** * Create an instruction for Evoware FACTS. * @static * @param {object} parsed - parsed object of command parameters * @param {object} data - protocol data * @param {string} variable [description] * @param {any} [value] - optional value; if value is a function, it will be called with the parameters (parsed, data). * @param {string} labwareName - labware used in this command * @return {object} an object representing an Evoware 'FACTS' instruction. */ function makeEvowareFacts(parsed, data, variable, value, labwareName) { const equipmentId = commandHelper.getParsedValue(parsed, data, "equipment", "evowareId"); const result2 = { command: "evoware._facts", agent: parsed.objectName.agent, factsEquipment: equipmentId, factsVariable: equipmentId+"_"+variable }; const value2 = (_.isFunction(value)) ? value(parsed, data) : value; return _.merge(result2, {factsValue: value2, labware: labwareName}); } /** * Create the predictates to be added to Roboliq's robot * configuration for Evoware's site/model relationships. * * Expect spec of this form: * ``{siteModel: string, sites: [string], labwareModels: [string]}`` * @static */ function makeSiteModelPredicates(spec) { return _.flatten([ {isSiteModel: {model: spec.siteModel}}, _.map(spec.sites, site => ({siteModel: {site, siteModel: spec.siteModel}})), _.map(spec.labwareModels, labwareModel => ({stackable: {below: spec.siteModel, above: labwareModel}})) ]); } /** * Create the predictates to be added to Roboliq's robot * configuration for Evoware's RoMa relationships. * * Expect specs of this form: * ``{<transporter>: {<program>: [site names]}}`` * @static */ function makeTransporterPredicates(namespaceName, agentName, specs) { let siteCliqueId = 1; const l = []; _.forEach(specs, (programs, equipment) => { _.forEach(programs, (cliques, program) => { _.forEach(cliques, (sites) => { const siteClique = `${namespaceName}.${agentName}.siteClique${siteCliqueId}`; siteCliqueId++; _.forEach(sites, site => { l.push({"siteCliqueSite": {siteClique, site}}); }); l.push({ "transporter.canAgentEquipmentProgramSites": { "agent": agentName, equipment, program, siteClique } }); }); }); }); return l; } module.exports = { makeEvowareExecute, makeEvowareFacts, makeSiteModelPredicates, makeTransporterPredicates, /** * objectToPredicateConverters for Evoware */ objectToPredicateConverters: { "EvowareRobot": function(name) { return [{ "isAgent": { "agent": name } }]; } }, /** * Returns the schemas for Evoware commands and objects. * @return {object} map from name to schema */ getSchemas: () => yaml.load(__dirname+"/../schemas/commands/evoware.yaml"), /** * Return command handlers for low-level evoware instructions. * @return {object} map from instruction name to handler. */ getCommandHandlers: () => ({ "evoware._execute": function(params, parsed, data) {}, "evoware._facts": function(params, parsed, data) {}, "evoware._raw": function(params, parsed, data) {}, "evoware._subroutine": function(params, parsed, data) {}, "evoware._userPrompt": function(params, parsed, data) {}, }), };