paste/
lib.rs

1//! [![github]](https://github.com/dtolnay/paste) [![crates-io]](https://crates.io/crates/paste) [![docs-rs]](https://docs.rs/paste)
2//!
3//! [github]: https://img.shields.io/badge/github-8da0cb?style=for-the-badge&labelColor=555555&logo=github
4//! [crates-io]: https://img.shields.io/badge/crates.io-fc8d62?style=for-the-badge&labelColor=555555&logo=rust
5//! [docs-rs]: https://img.shields.io/badge/docs.rs-66c2a5?style=for-the-badge&labelColor=555555&logoColor=white&logo=data:image/svg+xml;base64,PHN2ZyByb2xlPSJpbWciIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgdmlld0JveD0iMCAwIDUxMiA1MTIiPjxwYXRoIGZpbGw9IiNmNWY1ZjUiIGQ9Ik00ODguNiAyNTAuMkwzOTIgMjE0VjEwNS41YzAtMTUtOS4zLTI4LjQtMjMuNC0zMy43bC0xMDAtMzcuNWMtOC4xLTMuMS0xNy4xLTMuMS0yNS4zIDBsLTEwMCAzNy41Yy0xNC4xIDUuMy0yMy40IDE4LjctMjMuNCAzMy43VjIxNGwtOTYuNiAzNi4yQzkuMyAyNTUuNSAwIDI2OC45IDAgMjgzLjlWMzk0YzAgMTMuNiA3LjcgMjYuMSAxOS45IDMyLjJsMTAwIDUwYzEwLjEgNS4xIDIyLjEgNS4xIDMyLjIgMGwxMDMuOS01MiAxMDMuOSA1MmMxMC4xIDUuMSAyMi4xIDUuMSAzMi4yIDBsMTAwLTUwYzEyLjItNi4xIDE5LjktMTguNiAxOS45LTMyLjJWMjgzLjljMC0xNS05LjMtMjguNC0yMy40LTMzLjd6TTM1OCAyMTQuOGwtODUgMzEuOXYtNjguMmw4NS0zN3Y3My4zek0xNTQgMTA0LjFsMTAyLTM4LjIgMTAyIDM4LjJ2LjZsLTEwMiA0MS40LTEwMi00MS40di0uNnptODQgMjkxLjFsLTg1IDQyLjV2LTc5LjFsODUtMzguOHY3NS40em0wLTExMmwtMTAyIDQxLjQtMTAyLTQxLjR2LS42bDEwMi0zOC4yIDEwMiAzOC4ydi42em0yNDAgMTEybC04NSA0Mi41di03OS4xbDg1LTM4Ljh2NzUuNHptMC0xMTJsLTEwMiA0MS40LTEwMi00MS40di0uNmwxMDItMzguMiAxMDIgMzguMnYuNnoiPjwvcGF0aD48L3N2Zz4K
6//!
7//! <br>
8//!
9//! The nightly-only [`concat_idents!`] macro in the Rust standard library is
10//! notoriously underpowered in that its concatenated identifiers can only refer to
11//! existing items, they can never be used to define something new.
12//!
13//! [`concat_idents!`]: https://doc.rust-lang.org/std/macro.concat_idents.html
14//!
15//! This crate provides a flexible way to paste together identifiers in a macro,
16//! including using pasted identifiers to define new items.
17//!
18//! This approach works with any stable or nightly Rust compiler 1.30+.
19//!
20//! <br>
21//!
22//! # Pasting identifiers
23//!
24//! There are two entry points, `paste::expr!` for macros in expression position and
25//! `paste::item!` for macros in item position.
26//!
27//! Within either one, identifiers inside `[<`...`>]` are pasted together to form a
28//! single identifier.
29//!
30//! ```
31//! // Macro in item position: at module scope or inside of an impl block.
32//! paste::item! {
33//!     // Defines a const called `QRST`.
34//!     const [<Q R S T>]: &str = "success!";
35//! }
36//!
37//! fn main() {
38//!     // Macro in expression position: inside a function body.
39//!     assert_eq!(
40//!         paste::expr! { [<Q R S T>].len() },
41//!         8,
42//!     );
43//! }
44//! ```
45//!
46//! <br><br>
47//!
48//! # More elaborate examples
49//!
50//! This program demonstrates how you may want to bundle a paste invocation inside
51//! of a more convenient user-facing macro of your own. Here the `routes!(A, B)`
52//! macro expands to a vector containing `ROUTE_A` and `ROUTE_B`.
53//!
54//! ```
55//! const ROUTE_A: &str = "/a";
56//! const ROUTE_B: &str = "/b";
57//!
58//! macro_rules! routes {
59//!     ($($route:ident),*) => {{
60//!         paste::expr! {
61//!             vec![$( [<ROUTE_ $route>] ),*]
62//!         }
63//!     }}
64//! }
65//!
66//! fn main() {
67//!     let routes = routes!(A, B);
68//!     assert_eq!(routes, vec!["/a", "/b"]);
69//! }
70//! ```
71//!
72//! The next example shows a macro that generates accessor methods for some struct
73//! fields.
74//!
75//! ```
76//! macro_rules! make_a_struct_and_getters {
77//!     ($name:ident { $($field:ident),* }) => {
78//!         // Define a struct. This expands to:
79//!         //
80//!         //     pub struct S {
81//!         //         a: String,
82//!         //         b: String,
83//!         //         c: String,
84//!         //     }
85//!         pub struct $name {
86//!             $(
87//!                 $field: String,
88//!             )*
89//!         }
90//!
91//!         // Build an impl block with getters. This expands to:
92//!         //
93//!         //     impl S {
94//!         //         pub fn get_a(&self) -> &str { &self.a }
95//!         //         pub fn get_b(&self) -> &str { &self.b }
96//!         //         pub fn get_c(&self) -> &str { &self.c }
97//!         //     }
98//!         paste::item! {
99//!             impl $name {
100//!                 $(
101//!                     pub fn [<get_ $field>](&self) -> &str {
102//!                         &self.$field
103//!                     }
104//!                 )*
105//!             }
106//!         }
107//!     }
108//! }
109//!
110//! make_a_struct_and_getters!(S { a, b, c });
111//!
112//! fn call_some_getters(s: &S) -> bool {
113//!     s.get_a() == s.get_b() && s.get_c().is_empty()
114//! }
115//! #
116//! # fn main() {}
117//! ```
118//!
119//! <br><br>
120//!
121//! # Case conversion
122//!
123//! Use `$var:lower` or `$var:upper` in the segment list to convert an
124//! interpolated segment to lower- or uppercase as part of the paste. For
125//! example, `[<ld_ $reg:lower _expr>]` would paste to `ld_bc_expr` if invoked
126//! with $reg=`Bc`.
127//!
128//! Use `$var:snake` to convert CamelCase input to snake\_case.
129//! Use `$var:camel` to convert snake\_case to CamelCase.
130//! These compose, so for example `$var:snake:upper` would give you SCREAMING\_CASE.
131//!
132//! The precise Unicode conversions are as defined by [`str::to_lowercase`] and
133//! [`str::to_uppercase`].
134//!
135//! [`str::to_lowercase`]: https://doc.rust-lang.org/std/primitive.str.html#method.to_lowercase
136//! [`str::to_uppercase`]: https://doc.rust-lang.org/std/primitive.str.html#method.to_uppercase
137
138#![no_std]
139
140use proc_macro_hack::proc_macro_hack;
141
142/// Paste identifiers within a macro invocation that expands to an expression.
143#[proc_macro_hack]
144pub use paste_impl::expr;
145
146/// Paste identifiers within a macro invocation that expands to one or more
147/// items.
148///
149/// An item is like a struct definition, function, impl block, or anything else
150/// that can appear at the top level of a module scope.
151pub use paste_impl::item;
152
153/// Paste identifiers within a macro invocation that expands to one or more
154/// macro_rules macros or items containing macros.
155pub use paste_impl::item_with_macros;
156
157#[doc(hidden)]
158pub use paste_impl::EnumHack;