赞
踩
原始地址:https://dev.to/jennasys/creating-react-applications-with-python-2je1
让我先说说这个问题:
我真的很喜欢用Python进行编程,但我不是JavaScript的超级粉丝。 但让我们面对现实吧,JavaScript是Web的方式,而Python无法在Web浏览器中运行。那么故事的结局就写好了,对吗?嗯,并非如此快速,就像热门的TypeScript语言被转译成JavaScript在Web浏览器中运行一样,Transcrypt也为Python做同样的事情。
由于Transcrypt将Python的数据类型和语言构造映射到JavaScript的方式,你的Python代码能够利用现有的JavaScript库生态系统。Transcrypt充当了一个桥梁,使您能够利用现有的JavaScript Web应用程序技术,而不是试图重新发明它们。而且,它的工作方式不会显著影响应用程序性能,与使用纯JavaScript相比,也不需要大量的运行时模块下载到客户端。尽管我们使用JavaScript库,但我们不必使用JavaScript来使用它们的API。
Transcrypt的功能包括:
与其在Web浏览器应用程序中需要发出HTTP请求时转向urllib或requests库,不如使用window.fetch()或JavaScript的axios库。但是,您仍然可以使用Python编写来调用这些JavaScript库。
大多数Python语言构造和内置模块都已在Transcrypt中实现,因此使用标准的Python对象,如列表、字典、字符串等,会感觉就像使用Python一样。但一般来说,除非库(及其依赖项)是纯Python,否则不支持第三方Python库。
这意味着,当您的Web浏览器应用程序需要发出HTTP请求时,不要转向urllib或requests库,而是使用window.fetch()或JavaScript的axios库。但是,您仍然可以使用Python编写来调用这些JavaScript库。
使用Transcrypt非常简单。理想情况下,您应该为项目创建一个Python虚拟环境,并激活该环境,然后使用PIP安装Transcrypt。 Transcrypt当前支持Python 3.9或Python 3.7,因此您需要使用其中一个版本来创建您的虚拟环境,然后安装相应版本的Transcrypt:
$ python3.9 -m venv venv
或者
$ python3.7 -m venv venv
$ source venv/bin/activate (对于Windows,请使用 venv\Scripts\activate) (venv) $ pip install transcrypt==3.9
或者
(venv) $ pip install transcrypt==3.7.16
安装了Transcrypt之后,我们可以尝试一个简单的“Hello World”Web应用程序,以查看它的工作原理。我们将创建两个文件:一个带有几个函数的Python文件,以及一个在Web浏览器中打开的HTML文件:
清单1:
hello.py
def say_hello():
document.getElementById('destination').innerHTML = "Hello World!"
def clear_it():
document.getElementById('destination').innerHTML = ""
清单2:
hello.html
<!DOCTYPE html>
<html lang="en">
<body>
<script type="module">
import {say_hello, clear_it} from "./__target__/hello.js";
document.getElementById("sayBtn").onclick = say_hello;
document.getElementById("clearBtn").onclick = clear_it;
</script>
<button type="button" id="sayBtn">Click Me!</button>
<button type="button" id="clearBtn">Clear</button>
<div id="destination"></div>
</body>
</html>
然后,我们使用Transcrypt CLI转换Python文件:
(venv) $ transcrypt --nomin --map hello
hello是要转换的Python模块的名称
我们可以使用内置的Python HTTP服务器提供“Hello World”应用程序:
(venv) $ python -m http.server
这将启动一个Web服务器,从当前目录中提供文件,我们可以在以下位置打开我们的HTML文件:
http://localhost:8000/hello.html
正如您在这个简单示例中所看到的,我们使用Python语法使Python调用JavaScript对象的方法,而JavaScript调用已被转换的“Python”函数。正如前面提到的,生成的JavaScript代码非常可读:
清单3(生成的代码):
target/hello.js
// Transcrypt'ed from Python
import {AssertionError, ... , zip} from './org.transcrypt.__runtime__.js';
var __name__ = '__main__';
export var say_hello = function () {
document.getElementById('destination').innerHTML = 'Hello World!';
};
export var clear_it = function () {
document.getElementById('destination').innerHTML = '';
};
//# sourceMappingURL=hello.map
为了演示源码映射功能,我们可以再次创建两个源文件:一个包含要转换的函数的Python文件,一个HTML文件,它将是我们在Web浏览器中应用程序的入口点。这次,我们的Python文件将有一个使用JavaScript和Python方法将文本输出到Web浏览器控制台的函数,以及一个在运行时生成错误的JavaScript函数调用:
清单4:
sourcemap.py
def print_stuff():
console.log("Native JS console.log call")
print("Python print")
console.invalid_method("This will be an error")
清单5:
sourcemap.html
<!DOCTYPE html>
<html lang="en">
<body>
<script type="module">
import {print_stuff} from "./__target__/sourcemap.js";
document.getElementById("printBtn").onclick = print_stuff;
</script>
<button type="button" id="printBtn">Print</button>
</body>
</html>
(venv) $ transcrypt --nomin --map sourcemap
这一次,在启动了内置的Python HTTP服务器之后:
(venv) $ python -m http.server
我们可以在这里打开我们的测试应用程序:
http://localhost:8000/sourcemap.html
如果在Web浏览器中打开开发者控制台,然后点击按钮,前两个调用将会执行,并将文本打印到Web浏览器控制台上。调用JavaScript
console.log()方法的行为与您期望的相同。但如您在这里所见,Python print()函数最终会转换为调用JavaScript的console.log()方法。
第三个函数调用会生成一个错误,因为我们试图调用一个不存在的JavaScript
console对象的方法。但是,在这种情况下,源码映射可以将我们引导到问题的根本原因,即我们的Python源文件中发生错误的位置。因此,即使实际运行在Web浏览器中的是生成的JavaScript代码,使用源码映射,我们仍然可以在Web浏览器中查看我们的Python代码,看看在Python文件中错误发生的位置。
现在我们已经了解了Transcrypt如何让我们调用JavaScript,接下来我们将借助Transcrypt来调用React库。我们将再次从一个简单的Hello World应用程序开始,但这次的方式是使用React。我们仍然会使用两个源文件:一个要转换的Python文件和一个将在Web浏览器中打开的HTML文件。HTML文件将做一些额外的工作,负责加载React JavaScript库。
清单6:
hello_react.py
useState = React.useState el = React.createElement def App(): val, setVal = useState("") def say_hello(): setVal("Hello React!") def clear_it(): setVal("") return [ el('button', {'onClick': say_hello}, "Click Me!"), el('button', {'onClick': clear_it}, "Clear"), el('div', None, val) ] def render(): ReactDOM.render( el(App, None), document.getElementById('root') ) document.addEventListener('DOMContentLoaded', render)
清单7:
hello_react.html
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"/> <script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"> </script> <script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"> </script> <script type="module" src="__target__/hello_react.js"></script> </head> <body> <div id="root">Loading...</div> </body> </html>
现在,使用Transcrypt将Python文件转译为可执行的JavaScript文件:
(venv) $ transcrypt --nomin --map hello_react
再次,在启动了内置的Python HTTP服务器之后:
(venv) $ python -m http.server
然后,在Web浏览器中打开演示React应用程序:
http://localhost:8000/hello_react.html
虽然与我们之前做的第一个演示应用程序在功能上相同,但这次React将动态生成的HTML作为指定元素的子元素添加 - 在本例中是“root”div。
在这里,我们添加了一些方便的变量,将React的全局方法映射到本地的Python变量上。React的createElement()方法是该库的核心,用于在浏览器中动态生成HTML元素。
React是声明式、功能式的,并且基于状态。这意味着您定义了视图,然后React在状态发生变化时负责何时以及如何更新它。根据设计,React的状态变量是不可变的,并使用setter函数进行更新。这有助于React知道何时发生状态更改,以便根据需要重新呈现视图。在此示例中,我们使用React的useState()方法创建了一个名为val的变量及其对应的setVal()setter函数。
React函数组件的返回语句通常由对React.createElement()函数的多次嵌套和链接调用组成,它们共同形成HTML元素和/或React组件的树结构。这是声明性定义视图的地方。如果您不习惯使用Python中的函数式编程,这可能需要一些时间来适应。
ReactDOM的render()函数获取顶层React组件和要将其附加到的DOM中的HTML元素的引用。它将React生成的动态生成的HTML树作为指定元素的子元素添加。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。