blockparty 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (51) hide show
  1. package/README.md +102 -0
  2. package/dist/cli.d.ts +3 -0
  3. package/dist/cli.d.ts.map +1 -0
  4. package/dist/cli.js +54 -0
  5. package/dist/cli.js.map +1 -0
  6. package/dist/commands/build.d.ts +2 -0
  7. package/dist/commands/build.d.ts.map +1 -0
  8. package/dist/commands/build.js +66 -0
  9. package/dist/commands/build.js.map +1 -0
  10. package/dist/commands/storybook.d.ts +2 -0
  11. package/dist/commands/storybook.d.ts.map +1 -0
  12. package/dist/commands/storybook.js +95 -0
  13. package/dist/commands/storybook.js.map +1 -0
  14. package/dist/discoverBlocks.d.ts +9 -0
  15. package/dist/discoverBlocks.d.ts.map +1 -0
  16. package/dist/discoverBlocks.js +63 -0
  17. package/dist/discoverBlocks.js.map +1 -0
  18. package/dist/extractProps.d.ts +10 -0
  19. package/dist/extractProps.d.ts.map +1 -0
  20. package/dist/extractProps.js +251 -0
  21. package/dist/extractProps.js.map +1 -0
  22. package/dist/extractProps.test.d.ts +2 -0
  23. package/dist/extractProps.test.d.ts.map +1 -0
  24. package/dist/extractProps.test.js +305 -0
  25. package/dist/extractProps.test.js.map +1 -0
  26. package/dist/generateBlocksModule.d.ts +3 -0
  27. package/dist/generateBlocksModule.d.ts.map +1 -0
  28. package/dist/generateBlocksModule.js +21 -0
  29. package/dist/generateBlocksModule.js.map +1 -0
  30. package/dist/index.d.ts +4 -0
  31. package/dist/index.d.ts.map +1 -0
  32. package/dist/index.js +5 -0
  33. package/dist/index.js.map +1 -0
  34. package/dist/parseReadme.d.ts +15 -0
  35. package/dist/parseReadme.d.ts.map +1 -0
  36. package/dist/parseReadme.js +84 -0
  37. package/dist/parseReadme.js.map +1 -0
  38. package/dist/parseReadme.test.d.ts +2 -0
  39. package/dist/parseReadme.test.d.ts.map +1 -0
  40. package/dist/parseReadme.test.js +142 -0
  41. package/dist/parseReadme.test.js.map +1 -0
  42. package/dist/templates/App.tsx +236 -0
  43. package/dist/templates/ErrorBoundary.tsx +53 -0
  44. package/dist/templates/PropsEditor.tsx +707 -0
  45. package/dist/templates/index.html +27 -0
  46. package/dist/templates/index.tsx +10 -0
  47. package/dist/viteConfig.d.ts +12 -0
  48. package/dist/viteConfig.d.ts.map +1 -0
  49. package/dist/viteConfig.js +22 -0
  50. package/dist/viteConfig.js.map +1 -0
  51. package/package.json +60 -0
