-
Notifications
You must be signed in to change notification settings - Fork 29
/
agent.js
155 lines (124 loc) · 3.4 KB
/
agent.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
/**
* @author Rafael Vidaurre
* @requires Utils
* @requires TaskDefinition
* @module Agent
*/
'use strict';
var _, utils, TaskDefinition;
_ = require('lodash');
utils = require('./utils');
TaskDefinition = require('./task-definition');
/**
* @class
* @param {string} id Arbitrary value which identifies an agent instance
*/
function Agent (id) {
/**
* Determines wether the agent's config has been applied or not
*/
this.__applied = false;
/**
* Agent's configuration object (set by running all configCallback functions)
* @private
*/
this.__config = {
plan: []
};
/**
* Set of task instances for this agent
*/
this._taskDefinitions = {};
/**
* Routines defined at agent-level, these override scraper-level routines
*/
this._routines = {};
/**
* Formatted execution plan created based on the agent's config object
*/
this._plan = null;
/**
* Id by which an agent is identified
*/
this.id = id;
}
/**
* Turns every element in the execution plan into an array for type consistency
* @private
*/
Agent.prototype.__formatPlan = function () {
var _this, formattedPlan, currentGroup, formattedGroup, formattedTaskObj;
_this = this;
formattedPlan = [];
if (_this.__config.plan.length <= 0) {
throw new Error('Agent ' + _this.id + ' has no execution plan, use the agent\'s plan method' +
' to define it');
}
// Turn each tier into an array
_.each(this.__config.plan, function (taskGroup) {
currentGroup = _.isArray(taskGroup) ? taskGroup : [taskGroup];
formattedGroup = [];
// Turn each element in the array into an object
_.each(currentGroup, function (taskObj) {
formattedTaskObj = {};
if (_.isString(taskObj)) {
formattedTaskObj.taskId = taskObj;
} else {
formattedTaskObj = taskObj;
}
formattedGroup.push(formattedTaskObj);
});
formattedPlan.push(formattedGroup);
});
this._plan = formattedPlan;
};
/**
* Applies all necessary processes regarding the setup stage of the agent
*/
Agent.prototype._applySetup = function () {
if (this.__applied) {
return;
}
this.__formatPlan();
this.__applied = true;
};
/**
* Sets the task's execution plan
* @param {Array} executionPlan array representing the execution plan for this agent
*/
Agent.prototype.plan = function (executionPlan) {
// TODO: Validate execution plan format right away
if (!_.isArray(executionPlan)) {
throw new Error('Agent plan must be an array of task ids');
}
this.__config.plan = executionPlan;
return this;
};
/**
* Creates or retrieves a task for a given task id
* @param {string} taskId id which identifies the task
* @private
* @return {TaskDefinition}
*/
Agent.prototype.task = function (taskId) {
if (!utils.hasKey(this._taskDefinitions, taskId)) {
this._taskDefinitions[taskId] = new TaskDefinition(taskId);
}
return this._taskDefinitions[taskId];
};
/**
* Creates an agent-wide routine which will be available for all agents
* @param {string} routineName name of the routine
* @param {array} array of taskIds which the routine will include
*/
Agent.prototype.routine = function (routineName, taskIds) {
if (!_.isArray(taskIds)) {
throw new Error('An array of task Ids must be passed to the routine method');
}
if (!_.isString(routineName)) {
throw new Error('Routine name must be a string');
}
this._routines[routineName] = taskIds;
return this;
};
module.exports = Agent;