Rust 2018开发环境配置与效率工具

文档列表见:Rust 移动端跨平台复杂图形渲染项目开发总结 - 目录

一句话概括:macOS/Linux用户首选CLion + Rust插件,折腾VSCode收益太低。以下内容都是参与开发gfx-rs等Rust图形项目时所作尝试的总结。

配置Rust编译环境

使用Rust开发macOS、iOS、Android等跨平台共享源码的项目,开发环境避免不了这些系统所要求的开发环境,即:

  • macOS、iOS需要安装Xcode
  • Android需要Android Studio、Android SDK、Android NDK,并且配置SDK、NDK到环境变量。如果不想手工配置SDK、NDK变量,对于macOS,推荐先安装Android Studio到Application,之后通过Android Studio安装Android SDK、NDK,然后向profile、zsh配置文件等写入SDK、NDK变量。
  • 修改Rust软件更新源为中科大站点对国内用户而言可以提高下载速度,已翻墙可不考虑。
    // 1. 打开环境变量配置文件
    vi ~/.bashrc
    // 2. 加入如下内容
    export RUSTUP_DIST_SERVER=https://mirrors.ustc.edu.cn/rust-static
    export RUSTUP_UPDATE_ROOT=https://mirrors.ustc.edu.cn/rust-static/rustup
    // 3. 激活新配置内容
    source ~/.bashrc
    
  1. 安装Rsut,如果要安装nightly编译工具链才加--channel=nightly
    curl -sSf https://mirrors.ustc.edu.cn/rust-static/rustup.sh | sh # -s -- --channel=nightly
    
  2. cargo环境变量设置
    当前版本的cargo装好后,并不自动设置环境变量。在此进行手动配置,方便后面使用cargo安装的效率工具。在此以macOS为例,mac上的cargo一般安装在~/.cargo/bin下。
    export CARGO_BIN="[你的HOME目录]/.cargo/bin"
    export PATH="$PATH:$CARGO_BIN"
    

IDE配置

CLion与推荐插件

  • Rust插件
    提供代码提示、补全、跳转等功能,比Rust Language Server(RLS)稳定、好用,插件功能的更新速度快
  • Toml
    方便编写Cargo.toml文件
  • Active Intellij Tab Hightlighter
    高亮当前打开的Tab页
  • Dash
    查文档方便
  • Git Conflict
    在源文件中用颜色区分代码冲突,比Intellij系列产品原生做法更直观
  • Grep Console
    过滤控制台输出,比默认功能更强
  • HighlightBracketPair
    高亮显示光标所在的区域,比如在某个{}()[]内。

不推荐Visual Studio Code的原因

RLS不稳定导致代码跳转经常失效是最重要的原因,但是,VSCode的优势是,在无法代码跳转的情况下还能提供比CLion更强的代码提示,这让我感到意外。

另外,VSCode配置起来麻烦,对Rust新手不友好。

效率工具

CI配置appveyor与travis

  1. appveyor配置文件appveyor.yml
    language: rust
    sudo: false
    
    matrix:
      include:
    
      - rust: stable
        script:
        - cargo test --all --locked
        - rustup component add rustfmt-preview
        - cargo fmt -- --write-mode=diff
    
  2. travis配置文件.travis.yml
    language: rust
    rust:
      - stable
      - nightly
    
    branches:
      except:
        - staging.tmp
    
    before_install:
      # Do not run bors builds against the nightly compiler.
      # We want to find out about nightly bugs, so they're done in master, but we don't block on them.
      - if [[ $TRAVIS_RUST_VERSION == "nightly" && $TRAVIS_BRANCH == "staging" ]]; then exit; fi
    
    script:
      - cargo test
      - cargo build #--manifest-path your_project_path/Cargo.toml --features remote
      - cargo build
      #- (cd examples && make) #TODO
    

cbindgen 给Rust代码自动生成C头文件

给iOS/Android等编写跨平台C++/Rust项目最终还是以C接口方式让外部使用,当提供较多接口时,手写容易出错、开发慢,此时用自动头文件生成器是更合理的选择,cbindgen可帮我们实现这一目标。

  1. 安装
    cargo install cbindgen
    
  2. 更新cbindgen
    cargo install --force cbindgen
    
  3. 使用方式一:命令行执行
    cbindgen crate/ -o crate/bindings.h
    
  4. 使用方式一:作为项目的预处理使用方式写成build.rs,对于复杂项目,推荐用此方案
    extern crate cbindgen;
    
    use std::env;
    
    fn main() {
        let crate_dir = env::var("CARGO_MANIFEST_DIR").unwrap();
    
        cbindgen::Builder::new()
          .with_crate(crate_dir)
          .generate()
          .expect("Unable to generate bindings")
          .write_to_file("bindings.h");
    }
    

