1
Fork 0
mirror of https://github.com/RGBCube/alejandra synced 2025-07-30 12:07:46 +00:00

feat: support more inline comments

This commit is contained in:
Kevin Amado 2022-02-28 00:59:15 -05:00
parent ce2826be98
commit de6088b24c
14 changed files with 277 additions and 271 deletions

View file

@ -182,9 +182,7 @@ fn format(
// { }
rnix::SyntaxKind::NODE_ATTR_SET => crate::rules::attr_set::rule,
// a $op b
rnix::SyntaxKind::NODE_BIN_OP => {
crate::rules::bin_op_and_or_default::rule
}
rnix::SyntaxKind::NODE_BIN_OP => crate::rules::bin_op::rule,
// ${a} (interpolation but for NODE_SELECT)
rnix::SyntaxKind::NODE_DYNAMIC => crate::rules::dynamic::rule,
// $identifier
@ -213,9 +211,7 @@ fn format(
// let { }
rnix::SyntaxKind::NODE_LEGACY_LET => crate::rules::default,
// a or b
rnix::SyntaxKind::NODE_OR_DEFAULT => {
crate::rules::bin_op_and_or_default::rule
}
rnix::SyntaxKind::NODE_OR_DEFAULT => crate::rules::bin_op::rule,
// ( a )
rnix::SyntaxKind::NODE_PAREN => crate::rules::paren::rule,
// a | a ? b

View file

@ -0,0 +1,67 @@
use std::collections::LinkedList;
pub(crate) enum Trivia {
Comment(String),
Newlines(usize),
}
pub(crate) struct Child {
pub element: rnix::SyntaxElement,
pub inline_comment: Option<String>,
pub has_inline_comment: bool,
pub trivialities: LinkedList<Trivia>,
pub has_comments: bool,
pub has_trivialities: bool,
}
pub(crate) fn new(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> std::collections::linked_list::IntoIter<Child> {
let mut children = crate::children::Children::new(build_ctx, node);
let mut elements = LinkedList::new();
while let Some(element) = children.get_next() {
let mut inline_comment = None;
let mut trivialities = LinkedList::new();
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
if trivialities.is_empty() && text.starts_with('#') {
inline_comment = Some(text);
} else {
trivialities.push_back(Trivia::Comment(text));
}
}
crate::children::Trivia::Whitespace(text) => {
let newlines = crate::utils::count_newlines(&text);
if newlines > 0 {
trivialities.push_back(Trivia::Newlines(newlines))
}
}
});
let has_inline_comment = inline_comment.is_some();
let has_comments = trivialities
.iter()
.any(|trivia| matches!(trivia, Trivia::Comment(_)));
let has_trivialities = !trivialities.is_empty();
elements.push_back(Child {
element,
inline_comment,
has_inline_comment,
trivialities,
has_comments,
has_trivialities,
})
}
elements.into_iter()
}

View file

@ -29,6 +29,7 @@ static GLOBAL: mimalloc::MiMalloc = mimalloc::MiMalloc;
pub(crate) mod builder;
pub(crate) mod children;
pub(crate) mod children2;
pub mod format;
pub(crate) mod parsers;
pub(crate) mod position;

View file

@ -1,45 +0,0 @@
use std::collections::LinkedList;
#[derive(Debug)]
pub(crate) struct Apply {
pub left_expression: rnix::SyntaxElement,
pub comments_after_left: LinkedList<String>,
pub has_newlines_after_left: bool,
pub right_expression: rnix::SyntaxElement,
}
impl Apply {
pub(crate) fn parse(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> Apply {
let mut children = crate::children::Children::new(build_ctx, node);
// left_expression
let left_expression = children.get_next().unwrap();
// comments_after_left
// has_newlines_after_left
let mut comments_after_left = LinkedList::new();
let mut has_newlines_after_left = false;
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
comments_after_left.push_back(text);
}
crate::children::Trivia::Whitespace(text) => {
has_newlines_after_left = has_newlines_after_left
|| crate::utils::count_newlines(&text) > 0;
}
});
// right_expression
let right_expression = children.get_next().unwrap();
Apply {
left_expression,
comments_after_left,
has_newlines_after_left,
right_expression,
}
}
}

