import path from 'path' ; import { createPlugin , logger } from 'presta' ; import { addHook } from 'pirates' ; import filewatcher from 'filewatcher' ; import sync from 'tiny-glob/sync' ; let watcher ; const hash = { } ; export default createPlugin ( ( ) => { return ( config , hooks ) => { if ( config . env !== 'production' && ! watcher ) { watcher = filewatcher ( ) ; watcher . on ( 'change' , ( file ) => { if ( hash [ file ] ) { logger . debug ( { level : logger . Levels . Debug , label : `@presta/source-filesystem` , message : `parent updated, reset` , } ) ; watcher . remove ( hash [ file ] ) ; hash [ file ] . map ( ( file ) => watcher . remove ( file ) ) ; } else { logger . debug ( { level : logger . Levels . Debug , label : `@presta/source-filesystem` , message : `watched file updated build parent` , } ) ; outer : for ( const parent of Object . keys ( hash ) ) { for ( const child of hash [ parent ] ) { if ( child === file ) { hooks . emitBuildFile ( { file : parent } ) ; continue outer ; } } } } } ) ; } const revert = addHook ( ( code ) => `module.exports = \`${ code . replace ( /`/g , '\\`' ) }\`` , { exts : [ '.md' ] } ) ; logger . debug ( { level : logger . Levels . Debug , label : `@presta/source-filesystem` , message : `initialized` , } ) ; return { cleanup ( ) { if ( watcher ) { watcher . removeAll ( ) ; watcher = undefined ; } revert ( ) ; logger . debug ( { level : logger . Levels . Debug , label : `@presta/source-filesystem` , message : `cleaned up` , } ) ; } , } ; } ; } ) ; export function source ( globs , parent ) { const dirname = path . dirname ( parent ) ; const filepaths = ( [ ] as string [ ] ) . concat ( globs ) . map ( ( glob ) => path . resolve ( dirname , glob ) ) . map ( ( glob ) => sync ( glob , { absolute : true } ) ) . flat ( ) ; if ( watcher ) { setTimeout ( ( ) => { hash [ parent ] = hash [ parent ] || [ ] ; hash [ parent ] . push ( ... filepaths ) ; watcher . add ( parent ) ; filepaths . map ( ( file ) => watcher . add ( file ) ) ; } , 100 ) ; } return filepaths . map ( ( filepath ) => { delete require . cache [ filepath ] ; return [ filepath , require ( filepath ) ] ; } ) ; }