内容简介:在上一篇文章FFI1、将函数做成一个服务,通过进程间通信(IPC)或网络协议通信(RPC, RESTful等);
前言
在上一篇文章 使用Rust + Electron开发跨平台桌面应用 ( 一 ) 中,我们将Rust + Electron结合起来,使用Rust编写核心业务逻辑,并编译成node库提供给Electron的UI界面调用,但是在上一篇文章中发现遇到了很多问题,尤其是Electron 的版本和 Rust编译出来的版本必须要一致,否则会无法调用成功,这就很坑了,所以为了改变这一情况,今天我们将使用另一种方式将Rust的代码提供给Js进行调用,这就是FFI。
FFI是什么
FFI (Foreign Function Interface) 是用来与其它语言交互的接口,由于现实中很多程序是由不同编程语言写的,必然会涉及到跨语言调用,这时一般有两种解决方案:
1、将函数做成一个服务,通过进程间通信(IPC)或网络协议通信(RPC, RESTful等);
2、直接通过 FFI 调用。
前者需要至少两个独立的进程才能实现,而后者直接将其它语言的接口内嵌到本语言中,所以调用效率比前者高。
Rust作为系统级编程语言,也是对FFI提供了完善的支持。
mangle
由于rust支持重载,所以函数名会被编译器进行混淆,就像c++一样。因此当你的函数被编译完毕后,函数名会带上一串表明函数签名的字符串。
这样的函数名为ffi调用带来了困难,因此,rust提供了#[no_mangle]属性为函数修饰。 对于带有#[no_mangle]属性的函数,rust编译器不会为它进行函数名混淆, 如:
#[no_mangle] pub extern fn test() {}
下面我们来编写一个thread_count.rs,其实跟寻常的rust代码没有什么区别:
#[no_mangle] pub extern fn threadcount(x: i32) -> i32 { let result: i32 = num_cpus::get() as i32; return result * x; }
指定库类型
rust默认编译成rust自用的rlib格式库,要让rust编译成动态链接库或者静态链接库,需要显示指定,一共有三种方式,我这里采用的是直接在Cargo.Toml文件中指定,如下:
[lib] name = "thread_count" crate-type = ["dylib"]
需要注意的是 name
,必须符合rust的包结构,能够在src目录下找到。
我们执行cargo build命令,可以看到,在/target/debug目录下生成了我们需要的文件libthread_count.dylib
JS使用rust的动态链接库
那么我们要如何在JS中调用rust生成dylib呢?答案就是ffi-napi,我们使用ffi-napi这个包来在js中调用ffi,话不多说,直接看代码
let ffi = require('ffi-napi'); let path = require('path'); let threadCount = ffi.Library(path.join(__dirname, './target/debug/libthread_count'), { threadcount: ['int', ['int']] }); let result = threadCount.threadcount(12); console.log("thead_count: " + result);
结果如下:
好了,到此为止,我们就成功的将rust编译成动态链接库给JS调用了,这种方式是我觉得比较好的一种方式,虽然引入函数的方式比较丑,但是我们不用担心node版本的问题。
结语
虽然FFI是一种我认为比较好的方式,但是它也不是完美无缺的,例如,在跨越FFI的过程中,我们会丢失rust的类型信息,从而引发安全性问题,当然这也不是没有解决办法,我们可以使用rust的Box来包装我们的类型,这个可以单独开一篇文章来讲述,就不展开了(先挖个坑,哪天想起来再填)
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
猜你喜欢:- [译] 使用 Blazor 构建桌面应用
- Flutter 和桌面应用的最新进展
- Vue+Electron桌面应用程序
- electron vue桌面应用入门实例
- 桌面和应用交付:真的重要不紧急吗?
- PHPSciter 1.0 版本发布,轻松写桌面应用
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Python语言程序设计
(美)Y. Daniel Liang / 机械工业出版社 / 2013-3 / 79.00元
本书保持了Liang博士系列丛书中一贯的、标志性的教与学的哲学:以实例教,由实践学。书中采用了他所提出的已经经过实践检验的“基础先行”的方法,即在定义类之前,首先使用清晰简明的语言介绍基本程序设计概念,如选择语句、循环和函数;在介绍面向对象程序设计和GUI编程之前,首先介绍基本逻辑和程序设计概念。书中除了给出一些以游戏和数学为主的典型实例外,还在每章的开始使用简单的图形给出一两个例子,以激发学生的......一起来看看 《Python语言程序设计》 这本书的介绍吧!