James Blackburn
James Blackburn

Reputation: 616

Cannot call functions after running browserify

I have a an es6 JS class below which I am running through browserify to output in es5. Below is my es6 JS class:

import $j from "jquery";
import BaseComponent from './Components/base-component';

class QuestionnaireView extends BaseComponent {

constructor() {

    super();

    this.defaultOptions = {
        questionId : '#questionId',
        responseId : '#responseId',
        answerId : '#answerId',
        questionTextId : '#questionTextId'
    };

    this.state = {
    };
}

initChildren() {
}

addListeners() {
}

collectQuestions() {
    var questionAndAnswersDict = [];
    var answersAndWeightingsDict = [];
    
    $j(this.options.questionId).each(function () {
        var questionText = $j(this).find("input")[0].value;
        $j(this.options.answerId).each(function () {
            var answerText = $j(this).find("input")[0].value;
            var weighting = $j(this).find("input")[1].value;
            answersAndWeightingsDict.push({
                key: answerText,
                value: weighting
            });
        });
        questionAndAnswersDict.push({
            key: questionText,
            value: answersAndWeightingsDict
        });
    });
}

collectResponses() {
    var responsesDict = [];
    var weightingDict = [];

    $j(this.options.responseId).each(function () {
        var minWeighting = $j(this).find("input")[0].value;
        var maxWeighting = $j(this).find("input")[1].value;
        var responseText = $j(this).find("input")[2].value;
        weightingDict.push({
            key: minWeighting,
            value: maxWeighting
        });
        responsesDict.push({
            key: responseText,
            value: weightingDict
        });
    });
}
}

export default () => { return new QuestionnaireView(); };

And here is the browserify command I am running:

browserify Scripts/questionnaire-view.js -o wwwroot/js/questionnaire-view.js

I have also tried

browserify Scripts/questionnaire-view.js -o wwwroot/js/questionnaire-view.js -t [ babelify --presets [ @babel/preset-env @babel/preset-react ] --plugins [ @babel/plugin-transform-modules-commonjs ] ]

The output JS file looks okay and does not throw any errors in dev tools but when I go to call a function I get the following:

Error: Microsoft.JSInterop.JSException: Could not find 'collectQuestions' ('collectQuestions' was undefined).
Error: Could not find 'collectQuestions' ('collectQuestions' was undefined).
at http://localhost:41131/_framework/blazor.server.js:1:288
at Array.forEach (<anonymous>)
at r.findFunction (http://localhost:41131/_framework/blazor.server.js:1:256)
at v (http://localhost:41131/_framework/blazor.server.js:1:1882)
at http://localhost:41131/_framework/blazor.server.js:1:2662
at new Promise (<anonymous>)
at et.beginInvokeJSFromDotNet (http://localhost:41131/_framework/blazor.server.js:1:2643)
at http://localhost:41131/_framework/blazor.server.js:1:62750
at Array.forEach (<anonymous>)
at et._invokeClientMethod (http://localhost:41131/_framework/blazor.server.js:1:62736)

Any help is greatly appreciated :)

Upvotes: 0

Views: 100

Answers (1)

James Blackburn
James Blackburn

Reputation: 616

I ended up using webpack with babel loader:

var devJSConfig = Object.assign({}, config, {
mode: 'development',
entry: [
    path.resolve(__dirname, './Scripts/Components/base-component.js'),
    path.resolve(__dirname, './Scripts/address-view.js'),
    path.resolve(__dirname, './Scripts/customer-view.js'),
    path.resolve(__dirname, './Scripts/questionnaire-view.js')
],
output: {
    path: path.resolve(__dirname, 'wwwroot/js'),
    filename: "[name].js"
},
module: {
    rules: [
        {
            test: /\.(js|jsx)$/,
            exclude: '/node_modules/',
            use: [
                {
                    loader: 'babel-loader',
                    options: {
                        presets: [
                            "@babel/preset-env"
                        ]
                    }
                }
            ]
        }
    ]
}

});

In my _Host.cshtml I had the script tag type attribute for my js files set to 'text/javascript' when it needs to be 'module'. I was also linking the individual script files but only needed to reference the bundle js which was produced using the above.

Lastly in my script I had to expose the js class to the Window like so (place this at the end of your js class):

window['QuestionnaireView'] = new QuestionnaireView();

I could then call js functions in my Blazor component class using:

var test = await jSRuntime.InvokeAsync<Object>("QuestionnaireView.collectQuestions");

Upvotes: 0

Related Questions