前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Rust API 指南:文档

Rust API 指南:文档

作者头像
袁承兴
发布2020-12-10 10:46:28
1.9K0
发布2020-12-10 10:46:28
举报

原文:Rust API Guidelines chapter 4

Crate级别的文档应非常详尽,并包含示例(C-CRATE-DOC)

RFC1687.

所有条目都应有一个rustdoc示例(C-EXAMPLE)

每个公共模块,特型,结构,枚举,函数,方法,宏和类型定义都应具有一个示例,用于该功能的练习。

该准则应在合理范围内适用。

有时,附上另一个条目的适用示例的链接可能就足够了。例如,如果恰好一个函数使用特定类型,则可以在该函数或类型上编写单个示例后,从另一个链接到该示例。

示例的目的并不总是显示如何使用该条目。虽然读者希望了解如何调用函数,在枚举上进行匹配,以及一些基本任务。但是,一个示例最应该表明为什么要使用这个条目。

// 这是使用clone()的不良示例。它机械地显示*如何*
// 调用clone(),但没有显示出*为什么*要这样做。
fn main() {
    let hello = "hello";
​
    hello.clone();
}

示例使用?,不是try !,也不是unwrap(C-QUESTION-MARK)

不管喜欢与否,用户通常逐字复制示例代码。Unwrapping an error应该是用户需要做出的决定。

下面是这种常见的方式会构建易出错的示例代码。以#开头的行是在构建示例时通过cargo test编译的,但不会出现在用户可见的rustdoc中。

/// ```rust
/// # use std::error::Error;
/// #
/// # fn main() -> Result<(), Box<dyn Error>> {
/// your;
/// example?;
/// code;
/// #
/// #     Ok(())
/// # }
///

函数文档应包括错误,恐慌和安全注意事项(C-FAILURE)

错误条件应记录在“错误”部分中。这也适用于trait方法--实现允许或预期返回错误的trait方法应在“错误”部分进行记录。

例如在标准库中,std::io::Read::read trait方法的某些实现可能返回错误。

/// 从该源提取一些字节到指定的缓冲区中,返回
/// 读取了多少字节。
///
/// ... lots more info ...
///
/// # Errors
///
/// 如果此函数遇到任何形式的I/O或其他错误,错误
/// 变体将返回。如果返回错误,则必须
/// 保证不会读取任何字节。

恐慌情况应记录在“恐慌情况”部分。这也适用于trait方法-实现允许或预期产生恐慌的traits方法应在“ Panics”部分记录。

在标准库中,Vec::insert方法可能会出现恐慌。

/// 在向量中的索引位置处插入一个元素,将
/// 它后面的所有元素向右移位。
///
/// # Panics
///
/// 如果`index`超出范围,则产生恐慌。

不必记录所有可能的恐慌情况,特别是如果恐慌情况发生在调用方提供的逻辑中。例如,在以下代码中记录Display恐慌似乎过多。但如果不确定,也不是记录更多恐慌情况就更好。

/// # Panics
///
/// This function panics if `T`'s implementation of `Display` panics.
pub fn print<T: Display>(t: T) {
    println!("{}", t.to_string());
}

不安全的函数应记录在“安全性”部分,该部分说明了由调用者负责维护正确使用该函数的所有不变量。

不安全的std::ptr::read需要以下调用者。

/// 从`src`中读取值而不移动它。这使得
/// `src`中的内存不变。
///
/// # 安全
///
/// 除了接受原始指针之外,这是不安全的,因为它在语义上
/// 将值移出src,而不阻止未来使用src。
/// 如果`T`不是`Copy`,则必须注意确保`src`的值被
/// 数据再次覆盖之前不会使用(例如,使用`write`,
/// `zero_memory`或`copy_memory`)。注意,`*src = foo`也算使用
/// ,因为它将尝试把先前的值放在`*src`处。
///
/// 指针必须对齐;如果不是这种情况,请使用`read_unaligned`。

包含指向相关内容的超链接(C-LINK)

链接到相同类型内的方法通常如下所示:

[`serialize_struct`]: #method.serialize_struct

指向其他类型的链接通常如下所示

[`Deserialize`]: trait.Deserialize.html

链接也可能指向父模块或子模块:

[`Value`]: ../enum.Value.html
[`DeserializeOwned`]: de/trait.DeserializeOwned.html

RFC 1574在"Link all the things"标题下正式建议该准则。

Cargo.toml包含所有常见的元数据(C-METADATA)