bindgen 给C头文件生成Rust绑定代码

和cbindgen相反,bindgen可生成Rust调用C函数所需的FFI绑定代码,但是这个工具在遇到多重包含如#include "other_file.h"时会出错,详细说明见官方文档

  1. 安装 cargo install bindgen
  2. 使用bindgen input.h -o bindings.rs
    • --rust-target 指定Rust版本,如--rust-target 1.30
    • --rust-target nightly 使用nightly工具链

sccahe 多工作区共享编译缓存

目前Rust只支持工作区workspace内部多个项目间的编译缓存,不支持workspace之间的缓存。对于多个workspace引用了部分相同版本的组件,这花费了多余的编译时间,没意义。借助第三方工具sccahe 可解决此问题。

  1. 安装sccache cargo install sccache
  2. 配置sccache环境变量 export RUSTC_WRAPPER=sccache

rustfmt 统一代码风格

为避免无意义的风格争论,推荐使用Rust官方出品的统一代码风格组件rustfmt。以下所有命令都需要在已配置好Rust环境的终端上执行。

  1. 安装
    rustup component add rustfmt-preview
    
  2. 更新rustfmt版本,使用update命令可更新所有rustup已安装的组件。
    rustup update
    
  3. 使用 cargo fmt

自定义rustfmt代码风格

不建议自定义代码风格,最好和官方默认代码保持一致。 定制风格规则参考rustfmt#configuring-rustfmt

用built输出Rust项目构建信息

built是个编译依赖(dev-dependencies)的开源项目,详细用法见项目说明。

  1. 配置Cargo.toml

    [dev-dependencies]
    built = "*"
    
  2. 使用示例

    pub mod built_info {
        include!(concat!(env!("OUT_DIR"), "/built.rs"));
    }
    
    info!("This is version {}{}, built for {} by {}.",
          built_info::PKG_VERSION,
          built_info::GIT_VERSION.map_or_else(|| "".to_owned(),
                                              |v| format!(" (git {})", v)),
          built_info::TARGET,
          built_info::RUSTC_VERSION);
    trace!("I was built with profile \"{}\", features \"{}\" on {} using {}",
           built_info::PROFILE,
           built_info::FEATURES_STR,
           built_info::BUILT_TIME_UTC,
           built_info::DEPENDENCIES_STR);
    

输出信息:

This is version 0.1.0 (git 62eb1e2), built for x86_64-apple-darwin
by rustc 1.16.0-nightly (bf6d7b665 2017-01-15).

I was built with profile "debug", features "DEFAULT, ERR_PRINTLN"
on Thu, 16 Feb 2017 19:00:08 GMT using android_glue 0.2.1,
ansi_term 0.9.0, bitflags 0.3.3, bitflags 0.4.0, bitflags 0.6.0,
bitflags 0.7.0, block 0.1.6, built 0.1.0, byteorder 0.5.3,
bytes 0.3.0, cfg-if 0.1.0, cgl 0.1.5, cgmath 0.7.0, ...

Rust开发iOS项目的效率工具

cargo-lipo

cargo lipo一个命令可编译出iOS目前支持的5个CPU架构静态库,且自动合并成一个多合一的universal静态库。

  1. 安装 cargo install cargo-lipo
  2. 在Rust项目任意位置执行cargo lipo即可开始编译iOS静态库

Rust项目开启Bitcode编译

RUSTFLAGS="-C llvm-args=\"-fembed-bitcode\"" cargo build

You can tell cargo to pass any argument you wish to the Rust compiler by setting the RUSTFLAGS environment variable. The Rustc compiler has a flag -C llvm-args=val that you can use to pass additional arguments to llvm.

参考:Enable Bitcode Output in Cargo Build for iOS Targets?

cargo build指定需要的iOS版本

IPHONEOS_DEPLOYMENT_TARGET=7.0 cargo build

参考:libc .travis.yml文件

Rust开发Android JNI项目的效率工具

cargo-rumo

支持编译Android/iOS跨平台

  1. 安装cargo-rumo
    cargo install rumo
    
  2. 编译当前项目为APK
    rumo build
    
  3. 安装APK到模拟器或手机
    rumo device-install
    
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,847评论 4 362
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,208评论 1 292
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,587评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,942评论 0 205
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,332评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,587评论 1 218
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,853评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,568评论 0 198
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,273评论 1 242
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,542评论 2 246
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,033评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,373评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,031评论 3 236
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,073评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,830评论 0 195
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,628评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,537评论 2 269

推荐阅读更多精彩内容