Skip to content

Commit 2b9e4be

Browse files
authored
docs: Outputs documentation and more (#637)
1 parent a8f7246 commit 2b9e4be

File tree

30 files changed

+1100
-240
lines changed

30 files changed

+1100
-240
lines changed

.changeset/early-carrots-punch.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
---
2+
"@jsrepo/shadcn": patch
3+
"@jsrepo/mcp": patch
4+
---
5+
6+
chore: update docs links
7+

.changeset/wise-lions-hide.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
---
2+
"jsrepo": patch
3+
---
4+
5+
breaking: Rename manifest file from `jsrepo.json` -> `registry.json`
6+

apps/docs/content/docs/create-a-registry.mdx

Lines changed: 232 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ Now we can build our registry with the `jsrepo build` command:
9999
jsrepo build
100100
```
101101

102-
This will create a `jsrepo.json` file at the root of our project that contains everything we need to start adding items from our registry to other projects.
102+
This will create a `registry.json` file at the root of our project that contains everything we need to start adding items from our registry to other projects.
103103

104104
### Testing the registry
105105

@@ -146,3 +146,234 @@ jsrepo add logger
146146
Now that we have a working registry we can deploy it to wherever we want. Take a look at the [providers](/docs/providers) docs for the full list of hosting options.
147147

148148
Each provider has a guide on how to deploy your registry to that particular platform.
149+
150+
This is the end of the basic guide. You can now start adding items to your registry and deploying it to your favorite hosting platform.
151+
152+
## Advanced Usage
153+
154+
Now that we have covered the basics of creating a registry we can start to explore some of the features that make **jsrepo** so powerful.
155+
156+
### Exclude deps
157+
158+
Many times you may not want certain dependencies to be installed with your registry items. For instance if you import `useState` from `react` you probably don't want to force users to install `react` with your registry.
159+
160+
For this you can use the `excludeDeps` key of your registry config.
161+
162+
```ts title="jsrepo.config.mts"
163+
import { defineConfig } from "jsrepo";
164+
165+
export default defineConfig({
166+
registry: {
167+
// ...
168+
excludeDeps: ["react"], // [!code ++]
169+
},
170+
});
171+
```
172+
173+
### Configure when an item is added
174+
175+
We mentioned this briefly above but you can configure when an item is added in the user's project by setting the `add` key an item.
176+
177+
- `"on-init"` - Added on registry init or when it's needed by another item
178+
- `"when-needed"` - Not listed and only added when another item is added that depends on it
179+
- `"when-added"` - Added when the user selects it to be added
180+
181+
```ts title="jsrepo.config.mts"
182+
import { defineConfig } from "jsrepo";
183+
184+
export default defineConfig({
185+
registry: {
186+
items: [
187+
{
188+
// ...
189+
add: "when-added", // [!code ++]
190+
}
191+
]
192+
},
193+
});
194+
```
195+
196+
<Callout type="info">
197+
It's good practice to put your framework in the `excludeDeps` list whether that be `react`, `vue`, `svelte`, or `next` etc.
198+
</Callout>
199+
200+
### Configuring the user's project
201+
202+
There are a few common things you may want to automatically configure in the user's project when they first initialize your registry.
203+
204+
#### Default Paths
205+
206+
You can configure the `defaultPaths` key of your registry config to configure the default paths for items or item types to be added to in the user's project.
207+
208+
```ts title="jsrepo.config.mts"
209+
import { defineConfig } from "jsrepo";
210+
211+
export default defineConfig({
212+
registry: {
213+
// ...
214+
defaultPaths: {
215+
component: "src/components/ui",
216+
},
217+
},
218+
});
219+
```
220+
221+
#### Plugins
222+
223+
You can also configure the `plugins` key to automatically install plugins to the user's project when they initialize your registry.
224+
225+
```ts title="jsrepo.config.mts"
226+
import { defineConfig } from "jsrepo";
227+
228+
export default defineConfig({
229+
registry: {
230+
plugins: {
231+
languages: [{ package: "jsrepo-language-go" }], // [!code ++]
232+
// by setting the optional key to true the user will be prompted to install the plugin if it is not already installed.
233+
transforms: [{ package: "@jsrepo/transform-prettier", optional: true }], // [!code ++]
234+
},
235+
},
236+
});
237+
```
238+
239+
### Environment Variables
240+
241+
Sometimes your registry items may require environment variables to work.
242+
243+
For this you can define the `envVars` key of that particular item:
244+
245+
```ts title="jsrepo.config.mts"
246+
import { defineConfig } from "jsrepo";
247+
248+
export default defineConfig({
249+
registry: {
250+
// ...
251+
items: [
252+
// ...
253+
{
254+
// ...
255+
name: 'db',
256+
type: 'lib',
257+
files: [
258+
{
259+
path: 'src/db.ts',
260+
}
261+
],
262+
envVars: {
263+
DATABASE_URL: "https://example.com/database",
264+
DATABASE_SECRET_TOKEN: "",
265+
},
266+
}
267+
]
268+
},
269+
});
270+
```
271+
272+
Environment variables will be added to the users `.env.local` or `.env` file.
273+
274+
If you leave an environment variable blank the user will be prompted to add a value for it.
275+
276+
Values you configure here will ***never*** overwrite existing values in the user's env file.
277+
278+
### Distributing multiple registries
279+
280+
It's become common to distribute multiple registries to allow users to optionally use different variants of your registry for example JavaScript or TypeScript.
281+
282+
However until now there wasn't an easy way to do this.
283+
284+
**jsrepo** solves this by allowing you to define multiple registries in the same config:
285+
286+
```ts title="jsrepo.config.mts"
287+
import { defineConfig } from "jsrepo";
288+
289+
export default defineConfig({
290+
registry: [
291+
{
292+
name: '@my-registry/typescript',
293+
// ...
294+
},
295+
{
296+
name: '@my-registry/javascript',
297+
// ...
298+
}
299+
]
300+
});
301+
```
302+
303+
You can then use the `outputs` api to define where each registry should be output to:
304+
305+
```ts title="jsrepo.config.mts"
306+
import { defineConfig } from "jsrepo";
307+
import { distributed } from "jsrepo/outputs";
308+
309+
export default defineConfig({
310+
registry: [
311+
{
312+
name: '@my-registry/typescript',
313+
outputs: [distributed({ dir: "./public/r/ts" })], // [!code ++]
314+
// ...
315+
},
316+
{
317+
name: '@my-registry/javascript',
318+
outputs: [distributed({ dir: "./public/r/js" })], // [!code ++]
319+
// ...
320+
}
321+
]
322+
});
323+
```
324+
325+
### Dynamically generating registries
326+
327+
You don't always want to have to manually define your entire registry in your config file.
328+
329+
AI has made this less cumbersome but it's still annoying to have a 1k LOC file just to define your registry.
330+
331+
In **jsrepo v2** we automatically generated your registry based on a bunch of complicated options and this wasn't the best experience.
332+
333+
In **jsrepo v3** we are giving the control back to you allowing you to write your own code to generate your registry.
334+
335+
To do this simply pass a function to the `registry` key that returns a registry config:
336+
337+
```ts title="jsrepo.config.mts"
338+
import { defineConfig } from "jsrepo";
339+
// define your own custom function
340+
import { getItems } from "./getItems";
341+
342+
export default defineConfig({
343+
registry: ({ cwd }) => {
344+
return {
345+
name: 'my-registry',
346+
items: getItems(cwd)
347+
}
348+
}
349+
});
350+
```
351+
352+
Oh and of course you can also pass an array of functions:
353+
354+
```ts title="jsrepo.config.mts"
355+
import { defineConfig } from "jsrepo";
356+
// define your own custom function
357+
import { getItems } from "./getItems";
358+
359+
export default defineConfig({
360+
registry: [
361+
({ cwd }) => {
362+
return {
363+
name: '@my-registry/typescript',
364+
items: getItems(path.join(cwd, 'src/registry/ts'))
365+
}
366+
},
367+
({ cwd }) => {
368+
return {
369+
name: '@my-registry/javascript',
370+
items: getItems(path.join(cwd, 'src/registry/js'))
371+
}
372+
}
373+
]
374+
});
375+
```
376+
377+
<Callout type="info">
378+
Dynamically generated registries will still work with the `--watch` flag.
379+
</Callout>
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
---
2+
title: Distributed
3+
description: Output your registry as json files in a directory.
4+
---
5+
6+
import { Files, Folder, File } from "@/components/files";
7+
8+
<BadgeGroup>
9+
<SourceBadge path="packages/jsrepo/src/outputs/distributed.ts" />
10+
<OfficialBadge />
11+
</BadgeGroup>
12+
13+
The `distributed` output is used for maximizing performance when serving your registry as a static asset.
14+
15+
## Usage
16+
17+
```ts title="jsrepo.config.ts"
18+
import { defineConfig } from "jsrepo";
19+
import { distributed } from "jsrepo/outputs"; // [!code ++]
20+
21+
export default defineConfig({
22+
registry: {
23+
outputs: [distributed({ dir: "./public/r" })], // [!code ++]
24+
},
25+
});
26+
```
27+
28+
Now running `jsrepo build` will output your registry to the `./public/r` directory.
29+
30+
Unlike the `repository` output, the `distributed` output will output each item as a separate json file. For example:
31+
32+
<Files>
33+
<Folder name="public" defaultOpen>
34+
<Folder name="r" defaultOpen>
35+
<File name="registry.json" />
36+
<File name="button.json" />
37+
<File name="utils.json" />
38+
</Folder>
39+
</Folder>
40+
</Files>
41+
42+
Since each item file contains all the code for all the files required for that item this is much more performant, and portable than the `repository` output.

0 commit comments

Comments
 (0)