Tweld
(you can read it as tiny-weld, token-weld, or just tweld, I am just happy to be here)
Tweld is a procedural macro toolkit and naming DSL for Rust. It allows you to dynamically generate, modify, and compose identifiers directly within your Rust code using a clean, safe, and intuitive @[] syntax (hopefully). Because the parsing happens safely inside the macro, any syntax errors in your modifiers will point exactly to the broken line in your IDE (also hopefully).
weld!;
The name comes from idea of fusing tokens, to help when writing macros, or macros for your macros (which was my initial case).
The @[] "interpolator"
Anything inside the @[] "interpolator" will be fused together. You can use the @[] syntax inside structs, functions, trait implementations, or anywhere an identifier is expected, as well as in the content of string literal.
"@[one - two]"will render"one-two"
It can be used with tokens to create identifiers, or inside a string literal.
weld!;
List [] and single value () groups
Inside the the brackets, you can organize it in groups, and apply specific modifiers to that group.
List Group
When creating a group using [] and applying mods to it, each modification will be handled as in a collection, instead of a single concatenated value.
weld!;
use render_names;
weld!
And inside a list group, you can have other groups, either single value or lists.
weld!;
When modifying a list group, these modifiers will be applied to each item:
singular,plural,- casing modifiers
lowercase,uppercase,pascalcase,camelcase,snakecase,titlecase,kebabcase,traincase,shoutykebabcase,shoutysnakecase,
- string specific
replacesubstringpadstartpadend
While other modifiers will behave as handling a vector,
- reverse: reverses the order of items, not the items themselves,
- repeat: repeats the items N times,
- splice: replaces the specified range in the vector with the given value (if the value is informed) and either yield the removed items, if used with out, or the modified vector if used with into,
- slice: slices the vector, returning the the values whithn the range,
Using
splitin this mode will split all the items that can be separated, adding them to the collection in the same point
joinflattens the collection into a single value (a String), placing a given separator between each (if informed).
Single Value group
When creating a group using () and applying mods to it, each modification will be applied as in a single value. This group concatenates all the values with no separator.
weld!;
Modifiers
While inside a group, you can apply a chain of modifiers, where each one will perform an operation on the previous result.
Simple modifiers:
These are self explanatory, being singular and plural just the removal of the letter 's' from the last word.
singular,plural,lower,lowercaseupper,uppercase
Casing style modifiers:
Casing style modifiers make use of the crate heck.
- PascalCase:
pascal,pascalcase,uppercamelcase - camelCase:
lowercamelcase,camelcase,camel - snake_case
snakecase,snake,snekcase,snek - Title Case:
titlecase,title - kebab-case:
kebabcase,kebab - Train-Case:
traincase,train - SHOUTY-KEBAB-CASE:
shoutykebabcase,shoutykebab - SHOUTY_SNAKE_CASE:
shoutysnakecase,shoutysnake,shoutysnekcase,shoutysnek
Limitations
Given the nature of the syntax, when applied to tokens (as in the body or signature of a function, etc), some of these modifiers will behave a bit different.
kebabcase,shoutykebabcase, andtraincasewon't work,titlecasewill behave likePascalCaseWhen applied to string literals, they will all work as intended
Advanced modifiers:
This crate comes with some modifiers that offer more complex operations that can be pretty helpful, given the right context
replace
It replaces all non-overlapping occurrences of a pattern, with a replacement string.
// will render: const a_small_ident = "";
weld!;
substr, substring
This modifier returns the part of this string from the start index up to and excluding the end index, or to the end of the string if no end index is supplied. Both indexes are optional.
// will render: const a_long_ident = "";
weld!;
reverse, rev
Reverses the identifier, or literal.
// will render: const tnedi_gnol_a = "";
weld!;
// will render: const nolem_on_nomel_on = "";
weld!;
repeat, rep, times
Creates a new value by repeating it n times.
// will render: const rawhide = "rolling' ,rolling' ,rolling' ";
weld!;
split
This modifier will either break the whole value if applied to a single value group, or break each item in a list, if applied to a list group. This modifier accepts a char, a string or a number higher than 0.
(The second case will render a different result because it will have all items splitted)
Splitting by a char, or a string:
// will render: const val = "get, onetwo, 3, 4struct";
weld! = "";
// will render: const val = "get, one, two, 3, 4, struct";
weld!;
Splitting by an index:
// will render: const val = "get-te_st-struct";
weld!;
// will render: const val = "ge,t-,te,st,-,st,ruct";
weld!;
When splitting by index, if the value is bigger than the length, the argument will be ignored
// will render: const val = "get-,test,-,stru,ct";
weld!;
join
Flattens the list of values into a single value, placing a given separator between each. The separator can be a string or a char. (If used in a scenario where the previous result is a single value, it wont have any impact).
// will render: const val = "get-,Test,-,Struct";
weld!;
padstart, padleft, padl
Padstart pads the value with a given string (repeated and/or truncated, if needed) so that the resulting string has a given length. The padding is applied from the start of this string.
/*
0 1 2 3
0123456789012345678901234567890 */
// will render: const val = "-----get-Test-Struct",
weld!;
/*
0 1 2 3
0123456789012345678901234567890 */
// will render: const val = "get-Test-Struct",
weld!
padend, padright, padr
Padstart pads the value with a given string (repeated and/or truncated, if needed) so that the resulting string has a given length. The padding is applied from the end of this string.
/*
0 1 2 3
0123456789012345678901234567890 */
// will render: const val = "get-Test-Struct-----",
weld!;
/*
0 1 2 3
0123456789012345678901234567890 */
// will render: const val = "get-Test-Struct",
weld!;
slice
Extracts a substring from a string using start and end positions. Both parameters are optional and support negative indexing, where negative values count backwards from the end of the string. When no arguments are provided, returns the full string. If the start is less than end, it will return an empty value
// will render: const val = "get_Struct",
weld!;
// will render: const val = "get_Test_St",
weld!;
// will render: const val = "St",
weld!;
// will render: const val = "get_",
weld!;
splice
Modifies a string in place by removing a portion defined by start and end positions, optionally replacing it with new content. Returns either the removed portion or the modified string depending on the variant used. Both positions are optional and support negative indexing, where negative values count backwards from the end of the string.
Returning the altered value (value, val, into)
// will render: const val = "g";
weld!;
weld!;
weld!;
Returning the removed value out, removed, rm
// will render: const val = "et_Test_Struct";
weld!;
weld!;
weld!;
Removing
// will render: const val = "gTest_Struct";
weld!;
// will render: const val = "et";
weld!;
Replacing
// will render: const val = "got_Test_Struct";
weld!;
// will render: const val = "got_Test_Struct";
weld!;
// will render: const val = "got_Test_Struct";
weld!;
// will render: const val = "got_";
weld!;
// will render: const val = "new";
weld!;
Using negative start
Will start counting from the end of the string
// will render: const val = "get_Test_St";
weld!;
// will render: const val = "get_Test_Stru";
weld!;
Using negative end
Will count from the end of the string
// will render: const val = "get_Test_Stt";
weld!;
// will render: const val = "get_Test_Strut";
weld!;
// will render: const val = "get_Test_St<->t";
weld!;
spliceout, splice_out
Alias for splice with out argument.
// will render: const val = "ruc";
weld!;
spliceinto, splice_into
Alias for splice with the into argument.
// will render: const val = "get_Test_St<->t";
weld!;