basic_text_literals/
lib.rs

1use basic_text_internals::{is_basic_text, is_basic_text_substr};
2use proc_macro::TokenStream;
3use quote::quote_spanned;
4use syn::{parse_macro_input, LitStr};
5
6/// `TextStr` literal support: `text!("string literal")`.
7///
8/// Returns a `'static &TextStr` containing the provided string literal.
9#[proc_macro]
10pub fn text(input: TokenStream) -> TokenStream {
11    let input = parse_macro_input!(input as LitStr);
12    let span = input.span();
13
14    if !is_basic_text(&input.value()) {
15        return (quote_spanned! { span =>
16            compile_error!("string literal is not Basic Text")
17        })
18        .into();
19    }
20
21    (quote_spanned! { span =>
22        unsafe { ::basic_text::TextStr::from_text_unchecked(#input) }
23    })
24    .into()
25}
26
27/// `TextSubstr` literal support: `text_substr!("string literal\u{200e}")`.
28///
29/// Returns a `'static &TextSubstr` containing the provided string literal.
30#[proc_macro]
31pub fn text_substr(input: TokenStream) -> TokenStream {
32    let input = parse_macro_input!(input as LitStr);
33    let span = input.span();
34
35    if !is_basic_text_substr(&input.value()) {
36        return (quote_spanned! { span =>
37            compile_error!("string literal is not Basic Text substring")
38        })
39        .into();
40    }
41
42    (quote_spanned! { span =>
43        unsafe { ::basic_text::TextSubstr::from_text_unchecked(#input) }
44    })
45    .into()
46}