How to use Plotly with Stencil?

I’m trying to use Plotly.js with Stencil, but one of Plotly’s dependencies uses glslify, which apparently has an “Octal literal in strict mode”. Is no one else using Plotly with Stencil, or is there another way to get past this issue? I’m currently using the @types/plotly.js TypeScript types and running on Windows using the Stencil app template.

[ ERROR ]  Rollup: Parse Error
           Octal literal in strict mode (Note that you need plugins to import files that are not        
           JavaScript) 1: export default
           '...\node_modules\glslify' ^ 

I saw the note about Strict Mode, but I am not sure how to lobby the authors for such a large package.

Below is how i solve this problem for my to be app by importing it as external module loaded via script tag,
this way the typescript compiler will exclude plotly.js-dist and only include @types/plotly.js for the ambient declaration.

package.json:

  "devDependencies": {
    ...,
    "@types/plotly.js": "^1.50.16"
  },
  "dependencies": {
    ...,
    "plotly.js-dist": "^1.54.7"
  }

stencil.config.ts:

  outputTargets: [{
    ...,
    copy: [
      {
        src: '../node_modules/plotly.js-dist/plotly.js',
        dest: 'lib/plotly.js'
      }
    ],

tsconfig.json:

  "compilerOptions": {
    ...,
    "allowUmdGlobalAccess": true,
    "files": [
      "node_modules/@types/plotly.js/index.d.ts"
    ],

index.html:

...
<script nomodule src="/build/app.js"></script>
<script src="/lib/plotly.js"></script>

then in your tsx file you will be able to use Plotly.xxx

import { Component, h } from '@stencil/core';
@Component({
    tag: 'app-draw'
})

export class AppDraw {
    componentDidRender() {
        // mousewheel or two-finger scroll zooms the plot
        let trace1 = {
            x:['2020-10-04', '2021-11-04', '2023-12-04'],
            y: [90, 40, 60],
            type: 'scatter'
        } as Plotly.PlotData;

        var data = [trace1];

        var layout = {
            title: 'Scroll and Zoom',
            showlegend: false
        };

        Plotly.newPlot('myDiv', data, layout, {scrollZoom: true});
    }

    render() {
        return [
            <app-head head="Draw"></app-head>,
            <div id="myDiv"></div>
        ];
    }
}
1 Like

That is a fantastic solution! Thank you!