eel
https://github.com/ChrisKnott/Eel#intro
electron是一种实现GUI单体应用的框架, GUI部分使用web前端技术, 后台运行在nodejs上。
虽然在同一个机器上,实际上实现了前后台分离。
nodejs属于web领域发展形成的后端平台,
对于python生态积累的优势无法应用到,例如很多只有在python上才有的强大的库, 例如 pandas numpy.
无法否认, GUI领域python原生也有一些框架, 但是都没有web前端的能力强大。
所以如何将 python后端的优势 和 web前端的优势集成起来,这是个问题。
eel 就是为了解决此问题诞生的, 后端采用 python作为后台, 前端仍然使用 web前端的一套技术。
Eel is a little Python library for making simple Electron-like offline HTML/JS GUI apps, with full access to Python capabilities and libraries.
Eel hosts a local webserver, then lets you annotate functions in Python so that they can be called from Javascript, and vice versa.
Eel is designed to take the hassle out of writing short and simple GUI applications. If you are familiar with Python and web development, probably just jump to this example which picks random file names out of the given folder (something that is impossible from a browser).
For some reason many of the best-in-class number crunching and maths libraries are in Python (Tensorflow, Numpy, Scipy etc) but many of the best visualization libraries are in Javascript (D3, THREE.js etc). Hopefully Eel makes it easy to combine these into simple utility apps for assisting your development.
优点
- 前后端RPC互相调用
- 后端多任务并发执行
底层架构
之所以前后端能够以类似RPC方式相互调用, 底层实现是依赖 websocket 通讯层,
在此通讯层上, 实现RPC相关的监听处理逻辑:
客户端 ——-> 服务器端
- 客户端 发送 call 消息 到服务器端
- 服务器端接收到客户端发送来的 call 消息
- 服务器端 处理call 消息, 并返回return消息
- 客户端接收到服务器端返回的 return 消息
- 客户端处理return消息,触发回调函数
服务端 ——-> 客户端
- 服务器端 发送 call 消息 给客户端
- 客户端收到服务器端发送过来的 call 消息
- 客户端处理call消息
- 客户端发送return消息给服务器端
- 服务器端接收到客户端返回的 return 消息
- 服务器端处理return消息,触发回调。
react + python
https://github.com/ChrisKnott/Eel/tree/master/examples/07%20-%20CreateReactApp
callbacks demo
https://github.com/ChrisKnott/Eel/tree/master/examples/02%20-%20callbacks
后端
import eel import random eel.init('web') @eel.expose def py_random(): return random.random() @eel.expose def py_exception(error): if error: raise ValueError("Test") else: return "No Error" def print_num(n): print('Got this from Javascript:', n) def print_num_failed(error, stack): print("This is an example of what javascript errors would look like:") print("/tError: ", error) print("/tStack: ", stack) # Call Javascript function, and pass explicit callback function eel.js_random()(print_num) # Do the same with an inline callback eel.js_random()(lambda n: print('Got this from Javascript:', n)) # Show error handling eel.js_with_error()(print_num, print_num_failed) eel.start('callbacks.html', size=(400, 300))
前端
<!DOCTYPE html> <html> <head> <title>Callbacks Demo</title> <script type="text/javascript" src="/eel.js"></script> <script type="text/javascript"> eel.expose(js_random); function js_random() { return Math.random(); } eel.expose(js_with_error); function js_with_error() { var test = 0; test.something("does not exist"); } function print_num(n) { console.log('Got this from Python: ' + n); } // Call Python function, and pass explicit callback function eel.py_random()(print_num); // Do the same with an inline callback eel.py_random()(n => console.log('Got this from Python: ' + n)); // show usage with promises // show no error eel.py_exception(false)().then((result) => { // this will execute since we said no error console.log("No Error") }).catch((result) => { console.log("This won't be seen if no error") } ); // show if an error occurrs eel.py_exception(true)().then((result) => { // this will not execute console.log("No Error") }).catch((result) => { console.log("This is the repr(e) for an exception " + result.errorText); console.log("This is the full traceback:/n" + result.errorTraceback); } ) </script> </head> <body> Callbacks demo </body> </html>
原创文章,作者:306829225,如若转载,请注明出处:https://blog.ytso.com/277623.html