Rust Rubric

This document lists conventions to follow when writing Rust in the Fuchsia Source Tree. These conventions are a combination of best practices, project preferences, and some choices made for the sake of consistency.

Guidelines

Naming

Casing conforms to Rust idioms

See C-CASE.

Ad-hoc conversions follow as_, to_, into_ conventions

See C-CONV.

Getter names follow Rust convention

With a few exceptions, the get_ prefix is not used for getters in Rust code.

See C-GETTER.

Methods on collections that produce iterators follow iter, iter_mut, into_iter

See C-ITER.

Iterator type names match the methods that produce them

See C-ITER-TY.

Names use a consistent word order

See C-WORD-ORDER.

Interoperability

Types eagerly implement common traits

Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash, Debug, Display, Default should all be implemented when appropriate.

See C-COMMON-TRAITS.

Conversions use the standard traits From, AsRef, AsMut

See C-CONV-TRAITS.

Collections implement FromIterator and Extend

See C-COLLECT.

Data structures implement Serde's Serialize, Deserialize

See C-SERDE.

Types are Send and Sync where possible

See C-SEND-SYNC.

Error types are meaningful and well-behaved

See C-GOOD-ERR.

Binary number types provide Hex, Octal, Binary formatting

See C-NUM-FMT.

Generic reader/writer functions take R: Read and W: Write by value

See C-RW-VALUE.

Macros

Input syntax is evocative of the output

See C-EVOCATIVE.

Macros compose well with attributes

See C-MACRO-ATTR.

Item macros work anywhere that items are allowed

See C-ANYWHERE.

Item macros support visibility specifiers

See C-MACRO-VIS.

Type fragments are flexible

See C-MACRO-TY.

Documentation

Crate level docs are thorough and include examples

See C-CRATE-DOC.

All items have a rustdoc example

See C-EXAMPLE.

Examples use ?, not try!, not unwrap

See C-QUESTION-MARK.

Function docs include error, panic, and safety considerations

See C-FAILURE.

See C-LINK.

Rustdoc does not show unhelpful implementation details

See C-HIDDEN.

Predictability

Smart pointers do not add inherent methods

See C-SMART-PTR.

Conversions live on the most specific type involved

See C-CONV-SPECIFIC

Functions with a clear receiver are methods

See C-METHOD.

Functions do not take out-parameters

See C-NO-OUT.

Operator overloads are unsurprising

See C-OVERLOAD.

Only smart pointers implement Deref and DerefMut

See C-DEREF.

Constructors are static, inherent methods

See C-CTOR.

Flexibility

Functions expose intermediate results to avoid duplicate work

See C-INTERMEDIATE.

Caller decides where to copy and place data

See C-CALLER-CONTROL.

Functions minimize assumptions about parameters by using generics

See C-GENERIC.

Traits are object-safe if they may be useful as a trait object

See C-OBJECT.

Type safety

Newtypes provide static distinctions

See C-NEWTYPE.

Arguments convey meaning through types, not bool or Option

See C-CUSTOM-TYPE.

Types for a set of flags are bitflags, not enums

See C-BITFLAG.

Builders enable construction of complex values

See C-BUILDER.

Dependability

Functions validate their arguments

See C-VALIDATE.

Destructors never fail

See C-DTOR-FAIL.

Destructors that may block have alternatives

See C-DTOR-BLOCK.

Debuggability

All public types implement Debug

See C-DEBUG.

Debug representation is never empty

See C-DEBUG-NONEMPTY.

Future Proofing

Sealed traits protect against downstream implementations

See C-SEALED.

Structs have private fields

See C-STRUCT-PRIVATE.

Newtypes encapsulate implementation details

See C-NEWTYPE-HIDE.

Data structures do not duplicate derived trait bounds

See C-STRUCT-BOUNDS.

Updating the guidelines

This rubric is currently maintained by the Rust on Fuchsia Working Group. To propose additions or modifications, open a CL and cc fuchsia-rust-api-rubric@google.com to ensure it is reviewed.

Relationship with upstream Rust API guidelines

This rubric contains most of the Rust API Guidelines, however the following official guidelines are omitted:

  • C-FEATURE as Fuchsia does not currently support features for crates.
  • C-METADATA as Fuchsia does not maintain internal Cargo.toml files.
  • C-HTML-ROOT as Fuchsia does not currently publish most Rust code to crates.io.
  • C-RELNOTES as most Rust code in Fuchsia "lives at HEAD".
  • C-STABLE as Fuchsia does not currently publish most Rust code to crates.io.
  • C-PERMISSIVE as all of Fuchsia's Rust code is under the Fuchsia license.