lang_turtle/ecs/
format.rs1use bevy_ecs::prelude::*;
2use lsp_core::{components::*, prelude::*};
3use lsp_types::{Position, Range};
4use tracing::info;
5
6use crate::{lang::formatter::format_turtle, TurtleLang};
7
8pub fn format_turtle_system(
9 mut query: Query<(&RopeC, &Element<TurtleLang>, &Tokens, &mut FormatRequest), Without<Dirty>>,
10) {
11 info!("Format turtle system");
12
13 for (source, turtle, tokens, mut request) in &mut query {
14 if request.0.is_some() {
15 info!("Didn't format with the turtle format system, already formatted");
16 continue;
17 }
18 info!("Formatting with turtle format system");
19 let comments: Vec<_> = tokens
20 .iter()
21 .filter(|x| x.is_comment())
22 .cloned()
23 .map(|Spanned(x, span)| Spanned(x.into_comment(), span))
24 .collect();
25
26 let formatted = format_turtle(
27 &turtle.0,
28 lsp_types::FormattingOptions {
29 tab_size: 2,
30 ..Default::default()
31 },
32 &comments,
33 &source.0,
34 );
35
36 request.0 = formatted.map(|x| {
37 vec![lsp_types::TextEdit::new(
38 Range::new(
39 Position::new(0, 0),
40 Position::new(source.0.len_lines() as u32 + 1, 0),
41 ),
42 x,
43 )]
44 });
45 }
46}
47
48#[cfg(test)]
49mod test {
50 use lsp_core::prelude::FormatLabel;
51 use test_utils::{create_file, setup_world, TestClient};
52
53 use super::*;
54
55 #[test]
57 fn format_does_it() {
58 let (mut world, _) = setup_world(TestClient::new(), crate::setup_world);
59
60 let entity = create_file(
61 &mut world,
62 "@prefix foaf: <>.",
63 "http://example.com/ns#",
64 "turtle",
65 Open,
66 );
67
68 world.entity_mut(entity).insert(FormatRequest(None));
69 world.run_schedule(FormatLabel);
70 let m_formatted: Option<FormatRequest> = world.entity_mut(entity).take();
71 let m_formatted = m_formatted.and_then(|x| x.0);
72
73 assert!(m_formatted.is_some());
74 let formatted = &m_formatted.unwrap()[0].new_text;
75 assert_eq!(formatted, "@prefix foaf: <>.\n\n");
76 }
77}