Cargo.toml的[package]部分应包含以下值:

  • authors
  • description
  • license
  • repository
  • readme
  • keywords
  • categories

此外,还有两个可选的元数据字段:

  • documentation
  • homepage

默认情况下,http://crates.io会把crate的文档链接到docs.rs上。仅当文档托管在docs.rs以外的其他位置时,才需要设置documentation元数据,例如,因为crate链接到了docs.rs构建环境中不可用的共享库。

仅在有唯一的网站而不是代码库或API文档的情况下设置homepage元数据。不要使用documentationrepository值填充homepage。比如,serde将homepage设置为专用网站https://serde.rs

Crate设置html_root_url属性(C-HTML-ROOT)

假设crate使用docs.rs作为其主要API文档,则它应指向"https://docs.rs/CRATE/MAJOR.MINOR.PATCH"

html_root_url属性告诉rustdoc在编译下游crates时如何为crate中的项目创建URL。没有它,依赖于您的crate的crate文档中的链接将不正确。

#![doc(html_root_url = "https://docs.rs/log/0.3.8")]

由于此URL包含确切的版本号,因此必须与Cargo.toml中的版本号保持同步。 [version-sync](https://link.zhihu.com/?target=https%3A//crates.io/crates/version-sync)的crate可以帮助您解决此问题,方法是让您添加一个集成测试,如果html_root_url版本号与crate版本不同步,则该集成测试将失败。

如果您不喜欢这种机制,建议在Cargo.toml版本密钥中添加一条注释,提醒您自己将两者保持更新,例如:

version = "0.3.8" # remember to update html_root_url

对于在docs.rs外部托管的文档,如果在crate名称+ index.html后面的附加带您到crete根模块的文档,则html_root_url的值正确。例如,如果根模块的文档位于"https://api.rocket.rs/rocket/index.html",则html_root_url将为"https://api.rocket.rs"

Release notes记录所有重大更改(C-RELNOTES)

crate的用户可以阅读release notes,以找到crate每个已发行版本中发生更改的摘要。crate级文档和/或Cargo.toml中链接的存储库中应包含release notes的链接或说明本身。

release notes中应明确标识重大更改(如RFC 1105中所定义)。

如果使用Git跟踪crate的源代码,则发布到http://crates.io的每个发行版都应具有一个相应的tag,用于标识已发布的提交。非Git VCS工具也应使用类似的过程。

# Tag the current commit
GIT_COMMITTER_DATE=$(git log -n1 --pretty=%aD) git tag -a -m "Release 0.3.0" 0.3.0
git push --tags

首选带注释的标签,因为如果存在任何带注释的标签,则某些Git命令会忽略未注释的标签。

Example

Rustdoc不要显示无用的实现细节(C-HIDDEN)

Rustdoc应该包括用户完全使用crate所需的一切。可以在技术文章中解释相关的实现细节,但是它们不应该是文档中的真实条目。

尤其要选择在rustdoc可以看到哪些实现--所有用户需要使得能完全使用crate。在以下代码中,默认情况下,PublicError的rustdoc将显示From <PrivateError> impl。我们选择使用#[doc(hidden)]隐藏它,因为用户的代码中永远不会出现PrivateError,因此该隐含内容永远与他们无关。

// This error type is returned to users.
pub struct PublicError { /* ... */ }
​
// This error type is returned by some private helper functions.
struct PrivateError { /* ... */ }
​
// Enable use of `?` operator.
#[doc(hidden)]
impl From<PrivateError> for PublicError {
    fn from(err: PrivateError) -> PublicError {
        /* ... */
    }
}

[pub(crate)](https://link.zhihu.com/?target=https%3A//github.com/rust-lang/rfcs/blob/master/text/1422-pub-restricted.md) 是另一个用于从公共API删除实现细节的好工具。它允许项目从其自身模块的外部使用,但不能在同一crate外部使用。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • Crate级别的文档应非常详尽,并包含示例(C-CRATE-DOC)
  • 所有条目都应有一个rustdoc示例(C-EXAMPLE)
  • 示例使用?,不是try !,也不是unwrap(C-QUESTION-MARK)
  • 函数文档应包括错误,恐慌和安全注意事项(C-FAILURE)
  • 包含指向相关内容的超链接(C-LINK)
  • Cargo.toml包含所有常见的元数据(C-METADATA)
  • Crate设置html_root_url属性(C-HTML-ROOT)
  • Release notes记录所有重大更改(C-RELNOTES)
  • Example
  • Rustdoc不要显示无用的实现细节(C-HIDDEN)
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档