| name | lit |
| description | Web Components development with Lit including custom elements, reactive properties, shadow DOM, and interoperability. |
| allowed-tools | Read, Write, Edit, Bash, Glob, Grep |
| graph | {"domains":["domain:web-development"],"specializations":["specialization:web-development"],"skillAreas":["skill-area:ui-component-libraries","skill-area:react-components"],"roles":["role:frontend-engineer"],"topics":["topic:component-based-architecture"]} |
Lit Skill
Expert assistance for building Web Components with Lit.
Capabilities
- Create Lit elements with reactive properties
- Implement shadow DOM styling
- Handle events and lifecycle callbacks
- Build composable component libraries
- Ensure framework interoperability
- Configure SSR with Lit
Usage
Invoke this skill when you need to:
- Build framework-agnostic components
- Create design system primitives
- Implement custom elements
- Ensure cross-framework compatibility
- Build micro-frontends
Inputs
| Parameter | Type | Required | Description |
|---|
| elementName | string | Yes | Custom element name (must have hyphen) |
| properties | array | No | Reactive properties |
| shadowDom | boolean | No | Use shadow DOM (default: true) |
| typescript | boolean | No | Use TypeScript (default: true) |
Component Patterns
Basic Lit Element
import { LitElement, html, css } from 'lit';
import { customElement, property, state } from 'lit/decorators.js';
interface User {
id: string;
name: string;
email: string;
avatar?: string;
}
@customElement('user-card')
export class UserCard extends LitElement {
static styles = css`
:host {
display: block;
padding: 1rem;
border: 1px solid #e5e7eb;
border-radius: 0.5rem;
}
.user-card {
display: flex;
gap: 1rem;
}
.avatar {
width: 64px;
height: 64px;
border-radius: 50%;
overflow: hidden;
background: #e5e7eb;
display: flex;
align-items: center;
: center;
}
{
: ;
: ;
: cover;
}
{
: bold;
: ;
}
{
: ;
: none;
: ;
: pointer;
}
{
: ;
: white;
}
`;
({ : })
user!: ;
({ : })
editable = ;
()
isEditing = ;
()
editedName = ;
() {
..
.()
.( n[])
.()
.();
}
() {
. = ..;
. = ;
}
() {
.( (, {
: { ...., : . },
: ,
: ,
}));
. = ;
}
() {
. = ;
}
() {
html`;
}
}
{
{
: ;
}
}
Reactive Controller
import { ReactiveController, ReactiveControllerHost } from 'lit';
export class FetchController<T> implements ReactiveController {
host: ReactiveControllerHost;
data: T | null = null;
loading = false;
error: Error | null = null;
private abortController: AbortController | null = null;
constructor(host: ReactiveControllerHost, private url: string) {
(this.host = host).addController(this);
}
hostConnected() {
this.fetch();
}
hostDisconnected() {
this.abortController?.abort();
}
async fetch() {
this.abortController?.abort();
. = ();
. = ;
. = ;
..();
{
response = (., {
: ..,
});
(!response.) {
();
}
. = response.();
} (e) {
((e ). !== ) {
. = e ;
}
} {
. = ;
..();
}
}
}
()
{
usersController = <[]>(, );
() {
(..) {
html`;
}
(..) {
html`;
}
html`;
}
}
Directive for Custom Rendering
import { Directive, directive, PartInfo } from 'lit/directive.js';
class HighlightDirective extends Directive {
render(text: string, query: string) {
if (!query) return text;
const regex = new RegExp(`(${query})`, 'gi');
const parts = text.split(regex);
return parts.map(part =>
regex.test(part)
? document.createElement('mark').textContent = part
: part
);
}
}
export const highlight = directive(HighlightDirective);
html`<p>${highlight(text, searchQuery)}</p>`
Slots and Composition
@customElement('modal-dialog')
export class ModalDialog extends LitElement {
static styles = css`
:host {
display: none;
}
:host([open]) {
display: block;
}
.backdrop {
position: fixed;
inset: 0;
background: rgba(0, 0, 0, 0.5);
display: flex;
align-items: center;
justify-content: center;
}
.dialog {
background: white;
padding: 1.5rem;
border-radius: 0.5rem;
max-width: 500px;
width: 100%;
}
`;
@property({ type: Boolean, reflect: true })
open = false;
private handleBackdropClick(e: Event) {
if (e.target === e.currentTarget) {
.( ());
}
}
() {
html`;
}
}
html`
Best Practices
- Use custom element naming convention (hyphenated)
- Leverage shadow DOM for encapsulation
- Use @state for internal state
- Dispatch composed events for parent communication
- Implement reactive controllers for reusable logic
Target Processes
- web-component-library
- design-system-creation
- micro-frontend-architecture
- framework-agnostic-components