All Projects → taiki-e → easy-ext

taiki-e / easy-ext

Licence: other
An attribute macro for easily writing extension trait pattern.

Programming Languages

rust
11053 projects
shell
77523 projects

Projects that are alternatives of or similar to easy-ext

futures-async-stream
Async stream for Rust and the futures crate.
Stars: ✭ 141 (+729.41%)
Mutual labels:  no-std, proc-macro
atat
no_std crate for parsing AT commands
Stars: ✭ 50 (+194.12%)
Mutual labels:  no-std
m4vga-rs
VGA-style video output for STM32F4 processors, in Rust
Stars: ✭ 122 (+617.65%)
Mutual labels:  no-std
undo
A undo-redo library.
Stars: ✭ 38 (+123.53%)
Mutual labels:  no-std
m
Deprecated in favor of the libm crate.
Stars: ✭ 27 (+58.82%)
Mutual labels:  no-std
cast.rs
Machine scalar casting that meets your expectations
Stars: ✭ 70 (+311.76%)
Mutual labels:  no-std
drone-stm32-map
STM32 peripheral mappings for Drone, an Embedded Operating System.
Stars: ✭ 16 (-5.88%)
Mutual labels:  no-std
litrs
Parsing and inspecting Rust literals (particularly useful for proc macros)
Stars: ✭ 25 (+47.06%)
Mutual labels:  proc-macro
arraydeque
A circular buffer with fixed capacity (Rust).
Stars: ✭ 82 (+382.35%)
Mutual labels:  no-std
restricted-sparse-merkle-tree
An optimized sparse merkle tree.
Stars: ✭ 47 (+176.47%)
Mutual labels:  no-std
metric
This library provides zero-cost dimensional analysis for safe, unit-aware numeric computations in Rust.
Stars: ✭ 23 (+35.29%)
Mutual labels:  no-std
vcell
Just like `Cell` but with volatile read / write operations
Stars: ✭ 16 (-5.88%)
Mutual labels:  no-std
betafpv-f3
Board Support Crate for the BetaFPV F3 Drone Flight Controller
Stars: ✭ 37 (+117.65%)
Mutual labels:  no-std
lombok-rs
Lombok port for Rust
Stars: ✭ 31 (+82.35%)
Mutual labels:  proc-macro
rust-fsm
Finite state machine framework for Rust with readable specifications
Stars: ✭ 67 (+294.12%)
Mutual labels:  proc-macro
reacty yew
Generate Yew components from React components via Typescript type definitions
Stars: ✭ 46 (+170.59%)
Mutual labels:  proc-macro
core2
The bare essentials of std::io for use in no_std. Alloc support is optional.
Stars: ✭ 67 (+294.12%)
Mutual labels:  no-std
field names
proc-macro for accessing struct field names at runtime
Stars: ✭ 26 (+52.94%)
Mutual labels:  proc-macro
optimath
A #[no_std] LinAlg library
Stars: ✭ 47 (+176.47%)
Mutual labels:  no-std
pipe-trait
Make it possible to chain regular functions
Stars: ✭ 22 (+29.41%)
Mutual labels:  no-std

easy-ext

crates.io docs.rs license rustc build status

An attribute macro for easily writing extension trait pattern.

[dependencies]
easy-ext = "1"

Compiler support: requires rustc 1.31+

Examples

use easy_ext::ext;

#[ext(ResultExt)]
pub impl<T, E> Result<T, E> {
    fn err_into<U>(self) -> Result<T, U>
    where
        E: Into<U>,
    {
        self.map_err(Into::into)
    }
}

Code like this will be generated:

pub trait ResultExt<T, E> {
    fn err_into<U>(self) -> Result<T, U>
    where
        E: Into<U>;
}

impl<T, E> ResultExt<T, E> for Result<T, E> {
    fn err_into<U>(self) -> Result<T, U>
    where
        E: Into<U>,
    {
        self.map_err(Into::into)
    }
}

You can elide the trait name.

use easy_ext::ext;

#[ext]
impl<T, E> Result<T, E> {
    fn err_into<U>(self) -> Result<T, U>
    where
        E: Into<U>,
    {
        self.map_err(Into::into)
    }
}

Note that in this case, #[ext] assigns a random name, so you cannot import/export the generated trait.

Visibility

There are two ways to specify visibility.

Impl-level visibility

The first way is to specify visibility at the impl level. For example:

use easy_ext::ext;

// unnamed
#[ext]
pub impl str {
    fn foo(&self) {}
}

// named
#[ext(StrExt)]
pub impl str {
    fn bar(&self) {}
}

Associated-item-level visibility

Another way is to specify visibility at the associated item level.

For example, if the method is pub then the trait will also be pub:

use easy_ext::ext;

#[ext(ResultExt)] // generate `pub trait ResultExt`
impl<T, E> Result<T, E> {
    pub fn err_into<U>(self) -> Result<T, U>
    where
        E: Into<U>,
    {
        self.map_err(Into::into)
    }
}

This is useful when migrate from an inherent impl to an extension trait.

Note that the visibility of all the associated items in the impl must be identical.

Note that you cannot specify impl-level visibility and associated-item-level visibility at the same time.

Supertraits

If you want the extension trait to be a subtrait of another trait, add Self: SubTrait bound to the where clause.

use easy_ext::ext;

#[ext(Ext)]
impl<T> T
where
    Self: Default,
{
    fn method(&self) {}
}

Supported items

Associated functions (methods)

use easy_ext::ext;

#[ext]
impl<T> T {
    fn method(&self) {}
}

Associated constants

use easy_ext::ext;

#[ext]
impl<T> T {
    const MSG: &'static str = "Hello!";
}

Associated types

use easy_ext::ext;

#[ext]
impl str {
    type Owned = String;

    fn method(&self) -> Self::Owned {
        self.to_owned()
    }
}

License

Licensed under either of Apache License, Version 2.0 or MIT license at your option.

Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].