Giter Club home page Giter Club logo

lit-loader's Introduction

lit-loader

Build Status codecov Greenkeeper badge

npm

Single File Component LitElement loader for Webpack

Example repository

Checkout the working repository for a more comprehensive example: https://github.com/PolymerX/lit-loader-example

Why

Because we love separation of concerns also without separation of files! This loader will produce a Web Component using the LitElement starting from a Single File Component, like Vue.

What

The loader does a simple job: take your .lit file and build up as single js file. And you can easily use PostCSS on your styles.

Install

$ yarn add --dev lit-loader

Usage

Add to Webpack

Add the loader to your Webpack conf webpack.config.js:

...

module: {
    rules: [
      {
        test: /\.lit$/,
        loader: 'lit-loader'
      }
    ]
  }

...

Create your first .lit element

CounterElement.lit

<style lang="postcss"> <!-- This will enable PostCSS compilation -->
  span {
    width: 20px;
    display: inline-block;
    text-align: center;
    font-weight: bold;
  }
</style>

<template>
  <div>
    <p>
      Clicked: <span>${this.clicks}</span> times.
      Value is <span>${this.value}</span>.
      <button @click="${this._onIncrement}" title="Add 1">+</button>
      <button @click="${this._onDecrement}" title="Minus 1">-</button>
    </p>
  </div>
</template>

<script>
  export default class CounterElement {
    static get properties() { return {
      clicks: Number,
      value: Number
    }};

    constructor() {
      super();
      this.clicks = 0;
      this.value = 0;
    }

    _onIncrement() {
      this.value++;
      this.clicks++;
      this.dispatchEvent(new CustomEvent('counter-incremented'));
    }

    _onDecrement() {
      this.value--;
      this.clicks++;
      this.dispatchEvent(new CustomEvent('counter-decremented'));
    }
  }

  window.customElements.define('counter-element', CounterElement);
</script>

Import it within another element and use it

index.js

import {LitElement, html} from 'lit-element';

...

import './CounterElement.lit';

export default class MyApp extends LitElement {
	...


	_render(props) {
		return html`
		<div>
			<counter-element></counter-element>
		</div>
		`
	}

	...

}

Use with Babel

Just chain the babel-loader AFTER the lit-loader like so:

module: {
    rules: [
      {
        test: /\.lit$/,
        use: ['babel-loader', 'lit-loader']
      }
    ]
  }

PostCSS configuration

You need to add a PostCSS configuration file (postcss.config.js) if you want to use it.

Current status

I think this should be considered experimental and I will try to improve it as much as I can. I really would love to accept some PR's to improve the project. ๐Ÿค˜

License

MIT ยฉ LasaleFamine

lit-loader's People

Contributors

greenkeeper[bot] avatar lasalefamine avatar sizuhiko avatar stevvvn avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar

lit-loader's Issues

Can't add and use lit-loader in own project:

To reproduce it:

