I have a module called util
with the methods getMutedColor
and some others. getMutedColor
relies on another called rand
in the same module.
page.includeJs('https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.10/d3.min.js', function() {
var util = require('./util');
var svg = page.evaluate(pageContext.pageExec, data, meta, util);
/** ... **/
}
I can call util.getMutedColor()
just fine within this scope but in my pageContext.pageExec
function, util.getMutedColor
no longer exists. The util
parameter is still an object, but I cannot call any of the exported methods:
TypeError: 'undefined' is not a function (evaluating 'util.getMutedColor()')
Is there a way to pass a self-contained module to a page?
No, it is not really possible. As seen in the docs:
The function that you pass to evaluate must be self-contained and the data that you pass cannot contain functions or objects that are created with
new
. Those are stripped.This means that you must copy the
util
object completely into thepageExec
function.If
util
is too big to copy or if you use multiple functions ofutil
, you can try different things:Serialize the functions and pass them as strings to the evaluate callback where you would instantiate them with
new Function(string)
and bind them to theutil
object.and inside of
pageContext.pageExec
:Have only a single
pageContext
function which contains everything and you can use aswitch case
with a parameter that is passed every time toevaluate
to select the proper function inside of the singlepageContext
function.Use
page.injectJs
to inject the utils. It would be necessary to namespace the utils in by checking ifwindow
is present with something like that:Probably there are better scripts out there to do this depending on the environment.