TypeError: Cannot read property 'replace' of undefined when compiling in Node a tag with an import in its less stylesheet #1488

Closed
jrx-jsj opened this Issue Dec 28, 2015 · 3 comments

Projects

None yet

2 participants

@jrx-jsj
jrx-jsj commented Dec 28, 2015

I'm trying to compile a custom tag with an import in its less stylesheet:

<demo-button>
    <button><yield/></button>
    <style scoped type="less">
        @import "css/demo.less";

        :scope {
            display: inline-block;
        }

        button {
            background: @primary;
            color: fadeout(@base, @textfadeout);
            cursor: pointer;
        }

        button when (luma(@primary) < 50%) {
            color: fadeout(@reverse, @textfadeoutreverse);
        }

        button:active {
            background: lighten(@primary,20%);
        }
    </style>
    <script>
        this.on("mount", function() {
            //TODO: Stuff
        });
    </script>
</demo-button>

The demo.less looks like this:

@textfadeout: 13%;
@textfadeoutreverse: 0%;
@base: #000;
@reverse: #fff;
@primary: #3f51b5;
@accent: #ff5252;

When I run the riot command for compiling the tag, it throws the following error:

TypeError: Cannot read property 'replace' of undefined

The problem is that the call to less compiler in compiler.js is missing the syncImport parameter, so any import is loaded asynchronously and not available after the less.render call is done.

@GianlucaGuarini
Member

@jrx-jsj have you tried using a custom compiler? http://riotjs.com/guide/compiler/#es6-config-file You can use something like my-less to find a setup that fits better to your needs

@jrx-jsj
jrx-jsj commented Dec 28, 2015

What I am doing right now is adding the parameter into the riot compiler code. The original method looks like this:

less: function(tag, css, opts, url) {
  var less = _req('less'),
    ret

  less.render(css, extend({
    sync: true,
    compress: true
  }, opts), function (err, result) {
    // istanbul ignore next
    if (err) throw err
    ret = result.css
  })
  return ret
},

and it fails when compiling with Node.js as the syncImport parameter is not added too, so I've added it:

less: function(tag, css, opts, url) {
  var less = _req('less'),
    ret

  less.render(css, extend({
    sync: true,
    syncImport: true,
    compress: true
  }, opts), function (err, result) {
    // istanbul ignore next
    if (err) throw err
    ret = result.css
  })
  return ret
},

@GianlucaGuarini It looks harmless to me adding the syncImport parameter that less.js code look for when running in Node.js environment, as a sync parameter is already there. Otherwise, riot code would have to wait until the async rendering is done, I guess.

@GianlucaGuarini
Member

this seems to be more a less.js issue... @jrx-jsj can you do a pull request here please ?

@jrx-jsj jrx-jsj added a commit to jrx-jsj/compiler that referenced this issue Dec 28, 2015
@jrx-jsj jrx-jsj Workaround for riot/riot#1488 726dce6
@jrx-jsj jrx-jsj referenced this issue in riot/compiler Dec 28, 2015
Merged

Workaround for riot/riot#1488 #43

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment