mirror of
				https://github.com/astral-sh/ruff.git
				synced 2025-10-31 20:08:19 +00:00 
			
		
		
		
	 9c27c57b5b
			
		
	
	
		9c27c57b5b
		
	
	
	
	
		
			
			This merely adds the crate to our repository. Some cosmetic changes are made to make it work in our repo and follow our conventions, such as changing the name to `ruff_annotate_snippets`. We retain the original license information. We do drop some things, such as benchmarks, but keep tests and examples.
		
			
				
	
	
		
			783 lines
		
	
	
	
		
			17 KiB
		
	
	
	
		
			Rust
		
	
	
	
	
	
			
		
		
	
	
			783 lines
		
	
	
	
		
			17 KiB
		
	
	
	
		
			Rust
		
	
	
	
	
	
| //! These tests have been adapted from [Rust's parser tests][parser-tests].
 | |
| //!
 | |
| //! [parser-tests]: https://github.com/rust-lang/rust/blob/894f7a4ba6554d3797404bbf550d9919df060b97/compiler/rustc_parse/src/parser/tests.rs
 | |
| 
 | |
| use ruff_annotate_snippets::{Level, Renderer, Snippet};
 | |
| 
 | |
| use snapbox::{assert_data_eq, str};
 | |
| 
 | |
| #[test]
 | |
| fn ends_on_col0() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(10..13).label("test")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:2:10
 | |
|   |
 | |
| 2 |   fn foo() {
 | |
|   |  __________^
 | |
| 3 | | }
 | |
|   | |_^ test
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn ends_on_col2() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
| 
 | |
| 
 | |
|   }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(10..17).label("test")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:2:10
 | |
|   |
 | |
| 2 |   fn foo() {
 | |
|   |  __________^
 | |
| 3 | |
 | |
| 4 | |
 | |
| 5 | |   }
 | |
|   | |___^ test
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn non_nested() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0
 | |
|   X1 Y1
 | |
|   X2 Y2
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..32).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(17..35)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |      X0 Y0
 | |
|   |  ____^  -
 | |
|   | | ______|
 | |
| 4 | ||   X1 Y1
 | |
| 5 | ||   X2 Y2
 | |
|   | ||____^__- `Y` is a good letter too
 | |
|   | |_____|
 | |
|   |       `X` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn nested() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0
 | |
|   Y1 X1
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(17..24)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |      X0 Y0
 | |
|   |  ____^  -
 | |
|   | | ______|
 | |
| 4 | ||   Y1 X1
 | |
|   | ||____-__^ `X` is a good letter
 | |
|   |  |____|
 | |
|   |       `Y` is a good letter too
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn different_overlap() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(17..38).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(31..49)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:6
 | |
|   |
 | |
| 3 |      X0 Y0 Z0
 | |
|   |  _______^
 | |
| 4 | |    X1 Y1 Z1
 | |
|   | | _________-
 | |
| 5 | ||   X2 Y2 Z2
 | |
|   | ||____^ `X` is a good letter
 | |
| 6 |  |   X3 Y3 Z3
 | |
|   |  |____- `Y` is a good letter too
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn triple_overlap() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..38).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(17..41)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             )
 | |
|             .annotation(Level::Warning.span(20..44).label("`Z` label")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |       X0 Y0 Z0
 | |
|   |  _____^  -  -
 | |
|   | | _______|  |
 | |
|   | || _________|
 | |
| 4 | |||   X1 Y1 Z1
 | |
| 5 | |||   X2 Y2 Z2
 | |
|   | |||____^__-__- `Z` label
 | |
|   | ||_____|__|
 | |
|   | |______|  `Y` is a good letter too
 | |
|   |        `X` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn triple_exact_overlap() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..38).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(14..38)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             )
 | |
|             .annotation(Level::Warning.span(14..38).label("`Z` label")),
 | |
|     );
 | |
| 
 | |
|     // This should have a `^` but we currently don't support the idea of a
 | |
|     // "primary" annotation, which would solve this
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 | /   X0 Y0 Z0
 | |
| 4 | |   X1 Y1 Z1
 | |
| 5 | |   X2 Y2 Z2
 | |
|   | |    -
 | |
|   | |____|
 | |
|   |      `X` is a good letter
 | |
|   |      `Y` is a good letter too
 | |
|   |      `Z` label
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn minimum_depth() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(17..27).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(28..44)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             )
 | |
|             .annotation(Level::Warning.span(36..52).label("`Z`")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:6
 | |
|   |
 | |
| 3 |      X0 Y0 Z0
 | |
|   |  _______^
 | |
| 4 | |    X1 Y1 Z1
 | |
|   | | ____^_-
 | |
|   | ||____|
 | |
|   |  |    `X` is a good letter
 | |
| 5 |  |   X2 Y2 Z2
 | |
|   |  |___-______- `Y` is a good letter too
 | |
|   |   ___|
 | |
|   |  |
 | |
| 6 |  |   X3 Y3 Z3
 | |
|   |  |_______- `Z`
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn non_overlapping() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(39..55)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 | /   X0 Y0 Z0
 | |
| 4 | |   X1 Y1 Z1
 | |
|   | |____^ `X` is a good letter
 | |
| 5 |     X2 Y2 Z2
 | |
|   |  ______-
 | |
| 6 | |   X3 Y3 Z3
 | |
|   | |__________- `Y` is a good letter too
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn overlapping_start_and_end() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
|   X2 Y2 Z2
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(17..27).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(31..55)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:6
 | |
|   |
 | |
| 3 |      X0 Y0 Z0
 | |
|   |  _______^
 | |
| 4 | |    X1 Y1 Z1
 | |
|   | | ____^____-
 | |
|   | ||____|
 | |
|   |  |    `X` is a good letter
 | |
| 5 |  |   X2 Y2 Z2
 | |
| 6 |  |   X3 Y3 Z3
 | |
|   |  |__________- `Y` is a good letter too
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_primary_without_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(18..25).label(""))
 | |