โžœ  git clone https://github.com/PolymerX/lit-loader-example.git && cd lit-loader-element && yarn && yarn remove lit-loader && yarn add lit-loader && yarn build
yarn install v1.17.3
[1/5] Validating package.json...
[2/5] Resolving packages...
[3/5] Fetching packages...
info [email protected]: The platform "linux" is incompatible with this module.
info "[email protected]" is an optional dependency and failed compatibility check. Excluding it from installation.
[4/5] Linking dependencies...
warning " > [email protected]" has unmet peer dependency "babel-core@6".
[5/5] Building fresh packages...
Done in 3.70s.
yarn remove v1.17.3
[1/2] Removing module lit-loader...
[2/2] Regenerating lockfile and installing missing dependencies...
info [email protected]: The platform "linux" is incompatible with this module.
info "[email protected]" is an optional dependency and failed compatibility check. Excluding it from installation.
warning " > [email protected]" has unmet peer dependency "babel-core@6".
success Uninstalled packages.
Done in 2.97s.
yarn add v1.17.3
[1/5] Validating package.json...
[2/5] Resolving packages...
[3/5] Fetching packages...
info [email protected]: The platform "linux" is incompatible with this module.
info "[email protected]" is an optional dependency and failed compatibility check. Excluding it from installation.
[4/5] Linking dependencies...
warning " > [email protected]" has unmet peer dependency "babel-core@6".
[5/5] Building fresh packages...
success Saved lockfile.
success Saved 27 new dependencies.
info Direct dependencies
โ””โ”€ [email protected]
info All dependencies
โ”œโ”€ @babel/[email protected]
โ”œโ”€ @babel/[email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ”œโ”€ [email protected]
โ””โ”€ [email protected]
Done in 5.52s.
yarn run v1.17.3
$ webpack
Hash: 2e50d27a4f13d42b9c67
Version: webpack 4.16.1
Time: 346ms
Built at: 07/25/2019 12:20:54 PM
     Asset       Size  Chunks             Chunk Names
 bundle.js    128 KiB       0  [emitted]  main
index.html  334 bytes          [emitted]
[0] ./src/index.js 66 bytes {0} [built]
[1] ./src/app.js 379 bytes {0} [built]
    + 18 hidden modules

ERROR in ./src/components/CounterElement.lit
Module build failed (from ./node_modules/babel-loader/lib/index.js):
Error: Cannot find module 'babel-core'
Require stack:
- /home/user/Projects/lit-loader-example/node_modules/babel-loader/lib/index.js
- /home/user/Projects/lit-loader-example/node_modules/loader-runner/lib/loadLoader.js
- /home/user/Projects/lit-loader-example/node_modules/loader-runner/lib/LoaderRunner.js
- /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModule.js
- /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModuleFactory.js
- /home/user/Projects/lit-loader-example/node_modules/webpack/lib/Compiler.js
- /home/user/Projects/lit-loader-example/node_modules/webpack/lib/webpack.js
- /home/user/Projects/lit-loader-example/node_modules/webpack-cli/bin/convert-argv.js
- /home/user/Projects/lit-loader-example/node_modules/webpack-cli/bin/cli.js
- /home/user/Projects/lit-loader-example/node_modules/webpack/bin/webpack.js
    at Function.Module._resolveFilename (internal/modules/cjs/loader.js:625:15)
    at Function.Module._load (internal/modules/cjs/loader.js:527:27)
    at Module.require (internal/modules/cjs/loader.js:683:19)
    at require (/home/user/Projects/lit-loader-example/node_modules/v8-compile-cache/v8-compile-cache.js:159:20)
    at Object.<anonymous> (/home/user/Projects/lit-loader-example/node_modules/babel-loader/lib/index.js:3:13)
    at Module._compile (/home/user/Projects/lit-loader-example/node_modules/v8-compile-cache/v8-compile-cache.js:178:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:787:10)
    at Module.load (internal/modules/cjs/loader.js:643:32)
    at Function.Module._load (internal/modules/cjs/loader.js:556:12)
    at Module.require (internal/modules/cjs/loader.js:683:19)
    at require (/home/user/Projects/lit-loader-example/node_modules/v8-compile-cache/v8-compile-cache.js:159:20)
    at loadLoader (/home/user/Projects/lit-loader-example/node_modules/loader-runner/lib/loadLoader.js:13:17)
    at iteratePitchingLoaders (/home/user/Projects/lit-loader-example/node_modules/loader-runner/lib/LoaderRunner.js:169:2)
    at runLoaders (/home/user/Projects/lit-loader-example/node_modules/loader-runner/lib/LoaderRunner.js:362:2)
    at NormalModule.doBuild (/home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModule.js:263:3)
    at NormalModule.build (/home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModule.js:410:15)
    at Compilation.buildModule (/home/user/Projects/lit-loader-example/node_modules/webpack/lib/Compilation.js:616:10)
    at /home/user/Projects/lit-loader-example/node_modules/webpack/lib/Compilation.js:857:14
    at /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModuleFactory.js:405:6
    at /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModuleFactory.js:155:13
    at AsyncSeriesWaterfallHook.eval [as callAsync] (eval at create (/home/user/Projects/lit-loader-example/node_modules/tapable/lib/HookCodeFactory.js:24:12), <anonymous>:6:1)
    at /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModuleFactory.js:138:29
    at /home/user/Projects/lit-loader-example/node_modules/webpack/lib/NormalModuleFactory.js:342:9
    at processTicksAndRejections (internal/process/task_queues.js:75:11)
 @ ./src/app.js 5:0-41
 @ ./src/index.js
Child html-webpack-plugin for "index.html":
     1 asset
    [0] ./node_modules/html-webpack-plugin/lib/loader.js!./src/index.html 571 bytes {0} [built]
    [2] (webpack)/buildin/global.js 489 bytes {0} [built]
    [3] (webpack)/buildin/module.js 497 bytes {0} [built]
        + 1 hidden module
error Command failed with exit code 2.
info Visit https://yarnpkg.com/en/docs/cli/run for documentation about this command.

Ok. Then:

โžœ  lit-loader-example git:(master) โœ— yarn remove babel-loader && yarn add babel-loader && yarn build
yarn remove v1.17.3
[1/2] Removing module babel-loader...
[2/2] Regenerating lockfile and installing missing dependencies...
info [email protected]: The platform "linux" is incompatible with this module.
info "[email protected]" is an optional dependency and failed compatibility check. Excluding it from installation.
success Uninstalled packages.
Done in 2.76s.
yarn add v1.17.3
[1/5] Validating package.json...
[2/5] Resolving packages...
[3/5] Fetching packages...
info [email protected]: The platform "linux" is incompatible with this module.
info "[email protected]" is an optional dependency and failed compatibility check. Excluding it from installation.
[4/5] Linking dependencies...
[5/5] Building fresh packages...
success Saved lockfile.
success Saved 1 new dependency.
info Direct dependencies
โ””โ”€ [email protected]
info All dependencies
โ””โ”€ [email protected]
Done in 2.76s.
yarn run v1.17.3
$ webpack
(node:12799) UnhandledPromiseRejectionWarning: SyntaxError: super() is only valid inside a class constructor of a subclass. Maybe a typo in the method name ('constructor') or not extending another class? (13:6)
    at Object.raise (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:6325:17)
    at Object.parseExprAtom (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8667:16)
    at Object.parseExprAtom (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:460:22)
    at Object.parseExprAtom (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:3601:20)
    at Object.parseExprSubscripts (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8412:23)
    at Object.parseMaybeUnary (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8392:21)
    at Object.parseExprOps (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8267:23)
    at Object.parseMaybeConditional (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8240:23)
    at Object.parseMaybeAssign (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8187:21)
    at Object.parseExpression (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:8135:23)
    at Object.parseStatementContent (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9958:23)
    at Object.parseStatement (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9829:17)
    at Object.parseBlockOrModuleBlockBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10405:25)
    at Object.parseBlockBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10392:10)
    at Object.parseBlockBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:424:11)
    at Object.parseBlock (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10376:10)
    at Object.parseFunctionBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9424:24)
    at Object.parseFunctionBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:472:11)
    at Object.parseFunctionBodyAndFinish (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9394:10)
    at Object.parseMethod (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9348:10)
    at Object.parseMethod (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:479:22)
    at Object.pushClassMethod (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:431:10)
    at Object.parseClassMemberWithIsStatic (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10729:12)
    at Object.parseClassMember (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10668:10)
    at /home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10623:14
    at Object.withTopicForbiddingContext (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:9702:14)
    at Object.parseClassBody (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10600:10)
    at Object.parseClass (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10574:22)
    at Object.parseExportDefaultExpression (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10999:19)
    at Object.parseExport (/home/user/Projects/lit-loader-example/node_modules/@babel/parser/lib/index.js:10905:31)