View file

@ -1,66 +0,0 @@
use std::collections::LinkedList;
#[derive(Debug)]
pub(crate) struct BinOp {
pub left_expression: rnix::SyntaxElement,
pub comments_before_operator: LinkedList<String>,
pub has_newlines_before_operator: bool,
pub operator: rnix::SyntaxElement,
pub comments_after_operator: LinkedList<String>,
pub has_newlines_after_operator: bool,
pub right_expression: rnix::SyntaxElement,
}
impl BinOp {
pub(crate) fn parse(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> BinOp {
let mut children = crate::children::Children::new(build_ctx, node);
// left_expression
let left_expression = children.get_next().unwrap();
// comments_before_operator
let mut comments_before_operator = LinkedList::new();
let mut has_newlines_before_operator = false;
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
comments_before_operator.push_back(text);
}
crate::children::Trivia::Whitespace(text) => {
has_newlines_before_operator = has_newlines_before_operator
|| crate::utils::count_newlines(&text) > 0;
}
});
// operator
let operator = children.get_next().unwrap();
// comments_after_operator
let mut comments_after_operator = LinkedList::new();
let mut has_newlines_after_operator = false;
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
comments_after_operator.push_back(text);
}
crate::children::Trivia::Whitespace(text) => {
has_newlines_after_operator = has_newlines_after_operator
|| crate::utils::count_newlines(&text) > 0;
}
});
// right_expression
let right_expression = children.get_next().unwrap();
BinOp {
left_expression,
comments_before_operator,
has_newlines_before_operator,
operator,
comments_after_operator,
has_newlines_after_operator,
right_expression,
}
}
}

View file

@ -1,5 +1,3 @@
pub(crate) mod apply;
pub(crate) mod assert_or_with;
pub(crate) mod bin_op;
pub(crate) mod if_else;
pub(crate) mod pattern;

View file

