| banksean | 333aa67 | 2025-07-13 19:49:21 +0000 | [diff] [blame] | 1 | # Modern Component Architecture: SketchTailwindElement |
| 2 | |
| 3 | **IMPORTANT: New component architecture standards for all Sketch web components** |
| 4 | |
| 5 | ## New Component Standard (Use This) |
| 6 | |
| 7 | All new Sketch web components should: |
| 8 | |
| 9 | 1. **Inherit from `SketchTailwindElement`** instead of `LitElement` |
| 10 | 2. **Use Tailwind CSS classes** for styling instead of CSS-in-JS |
| 11 | 3. **Use property-based composition** instead of slot-based composition |
| 12 | 4. **Avoid Shadow DOM** whenever possible |
| 13 | |
| 14 | ### Example of Modern Component: |
| 15 | |
| 16 | ```typescript |
| 17 | import { html } from "lit"; |
| 18 | import { customElement, property } from "lit/decorators.js"; |
| 19 | import { SketchTailwindElement } from "./sketch-tailwind-element"; |
| 20 | import "./sketch-tool-card-base"; |
| 21 | |
| 22 | @customElement("sketch-tool-card-example") |
| 23 | export class SketchToolCardExample extends SketchTailwindElement { |
| 24 | @property() toolCall: ToolCall; |
| 25 | @property() open: boolean; |
| 26 | |
| 27 | render() { |
| 28 | const summaryContent = html`<span class="font-mono text-sm text-gray-700"> |
| 29 | ${this.toolCall?.name} |
| 30 | </span>`; |
| 31 | |
| 32 | const inputContent = html`<div class="p-2 bg-gray-100 rounded"> |
| 33 | <pre class="whitespace-pre-wrap break-words">${this.toolCall?.input}</pre> |
| 34 | </div>`; |
| 35 | |
| 36 | return html`<sketch-tool-card-base |
| 37 | .open=${this.open} |
| 38 | .toolCall=${this.toolCall} |
| 39 | .summaryContent=${summaryContent} |
| 40 | .inputContent=${inputContent} |
| 41 | ></sketch-tool-card-base>`; |
| 42 | } |
| 43 | } |
| 44 | ``` |
| 45 | |
| 46 | ### Key Differences from Legacy Components: |
| 47 | |
| 48 | - **Extends SketchTailwindElement** (not LitElement) |
| 49 | - **Uses sketch-tool-card-base** with property binding (not slots) |
| 50 | - **Tailwind classes** like `font-mono text-sm text-gray-700` (not CSS-in-JS) |
| 51 | - **No static styles** or Shadow DOM |
| 52 | - **Property-based composition** (`.summaryContent=${html\`...\`}`) |
| 53 | |
| banksean | c5c3bea | 2025-07-17 10:11:35 -0700 | [diff] [blame] | 54 | ## Preview, debug and iterate on your component changes with the demo server |
| 55 | |
| 56 | ### Setup (first time): |
| 57 | |
| 58 | 1. Navigate to the webui directory: `cd ./sketch/webui` |
| 59 | 2. Install dependencies: `npm install` |
| 60 | 3. If you encounter rollup/architecture errors, remove dependencies and reinstall: |
| 61 | ```bash |
| 62 | rm -rf node_modules package-lock.json |
| 63 | npm install |
| 64 | ``` |
| 65 | |
| 66 | ### Running the demo server: |
| 67 | |
| banksean | 581bd79 | 2025-07-20 18:30:12 -0700 | [diff] [blame] | 68 | - Use the `npm run demo` command to start the demo server. It will render your component changes, populated with fake example data. |
| 69 | - The server runs at http://localhost:5173/src/web-components/demo/demo.html |
| banksean | c5c3bea | 2025-07-17 10:11:35 -0700 | [diff] [blame] | 70 | - If you need to write or update the demo definition for an element, do so in demo files like ./demo/some-component-name.demo.ts |
| 71 | - If you need to add new example data objects for demoing components, do so in ./demo/fixtures |
| 72 | |
| banksean | 4432056 | 2025-07-21 11:09:38 -0700 | [diff] [blame^] | 73 | ## Migration Complete ✅ |
| banksean | 333aa67 | 2025-07-13 19:49:21 +0000 | [diff] [blame] | 74 | |
| banksean | 4432056 | 2025-07-21 11:09:38 -0700 | [diff] [blame^] | 75 | All Sketch web components have been successfully migrated to the modern SketchTailwindElement architecture: |
| banksean | 333aa67 | 2025-07-13 19:49:21 +0000 | [diff] [blame] | 76 | |
| banksean | 4432056 | 2025-07-21 11:09:38 -0700 | [diff] [blame^] | 77 | - ✅ **34 components** now extend `SketchTailwindElement` |
| 78 | - ✅ **0 components** still extend `LitElement` directly |
| 79 | - ✅ **All components** use Tailwind CSS classes instead of CSS-in-JS |
| 80 | - ✅ **No Shadow DOM** conflicts with global Tailwind styles |
| banksean | 333aa67 | 2025-07-13 19:49:21 +0000 | [diff] [blame] | 81 | |
| banksean | 4432056 | 2025-07-21 11:09:38 -0700 | [diff] [blame^] | 82 | **All components now follow the modern architecture patterns described above.** The migration from legacy LitElement patterns is complete. |
| banksean | 333aa67 | 2025-07-13 19:49:21 +0000 | [diff] [blame] | 83 | |
| Philip Zeyliger | 3321939 | 2025-05-14 20:43:24 -0700 | [diff] [blame] | 84 | # API URLs Must Be Relative |
| 85 | |
| 86 | When making fetch requests to backend APIs in Sketch, all URLs **must be relative** without leading slashes. The base URL for Sketch varies depending on how it is deployed and run: |
| 87 | |
| 88 | ```javascript |
| 89 | // CORRECT - use relative paths without leading slash |
| 90 | const response = await fetch(`git/rawdiff?commit=${commit}`); |
| 91 | const data = await fetch(`git/show?hash=${hash}`); |
| 92 | |
| 93 | // INCORRECT - do not use absolute paths with leading slash |
| 94 | const response = await fetch(`/git/rawdiff?commit=${commit}`); // WRONG! |
| 95 | const data = await fetch(`/git/show?hash=${hash}`); // WRONG! |
| 96 | ``` |
| 97 | |
| 98 | The reason for this requirement is that Sketch may be deployed: |
| 99 | |
| 100 | 1. At the root path of a domain |
| 101 | 2. In a subdirectory |
| 102 | 3. Behind a proxy with a path prefix |
| 103 | 4. In different environments (dev, production) |
| 104 | |
| 105 | Using relative paths ensures that requests are correctly routed regardless of the deployment configuration. The browser will resolve the URLs relative to the current page location. |