package/README.md ADDED
@@ -0,0 +1,102 @@
1
+ # Block Party
2
+
3
+ [![NPM Version](https://img.shields.io/npm/v/blockparty)](https://www.npmjs.com/package/blockparty)
4
+
5
+ Easy, zero-config, convention-based React components.
6
+
7
+ ## Hello, World
8
+
9
+ A component in Block Party is called a Block. Here is a simple Block:
10
+
11
+ ```typescript
12
+ export interface Props {
13
+ who: string
14
+ }
15
+
16
+ export default ({ who }: Props) => (
17
+ <h1>Hello, {who}!</h1>
18
+ )
19
+ ```
20
+
21
+ Create a new directory and paste the above into a file called `index.tsx`. You've just created your first Block!
22
+
23
+ ### Run the Storybook
24
+
25
+ Block Party includes a storybook-style UI for quick previews of your Blocks.
26
+
27
+ Just run `npx blockparty` in the directory with your Block. The preview will automatically update if changes are made to the Block's source code.
28
+
29
+ ### Publish the Storybook
30
+
31
+ You may want to publish a static site build of the storybook UI, for instance during a CI run on a git repo.
32
+
33
+ To create a static site build of the storybook, run `npx blockparty build` from the root (where each block is in a different subdirectory).
34
+
35
+ By default, the output goes into a `dist` directory, but you can specify a different path on the command line. For instance, if you are using GitHub Pages, you may want to put it in the `docs` directory:
36
+
37
+ ```
38
+ npx blockparty build . docs
39
+ ```
40
+
41
+ ## Metadata
42
+
43
+ If the Block has a `README.md` file in its directory, frontmatter can be added to the beginning of the file to provide metadata:
44
+
45
+ ```markdown
46
+ ---
47
+ name: Hello Component
48
+ description: Greets whomever is specified.
49
+ foo: bar
50
+ ...
51
+
52
+ ---
53
+
54
+ # Detailed documentation...
55
+
56
+ Blah blah blah
57
+ ```
58
+
59
+ If the `name` or `description` fields are not present in the frontmatter, Block Party will extract them from the README content:
60
+
61
+ - **Name**: The first heading (`# Heading`) in the document
62
+ - **Description**: The first paragraph of text after the heading
63
+
64
+ For example:
65
+
66
+ ```markdown
67
+ # Hello Component
68
+
69
+ Greets whomever is specified.
70
+
71
+ ## Usage
72
+
73
+ ...
74
+ ```
75
+
76
+ Both of the above `README.md` files will yield the name, "Hello Component" and description, "Greets whomever is specified."
77
+
78
+ The name and description are displayed in the storybook UI.
79
+
80
+ ## Documenting Props
81
+
82
+ You can add JSDoc comments to your props to provide helpful descriptions in the storybook UI:
83
+
84
+ ```typescript
85
+ export interface Props {
86
+ /**
87
+ * The person's name to greet
88
+ */
89
+ who: string
90
+
91
+ /**
92
+ * Optional greeting message (default: 'Hello')
93
+ */
94
+ greeting?: string
95
+ }
96
+
97
+ export default ({ who, greeting = 'Hello' }: Props) => (
98
+ <h1>{greeting}, {who}!</h1>
99
+ )
100
+ ```
101
+
102
+
package/dist/cli.d.ts ADDED
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=cli.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":""}
package/dist/cli.js ADDED
@@ -0,0 +1,54 @@
1
+ #!/usr/bin/env node
2
+ import { existsSync } from 'fs';
3
+ import { resolve } from 'path';
4
+ import { startStorybookServer } from './commands/storybook.js';
5
+ import { buildStorybook } from './commands/build.js';
6
+ async function main() {
7
+ const args = process.argv.slice(2);
8
+ // Parse command and path
9
+ let command;
10
+ let targetPath;
11
+ let outDir;
12
+ if (args.length === 0) {
13
+ // No arguments - default to storybook in current directory
14
+ command = 'storybook';
15
+ targetPath = process.cwd();
16
+ }
17
+ else if (args[0] === 'storybook' || args[0] === 'build') {
18
+ // Explicit command
19
+ command = args[0];
20
+ targetPath = args[1] ?? process.cwd();
21
+ outDir = args[2]; // Optional output directory for build command
22
+ }
23
+ else {
24
+ console.error('❌ Unknown command');
25
+ console.error('Usage: blockparty [storybook|build] [path] [outDir]');
26
+ console.error('');
27
+ console.error('Commands:');
28
+ console.error(' storybook Start storybook dev server (default)');
29
+ console.error(' build Build storybook to static files');
30
+ console.error('');
31
+ console.error('Arguments:');
32
+ console.error(' path Path to Block or root directory for Blocks (default: current directory)');
33
+ console.error(' outDir Output directory for build (default: dist)');
34
+ process.exit(1);
35
+ }
36
+ // Resolve the path
37
+ const resolvedPath = resolve(process.cwd(), targetPath);
38
+ if (!existsSync(resolvedPath)) {
39
+ console.error(`❌ Path not found: ${resolvedPath}`);
40
+ process.exit(1);
41
+ }
42
+ // Run the appropriate command
43
+ if (command === 'storybook') {
44
+ await startStorybookServer(resolvedPath);
45
+ }
46
+ else if (command === 'build') {
47
+ await buildStorybook(resolvedPath, outDir ?? 'dist');
48
+ }
49
+ }
50
+ main().catch(error => {
51
+ console.error('Failed to run Block Party:', error);
52
+ process.exit(1);
53
+ });
54
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AAEA,OAAO,EAAE,UAAU,EAAE,MAAM,IAAI,CAAA;AAC/B,OAAO,EAAE,OAAO,EAAE,MAAM,MAAM,CAAA;AAC9B,OAAO,EAAE,oBAAoB,EAAE,MAAM,yBAAyB,CAAA;AAC9D,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAA;AAEpD,KAAK,UAAU,IAAI;IACjB,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAA;IAElC,yBAAyB;IACzB,IAAI,OAAe,CAAA;IACnB,IAAI,UAAkB,CAAA;IACtB,IAAI,MAA0B,CAAA;IAE9B,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtB,2DAA2D;QAC3D,OAAO,GAAG,WAAW,CAAA;QACrB,UAAU,GAAG,OAAO,CAAC,GAAG,EAAE,CAAA;IAC5B,CAAC;SAAM,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,WAAW,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,OAAO,EAAE,CAAC;QAC1D,mBAAmB;QACnB,OAAO,GAAG,IAAI,CAAC,CAAC,CAAC,CAAA;QACjB,UAAU,GAAG,IAAI,CAAC,CAAC,CAAC,IAAI,OAAO,CAAC,GAAG,EAAE,CAAA;QACrC,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,CAAA,CAAC,8CAA8C;IACjE,CAAC;SAAM,CAAC;QACN,OAAO,CAAC,KAAK,CAAC,mBAAmB,CAAC,CAAA;QAClC,OAAO,CAAC,KAAK,CAAC,qDAAqD,CAAC,CAAA;QACpE,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC,CAAA;QACjB,OAAO,CAAC,KAAK,CAAC,WAAW,CAAC,CAAA;QAC1B,OAAO,CAAC,KAAK,CAAC,mDAAmD,CAAC,CAAA;QAClE,OAAO,CAAC,KAAK,CAAC,8CAA8C,CAAC,CAAA;QAC7D,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC,CAAA;QACjB,OAAO,CAAC,KAAK,CAAC,YAAY,CAAC,CAAA;QAC3B,OAAO,CAAC,KAAK,CAAC,sFAAsF,CAAC,CAAA;QACrG,OAAO,CAAC,KAAK,CAAC,yDAAyD,CAAC,CAAA;QACxE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,mBAAmB;IACnB,MAAM,YAAY,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,UAAU,CAAC,CAAA;IAEvD,IAAI,CAAC,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;QAC9B,OAAO,CAAC,KAAK,CAAC,qBAAqB,YAAY,EAAE,CAAC,CAAA;QAClD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,8BAA8B;IAC9B,IAAI,OAAO,KAAK,WAAW,EAAE,CAAC;QAC5B,MAAM,oBAAoB,CAAC,YAAY,CAAC,CAAA;IAC1C,CAAC;SAAM,IAAI,OAAO,KAAK,OAAO,EAAE,CAAC;QAC/B,MAAM,cAAc,CAAC,YAAY,EAAE,MAAM,IAAI,MAAM,CAAC,CAAA;IACtD,CAAC;AACH,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,KAAK,CAAC,EAAE;IACnB,OAAO,CAAC,KAAK,CAAC,4BAA4B,EAAE,KAAK,CAAC,CAAA;IAClD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;AACjB,CAAC,CAAC,CAAA"}
@@ -0,0 +1,2 @@
1
+ export declare function buildStorybook(targetPath: string, outDir: string): Promise<void>;
2
+ //# sourceMappingURL=build.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"build.d.ts","sourceRoot":"","sources":["../../src/commands/build.ts"],"names":[],"mappings":"AAOA,wBAAsB,cAAc,CAAC,UAAU,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,iBAgEtE"}
@@ -0,0 +1,66 @@
1
+ import { resolve } from 'path';
2
+ import { mkdir, writeFile, rm } from 'fs/promises';
3
+ import { build as viteBuild } from 'vite';
4
+ import { discoverBlocks } from '../discoverBlocks.js';
5
+ import { generateBlocksModule } from '../generateBlocksModule.js';
6
+ import { templatesDir, getViteResolveConfig, getVitePlugins } from '../viteConfig.js';
7
+ export async function buildStorybook(targetPath, outDir) {
8
+ console.log('🏗️ Building Blocks...');
9
+ console.log(`📂 Target: ${targetPath}`);
10
+ console.log(`📦 Output: ${outDir}\n`);
11
+ const blocks = await discoverBlocks(targetPath);
12
+ if (blocks.length === 0) {
13
+ console.error('❌ No Blocks found!');
14
+ console.error('A Block should have an index.ts or index.tsx file with:');
15
+ console.error(' - An exported Props interface');
16
+ console.error(' - A default exported function component');
17
+ process.exit(1);
18
+ }
19
+ console.log(`✅ Found ${blocks.length} Block(s):`);
20
+ blocks.forEach(block => {
21
+ console.log(` - ${block.name}`);
22
+ });
23
+ console.log();
24
+ // Generate blocks module
25
+ const blocksModule = await generateBlocksModule(blocks);
26
+ // Create a temporary directory for the virtual blocks module
27
+ const tempDir = resolve(process.cwd(), '.blockparty-build');
28
+ await mkdir(tempDir, { recursive: true });
29
+ const blocksPath = resolve(tempDir, 'blocks.ts');
30
+ await writeFile(blocksPath, blocksModule);
31
+ console.log('📝 Generating static bundle...');
32
+ try {
33
+ // Build with Vite
34
+ const viteResolve = getViteResolveConfig();
35
+ await viteBuild({
36
+ root: templatesDir,
37
+ base: './',
38
+ resolve: {
39
+ ...viteResolve,
40
+ alias: {
41
+ ...viteResolve.alias,
42
+ './blocks': blocksPath,
43
+ './blocks.ts': blocksPath
44
+ }
45
+ },
46
+ plugins: getVitePlugins(),
47
+ build: {
48
+ outDir: resolve(process.cwd(), outDir),
49
+ emptyOutDir: true,
50
+ rollupOptions: {
51
+ input: resolve(templatesDir, 'index.html')
52
+ }
53
+ }
54
+ });
55
+ console.log(`\n✅ Build complete! Output in ${outDir}/`);
56
+ }
57
+ catch (error) {
58
+ console.error('\n❌ Build failed:', error);
59
+ process.exit(1);
60
+ }
61
+ finally {
62
+ // Clean up temporary directory
63
+ await rm(tempDir, { recursive: true, force: true });
64
+ }
65
+ }
66
+ //# sourceMappingURL=build.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"build.js","sourceRoot":"","sources":["../../src/commands/build.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function startStorybookServer(targetPath: string): Promise<void>;
2
+ //# sourceMappingURL=storybook.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"storybook.d.ts","sourceRoot":"","sources":["../../src/commands/storybook.ts"],"names":[],"mappings":"AAMA,wBAAsB,oBAAoB,CAAC,UAAU,EAAE,MAAM,iBAsG5D"}
@@ -0,0 +1,95 @@
1
+ import { realpathSync } from 'fs';
2
+ import { createServer } from 'vite';
3
+ import { discoverBlocks } from '../discoverBlocks.js';
4
+ import { generateBlocksModule } from '../generateBlocksModule.js';
5
+ import { blockPartyRoot, templatesDir, getViteResolveConfig, getVitePlugins } from '../viteConfig.js';
6
+ export async function startStorybookServer(targetPath) {
7
+ console.log('🎉 Starting Block Party...');
8
+ console.log(`📂 Target path: ${targetPath}\n`);
9
+ const blocks = await discoverBlocks(targetPath);
10
+ if (blocks.length === 0) {
11
+ console.error('❌ No Blocks found!');
12
+ console.error('A Block should have an index.ts or index.tsx file with:');
13
+ console.error(' - An exported Props interface');
14
+ console.error(' - A default exported function component');
15
+ process.exit(1);
16
+ }
17
+ console.log(`✅ Found ${blocks.length} Block(s):`);
18
+ blocks.forEach(block => {
19
+ console.log(` - ${block.name}`);
20
+ });
21
+ console.log();
22
+ // Generate initial blocks module
23
+ let blocksModule = await generateBlocksModule(blocks);
24
+ // Resolve target path through symlinks for comparison
25
+ const realTargetPath = realpathSync(targetPath);
26
+ // Start Vite dev server
27
+ const server = await createServer({
28
+ root: templatesDir,
29
+ resolve: getViteResolveConfig(),
30
+ optimizeDeps: {
31
+ include: ['react', 'react-dom', 'react/jsx-runtime', 'react/jsx-dev-runtime']
32
+ },
33
+ plugins: [
34
+ {
35
+ name: 'blockparty-virtual',
36
+ enforce: 'pre',
37
+ resolveId(id) {
38
+ if (id === './blocks' || id === './blocks.ts') {
39
+ return '\0virtual:blocks.ts';
40
+ }
41
+ },
42
+ load(id) {
43
+ if (id === '\0virtual:blocks.ts') {
44
+ return blocksModule;
45
+ }
46
+ },
47
+ async handleHotUpdate({ file, server }) {
48
+ // Check if the changed file is in the target directory (resolve through symlinks)
49
+ if (file.startsWith(realTargetPath)) {
50
+ console.log(`🔄 Block file changed: ${file}`);
51
+ // Re-discover blocks to get updated prop definitions
52
+ const updatedBlocks = await discoverBlocks(targetPath);
53
+ blocksModule = await generateBlocksModule(updatedBlocks);
54
+ // Invalidate the virtual module
55
+ const module = server.moduleGraph.getModuleById('\0virtual:blocks.ts');
56
+ if (module) {
57
+ server.moduleGraph.invalidateModule(module);
58
+ }
59
+ // Trigger HMR for the blocks module
60
+ server.ws.send({
61
+ type: 'full-reload'
62
+ });
63
+ }
64
+ }
65
+ },
66
+ ...getVitePlugins()
67
+ ],
68
+ server: {
69
+ fs: {
70
+ allow: [blockPartyRoot, targetPath]
71
+ },
72
+ port: 5173,
73
+ strictPort: false,
74
+ open: true
75
+ }
76
+ });
77
+ await server.listen();
78
+ const urls = server.resolvedUrls;
79
+ console.log('🚀 Block Party is running!');
80
+ if (urls?.local && urls.local.length > 0) {
81
+ urls.local.forEach(url => {
82
+ console.log(` Local: ${url}`);
83
+ });
84
+ }
85
+ if (urls?.network && urls.network.length > 0) {
86
+ urls.network.forEach(url => {
87
+ console.log(` Network: ${url}`);
88
+ });
89
+ }
90
+ if (!urls?.local && !urls?.network) {
91
+ console.log(' http://localhost:5173');
92
+ }
93
+ console.log();
94
+ }
95
+ //# sourceMappingURL=storybook.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"storybook.js","sourceRoot":"","sources":["../../src/commands/storybook.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,9 @@
1
+ import { type PropDefinition } from './extractProps.js';
2
+ import { type BlockMetadata } from './parseReadme.js';
3
+ export interface BlockInfo extends BlockMetadata {
4
+ name: string;
5
+ path: string;
6
+ propDefinitions: PropDefinition[];
7
+ }
8
+ export declare function discoverBlocks(targetPath: string): Promise<BlockInfo[]>;
9
+ //# sourceMappingURL=discoverBlocks.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"discoverBlocks.d.ts","sourceRoot":"","sources":["../src/discoverBlocks.ts"],"names":[],"mappings":"AAGA,OAAO,EAAwB,KAAK,cAAc,EAAE,MAAM,mBAAmB,CAAA;AAC7E,OAAO,EAAE,KAAK,aAAa,EAAuB,MAAM,kBAAkB,CAAA;AAE1E,MAAM,WAAW,SAAU,SAAQ,aAAa;IAC9C,IAAI,EAAE,MAAM,CAAA;IACZ,IAAI,EAAE,MAAM,CAAA;IACZ,eAAe,EAAE,cAAc,EAAE,CAAA;CAClC;AAmCD,wBAAsB,cAAc,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC,CA4B7E"}
@@ -0,0 +1,63 @@
1
+ import { existsSync } from 'fs';
2
+ import { readdir, stat } from 'fs/promises';
3
+ import { join, dirname, basename } from 'path';
4
+ import { extractPropsFromFile } from './extractProps.js';
5
+ import { parseReadmeMetadata } from './parseReadme.js';
6
+ async function getBlockInfo(path) {
7
+ let blockDir;
8
+ let indexPath;
9
+ const targetStat = await stat(path);
10
+ if (targetStat.isFile()) {
11
+ blockDir = dirname(path);
12
+ indexPath = path;
13
+ }
14
+ else {
15
+ blockDir = path;
16
+ const indexTsPath = join(blockDir, 'index.ts');
17
+ const indexTsxPath = join(blockDir, 'index.tsx');
18
+ if (existsSync(indexTsxPath)) {
19
+ indexPath = indexTsxPath;
20
+ }
21
+ else if (existsSync(indexTsPath)) {
22
+ indexPath = indexTsPath;
23
+ }
24
+ else {
25
+ return undefined;
26
+ }
27
+ }
28
+ const propDefinitions = await extractPropsFromFile(indexPath);
29
+ const blockName = basename(blockDir);
30
+ const metadata = await parseReadmeMetadata(blockDir);
31
+ return {
32
+ ...metadata,
33
+ name: metadata.name ?? blockName,
34
+ path: indexPath,
35
+ propDefinitions
36
+ };
37
+ }
38
+ export async function discoverBlocks(targetPath) {
39
+ const blocks = [];
40
+ const blockInfo = await getBlockInfo(targetPath);
41
+ if (blockInfo) {
42
+ blocks.push(blockInfo);
43
+ return blocks;
44
+ }
45
+ // Check subdirectories for Blocks
46
+ try {
47
+ const entries = await readdir(targetPath, { withFileTypes: true });
48
+ for (const entry of entries) {
49
+ if (entry.isDirectory() && !entry.name.startsWith('.') && entry.name !== 'node_modules') {
50
+ const dirPath = join(targetPath, entry.name);
51
+ const blockInfo = await getBlockInfo(dirPath);
52
+ if (blockInfo) {
53
+ blocks.push(blockInfo);
54
+ }
55
+ }
56
+ }
57
+ }
58
+ catch (error) {
59
+ console.error('Error reading directory:', error);
60
+ }
61
+ return blocks;
62
+ }
63
+ //# sourceMappingURL=discoverBlocks.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"discoverBlocks.js","sourceRoot":"","sources":["../src/discoverBlocks.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,IAAI,CAAA;AAC/B,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,aAAa,CAAA;AAC3C,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,MAAM,CAAA;AAC9C,OAAO,EAAE,oBAAoB,EAAuB,MAAM,mBAAmB,CAAA;AAC7E,OAAO,EAAsB,mBAAmB,EAAE,MAAM,kBAAkB,CAAA;AAQ1E,KAAK,UAAU,YAAY,CAAC,IAAY;IACtC,IAAI,QAAgB,CAAA;IACpB,IAAI,SAAiB,CAAA;IAErB,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,CAAA;IACnC,IAAI,UAAU,CAAC,MAAM,EAAE,EAAE,CAAC;QACxB,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;QACxB,SAAS,GAAG,IAAI,CAAA;IAClB,CAAC;SAAM,CAAC;QACN,QAAQ,GAAG,IAAI,CAAA;QAEf,MAAM,WAAW,GAAG,IAAI,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAA;QAC9C,MAAM,YAAY,GAAG,IAAI,CAAC,QAAQ,EAAE,WAAW,CAAC,CAAA;QAChD,IAAI,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;YAC7B,SAAS,GAAG,YAAY,CAAA;QAC1B,CAAC;aAAM,IAAI,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;YACnC,SAAS,GAAG,WAAW,CAAA;QACzB,CAAC;aAAM,CAAC;YACN,OAAO,SAAS,CAAA;QAClB,CAAC;IACH,CAAC;IACD,MAAM,eAAe,GAAG,MAAM,oBAAoB,CAAC,SAAS,CAAC,CAAA;IAC7D,MAAM,SAAS,GAAG,QAAQ,CAAC,QAAQ,CAAC,CAAA;IACpC,MAAM,QAAQ,GAAG,MAAM,mBAAmB,CAAC,QAAQ,CAAC,CAAA;IAEpD,OAAO;QACL,GAAG,QAAQ;QACX,IAAI,EAAE,QAAQ,CAAC,IAAI,IAAI,SAAS;QAChC,IAAI,EAAE,SAAS;QACf,eAAe;KAChB,CAAA;AACH,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,UAAkB;IACrD,MAAM,MAAM,GAAgB,EAAE,CAAA;IAE9B,MAAM,SAAS,GAAG,MAAM,YAAY,CAAC,UAAU,CAAC,CAAA;IAChD,IAAI,SAAS,EAAE,CAAC;QACd,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,CAAA;QACtB,OAAO,MAAM,CAAA;IACf,CAAC;IAED,kCAAkC;IAClC,IAAI,CAAC;QACH,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,UAAU,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAA;QAElE,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;YAC5B,IAAI,KAAK,CAAC,WAAW,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,IAAI,KAAK,CAAC,IAAI,KAAK,cAAc,EAAE,CAAC;gBACxF,MAAM,OAAO,GAAG,IAAI,CAAC,UAAU,EAAE,KAAK,CAAC,IAAI,CAAC,CAAA;gBAC5C,MAAM,SAAS,GAAG,MAAM,YAAY,CAAC,OAAO,CAAC,CAAA;gBAE7C,IAAI,SAAS,EAAE,CAAC;oBACd,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,CAAA;gBACxB,CAAC;YACH,CAAC;QACH,CAAC;IACH,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,0BAA0B,EAAE,KAAK,CAAC,CAAA;IAClD,CAAC;IAED,OAAO,MAAM,CAAA;AACf,CAAC"}
@@ -0,0 +1,10 @@
1
+ export interface PropDefinition {
2
+ name: string;
3
+ type: string;
4
+ optional: boolean;
5
+ properties?: PropDefinition[];
6
+ description?: string;
7
+ }
8
+ export declare function extractPropsFromSource(content: string, fileName?: string): PropDefinition[];
9
+ export declare function extractPropsFromFile(filePath: string): Promise<PropDefinition[]>;
10
+ //# sourceMappingURL=extractProps.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"extractProps.d.ts","sourceRoot":"","sources":["../src/extractProps.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,CAAA;IACZ,IAAI,EAAE,MAAM,CAAA;IACZ,QAAQ,EAAE,OAAO,CAAA;IACjB,UAAU,CAAC,EAAE,cAAc,EAAE,CAAA;IAC7B,WAAW,CAAC,EAAE,MAAM,CAAA;CACrB;AA2MD,wBAAgB,sBAAsB,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAqB,GAAG,cAAc,EAAE,CAiEzG;AAwBD,wBAAsB,oBAAoB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,EAAE,CAAC,CAQtF"}