@ -4,35 +4,48 @@ pub(crate) fn rule(
) -> std::collections::LinkedList<crate::builder::Step> {
let mut steps = std::collections::LinkedList::new();
let parsed = crate::parsers::apply::Apply::parse(build_ctx, node);
let mut children = crate::children2::new(build_ctx, node);
let first = children.next().unwrap();
let second = children.next().unwrap();
let vertical = build_ctx.vertical
|| !parsed.comments_after_left.is_empty()
|| parsed.has_newlines_after_left;
|| first.has_inline_comment
|| first.has_trivialities
|| second.has_inline_comment
|| second.has_trivialities;
// left_expression
// first
if vertical {
steps.push_back(crate::builder::Step::FormatWider(
parsed.left_expression,
));
steps.push_back(crate::builder::Step::FormatWider(first.element));
} else {
steps.push_back(crate::builder::Step::Format(parsed.left_expression));
steps.push_back(crate::builder::Step::Format(first.element));
}
// comments_after_left
let has_comments_after_left = !parsed.comments_after_left.is_empty();
for text in parsed.comments_after_left {
if let Some(text) = first.inline_comment {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
steps.push_back(crate::builder::Step::Comment(text));
}
// right_expression
for trivia in first.trivialities {
match trivia {
crate::children2::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
steps.push_back(crate::builder::Step::Comment(text));
}
crate::children2::Trivia::Newlines(_) => {}
}
}
// second
if vertical {
if !has_comments_after_left
&& !parsed.has_newlines_after_left
if !first.has_inline_comment
&& !first.has_trivialities
&& matches!(
parsed.right_expression.kind(),
second.element.kind(),
rnix::SyntaxKind::NODE_ATTR_SET
| rnix::SyntaxKind::NODE_LIST
| rnix::SyntaxKind::NODE_PAREN
@ -44,12 +57,10 @@ pub(crate) fn rule(
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
};
steps.push_back(crate::builder::Step::FormatWider(
parsed.right_expression,
));
steps.push_back(crate::builder::Step::FormatWider(second.element));
} else {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Format(parsed.right_expression));
steps.push_back(crate::builder::Step::Format(second.element));
}
steps

View file

@ -0,0 +1,111 @@
pub(crate) fn rule(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> std::collections::LinkedList<crate::builder::Step> {
rule_with_configuration(build_ctx, node, "bin_op_and_or_default")
}
pub(crate) fn rule_with_configuration(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
parent_kind: &str,
) -> std::collections::LinkedList<crate::builder::Step> {
let mut steps = std::collections::LinkedList::new();
let mut children = crate::children2::new(build_ctx, node);
let first = children.next().unwrap();
let second = children.next().unwrap();
let third = children.next().unwrap();
let vertical = build_ctx.vertical
|| first.has_inline_comment
|| first.has_trivialities
|| second.has_inline_comment
|| second.has_trivialities
|| third.has_inline_comment
|| third.has_trivialities;
// first
if vertical {
let kind = first.element.kind();
if (parent_kind == "bin_op_and_or_default"
&& matches!(
kind,
rnix::SyntaxKind::NODE_BIN_OP
| rnix::SyntaxKind::NODE_OR_DEFAULT
))
|| (parent_kind == "select"
&& matches!(kind, rnix::SyntaxKind::NODE_SELECT))
{
steps.push_back(crate::builder::Step::Format(first.element));
} else {
steps.push_back(crate::builder::Step::FormatWider(first.element));
}
} else {
steps.push_back(crate::builder::Step::Format(first.element));
}
if let Some(text) = first.inline_comment {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
} else if vertical {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
for trivia in first.trivialities {
match trivia {
crate::children2::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
crate::children2::Trivia::Newlines(_) => {}
}
}
// second
if !vertical && parent_kind == "bin_op_and_or_default" {
steps.push_back(crate::builder::Step::Whitespace);
}
steps.push_back(crate::builder::Step::Format(second.element));
if let Some(text) = second.inline_comment {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
if second.has_comments {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
for trivia in second.trivialities {
match trivia {
crate::children2::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
crate::children2::Trivia::Newlines(_) => {}
}
}
} else if !second.has_inline_comment
&& parent_kind == "bin_op_and_or_default"
{
steps.push_back(crate::builder::Step::Whitespace);
}
// third
if vertical {
steps.push_back(crate::builder::Step::FormatWider(third.element));
} else {
steps.push_back(crate::builder::Step::Format(third.element));
}
steps
}

View file

@ -1,88 +0,0 @@
pub(crate) fn rule(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> std::collections::LinkedList<crate::builder::Step> {
rule_with_configuration(build_ctx, node, "bin_op_and_or_default")
}
pub(crate) fn rule_with_configuration(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
parent_kind: &str,
) -> std::collections::LinkedList<crate::builder::Step> {
let mut steps = std::collections::LinkedList::new();
let parsed = crate::parsers::bin_op::BinOp::parse(build_ctx, node);
let vertical = build_ctx.vertical
|| !parsed.comments_before_operator.is_empty()
|| parsed.has_newlines_before_operator
|| !parsed.comments_after_operator.is_empty()
|| parsed.has_newlines_after_operator;
// left_expression
if vertical {
let kind = parsed.left_expression.kind();
if (parent_kind == "bin_op_and_or_default"
&& matches!(
kind,
rnix::SyntaxKind::NODE_BIN_OP
| rnix::SyntaxKind::NODE_OR_DEFAULT
))
|| (parent_kind == "select"
&& matches!(kind, rnix::SyntaxKind::NODE_SELECT))
{
steps.push_back(crate::builder::Step::Format(
parsed.left_expression,
));
} else {
steps.push_back(crate::builder::Step::FormatWider(
parsed.left_expression,
));
}
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
} else {
steps.push_back(crate::builder::Step::Format(parsed.left_expression));
}
// comments_before_operator
for text in parsed.comments_before_operator {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
// operator
if !vertical && parent_kind == "bin_op_and_or_default" {
steps.push_back(crate::builder::Step::Whitespace);
}
steps.push_back(crate::builder::Step::Format(parsed.operator));
// comments_before_operator
if parsed.comments_after_operator.is_empty() {
if parent_kind == "bin_op_and_or_default" {
steps.push_back(crate::builder::Step::Whitespace);
}
} else {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
for text in parsed.comments_after_operator {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
}
// right_expression
if vertical {
steps.push_back(crate::builder::Step::FormatWider(
parsed.right_expression,
));
} else {
steps.push_back(crate::builder::Step::Format(parsed.right_expression));
}
steps
}

View file

@ -4,57 +4,79 @@ pub(crate) fn rule(
) -> std::collections::LinkedList<crate::builder::Step> {
let mut steps = std::collections::LinkedList::new();
let mut children = crate::children::Children::new(build_ctx, node);
let mut children = crate::children2::new(build_ctx, node);
let vertical = children.has_comments()
|| children.has_newlines()
|| build_ctx.vertical;
let first = children.next().unwrap();
let second = children.next().unwrap();
let third = children.next().unwrap();
// ${
let child = children.get_next().unwrap();
steps.push_back(crate::builder::Step::Format(child));
let vertical = build_ctx.vertical
|| first.has_inline_comment
|| first.has_trivialities
|| second.has_inline_comment
|| second.has_trivialities
|| third.has_inline_comment
|| third.has_trivialities;
// first
steps.push_back(crate::builder::Step::Format(first.element));
if vertical {
steps.push_back(crate::builder::Step::Indent);
}
if let Some(text) = first.inline_comment {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
} else if vertical {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
// /**/
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
for trivia in first.trivialities {
match trivia {
crate::children2::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
crate::children2::Trivia::Newlines(_) => {}
}
crate::children::Trivia::Whitespace(_) => {}
});
// expr
let child = children.get_next().unwrap();
if vertical {
steps.push_back(crate::builder::Step::FormatWider(child));
} else {
steps.push_back(crate::builder::Step::Format(child));
}
// /**/
children.drain_trivia(|element| match element {
crate::children::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
steps.push_back(crate::builder::Step::Comment(text));
}
crate::children::Trivia::Whitespace(_) => {}
});
// second
if vertical {
steps.push_back(crate::builder::Step::FormatWider(second.element));
} else {
steps.push_back(crate::builder::Step::Format(second.element));
}
// }
let child = children.get_next().unwrap();
if let Some(text) = second.inline_comment {
steps.push_back(crate::builder::Step::Whitespace);
steps.push_back(crate::builder::Step::Comment(text));
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
for trivia in second.trivialities {
match trivia {
crate::children2::Trivia::Comment(text) => {
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
steps.push_back(crate::builder::Step::Comment(text));
}
crate::children2::Trivia::Newlines(_) => {}
}
}
// third
if vertical {
steps.push_back(crate::builder::Step::Dedent);
steps.push_back(crate::builder::Step::NewLine);
steps.push_back(crate::builder::Step::Pad);
}
steps.push_back(crate::builder::Step::Format(child));
steps.push_back(crate::builder::Step::Format(third.element));
steps
}

View file

@ -1,7 +1,7 @@
pub(crate) mod apply;
pub(crate) mod assert_or_with;
pub(crate) mod attr_set;
pub(crate) mod bin_op_and_or_default;
pub(crate) mod bin_op;
pub(crate) mod dynamic;
pub(crate) mod if_else;
pub(crate) mod inherit;

View file

@ -2,7 +2,5 @@ pub(crate) fn rule(
build_ctx: &crate::builder::BuildCtx,
node: &rnix::SyntaxNode,
) -> std::collections::LinkedList<crate::builder::Step> {
crate::rules::bin_op_and_or_default::rule_with_configuration(
build_ctx, node, "select",
)
crate::rules::bin_op::rule_with_configuration(build_ctx, node, "select")
}

View file

@ -6,9 +6,9 @@
(a.b/**/or/**/(a.b/**/or/**/(a.b/**/or/**/c)))
(a.b/**/or/**/(a.b/**/or/**/(a.b/**/or/**/c)))
( a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a )
( a.a or a.a
or a.a
or
( a.a or a.a # test
or a.a # test
or # test
a.a or
a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a)
]

View file

@ -40,8 +40,9 @@
c)))
(a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a)
(a.a
or a.a
or a.a
or a.a
or a.a # test
or a.a # test
or # test
a.a
or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a or a.a)
]