|             .annotation(Level::Warning.span(14..27).label("`a` is a good letter"))
 | |
|             .annotation(Level::Warning.span(22..23).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:7
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ----^^^^-^^-- `a` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_secondary_without_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("`a` is a good letter"))
 | |
|             .annotation(Level::Warning.span(18..25).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^-------^^ `a` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_primary_without_message_2() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(18..25).label("`b` is a good letter"))
 | |
|             .annotation(Level::Warning.span(14..27).label(""))
 | |
|             .annotation(Level::Warning.span(22..23).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:7
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ----^^^^-^^--
 | |
|   |       |
 | |
|   |       `b` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_secondary_without_message_2() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label(""))
 | |
|             .annotation(Level::Warning.span(18..25).label("`b` is a good letter")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^-------^^
 | |
|   |       |
 | |
|   |       `b` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_secondary_without_message_3() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a  bc  d
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..18).label("`a` is a good letter"))
 | |
|             .annotation(Level::Warning.span(18..22).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a  bc  d
 | |
|   |   ^^^^----
 | |
|   |   |
 | |
|   |   `a` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_without_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label(""))
 | |
|             .annotation(Level::Warning.span(18..25).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^-------^^
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_without_message_2() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(18..25).label(""))
 | |
|             .annotation(Level::Warning.span(14..27).label(""))
 | |
|             .annotation(Level::Warning.span(22..23).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:7
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ----^^^^-^^--
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn multiple_labels_with_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("`a` is a good letter"))
 | |
|             .annotation(Level::Warning.span(18..25).label("`b` is a good letter")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^-------^^
 | |
|   |   |   |
 | |
|   |   |   `b` is a good letter
 | |
|   |   `a` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn ingle_label_with_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("`a` is a good letter")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^^^^^^^^^^ `a` is a good letter
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn single_label_without_message() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   a { b { c } d }
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(14..27).label("")),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|  --> test.rs:3:3
 | |
|   |
 | |
| 3 |   a { b { c } d }
 | |
|   |   ^^^^^^^^^^^^^
 | |
|   |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn long_snippet() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
|   X1 Y1 Z1
 | |
| 1
 | |
| 2
 | |
| 3
 | |
| 4
 | |
| 5
 | |
| 6
 | |
| 7
 | |
| 8
 | |
| 9
 | |
| 10
 | |
|   X2 Y2 Z2
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(17..27).label("`X` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(31..76)
 | |
|                     .label("`Y` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|   --> test.rs:3:6
 | |
|    |
 | |
|  3 |      X0 Y0 Z0
 | |
|    |  _______^
 | |
|  4 | |    X1 Y1 Z1
 | |
|    | | ____^____-
 | |
|    | ||____|
 | |
|    |  |    `X` is a good letter
 | |
|  5 |  | 1
 | |
| ...   |
 | |
| 15 |  |   X2 Y2 Z2
 | |
| 16 |  |   X3 Y3 Z3
 | |
|    |  |__________- `Y` is a good letter too
 | |
|    |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 | |
| #[test]
 | |
| fn long_snippet_multiple_spans() {
 | |
|     let source = r#"
 | |
| fn foo() {
 | |
|   X0 Y0 Z0
 | |
| 1
 | |
| 2
 | |
| 3
 | |
|   X1 Y1 Z1
 | |
| 4
 | |
| 5
 | |
| 6
 | |
|   X2 Y2 Z2
 | |
| 7
 | |
| 8
 | |
| 9
 | |
| 10
 | |
|   X3 Y3 Z3
 | |
| }
 | |
| "#;
 | |
|     let input = Level::Error.title("foo").snippet(
 | |
|         Snippet::source(source)
 | |
|             .line_start(1)
 | |
|             .origin("test.rs")
 | |
|             .fold(true)
 | |
|             .annotation(Level::Error.span(17..73).label("`Y` is a good letter"))
 | |
|             .annotation(
 | |
|                 Level::Warning
 | |
|                     .span(37..56)
 | |
|                     .label("`Z` is a good letter too"),
 | |
|             ),
 | |
|     );
 | |
| 
 | |
|     let expected = str![[r#"
 | |
| error: foo
 | |
|   --> test.rs:3:6
 | |
|    |
 | |
|  3 |      X0 Y0 Z0
 | |
|    |  _______^
 | |
|  4 | |  1
 | |
|  5 | |  2
 | |
|  6 | |  3
 | |
|  7 | |    X1 Y1 Z1
 | |
|    | | _________-
 | |
|  8 | || 4
 | |
|  9 | || 5
 | |
| 10 | || 6
 | |
| 11 | ||   X2 Y2 Z2
 | |
|    | ||__________- `Z` is a good letter too
 | |
| 12 | |  7
 | |
| ...  |
 | |
| 15 | |  10
 | |
| 16 | |    X3 Y3 Z3
 | |
|    | |________^ `Y` is a good letter
 | |
|    |
 | |
| "#]];
 | |
|     let renderer = Renderer::plain();
 | |
|     assert_data_eq!(renderer.render(input).to_string(), expected);
 | |
| }
 |