mirror of
https://github.com/rustfs/rustfs.git
synced 2026-08-07 05:43:14 +00:00
feat: add comprehensive formatting rules and type inference guidelines
This commit is contained in:
@@ -193,12 +193,18 @@ mod tests {
|
||||
let valid_parts = ['a', 'A', '0', '9', '_', '#', '@', '$', 'α', '中'];
|
||||
|
||||
for start_char in valid_starts {
|
||||
assert!(dialect.is_identifier_start(start_char),
|
||||
"Character '{}' should be valid identifier start", start_char);
|
||||
assert!(
|
||||
dialect.is_identifier_start(start_char),
|
||||
"Character '{}' should be valid identifier start",
|
||||
start_char
|
||||
);
|
||||
|
||||
for part_char in valid_parts {
|
||||
assert!(dialect.is_identifier_part(part_char),
|
||||
"Character '{}' should be valid identifier part", part_char);
|
||||
assert!(
|
||||
dialect.is_identifier_part(part_char),
|
||||
"Character '{}' should be valid identifier part",
|
||||
part_char
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -211,8 +217,14 @@ mod tests {
|
||||
assert!(!dialect.is_identifier_start('\0'), "Null character should not be valid identifier start");
|
||||
assert!(!dialect.is_identifier_part('\0'), "Null character should not be valid identifier part");
|
||||
|
||||
assert!(!dialect.is_identifier_start('\x01'), "Control character should not be valid identifier start");
|
||||
assert!(!dialect.is_identifier_part('\x01'), "Control character should not be valid identifier part");
|
||||
assert!(
|
||||
!dialect.is_identifier_start('\x01'),
|
||||
"Control character should not be valid identifier start"
|
||||
);
|
||||
assert!(
|
||||
!dialect.is_identifier_part('\x01'),
|
||||
"Control character should not be valid identifier part"
|
||||
);
|
||||
|
||||
assert!(!dialect.is_identifier_start('\x7F'), "DEL character should not be valid identifier start");
|
||||
assert!(!dialect.is_identifier_part('\x7F'), "DEL character should not be valid identifier part");
|
||||
@@ -226,10 +238,12 @@ mod tests {
|
||||
let unicode_letters = ['α', 'β', 'γ', 'Α', 'Β', 'Γ', '中', '文', '日', '本', 'ñ', 'ü', 'ç'];
|
||||
|
||||
for ch in unicode_letters {
|
||||
assert!(dialect.is_identifier_start(ch),
|
||||
"Unicode letter '{}' should be valid identifier start", ch);
|
||||
assert!(dialect.is_identifier_part(ch),
|
||||
"Unicode letter '{}' should be valid identifier part", ch);
|
||||
assert!(
|
||||
dialect.is_identifier_start(ch),
|
||||
"Unicode letter '{}' should be valid identifier start",
|
||||
ch
|
||||
);
|
||||
assert!(dialect.is_identifier_part(ch), "Unicode letter '{}' should be valid identifier part", ch);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -239,10 +253,16 @@ mod tests {
|
||||
|
||||
// Test all ASCII digits
|
||||
for digit in '0'..='9' {
|
||||
assert!(!dialect.is_identifier_start(digit),
|
||||
"ASCII digit '{}' should not be valid identifier start", digit);
|
||||
assert!(dialect.is_identifier_part(digit),
|
||||
"ASCII digit '{}' should be valid identifier part", digit);
|
||||
assert!(
|
||||
!dialect.is_identifier_start(digit),
|
||||
"ASCII digit '{}' should not be valid identifier start",
|
||||
digit
|
||||
);
|
||||
assert!(
|
||||
dialect.is_identifier_part(digit),
|
||||
"ASCII digit '{}' should be valid identifier part",
|
||||
digit
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -252,14 +272,16 @@ mod tests {
|
||||
|
||||
// Test that all valid identifier starts are also valid identifier parts
|
||||
let test_chars = [
|
||||
'a', 'A', 'z', 'Z', '_', '#', '@', 'α', '中', 'ñ',
|
||||
'0', '9', '$', ' ', '.', ',', ';', '(', ')', '=', '+', '-'
|
||||
'a', 'A', 'z', 'Z', '_', '#', '@', 'α', '中', 'ñ', '0', '9', '$', ' ', '.', ',', ';', '(', ')', '=', '+', '-',
|
||||
];
|
||||
|
||||
for ch in test_chars {
|
||||
if dialect.is_identifier_start(ch) {
|
||||
assert!(dialect.is_identifier_part(ch),
|
||||
"Character '{}' that is valid identifier start should also be valid identifier part", ch);
|
||||
assert!(
|
||||
dialect.is_identifier_part(ch),
|
||||
"Character '{}' that is valid identifier start should also be valid identifier part",
|
||||
ch
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -285,7 +307,10 @@ mod tests {
|
||||
assert!(!dialect_ref.is_identifier_start('0'), "Trait method should work for invalid start");
|
||||
assert!(dialect_ref.is_identifier_part('a'), "Trait method should work for valid part");
|
||||
assert!(dialect_ref.is_identifier_part('0'), "Trait method should work for digit part");
|
||||
assert!(dialect_ref.supports_group_by_expr(), "Trait method should return true for GROUP BY support");
|
||||
assert!(
|
||||
dialect_ref.supports_group_by_expr(),
|
||||
"Trait method should return true for GROUP BY support"
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -297,13 +322,22 @@ mod tests {
|
||||
let test_chars = ['a', 'A', '0', '_', '#', '@', '$', ' ', '.'];
|
||||
|
||||
for ch in test_chars {
|
||||
assert_eq!(dialect1.is_identifier_start(ch), dialect2.is_identifier_start(ch),
|
||||
"Different instances should behave the same for is_identifier_start");
|
||||
assert_eq!(dialect1.is_identifier_part(ch), dialect2.is_identifier_part(ch),
|
||||
"Different instances should behave the same for is_identifier_part");
|
||||
assert_eq!(
|
||||
dialect1.is_identifier_start(ch),
|
||||
dialect2.is_identifier_start(ch),
|
||||
"Different instances should behave the same for is_identifier_start"
|
||||
);
|
||||
assert_eq!(
|
||||
dialect1.is_identifier_part(ch),
|
||||
dialect2.is_identifier_part(ch),
|
||||
"Different instances should behave the same for is_identifier_part"
|
||||
);
|
||||
}
|
||||
|
||||
assert_eq!(dialect1.supports_group_by_expr(), dialect2.supports_group_by_expr(),
|
||||
"Different instances should behave the same for supports_group_by_expr");
|
||||
assert_eq!(
|
||||
dialect1.supports_group_by_expr(),
|
||||
dialect2.supports_group_by_expr(),
|
||||
"Different instances should behave the same for supports_group_by_expr"
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -90,7 +90,10 @@ mod tests {
|
||||
let _builder = CascadeOptimizerBuilder::default();
|
||||
|
||||
// Test that builder can be created successfully
|
||||
assert!(std::mem::size_of::<CascadeOptimizerBuilder>() > 0, "Builder should be created successfully");
|
||||
assert!(
|
||||
std::mem::size_of::<CascadeOptimizerBuilder>() > 0,
|
||||
"Builder should be created successfully"
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -109,7 +112,10 @@ mod tests {
|
||||
|
||||
// Test that we can call builder methods (even if we don't have mock implementations)
|
||||
// This tests the builder pattern itself
|
||||
assert!(std::mem::size_of::<CascadeOptimizerBuilder>() > 0, "Builder should be created successfully");
|
||||
assert!(
|
||||
std::mem::size_of::<CascadeOptimizerBuilder>() > 0,
|
||||
"Builder should be created successfully"
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
||||
@@ -104,7 +104,7 @@ mod tests {
|
||||
assert!(std::mem::size_of::<DefaultParser>() == 0, "Parser should be zero-sized");
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_default_parser_simple_select() {
|
||||
let parser = DefaultParser::default();
|
||||
let sql = "SELECT * FROM S3Object";
|
||||
@@ -119,11 +119,11 @@ mod tests {
|
||||
match &statements[0] {
|
||||
ExtStatement::SqlStatement(_) => {
|
||||
// Successfully parsed as SQL statement
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_default_parser_select_with_columns() {
|
||||
let parser = DefaultParser::default();
|
||||
let sql = "SELECT id, name, age FROM S3Object";
|
||||
@@ -137,11 +137,11 @@ mod tests {
|
||||
match &statements[0] {
|
||||
ExtStatement::SqlStatement(_) => {
|
||||
// Successfully parsed as SQL statement
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_default_parser_select_with_where() {
|
||||
let parser = DefaultParser::default();
|
||||
let sql = "SELECT * FROM S3Object WHERE age > 25";
|
||||
@@ -155,7 +155,7 @@ mod tests {
|
||||
match &statements[0] {
|
||||
ExtStatement::SqlStatement(_) => {
|
||||
// Successfully parsed as SQL statement
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -248,7 +248,7 @@ mod tests {
|
||||
assert!(result.is_ok(), "ExtParser::new_with_dialect should work");
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_ext_parser_complex_query() {
|
||||
let sql = "SELECT id, name, age FROM S3Object WHERE age > 25 AND department = 'IT' ORDER BY age DESC LIMIT 10";
|
||||
|
||||
@@ -261,11 +261,11 @@ mod tests {
|
||||
match &statements[0] {
|
||||
ExtStatement::SqlStatement(_) => {
|
||||
// Successfully parsed as SQL statement
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_ext_parser_aggregate_functions() {
|
||||
let sql = "SELECT COUNT(*), AVG(age), MAX(salary) FROM S3Object GROUP BY department";
|
||||
|
||||
@@ -278,7 +278,7 @@ mod tests {
|
||||
match &statements[0] {
|
||||
ExtStatement::SqlStatement(_) => {
|
||||
// Successfully parsed as SQL statement
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -348,14 +348,14 @@ mod tests {
|
||||
assert_eq!(statements.len(), 1, "Should have exactly one statement");
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_ext_parser_error_handling() {
|
||||
let invalid_sqls = vec![
|
||||
"SELECT FROM", // Missing column list
|
||||
"SELECT * FROM", // Missing table name
|
||||
"SELECT * FROM S3Object WHERE", // Incomplete WHERE clause
|
||||
"SELECT * FROM S3Object GROUP", // Incomplete GROUP BY
|
||||
"SELECT * FROM S3Object ORDER", // Incomplete ORDER BY
|
||||
"SELECT FROM", // Missing column list
|
||||
"SELECT * FROM", // Missing table name
|
||||
"SELECT * FROM S3Object WHERE", // Incomplete WHERE clause
|
||||
"SELECT * FROM S3Object GROUP", // Incomplete GROUP BY
|
||||
"SELECT * FROM S3Object ORDER", // Incomplete ORDER BY
|
||||
];
|
||||
|
||||
for sql in invalid_sqls {
|
||||
@@ -402,7 +402,7 @@ mod tests {
|
||||
assert_eq!(statements.len(), 1, "Should have exactly one statement");
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[test]
|
||||
fn test_parser_err_macro() {
|
||||
let error: Result<()> = parser_err!("Test error message");
|
||||
assert!(error.is_err(), "parser_err! macro should create error");
|
||||
@@ -410,7 +410,7 @@ mod tests {
|
||||
match error {
|
||||
Err(ParserError::ParserError(msg)) => {
|
||||
assert_eq!(msg, "Test error message", "Error message should match");
|
||||
},
|
||||
}
|
||||
_ => panic!("Expected ParserError::ParserError"),
|
||||
}
|
||||
}
|
||||
@@ -428,7 +428,7 @@ mod tests {
|
||||
Err(ParserError::ParserError(msg)) => {
|
||||
assert!(msg.contains("Expected test token"), "Error should contain expected message");
|
||||
assert!(msg.contains("found: found token"), "Error should contain found message");
|
||||
},
|
||||
}
|
||||
_ => panic!("Expected ParserError::ParserError"),
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user