webpack-plugins.ts 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. /*-----------------------------------------------------------------------------
  2. | Copyright (c) Jupyter Development Team.
  3. | Distributed under the terms of the Modified BSD License.
  4. |----------------------------------------------------------------------------*/
  5. import * as webpack from 'webpack';
  6. import * as fs from 'fs-extra';
  7. export namespace WPPlugin {
  8. /**
  9. * A WebPack Plugin that copies the assets to the static directory
  10. */
  11. export class FrontEndPlugin {
  12. constructor(buildDir: string, staticDir: string) {
  13. this.buildDir = buildDir;
  14. this.staticDir = staticDir;
  15. this._first = true;
  16. }
  17. apply(compiler: any) {
  18. compiler.hooks.afterEmit.tap('FrontEndPlugin', () => {
  19. // bail if no staticDir
  20. if (!this.staticDir) {
  21. return;
  22. }
  23. // ensure a clean static directory on the first emit
  24. if (this._first && fs.existsSync(this.staticDir)) {
  25. fs.removeSync(this.staticDir);
  26. }
  27. this._first = false;
  28. fs.copySync(this.buildDir, this.staticDir);
  29. });
  30. }
  31. buildDir: string;
  32. staticDir: string;
  33. private _first: boolean;
  34. }
  35. /**
  36. * A WebPack Plugin that ignores files that are filtered by a callback
  37. */
  38. export class FilterIgnorePlugin extends webpack.IgnorePlugin {
  39. constructor(ignored: (path: string) => boolean) {
  40. super({});
  41. // ignored should be a callback function that filters the build files
  42. this.ignored = ignored;
  43. }
  44. checkIgnore(result: any): any | null {
  45. if (!result) {
  46. return result;
  47. }
  48. return this.ignored(result.resource) ? result : null;
  49. }
  50. ignored: (path: string) => boolean;
  51. }
  52. /**
  53. * A helper class for the WatchIgnoreFilterPlugin. This is a close copy of
  54. * (the non-exported) webpack.IgnoringWatchFileSystem
  55. */
  56. class FilterIgnoringWatchFileSystem {
  57. constructor(wfs: any, ignored: (path: string) => boolean) {
  58. this.wfs = wfs;
  59. // ignored should be a callback function that filters the build files
  60. this.ignored = ignored;
  61. }
  62. watch(
  63. files: any,
  64. dirs: any,
  65. missing: any,
  66. startTime: any,
  67. options: any,
  68. callback: any,
  69. callbackUndelayed: any
  70. ) {
  71. const notIgnored = (path: string) => !this.ignored(path);
  72. const ignoredFiles = files.filter(this.ignored);
  73. const ignoredDirs = dirs.filter(this.ignored);
  74. const watcher = this.wfs.watch(
  75. files.filter(notIgnored),
  76. dirs.filter(notIgnored),
  77. missing,
  78. startTime,
  79. options,
  80. (
  81. err: any,
  82. filesModified: any,
  83. dirsModified: any,
  84. missingModified: any,
  85. fileTimestamps: any,
  86. dirTimestamps: any,
  87. removedFiles: any
  88. ) => {
  89. if (err) {
  90. return callback(err);
  91. }
  92. for (const path of ignoredFiles) {
  93. fileTimestamps.set(path, 1);
  94. }
  95. for (const path of ignoredDirs) {
  96. dirTimestamps.set(path, 1);
  97. }
  98. callback(
  99. err,
  100. filesModified,
  101. dirsModified,
  102. missingModified,
  103. fileTimestamps,
  104. dirTimestamps,
  105. removedFiles
  106. );
  107. },
  108. callbackUndelayed
  109. );
  110. return {
  111. close: () => watcher.close(),
  112. pause: () => watcher.pause(),
  113. getContextTimestamps: () => {
  114. const dirTimestamps = watcher.getContextTimestamps();
  115. for (const path of ignoredDirs) {
  116. dirTimestamps.set(path, 1);
  117. }
  118. return dirTimestamps;
  119. },
  120. getFileTimestamps: () => {
  121. const fileTimestamps = watcher.getFileTimestamps();
  122. for (const path of ignoredFiles) {
  123. fileTimestamps.set(path, 1);
  124. }
  125. return fileTimestamps;
  126. }
  127. };
  128. }
  129. ignored: (path: string) => boolean;
  130. wfs: any;
  131. }
  132. /**
  133. * A WebPack Plugin that ignores files files that are filtered
  134. * by a callback during a `--watch` build
  135. */
  136. export class FilterWatchIgnorePlugin {
  137. constructor(ignored: (path: string) => boolean) {
  138. this.ignored = ignored;
  139. }
  140. apply(compiler: any) {
  141. compiler.hooks.afterEnvironment.tap('FilterWatchIgnorePlugin', () => {
  142. compiler.watchFileSystem = new FilterIgnoringWatchFileSystem(
  143. compiler.watchFileSystem,
  144. this.ignored
  145. );
  146. });
  147. }
  148. ignored: (path: string) => boolean;
  149. }
  150. }