diff --git a/bin/packages/build.js b/bin/packages/build.js index 9639f8b232f70e..e1a6bd7142f80d 100755 --- a/bin/packages/build.js +++ b/bin/packages/build.js @@ -64,6 +64,43 @@ function createStyleEntryTransform() { } ); } +/** + * Returns a stream transform which maps an individual block.json to the + * index.js that imports it. Presently, babel resolves the import of json + * files by inlining them as a JavaScript primitive in the importing file. + * This transform ensures the importing file is rebuilt. + * + * @return {Transform} Stream transform instance. + */ +function createBlockJsonEntryTransform() { + const blocks = new Set; + + return new Transform( { + objectMode: true, + async transform( file, encoding, callback ) { + const matches = /block-library[\/\\]src[\/\\](.*)[\/\\]block.json$/.exec( file ); + const blockName = matches ? matches[ 1 ] : undefined; + + // Only block.json files in the block-library folder are subject to this transform. + if ( ! blockName ) { + this.push( file ); + callback(); + return; + } + + // Only operate once per block, assuming entries are common. + if ( blockName && blocks.has( blockName ) ) { + callback(); + return; + } + + blocks.add( blockName ); + this.push( file.replace( 'block.json', 'index.js' ) ); + callback(); + }, + } ); +} + let onFileComplete = () => {}; let stream; @@ -72,7 +109,9 @@ if ( files.length ) { stream = new Readable( { encoding: 'utf8' } ); files.forEach( ( file ) => stream.push( file ) ); stream.push( null ); - stream = stream.pipe( createStyleEntryTransform() ); + stream = stream + .pipe( createStyleEntryTransform() ) + .pipe( createBlockJsonEntryTransform() ); } else { const bar = new ProgressBar( 'Build Progress: [:bar] :percent', { width: 30,