Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 37 additions & 0 deletions .vscode/linter.code-snippets
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
{
// Place your tea workspace snippets here. Each snippet is defined under a snippet name and has a scope, prefix, body and
// description. Add comma separated ids of the languages where the snippet is applicable in the scope field. If scope
// is left empty or omitted, the snippet gets applied to all languages. The prefix is what is
// used to trigger the snippet and the body will be expanded and inserted. Possible variables are:
// $1, $2 for tab stops, $0 for the final cursor position, and ${1:label}, ${2:another} for placeholders.
// Placeholders with the same ids are connected.
// Example:
// "Print to console": {
// "scope": "javascript,typescript",
// "prefix": "log",
// "body": [
// "console.log('$1');",
// "$2"
// ],
// "description": "Log output to console"
// }

"linttest": {
"scope": "rust",
"prefix": "linttest",
"body": [
"#[test]",
"fn $1() {",
" let sql = r#\"",
"$2",
" \"#;",
"",
" let file = SourceFile::parse(&sql);",
" let mut linter = Linter::new([Rule::$3]);",
" let errors = linter.lint(file, sql);",
" assert_debug_snapshot!(errors);",
"}",

]
}
}
83 changes: 83 additions & 0 deletions .vscode/syntax.code-snippets
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
{
// Place your tea workspace snippets here. Each snippet is defined under a snippet name and has a scope, prefix, body and
// description. Add comma separated ids of the languages where the snippet is applicable in the scope field. If scope
// is left empty or omitted, the snippet gets applied to all languages. The prefix is what is
// used to trigger the snippet and the body will be expanded and inserted. Possible variables are:
// $1, $2 for tab stops, $0 for the final cursor position, and ${1:label}, ${2:another} for placeholders.
// Placeholders with the same ids are connected.
// Example:
// "Print to console": {
// "scope": "javascript,typescript",
// "prefix": "log",
// "body": [
// "console.log('$1');",
// "$2"
// ],
// "description": "Log output to console"
// }
"astnode": {
"scope": "rust",
"prefix": "astnode",
"body": [

"#[derive(Debug, Clone, PartialEq, Eq, Hash)]",
"pub struct $1 {",
" pub(crate) syntax: SyntaxNode,",
"}",
"",
"impl AstNode for $1 {",
" #[inline]",
" fn can_cast(kind: SyntaxKind) -> bool {",
" kind == SyntaxKind::$2",
" }",
" #[inline]",
" fn cast(syntax: SyntaxNode) -> Option<Self> {",
" if Self::can_cast(syntax.kind()) {",
" Some(Self { syntax })",
" } else {",
" None",
" }",
" }",
" #[inline]",
" fn syntax(&self) -> &SyntaxNode {",
" &self.syntax",
" }",
"}",

]
},
"astenum": {
"scope": "rust",
"prefix": "astenum",
"body": [
"#[derive(Debug, Clone, PartialEq, Eq, Hash)]",
"pub enum $1 {",
" $3($3),",
"}",
"",
"impl AstNode for $1 {",
" #[inline]",
" fn can_cast(kind: SyntaxKind) -> bool {",
" matches!(kind, SyntaxKind::$2)",
" }",
" #[inline]",
" fn cast(syntax: SyntaxNode) -> Option<Self> {",
" let res = match syntax.kind() {",
" SyntaxKind::DEFAULT_CONSTRAINT => {",
" $1::$3($3 { syntax })",
" }",
" _ => return None,",
" };",
" Some(res)",
" }",
" #[inline]",
" fn syntax(&self) -> &SyntaxNode {",
" match self {",
" $1::$3(it) => &it.syntax,",
" }",
" }",
"}",

]
}
}
4 changes: 4 additions & 0 deletions crates/squawk_linter/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ use rules::renaming_column;
use rules::renaming_table;
use rules::require_concurrent_index_creation;
use rules::require_concurrent_index_deletion;
use rules::transaction_nesting;
// xtask:new-lint:rule-import

#[derive(Debug, PartialEq, Clone, Copy, Serialize, Hash, Eq, Deserialize, Sequence)]
Expand Down Expand Up @@ -340,6 +341,9 @@ impl Linter {
if self.rules.contains(&Rule::BanAlterDomainWithAddConstraint) {
ban_alter_domain_with_add_constraint(self, &file);
}
if self.rules.contains(&Rule::TransactionNesting) {
transaction_nesting(self, &file);
}
// xtask:new-lint:rule-call

// locate any ignores in the file
Expand Down
2 changes: 2 additions & 0 deletions crates/squawk_linter/src/rules/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ pub(crate) mod renaming_column;
pub(crate) mod renaming_table;
pub(crate) mod require_concurrent_index_creation;
pub(crate) mod require_concurrent_index_deletion;
pub(crate) mod transaction_nesting;
// xtask:new-lint:mod-decl

pub(crate) use adding_field_with_default::adding_field_with_default;
Expand Down Expand Up @@ -52,4 +53,5 @@ pub(crate) use renaming_column::renaming_column;
pub(crate) use renaming_table::renaming_table;
pub(crate) use require_concurrent_index_creation::require_concurrent_index_creation;
pub(crate) use require_concurrent_index_deletion::require_concurrent_index_deletion;
pub(crate) use transaction_nesting::transaction_nesting;
// xtask:new-lint:export
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
---
source: crates/squawk_linter/src/rules/transaction_nesting.rs
expression: errors
---
[
Violation {
code: TransactionNesting,
message: "There is an existing transaction already in progress, managed by your migration tool.",
text_range: 1..6,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
Violation {
code: TransactionNesting,
message: "There is an existing transaction already in progress, managed by your migration tool.",
text_range: 8..13,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
Violation {
code: TransactionNesting,
message: "Attempting to end the transaction that is managed by your migration tool",
text_range: 25..31,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: crates/squawk_linter/src/rules/transaction_nesting.rs
expression: errors
---
[
Violation {
code: TransactionNesting,
message: "There is an existing transaction already in progress.",
text_range: 8..13,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: crates/squawk_linter/src/rules/transaction_nesting.rs
expression: errors
---
[
Violation {
code: TransactionNesting,
message: "There is no transaction to `COMMIT` or `ROLLBACK`.",
text_range: 26..32,
help: Some(
"`BEGIN` a transaction at an earlier point in the migration or remove this statement.",
),
},
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: crates/squawk_linter/src/rules/transaction_nesting.rs
expression: errors
---
[
Violation {
code: TransactionNesting,
message: "Attempting to end the transaction that is managed by your migration tool",
text_range: 11..17,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
source: crates/squawk_linter/src/rules/transaction_nesting.rs
expression: errors
---
[
Violation {
code: TransactionNesting,
message: "Attempting to end the transaction that is managed by your migration tool",
text_range: 92..100,
help: Some(
"Put migration statements in separate files to have them be in separate transactions or don't use the assume-in-transaction setting.",
),
},
]
Loading
Loading