(node:12799) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:12799) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
Done in 2.10s.

TypeScript support

First, really pleased to see this, and I'd like to move at least part of our project to use single-file components as we go forward ... but we use TypeScript, and as I understand it (and from a brief skim of the sources) only JavaScript is supported inside the <script> element.

It would be excellent to see support for TypeScript in the <script> element of the .lit single file :)

> improperly escaped to &gt; in templates

When > occurs in a <template>, it is escaped to &gt; unless it happens to be quoted in an attribute.

I ran into this with lit-html's repeat helper, but it doesn't have anything specifically to do with that.

To reproduce, you can clone https://github.com/stevvvn/lit-loader-example. This is the same as the lit-loader-example from the readme except I replaced the component with:

<style lang="postcss">
</style>

<template>
        <ol>
                ${ repeat(this.items, (_, idx) => idx, (i) => html`<li>${ i }</li>`) }
        </ol>
</template>

<script>
import { repeat } from 'lit-html/lib/repeat';

export default class CounterElement {
        constructor() {
                super();
                this.items = [ 1, 2, 3 ];
        }
}
window.customElements.define('counter-element', CounterElement);
</script>

Attempting to yarn build this reports:

SyntaxError: /tmp/lit-loader-example/src/components/CounterElement.lit: Invalid left-hand side in assignment expression (17:27)

  15 |     </style>
  16 |     <ol>
