sindresorhus / project-ideas

Need a JavaScript module or looking for ideas? Welcome ✨
544 stars 9 forks source link

Pure JS `xz` compressing/decompressing #1

Open sindresorhus opened 9 years ago

sindresorhus commented 9 years ago

xz is a lossless data compression program and file format which incorporates the LZMA/LZMA2 compression algorithms.

The current xz modules on npm uses native bindings, which is very fragile and not very suitable for reusable modules. It would be nice to have a pure JS version even though it would be a lot slower. Could then make a wrapper module that used the native binding if it installed successfully, otherwise the JS version.

Might be worth looking into compiling the native xz code to JS using emscripten.

This could potentially also be useful in the browser, where everything have to be pure JS.

Prior art

// @puzrin @mafintosh

puzrin commented 9 years ago

Personally, i'm more interested in high quality brotli port for ttf -> woff2 convertor.

squarejaw commented 9 years ago

My attempts to compile the xz code with emscripten have failed so far. At least some of the code uses multi-threading which is unsupported.

sindresorhus commented 9 years ago

@squarejaw You could compile with the --disable-threads flag, see the INSTALL file.

squarejaw commented 9 years ago

@sindresorhus That seems to fix part of it, but I'm still running into issues running the compiled js, e.g.

pipe() returning an error as we do not support them

If I remove some of the offending code calling pipe() it seems unable to find the files I specify to compress/decompress. I'll probably dig into it some more, but after looking at the spec and Java implementation it might not be too bad to write a JS version from scratch.

sindresorhus commented 9 years ago

@puzrin → https://github.com/devongovett/brotli.js

sindresorhus commented 9 years ago

it might not be too bad to write a JS version from scratch.

Sure, but it would most likely be slower and would require manual maintenance. Compiling it to JS with Emscripten would IMHO be the best option.

puzrin commented 9 years ago

@sindresorhus i know that project. It's cross-compiled, noticeable size - not interesting for me.

puzrin commented 9 years ago

Sure, but it would most likely be slower and would require manual maintenance. Compiling it to JS with Emscripten would IMHO be the best option.

That depends on your goals. If you need to get result fast - cross compiling is the best choice. But size will be 4x more than manually ported. Manually ported code is not slower, if you know how to do it. We did zlib porting as excercise to learn v8 optimizations.

sindresorhus commented 9 years ago

@puzrin I need this for Node.js so size isn't really that big of an issue. Performance is though. I know you could make it as fast, but most couldn't, and it would require a lot more work than with Emscripten.

puzrin commented 9 years ago

@sindresorhus you are right. In most cases, cross-compiling will be more optimal way to get predictable result in minimal time.

As i said, we had different and "crazy" (not business friendly) criterias to do zlib port - "interesting", "learning", "nobody will repeat" and so on :)

simlu commented 6 years ago

Any update on this?

Richienb commented 4 years ago

@sindresorhus Is https://www.npmjs.com/package/lzma what you're looking for?

simlu commented 4 years ago

@Richienb Unfortunately no. The lzma package also uses native bindings which exactly what the OP was trying to avoid

pimterry commented 3 years ago

https://www.npmjs.com/package/xzwasm was just published a couple of weeks ago, looks promising

phanirithvij commented 2 years ago

A side note: xzwasm only implements decompression