Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Remove lint for grid-template-areas #8195

Merged
merged 1 commit into from
May 23, 2024
Merged
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
216 changes: 12 additions & 204 deletions crates/turbopack-css/src/process.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
use std::{
collections::{HashMap, HashSet},
collections::HashMap,
sync::{Arc, RwLock},
};

use anyhow::{bail, Context, Result};
use indexmap::{IndexMap, IndexSet};
use indexmap::IndexMap;
use lightningcss::{
css_modules::{CssModuleExport, CssModuleExports, CssModuleReference, Pattern, Segment},
dependencies::{Dependency, ImportDependency, Location, SourceRange},
stylesheet::{ParserOptions, PrinterOptions, StyleSheet, ToCssResult},
targets::{Features, Targets},
values::url::Url,
visit_types,
visitor::Visit,
};
use once_cell::sync::Lazy;
Expand Down Expand Up @@ -573,9 +574,8 @@ async fn process_content(
) {
Ok(mut ss) => {
if matches!(ty, CssModuleAssetType::Module) {
let mut validator = CssModuleValidator::default();
let mut validator = CssValidator { errors: Vec::new() };
ss.visit(&mut validator).unwrap();
validator.validate_done();

for err in validator.errors {
err.report(source, fs_path_vc);
Expand Down Expand Up @@ -678,9 +678,8 @@ async fn process_content(
}

if matches!(ty, CssModuleAssetType::Module) {
let mut validator = CssModuleValidator::default();
let mut validator = CssValidator { errors: vec![] };
ss.visit_with(&mut validator);
validator.validate_done();

for err in validator.errors {
err.report(source, fs_path_vc);
Expand Down Expand Up @@ -734,29 +733,14 @@ async fn process_content(
/// ```
///
/// is wrong for a css module because it doesn't have a class name.
#[derive(Default)]
struct CssModuleValidator {
struct CssValidator {
errors: Vec<CssError>,
used_grid_areas: IndexSet<String>,
used_grid_templates: HashSet<String>,
}
impl CssModuleValidator {
fn validate_done(&mut self) {
for grid_area in &self.used_grid_areas {
if !self.used_grid_templates.contains(grid_area) {
self.errors.push(CssError::UnknownGridAreaInModules {
name: grid_area.to_string(),
});
}
}
}
}

#[derive(Debug, PartialEq, Eq)]
enum CssError {
SwcSelectorInModuleNotPure { span: Span },
LightningCssSelectorInModuleNotPure { selector: String },
UnknownGridAreaInModules { name: String },
}

impl CssError {
Expand Down Expand Up @@ -784,18 +768,6 @@ impl CssError {
.cell()
.emit();
}

CssError::UnknownGridAreaInModules { name } => {
ParsingIssue {
file,
msg: Vc::cell(format!(
"Cannot find grid-template-areas with name '{name}'"
)),
source: Vc::cell(None),
}
.cell()
.emit();
}
}
}
}
Expand All @@ -804,7 +776,7 @@ const CSS_MODULE_ERROR: &str =
"Selector is not pure (pure selectors must contain at least one local class or id)";

/// We only vist top-level selectors.
impl swc_core::css::visit::Visit for CssModuleValidator {
impl swc_core::css::visit::Visit for CssValidator {
fn visit_complex_selector(&mut self, n: &ComplexSelector) {
fn is_complex_not_pure(sel: &ComplexSelector) -> bool {
sel.children.iter().all(|sel| match sel {
Expand Down Expand Up @@ -908,73 +880,11 @@ impl swc_core::css::visit::Visit for CssModuleValidator {
}

/// We only vist top-level selectors.
impl lightningcss::visitor::Visitor<'_> for CssModuleValidator {
impl lightningcss::visitor::Visitor<'_> for CssValidator {
type Error = ();

fn visit_types(&self) -> lightningcss::visitor::VisitTypes {
lightningcss::visitor::VisitTypes::all()
}

fn visit_property(
&mut self,
property: &mut lightningcss::properties::Property,
) -> Result<(), Self::Error> {
match property {
lightningcss::properties::Property::GridArea(p) => {
for line in [&p.row_start, &p.row_end, &p.column_start, &p.column_end] {
if let lightningcss::properties::grid::GridLine::Area { name } = line {
self.used_grid_areas.insert(name.to_string());
}
}
}

lightningcss::properties::Property::GridColumn(p) => {
for line in [&p.start, &p.end] {
if let lightningcss::properties::grid::GridLine::Area { name } = line {
self.used_grid_areas.insert(name.to_string());
}
}
}

lightningcss::properties::Property::GridRow(p) => {
for line in [&p.start, &p.end] {
if let lightningcss::properties::grid::GridLine::Area { name } = line {
self.used_grid_areas.insert(name.to_string());
}
}
}

lightningcss::properties::Property::GridRowStart(p)
| lightningcss::properties::Property::GridRowEnd(p)
| lightningcss::properties::Property::GridColumnStart(p)
| lightningcss::properties::Property::GridColumnEnd(p) => {
if let lightningcss::properties::grid::GridLine::Area { name } = p {
self.used_grid_areas.insert(name.to_string());
}
}

lightningcss::properties::Property::GridTemplateAreas(
lightningcss::properties::grid::GridTemplateAreas::Areas { areas, .. },
) => {
for area in areas.iter().flatten() {
self.used_grid_templates.insert(area.clone());
}
}

lightningcss::properties::Property::GridTemplate(p) => {
if let lightningcss::properties::grid::GridTemplateAreas::Areas { areas, .. } =
&mut p.areas
{
for area in areas.iter().flatten() {
self.used_grid_templates.insert(area.clone());
}
}
}

_ => {}
}

Ok(())
visit_types!(SELECTORS)
}

fn visit_selector(
Expand Down Expand Up @@ -1220,7 +1130,7 @@ mod tests {
css::{ast::Stylesheet, parser::parser::ParserConfig, visit::VisitWith},
};

use super::{CssError, CssModuleValidator};
use super::{CssError, CssValidator};

fn lint_lightningcss(code: &str) -> Vec<CssError> {
let mut ss = StyleSheet::parse(
Expand All @@ -1237,9 +1147,8 @@ mod tests {
)
.unwrap();

let mut validator = CssModuleValidator::default();
let mut validator = CssValidator { errors: Vec::new() };
ss.visit(&mut validator).unwrap();
validator.validate_done();

validator.errors
}
Expand All @@ -1260,9 +1169,8 @@ mod tests {
)
.unwrap();

let mut validator = CssModuleValidator::default();
let mut validator = CssValidator { errors: Vec::new() };
ss.visit_with(&mut validator);
validator.validate_done();

validator.errors
}
Expand All @@ -1279,11 +1187,6 @@ mod tests {
assert_ne!(lint_swc(code), vec![], "swc: {code}");
}

#[track_caller]
fn assert_lint_failure_only_lightning_css(code: &str) {
assert_ne!(lint_lightningcss(code), vec![], "lightningcss: {code}");
}

#[test]
fn css_module_pure_lint() {
assert_lint_success(
Expand Down Expand Up @@ -1406,99 +1309,4 @@ mod tests {
}",
);
}

#[test]
fn css_module_grid_lint() {
assert_lint_success(
r#"
.item1 {
grid-area: myArea;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);

assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-area: my;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);

assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-row-start: my;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);
assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-row-end: my;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);
assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-column-start: my;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);
assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-column-end: my;
}
.grid-container {
display: grid;
grid-template-areas: "myArea myArea";
}
"#,
);

assert_lint_success(
r#"
.item1 {
grid-area: my;
}
.grid-container {
display: grid;
grid-template: "my" "my";
}
"#,
);
assert_lint_failure_only_lightning_css(
r#"
.item1 {
grid-area: my;
}
.grid-container {
display: grid;
grid-template: "myArea" "myArea"
}
"#,
);
}
}
Loading