> 17 |     ${ repeat(this.items, (_, idx) =&gt; idx, (i) =&gt; html`<li>${ i }</li>`) }
     |                            ^
  18 |     </ol>
  19 |     `
  20 |     }

One can "fix" this by changing src/parser.js to undo the escaping after serialization, but this can't possibly be the right way to go about it:

  value: node.childNodes.length > 0 ? node.childNodes[0].value : serialize(node.content).replace(/&gt;/g, '>')

(Thanks for working on this BTW, I really like this way of organizing components.)

Question

How does this work with SVG from lit-html?

UnhandledPromiseRejectionWarning

(node:772) UnhandledPromiseRejectionWarning: SyntaxError: Unexpected token, expected "{" (5:57)
at Object.raise (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:3834:17)
at Object.unexpected (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:5142:16) at Object.expect (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:5134:28)
at Object.parseClassBody (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7938:10)
at Object.parseClass (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7913:10)
at Object.parseExportDefaultExpression (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:8279:19)
at Object.parseExport (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:8228:31)
at Object.parseStatementContent (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7290:27)
at Object.parseStatement (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7199:17)
at Object.parseBlockOrModuleBlockBody (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7757:25)
at Object.parseBlockBody (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7744:10)
at Object.parseBlockBody (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:400:11)
at Object.parseTopLevel (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:7164:10)
at Object.parse (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:8565:17)
at Object.parse (E:\vscode\lit-loader-example\node_modules\jscodeshift\node_modules@babel\parser\lib\index.js:10537:38) at Object.parse (E:\vscode\lit-loader-example\node_modules\jscodeshift\parser\babel5Compat.js:48:22)
at Object.parse (E:\vscode\lit-loader-example\node_modules\recast\lib\parser.js:28:30) at fromSource (E:\vscode\lit-loader-example\node_modules\jscodeshift\src\core.js:84:25)
at core (E:\vscode\lit-loader-example\node_modules\jscodeshift\src\core.js:46:5) at addRenderTemplate (E:\vscode\lit-loader-example\node_modules\lit-loader\src\enrich.js:17:57)
at module.exports (E:\vscode\lit-loader-example\node_modules\lit-loader\src\enrich.js:26:2) at Object.module.exports (E:\vscode\lit-loader-example\node_modules\lit-loader\src\index.js:20:19)
(node:772) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1) (node:772) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.