README.md
1Macros for all your token pasting needs
2=======================================
3
4[<img alt="github" src="https://img.shields.io/badge/github-dtolnay/paste-8da0cb?style=for-the-badge&labelColor=555555&logo=github" height="20">](https://github.com/dtolnay/paste)
5[<img alt="crates.io" src="https://img.shields.io/crates/v/paste.svg?style=for-the-badge&color=fc8d62&logo=rust" height="20">](https://crates.io/crates/paste)
6[<img alt="docs.rs" src="https://img.shields.io/badge/docs.rs-paste-66c2a5?style=for-the-badge&labelColor=555555&logoColor=white&logo=data:image/svg+xml;base64,PHN2ZyByb2xlPSJpbWciIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgdmlld0JveD0iMCAwIDUxMiA1MTIiPjxwYXRoIGZpbGw9IiNmNWY1ZjUiIGQ9Ik00ODguNiAyNTAuMkwzOTIgMjE0VjEwNS41YzAtMTUtOS4zLTI4LjQtMjMuNC0zMy43bC0xMDAtMzcuNWMtOC4xLTMuMS0xNy4xLTMuMS0yNS4zIDBsLTEwMCAzNy41Yy0xNC4xIDUuMy0yMy40IDE4LjctMjMuNCAzMy43VjIxNGwtOTYuNiAzNi4yQzkuMyAyNTUuNSAwIDI2OC45IDAgMjgzLjlWMzk0YzAgMTMuNiA3LjcgMjYuMSAxOS45IDMyLjJsMTAwIDUwYzEwLjEgNS4xIDIyLjEgNS4xIDMyLjIgMGwxMDMuOS01MiAxMDMuOSA1MmMxMC4xIDUuMSAyMi4xIDUuMSAzMi4yIDBsMTAwLTUwYzEyLjItNi4xIDE5LjktMTguNiAxOS45LTMyLjJWMjgzLjljMC0xNS05LjMtMjguNC0yMy40LTMzLjd6TTM1OCAyMTQuOGwtODUgMzEuOXYtNjguMmw4NS0zN3Y3My4zek0xNTQgMTA0LjFsMTAyLTM4LjIgMTAyIDM4LjJ2LjZsLTEwMiA0MS40LTEwMi00MS40di0uNnptODQgMjkxLjFsLTg1IDQyLjV2LTc5LjFsODUtMzguOHY3NS40em0wLTExMmwtMTAyIDQxLjQtMTAyLTQxLjR2LS42bDEwMi0zOC4yIDEwMiAzOC4ydi42em0yNDAgMTEybC04NSA0Mi41di03OS4xbDg1LTM4Ljh2NzUuNHptMC0xMTJsLTEwMiA0MS40LTEwMi00MS40di0uNmwxMDItMzguMiAxMDIgMzguMnYuNnoiPjwvcGF0aD48L3N2Zz4K" height="20">](https://docs.rs/paste)
7[<img alt="build status" src="https://img.shields.io/github/workflow/status/dtolnay/paste/CI/master?style=for-the-badge" height="20">](https://github.com/dtolnay/paste/actions?query=branch%3Amaster)
8
9The nightly-only [`concat_idents!`] macro in the Rust standard library is
10notoriously underpowered in that its concatenated identifiers can only refer to
11existing 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
15This crate provides a flexible way to paste together identifiers in a macro,
16including using pasted identifiers to define new items.
17
18```toml
19[dependencies]
20paste = "1.0"
21```
22
23This approach works with any Rust compiler 1.31+.
24
25<br>
26
27## Pasting identifiers
28
29Within the `paste!` macro, identifiers inside `[<`...`>]` are pasted together to
30form a single identifier.
31
32```rust
33use paste::paste;
34
35paste! {
36 // Defines a const called `QRST`.
37 const [<Q R S T>]: &str = "success!";
38}
39
40fn main() {
41 assert_eq!(
42 paste! { [<Q R S T>].len() },
43 8,
44 );
45}
46```
47
48<br>
49
50## More elaborate example
51
52The next example shows a macro that generates accessor methods for some struct
53fields. It demonstrates how you might find it useful to bundle a paste
54invocation inside of a macro\_rules macro.
55
56```rust
57use paste::paste;
58
59macro_rules! make_a_struct_and_getters {
60 ($name:ident { $($field:ident),* }) => {
61 // Define a struct. This expands to:
62 //
63 // pub struct S {
64 // a: String,
65 // b: String,
66 // c: String,
67 // }
68 pub struct $name {
69 $(
70 $field: String,
71 )*
72 }
73
74 // Build an impl block with getters. This expands to:
75 //
76 // impl S {
77 // pub fn get_a(&self) -> &str { &self.a }
78 // pub fn get_b(&self) -> &str { &self.b }
79 // pub fn get_c(&self) -> &str { &self.c }
80 // }
81 paste! {
82 impl $name {
83 $(
84 pub fn [<get_ $field>](&self) -> &str {
85 &self.$field
86 }
87 )*
88 }
89 }
90 }
91}
92
93make_a_struct_and_getters!(S { a, b, c });
94
95fn call_some_getters(s: &S) -> bool {
96 s.get_a() == s.get_b() && s.get_c().is_empty()
97}
98```
99
100<br>
101
102## Case conversion
103
104Use `$var:lower` or `$var:upper` in the segment list to convert an interpolated
105segment to lower- or uppercase as part of the paste. For example, `[<ld_
106$reg:lower _expr>]` would paste to `ld_bc_expr` if invoked with $reg=`Bc`.
107
108Use `$var:snake` to convert CamelCase input to snake\_case.
109Use `$var:camel` to convert snake\_case to CamelCase.
110These compose, so for example `$var:snake:upper` would give you SCREAMING\_CASE.
111
112The precise Unicode conversions are as defined by [`str::to_lowercase`] and
113[`str::to_uppercase`].
114
115[`str::to_lowercase`]: https://doc.rust-lang.org/std/primitive.str.html#method.to_lowercase
116[`str::to_uppercase`]: https://doc.rust-lang.org/std/primitive.str.html#method.to_uppercase
117
118<br>
119
120## Pasting documentation strings
121
122Within the `paste!` macro, arguments to a #\[doc ...\] attribute are implicitly
123concatenated together to form a coherent documentation string.
124
125```rust
126use paste::paste;
127
128macro_rules! method_new {
129 ($ret:ident) => {
130 paste! {
131 #[doc = "Create a new `" $ret "` object."]
132 pub fn new() -> $ret { todo!() }
133 }
134 };
135}
136
137pub struct Paste {}
138
139method_new!(Paste); // expands to #[doc = "Create a new `Paste` object"]
140```
141
142<br>
143
144#### License
145
146<sup>
147Licensed under either of <a href="LICENSE-APACHE">Apache License, Version
1482.0</a> or <a href="LICENSE-MIT">MIT license</a> at your option.
149</sup>
150
151<br>
152
153<sub>
154Unless you explicitly state otherwise, any contribution intentionally submitted
155for inclusion in this crate by you, as defined in the Apache-2.0 license, shall
156be dual licensed as above, without any additional terms or conditions.
157</sub>
158