Skip to content

Commit

Permalink
Merge branch 'oxc-project:main' into linter/order
Browse files Browse the repository at this point in the history
  • Loading branch information
Spoutnik97 authored Jan 9, 2025
2 parents 2c4a972 + fd35866 commit 50fdf58
Show file tree
Hide file tree
Showing 609 changed files with 6,059 additions and 4,306 deletions.
17 changes: 17 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,23 @@
"SERVER_PATH_DEV": "${workspaceRoot}/target/debug/oxc_language_server",
"RUST_LOG": "debug"
}
},
{
"type": "lldb",
"request": "launch",
"name": "Debug Oxlint",
"cargo": {
"env": {
"RUSTFLAGS": "-g"
},
"args": ["build", "--bin=oxlint", "--package=oxlint"],
"filter": {
"name": "oxlint",
"kind": "bin"
}
}
// "args": ["--ARGS-TO-OXLINT"],
// "cwd": "PATH-TO-TEST-PROJECT"
}
]
}
2 changes: 2 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ homepage = "https://oxc.rs"
keywords = ["JavaScript", "TypeScript", "linter", "minifier", "parser"]
license = "MIT"
repository = "https://github.com/oxc-project/oxc"
rust-version = "1.78" # Support last 6 minor versions.
rust-version = "1.79" # Support last 6 minor versions.
description = "A collection of JavaScript tools written in Rust."

# <https://doc.rust-lang.org/rustc/lints/listing/allowed-by-default.html>
Expand Down
15 changes: 12 additions & 3 deletions crates/oxc_allocator/src/vec.rs
Original file line number Diff line number Diff line change
Expand Up @@ -245,15 +245,24 @@ impl<'alloc, T> IntoIterator for Vec<'alloc, T> {
}
}

impl<'alloc, T> IntoIterator for &'alloc Vec<'alloc, T> {
type IntoIter = std::slice::Iter<'alloc, T>;
type Item = &'alloc T;
impl<'i, T> IntoIterator for &'i Vec<'_, T> {
type IntoIter = std::slice::Iter<'i, T>;
type Item = &'i T;

fn into_iter(self) -> Self::IntoIter {
self.0.iter()
}
}

impl<'i, T> IntoIterator for &'i mut Vec<'_, T> {
type IntoIter = std::slice::IterMut<'i, T>;
type Item = &'i mut T;

fn into_iter(self) -> Self::IntoIter {
self.0.iter_mut()
}
}

impl<T, I> ops::Index<I> for Vec<'_, T>
where
I: SliceIndex<[T]>,
Expand Down
22 changes: 20 additions & 2 deletions crates/oxc_ast/src/ast_impl/js.rs
Original file line number Diff line number Diff line change
Expand Up @@ -263,6 +263,18 @@ impl<'a> Expression<'a> {
matches!(self, Expression::FunctionExpression(_) | Expression::ArrowFunctionExpression(_))
}

/// Returns `true` if this [`Expression`] is an anonymous function definition.
/// Note that this includes [`Class`]s.
/// <https://262.ecma-international.org/15.0/#sec-isanonymousfunctiondefinition>
pub fn is_anonymous_function_definition(&self) -> bool {
match self {
Self::ArrowFunctionExpression(_) => true,
Self::FunctionExpression(func) => func.name().is_none(),
Self::ClassExpression(class) => class.name().is_none(),
_ => false,
}
}

/// Returns `true` if this [`Expression`] is a [`CallExpression`].
pub fn is_call_expression(&self) -> bool {
matches!(self, Expression::CallExpression(_))
Expand Down Expand Up @@ -1160,7 +1172,13 @@ impl<'a> ArrowFunctionExpression<'a> {
}
}

impl Class<'_> {
impl<'a> Class<'a> {
/// Returns this [`Class`]'s name, if it has one.
#[inline]
pub fn name(&self) -> Option<Atom<'a>> {
self.id.as_ref().map(|id| id.name.clone())
}

