forked from tableau/wdclib
-
Notifications
You must be signed in to change notification settings - Fork 1
/
Shared.js
156 lines (124 loc) · 5.46 KB
/
Shared.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
156
var Table = require('./Table.js');
var Enums = require('./Enums.js');
/** @class This class represents the shared parts of the javascript
* library which do not have any dependence on whether we are running in
* the simulator, in Tableau, or anywhere else
* @param tableauApiObj {Object} - The already created tableau API object (usually window.tableau)
* @param privateApiObj {Object} - The already created private API object (usually window._tableau)
* @param globalObj {Object} - The global object to attach things to (usually window)
*/
function Shared (tableauApiObj, privateApiObj, globalObj) {
this.privateApiObj = privateApiObj;
this.globalObj = globalObj;
this._hasAlreadyThrownErrorSoDontThrowAgain = false;
this.changeTableauApiObj(tableauApiObj);
}
Shared.prototype.init = function() {
console.log("Initializing shared WDC");
this.globalObj.onerror = this._errorHandler.bind(this);
// Initialize the functions which will be invoked by the native code
this._initTriggerFunctions();
// Assign the deprecated functions which aren't availible in this version of the API
this._initDeprecatedFunctions();
}
Shared.prototype.changeTableauApiObj = function(tableauApiObj) {
this.tableauApiObj = tableauApiObj;
// Assign our make & register functions right away because a connector can use
// them immediately, even before bootstrapping has completed
this.tableauApiObj.makeConnector = this._makeConnector.bind(this);
this.tableauApiObj.registerConnector = this._registerConnector.bind(this);
Enums.apply(this.tableauApiObj);
}
Shared.prototype._errorHandler = function(message, file, line, column, errorObj) {
console.error(errorObj); // print error for debugging in the browser
if (this._hasAlreadyThrownErrorSoDontThrowAgain) {
return true;
}
var msg = message;
if(errorObj) {
msg += " stack:" + errorObj.stack;
} else {
msg += " file: " + file;
msg += " line: " + line;
}
if (this.tableauApiObj && this.tableauApiObj.abortWithError) {
this.tableauApiObj.abortWithError(msg);
} else {
throw msg;
}
this._hasAlreadyThrownErrorSoDontThrowAgain = true;
return true;
}
Shared.prototype._makeConnector = function() {
var defaultImpls = {
init: function(cb) { cb(); },
shutdown: function(cb) { cb(); }
};
return defaultImpls;
}
Shared.prototype._registerConnector = function (wdc) {
// do some error checking on the wdc
var functionNames = ["init", "shutdown", "getSchema", "getData"];
for (var ii = functionNames.length - 1; ii >= 0; ii--) {
if (typeof(wdc[functionNames[ii]]) !== "function") {
throw "The connector did not define the required function: " + functionNames[ii];
}
};
console.log("Connector registered");
this.globalObj._wdc = wdc;
this._wdc = wdc;
}
Shared.prototype._initTriggerFunctions = function() {
this.privateApiObj.triggerInitialization = this._triggerInitialization.bind(this);
this.privateApiObj.triggerSchemaGathering = this._triggerSchemaGathering.bind(this);
this.privateApiObj.triggerDataGathering = this._triggerDataGathering.bind(this);
this.privateApiObj.triggerShutdown = this._triggerShutdown.bind(this);
}
// Starts the WDC
Shared.prototype._triggerInitialization = function() {
this._wdc.init(this.privateApiObj._initCallback);
}
// Starts the schema gathering process
Shared.prototype._triggerSchemaGathering = function() {
this._wdc.getSchema(this.privateApiObj._schemaCallback);
}
// Starts the data gathering process
Shared.prototype._triggerDataGathering = function(tablesAndIncrementValues) {
if (tablesAndIncrementValues.length != 1) {
throw ("Unexpected number of tables specified. Expected 1, actual " + tablesAndIncrementValues.length.toString());
}
var tableAndIncremntValue = tablesAndIncrementValues[0];
var isJoinFiltered = !!tableAndIncremntValue.filterColumnId;
var table = new Table(
tableAndIncremntValue.tableInfo,
tableAndIncremntValue.incrementValue,
isJoinFiltered,
tableAndIncremntValue.filterColumnId || '',
tableAndIncremntValue.filterValues || [],
this.privateApiObj._tableDataCallback);
this._wdc.getData(table, this.privateApiObj._dataDoneCallback);
}
// Tells the WDC it's time to shut down
Shared.prototype._triggerShutdown = function() {
this._wdc.shutdown(this.privateApiObj._shutdownCallback);
}
// Initializes a series of global callbacks which have been deprecated in version 2.0.0
Shared.prototype._initDeprecatedFunctions = function() {
this.tableauApiObj.initCallback = this._initCallback.bind(this);
this.tableauApiObj.headersCallback = this._headersCallback.bind(this);
this.tableauApiObj.dataCallback = this._dataCallback.bind(this);
this.tableauApiObj.shutdownCallback = this._shutdownCallback.bind(this);
}
Shared.prototype._initCallback = function () {
this.tableauApiObj.abortWithError("tableau.initCallback has been deprecated in version 2.0.0. Please use the callback function passed to init");
};
Shared.prototype._headersCallback = function (fieldNames, types) {
this.tableauApiObj.abortWithError("tableau.headersCallback has been deprecated in version 2.0.0");
};
Shared.prototype._dataCallback = function (data, lastRecordToken, moreData) {
this.tableauApiObj.abortWithError("tableau.dataCallback has been deprecated in version 2.0.0");
};
Shared.prototype._shutdownCallback = function () {
this.tableauApiObj.abortWithError("tableau.shutdownCallback has been deprecated in version 2.0.0. Please use the callback function passed to shutdown");
};
module.exports = Shared;