Skip to content

Releases: evanw/esbuild

v0.8.12

21 Nov 06:53
Compare
Choose a tag to compare
  • Added an API for incremental builds (#21)

    There is now an API for incremental builds. This is what using the API looks like from JavaScript:

    require('esbuild').build({
      entryPoints: ['app.js'],
      bundle: true,
      outfile: 'out.js',
      incremental: true,
    }).then(result => {
      // The "rebuild" method is present if "incremental" is true. It returns a
      // promise that resolves to the same kind of object that "build" returns.
      // You can call "rebuild" as many times as you like.
      result.rebuild().then(result2 => {
        // Call "dispose" when you're done to free up resources.
        result.rebuild.dispose()
      })
    })

    Using the API from Go is similar, except there is no need to manually dispose of the rebuild callback:

    result := api.Build(api.BuildOptions{
      EntryPoints: []string{"app.js"},
      Bundle: true,
      Outfile: "out.js",
      Incremental: true,
    })
    result2 := result.Rebuild()

    Incremental builds are more efficient than regular builds because some data is cached and can be reused if the original files haven't changed since the last build. There are currently two forms of caching used by the incremental build API:

    • Files are stored in memory and are not re-read from the file system if the file metadata hasn't changed since the last build. This optimization only applies to file system paths. It does not apply to virtual modules created by plugins.

    • Parsed ASTs are stored in memory and re-parsing the AST is avoided if the file contents haven't changed since the last build. This optimization applies to virtual modules created by plugins in addition to file system modules, as long as the virtual module path remains the same.

    This is just the initial release of the incremental build API. Incremental build times still have room for improvement. Right now esbuild still re-resolves, re-loads, and re-links everything even if none of the input files have changed. Improvements to the incremental build mechanism will be coming in later releases.

  • Support for a local file server (#537)

    You can now run esbuild with the --serve flag to start a local server that serves the output files over HTTP. This is intended to be used during development. You can point your <script> tag to a local server URL and your JavaScript and CSS files will be automatically built by esbuild whenever that URL is accessed. The server defaults to port 8000 but you can customize the port with --serve=....

    There is also an equivalent API for JavaScript:

    require('esbuild').serve({
      port: 8000,
    },{
      entryPoints: ['app.js'],
      bundle: true,
      outfile: 'out.js',
      incremental: true,
    }).then(server => {
      // Call "stop" on the server when you're done
      server.stop()
    })

    and for Go:

    server, err := api.Serve(api.ServeOptions{
      Port: 8000,
    }, api.BuildOptions{
      EntryPoints: []string{"app.js"},
      Bundle:      true,
      Outfile:     "out.js",
      Incremental: true,
    })
    
    // Call "stop" on the server when you're done
    server.Stop()

    This is a similar use case to "watch mode" in other tools where something automatically rebuilds your code when a file has changed on disk. The difference is that you don't encounter the problem where you make an edit, switch to your browser, and reload only to load the old files because the rebuild hasn't finished yet. Using a HTTP request instead of a file system access gives the rebuild tool the ability to delay the load until the rebuild operation has finished so your build is always up to date.

  • Install to a temporary directory for Windows (#547)

    The install script runs npm in a temporary directory to download the correct binary executable for the current architecture. It then removes the temporary directory after the installation. However, removing a directory is sometimes impossible on Windows. To work around this problem, the install script now installs to the system's temporary directory instead of a directory inside the project itself. That way it's not problematic if a directory is left behind by the install script. This change was contributed by @Djaler.

  • Fix the public path ending up in the metafile (#549)

    The change in version 0.8.7 to include the public path in import paths of code splitting chunks caused a regression where the public path was also included in the list of chunk imports in the metafile. This was unintentional. Now the public path setting should not affect the metafile contents.

v0.8.11

18 Nov 22:26
Compare
Choose a tag to compare
  • Fix parsing of casts in TypeScript followed by certain tokens

    This aligns esbuild's TypeScript parser with the official TypeScript parser as far as parsing of as casts. It's not valid to form an expression after an as cast if the next token is a (, [, ++, --, ?., assignment operator, or template literal. Previously esbuild wouldn't generate an error for these expressions. This is normally not a problem because the TypeScript compiler itself would reject the code as invalid. However, if the next token starts on a new line, that new token may be the start of another statement. In that case the code generated by esbuild was different than the code generated by the TypeScript compiler. This difference has been fixed.

  • Implement wildcards for external paths (#406)

    You can now use a * wildcard character with the --external option to mark all files matching a certain pattern as external, which will remove them from the bundle. For example, you can now do --external:*.png to remove all .png files. When a * wildcard character is present in an external path, that pattern will be applied to the original path in the source code instead of to the path after it has been resolved to a real file system path. This lets you match on paths that aren't real file system paths.

  • Add a warning about self-assignment

    This release adds a warning for code that assigns an identifier to itself (e.g. x = x). This code is likely a mistake since doing this has no effect. This warning is not generated for assignments to global variables, since that can have side effects, and self-assignments with TypeScript casts, since those can be useful for changing the type of a variable in TypeScript. The warning is also not generated for code inside a node_modules folder.

v0.8.10

18 Nov 05:13
Compare
Choose a tag to compare
  • Fix parsing of conditional types in TypeScript (#541)

    Conditional types in TypeScript take the form A extends B ? C : D. Parsing of conditional types in esbuild was incorrect. The ? can only follow an extends clause but esbuild didn't require the extends clause, which potentially led to build failures or miscompilation. The parsing for this syntax has been fixed and should now match the behavior of the TypeScript compiler. This fix was contributed by @rtsao.

  • Ignore comments for character frequency analysis (#543)

    Character frequency analysis is used to derive the order of minified names for better gzip compression. The idea is to prefer using the most-used characters in the non-symbol parts of the document (keywords, strings, etc.) over characters that are less-used or absent. This is a very slight win, and is only approximate based on the input text instead of the output text because otherwise it would require minifying twice.

    Right now comments are included in this character frequency histogram. This is not a correctness issue but it does mean that documents with the same code but different comments may be minified to different output files. This release fixes this difference by removing comments from the character frequency histogram.

  • Add an option to ignore tree-shaking annotations (#458)

    Tree shaking is the term the JavaScript community uses for dead code elimination, a common compiler optimization that automatically removes unreachable code. Since JavaScript is a dynamic language, identifying unused code is sometimes very difficult for a compiler, so the community has developed certain annotations to help tell compilers what code should be considered unused. Currently there two forms of tree-shaking annotations that esbuild supports: inline /* @__PURE__ */ comments before function calls and the sideEffects field in package.json.

    These annotations can be problematic because the compiler depends completely on developers for accuracy and the annotations are occasionally incorrect. The sideEffects field is particularly error-prone because by default it causes all files in your package to be considered dead code if no imports are used. If you add a new file containing side effects and forget to update that field, your package will break when people try to bundle it.

    This release adds a new flag --tree-shaking=ignore-annotations to allow you to bundle code that contains incorrect tree-shaking annotations with esbuild. An example of such code is @tensorflow/tfjs. Ideally the --tree-shaking=ignore-annotations flag is only a temporary workaround. You should report these issues to the maintainer of the package to get them fixed since they will trip up other people too.

  • Add support for absolute baseUrl paths in tsconfig.json files

    Previously esbuild always joined the baseUrl path to the end of the current directory path. However, if the baseUrl was an absolute path, that would end up including the current directory path twice. This situation could arise internally in certain cases involving multiple tsconfig.json files and extends fields even if the tsconfig.json files themselves didn't have absolute paths. Absolute paths are now not modified and should work correctly.

  • Fix crash for modules that do module.exports = null (#532)

    The code generated by esbuild would crash at run-time if a module overwrote module.exports with null or undefined. This has been fixed and no longer crashes.

v0.8.9

17 Nov 08:15
Compare
Choose a tag to compare
  • Add support for the mips64le architecture (#523)

    You should now be able to install esbuild on the mips64le architecture. This build target is second-tier as it's not covered by CI, but I tested it in an emulator and it appears to work at the moment.

  • Fix for packages with inconsistent side effect markings

    Packages can have multiple entry points in their package.json file. Two commonly-used ones are specified using the fields main and module. Packages can also mark files in the package as not having side effects using the sideEffects field. Some packages have one entry point marked as having side effects and the other entry point as not having side effects. This is arguably a problem with the package itself. However, this caused an issue with esbuild's automatic entry point field selection method where it would incorrectly consider both main and module to not have side effects if one of them was marked as not having side effects. Now main and module will only be considered to not have side effects if the individual file was marked as not having side effects.

  • Warn about import './file' when ./file was marked as having no side effects

    Files in packages containing "sideEffects": false in the enclosing package.json file are intended to be automatically removed from the bundle if they aren't used. However, code containing import './file' is likely trying to import that file for a side effect. This is a conflict of intentions so it seems like a good idea to warn about this. It's likely a configuration error by the author of the package. The warning points to the location in package.json that caused this situation.

  • Add support for glob-style tests in sideEffects arrays

    The sideEffects field in package.json can optionally contain an array of files that are considered to have side effects. Any file not in that list will be removed if the import isn't used. Webpack supports the * and ? wildcard characters in these file strings. With this release, esbuild supports these wildcard characters too.