use quote::{format_ident, ToTokens};
use syn::{parse_quote, Ident, Item, Pat};
use crate::codegen::logic::Compiler;
impl Compiler {
pub fn define_invisible_item(&mut self, item: Item) {
let mod_ident = self.get_private_scope_ident();
if let Some(Item::Mod(m)) = self.shared_definition.get_mut(0) {
if let Some((_, items)) = m.content.as_mut() {
items.push(item);
return;
}
}
let mod_definition: Item = parse_quote! {
#[doc(hidden)]
#[allow(non_snake_case)]
pub mod #mod_ident {
use super::*;
use ::syn::parse::Parse;
#item
}
};
self.scoped_definition.push(parse_quote! {
#[allow(unused_imports)]
use #mod_ident::*;
});
self.shared_definition.insert(0, mod_definition);
}
pub fn get_private_scope_ident(&self) -> Ident {
format_ident!("__private_scope_for_{}", self.target)
}
pub fn pat_to_ident(pat: &Pat) -> Ident {
let raw_string = pat.to_token_stream().to_string();
let mut sanitized = String::with_capacity(raw_string.len());
let mut last_was_underscore = false;
for c in raw_string.chars() {
if c.is_alphanumeric() {
sanitized.push(c.to_ascii_lowercase());
last_was_underscore = false;
} else {
if !last_was_underscore {
sanitized.push('_');
last_was_underscore = true;
}
}
}
let final_str = sanitized.trim_matches('_');
let valid_name = if final_str.is_empty() { "_" } else { final_str };
format_ident!("{valid_name}")
}
}