1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
#![deny(missing_docs)]
#[macro_export]
macro_rules! collapsed_eq {
($input:expr, $output:expr) => {
assert_eq!(collapse($input), collapse($output));
};
($input:expr, $output:expr, $($arg:tt)+) => {
assert_eq!(collapse($input), collapse($output), $($arg)+);
};
}
#[macro_export]
macro_rules! collapsed_ne {
($input:expr, $output:expr) => {
assert_ne!(collapse($input), collapse($output));
};
($input:expr, $output:expr, $($arg:tt)+) => {
assert_ne!(collapse($input), collapse($output), $($arg)+);
};
}
pub fn collapse(s: &str) -> String {
let s = s.trim();
let mut collapsed = String::new();
for c in s.chars() {
if let Some(last) = collapsed.chars().last() {
if c.is_whitespace() {
if !last.is_whitespace() {
collapsed.push(' ');
}
} else {
collapsed.push(c);
}
} else {
collapsed.push(c);
}
}
collapsed
}
#[cfg(test)]
mod test {
use crate::*;
#[test]
fn macro_test() {
collapsed_eq!(
r#"CREATE TABLE "test" (
"id" integer NOT NULL PRIMARY KEY AUTOINCREMENT
)"#,
r#"CREATE TABLE "test" ( "id" integer NOT NULL PRIMARY KEY AUTOINCREMENT )"#,
"This is a panic message you should never see"
);
collapsed_ne!(
"This is not the same...",
"...as this string.",
"You should never see this panic message either."
);
}
macro_rules! test {
($(#[$attr:meta])* $name:ident, $input:expr, $output:expr) => {
#[test]
$(#[$attr])*
fn $name() {
collapsed_eq!($input, $output);
}
}
}
test!(two_spaces, "two spaces", "two spaces");
test!(space_tab, "space tab", "space tab");
test!(line_space, "line\r\nspace", "line space");
test!(new_lines, "new\r\n
lines", "new lines");
test!(tabs, "some tabs\there", "some tabs here");
test!(no_change, "no change", "no change");
test!(all_whitespace, "\r\n\t ", " \n\r\t\n ");
test!(empty, "", "");
test!(empty1, " ", "");
test!(empty2, " ", "\n");
test!(empty3, " ", "\r\n");
test!(empty4, " ", " \t\t ");
test!(lead_tail, " lead \t tail \r", "lead tail");
test!(#[should_panic] should_fail1, "should fail", "SHOULD FAIL");
test!(#[should_panic] should_fail2, "should fail", "SHOULD FAIL");
test!(#[should_panic] should_fail3, "should\n fail", "SHOULD\n FAIL");
}