我已经读过可以将Python 2.7代码转换为Web程序集,但是我找不到关于如何这样做的明确指南。
到目前为止,我已经使用Emscripten及其所有必要的组件编译了一个C程序到Web程序集,所以我知道它正在工作(使用指南:http://webassembly.org/getting-started/developers-guide/)
为了在Ubuntu机器上执行此操作,我必须采取哪些步骤?我是否必须将python代码转换为LLVM bitcode然后使用Emscripten进行编译?如果是这样,我将如何实现这一目标?
首先,让我们看一下原则上WebAssembly与asm.js的不同之处,以及是否有可能重用现有的知识和工具。以下是非常好的概述:
让我们重新概括一下,WebAssembly(MVP,就像its roadmap上的更多内容,粗略地说):
因此,目前WebAssembly是对asm.js的迭代,仅针对C / C ++。
它看起来不像GC是阻止Python代码定位WebAssembly / asm.js的唯一因素。两者都代表低级静态类型代码,其中Python代码不能(现实地)表示。由于WebAssembly / asm.js的当前工具链基于LLVM,因此可以轻松编译为LLVM IR的语言可以转换为WebAssembly / asm.js。但是唉,Python太活泼了,不适合它,正如pypy的Unladen Swallow和several attempts所证明的那样。
这个asm.js演示文稿有slides about the state of dynamic languages。这意味着目前只能将整个VM(C / C ++中的语言实现)编译为WebAssembly / asm.js并解释(在可能的情况下使用JIT)原始源。对于Python,有几个现有项目:
pypyjs.vm.js
,是13 MB(gzip -6
之后2MB)+ Python stdlib +其他东西。empython.js
是5.8 MB(gzip -6
后2.1 MB),没有stdlib。trzeci/emscripten/
构建它,这是一个现成的Emscripten工具链。就像是:
git clone https://github.com/matthewelse/micropython.git
cd micropython
docker run --rm -it -v $(pwd):/src trzeci/emscripten bash
apt-get update && apt-get install -y python3
cd emscripten
make -j
# to run REPL: npm install && nodejs server.js
它产生1.1 MB的micropython.js
(在gzip -d
之后为225 KB)。如果你只需要非常合规的实现而没有stdlib,那么后者已经需要考虑了。
要生成WebAssembly构建,您可以将Makefile
的第13行更改为
CC = emcc -s RESERVED_FUNCTION_POINTERS=20 -s WASM=1
然后make -j
产生:
113 KB micropython.js
240 KB micropython.wasm
您可以查看emcc hello.c -s WASM=1 -o hello.html
的HTML输出,以了解如何使用这些文件。
这样,您还可以在WebAssembly中构建PyPy和CPython,以在兼容的浏览器中解释您的Python应用程序。另一个可能有趣的事情是Nuitka,一个Python到C ++的编译器。可能有可能将您的Python应用程序构建到C ++,然后与CPython一起使用Emscripten进行编译。但实际上我不知道该怎么做。
目前,如果您正在构建一个传统的网站或Web应用程序,其中下载几兆字节的JS文件几乎不可用,请查看Python-to-JavaScript转换器(例如Transcrypt)或JavaScript Python实现(例如Brython) )。或者试试与list of languages that compile to JavaScript的其他人的运气。
否则,如果下载大小不是问题,并且您已准备好处理大量粗糙边缘,请在上述三个之间进行选择。
在Web程序集实现垃圾收集之前,这是不可能的。你可以在这里关注进展:https://github.com/WebAssembly/proposals/issues/16
简而言之:你无法将任意Python转换为Web Assembly,我怀疑你能在很长一段时间内完成。解决方法可能是Python到C到Web程序集,但由于Python-to-C很脆弱,因此通常不会起作用(见下文)。
WebAssembly专门针对类似C语言,您可以在http://webassembly.org/docs/high-level-goals/上看到
从Python到C的转换可以使用像PyPy这样的工具来完成,PyPy已经开发了很长时间,但它仍然不适用于任意Python代码。有几个原因:
1)Python有一些非常方便,抽象和漂亮的数据结构,但它们很难转换为静态代码。 2)Python依赖于动态垃圾收集。 2)大多数Python代码在很大程度上依赖于各种库,每个库都有自己的怪癖和问题(例如用C语言编写,甚至是汇编程序)。
如果你仔细研究为什么Python-to-C(或Python to C ++)如此棘手,你可以看到这个简洁答案背后的详细原因,但我认为这超出了你的问题的范围。