/// `true` if this [`Class`] is an expression.
///
/// For example,
Expand Down Expand Up @@ -1479,7 +1497,7 @@ impl ExportNamedDeclaration<'_> {
#[allow(missing_docs)]
pub fn is_typescript_syntax(&self) -> bool {
self.export_kind == ImportOrExportKind::Type
|| self.declaration.as_ref().map_or(false, Declaration::is_typescript_syntax)
|| self.declaration.as_ref().is_some_and(Declaration::is_typescript_syntax)
}
}

Expand Down
46 changes: 31 additions & 15 deletions crates/oxc_codegen/src/gen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,6 @@ impl Gen for Statement<'_> {
p.print_statement_comments(stmt.span.start);
stmt.print(p, ctx);
}

Self::ImportDeclaration(decl) => {
p.print_statement_comments(decl.span.start);
decl.print(p, ctx);
Expand All @@ -197,7 +196,6 @@ impl Gen for Statement<'_> {
p.print_statement_comments(decl.span.start);
decl.print(p, ctx);
}

Self::VariableDeclaration(decl) => {
p.print_statement_comments(decl.span.start);
p.print_indent();
Expand Down Expand Up @@ -273,6 +271,7 @@ impl Gen for IfStatement<'_> {
}

fn print_if(if_stmt: &IfStatement<'_>, p: &mut Codegen, ctx: Context) {
p.print_space_before_identifier();
p.print_str("if");
p.print_soft_space();
p.print_ascii_byte(b'(');
Expand Down Expand Up @@ -362,6 +361,7 @@ impl Gen for ForStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("for");
p.print_soft_space();
p.print_ascii_byte(b'(');
Expand Down Expand Up @@ -393,6 +393,7 @@ impl Gen for ForInStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("for");
p.print_soft_space();
p.print_ascii_byte(b'(');
Expand All @@ -411,6 +412,7 @@ impl Gen for ForOfStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("for");
if self.r#await {
p.print_str(" await");
Expand Down Expand Up @@ -458,6 +460,7 @@ impl Gen for WhileStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("while");
p.print_soft_space();
p.print_ascii_byte(b'(');
Expand All @@ -471,17 +474,23 @@ impl Gen for DoWhileStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_str("do ");
if let Statement::BlockStatement(block) = &self.body {
p.print_block_statement(block, ctx);
p.print_soft_space();
} else {
p.print_soft_newline();
p.indent();
self.body.print(p, ctx);
p.print_semicolon_if_needed();
p.dedent();
p.print_indent();
p.print_space_before_identifier();
p.print_str("do");
match &self.body {
Statement::BlockStatement(block) => {
p.print_soft_space();
p.print_block_statement(block, ctx);
p.print_soft_space();
}
Statement::EmptyStatement(s) => s.print(p, ctx),
_ => {
p.print_soft_newline();
p.indent();
self.body.print(p, ctx);
p.print_semicolon_if_needed();
p.dedent();
p.print_indent();
}
}
p.print_str("while");
p.print_soft_space();
Expand All @@ -505,6 +514,7 @@ impl Gen for ContinueStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("continue");
if let Some(label) = &self.label {
p.print_soft_space();
Expand All @@ -518,6 +528,7 @@ impl Gen for BreakStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("break");
if let Some(label) = &self.label {
p.print_soft_space();
Expand All @@ -531,6 +542,7 @@ impl Gen for SwitchStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("switch");
p.print_soft_space();
p.print_ascii_byte(b'(');
Expand Down Expand Up @@ -638,6 +650,7 @@ impl Gen for ThrowStatement<'_> {
fn gen(&self, p: &mut Codegen, _ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("throw");
p.print_soft_space();
p.print_expression(&self.argument);
Expand All @@ -649,6 +662,7 @@ impl Gen for WithStatement<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("with");
p.print_ascii_byte(b'(');
p.print_expression(&self.object);
Expand All @@ -661,6 +675,7 @@ impl Gen for DebuggerStatement {
fn gen(&self, p: &mut Codegen, _ctx: Context) {
p.add_source_mapping(self.span);
p.print_indent();
p.print_space_before_identifier();
p.print_str("debugger");
p.print_semicolon_after_statement();
}
Expand All @@ -669,6 +684,7 @@ impl Gen for DebuggerStatement {
impl Gen for VariableDeclaration<'_> {
fn gen(&self, p: &mut Codegen, ctx: Context) {
p.add_source_mapping(self.span);
p.print_space_before_identifier();
if self.declare {
p.print_str("declare ");
}
Expand Down Expand Up @@ -1308,9 +1324,9 @@ impl GenExpr for NumericLiteral<'_> {

impl GenExpr for BigIntLiteral<'_> {
fn gen_expr(&self, p: &mut Codegen, precedence: Precedence, _ctx: Context) {
let raw = self.raw.as_str().cow_replace('_', "");

p.print_space_before_identifier();
p.add_source_mapping(self.span);
let raw = self.raw.as_str().cow_replace('_', "");
if !raw.starts_with('-') {
p.print_str(&raw);
} else if precedence >= Precedence::Prefix {
Expand Down
23 changes: 23 additions & 0 deletions crates/oxc_codegen/tests/integration/unit.rs
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,26 @@ fn for_stmt() {
);
}

#[test]
fn do_while_stmt() {
test("do ; while (true)", "do;\nwhile (true);\n");
test_minify("do ; while (true)", "do;while(true);");
test_minify("do break; while (true)", "do break;while(true);");
test_minify("do continue; while (true)", "do continue;while(true);");
test_minify("do debugger; while (true)", "do debugger;while(true);");
test_minify("do for(x in y); while (true)", "do for(x in y);while(true);");
test_minify("do for(x of y); while (true)", "do for(x of y);while(true);");
test_minify("do for(;;); while (true)", "do for(;;);while(true);");
test_minify("do if (test) {} while (true)", "do if(test){}while(true);");
test_minify("do foo:; while (true)", "do foo:;while(true);");
test_minify("do return; while (true)", "do return;while(true);");
test_minify("do switch(test){} while (true)", "do switch(test){}while(true);");
test_minify("do throw x; while (true)", "do throw x;while(true);");
test_minify("do with(x); while (true)", "do with(x);while(true);");
test_minify("do try{} catch{} while (true)", "do try{}catch{}while(true);");
test_minify("do do ; while(true) while (true)", "do do;while(true);while(true);");
}

#[test]
fn if_stmt() {
test(
Expand Down Expand Up @@ -382,6 +402,9 @@ fn big_int() {
test("0xfabn", "0xfabn;\n");
test("0xaef_en;", "0xaefen;\n");
test("0xaefen;", "0xaefen;\n");

test("return 1n", "return 1n;\n");
test_minify("return 1n", "return 1n;");
}

#[test]
Expand Down
11 changes: 7 additions & 4 deletions crates/oxc_data_structures/src/stack/mod.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
//! Contains the following FILO data structures:
//! - [`Stack`]: A growable stack
//! - [`SparseStack`]: A stack that can have empty entries
//! - [`NonEmptyStack`]: A growable stack that can never be empty, allowing for more efficient
//! operations
//!
//! * [`Stack`]: A growable stack, equivalent to [`Vec`], but more efficient for stack usage (push/pop).
//! * [`NonEmptyStack`]: A growable stack that can never be empty, allowing for more efficient operations
//! (very fast `last` / `last_mut`).
//! * [`SparseStack`]: A growable stack of `Option`s, optimized for low memory usage when many entries in
//! the stack are empty (`None`).
mod capacity;
mod common;
mod non_empty;
Expand Down
Loading

0 comments on commit 50fdf58

Please sign in to comment.