aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_cli
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_cli')
-rw-r--r--crates/ra_cli/Cargo.toml12
-rw-r--r--crates/ra_cli/src/main.rs97
2 files changed, 109 insertions, 0 deletions
diff --git a/crates/ra_cli/Cargo.toml b/crates/ra_cli/Cargo.toml
new file mode 100644
index 000000000..17011e063
--- /dev/null
+++ b/crates/ra_cli/Cargo.toml
@@ -0,0 +1,12 @@
1[package]
2name = "ra_cli"
3version = "0.1.0"
4authors = ["Aleksey Kladov <[email protected]>"]
5publish = false
6
7[dependencies]
8clap = "2.32.0"
9failure = "0.1.1"
10ra_syntax = { path = "../ra_syntax" }
11ra_editor = { path = "../ra_editor" }
12tools = { path = "../tools" }
diff --git a/crates/ra_cli/src/main.rs b/crates/ra_cli/src/main.rs
new file mode 100644
index 000000000..96e5b718c
--- /dev/null
+++ b/crates/ra_cli/src/main.rs
@@ -0,0 +1,97 @@
1extern crate clap;
2#[macro_use]
3extern crate failure;
4extern crate ra_syntax;
5extern crate ra_editor;
6extern crate tools;
7
8use std::{
9 fs, io::Read, path::Path,
10 time::Instant
11};
12use clap::{App, Arg, SubCommand};
13use tools::collect_tests;
14use ra_syntax::File;
15use ra_editor::{syntax_tree, file_structure};
16
17type Result<T> = ::std::result::Result<T, failure::Error>;
18
19fn main() -> Result<()> {
20 let matches = App::new("ra-cli")
21 .setting(clap::AppSettings::SubcommandRequiredElseHelp)
22 .subcommand(
23 SubCommand::with_name("render-test")
24 .arg(
25 Arg::with_name("line")
26 .long("--line")
27 .required(true)
28 .takes_value(true),
29 )
30 .arg(
31 Arg::with_name("file")
32 .long("--file")
33 .required(true)
34 .takes_value(true),
35 ),
36 )
37 .subcommand(
38 SubCommand::with_name("parse")
39 .arg(Arg::with_name("no-dump").long("--no-dump"))
40 )
41 .subcommand(SubCommand::with_name("symbols"))
42 .get_matches();
43 match matches.subcommand() {
44 ("parse", Some(matches)) => {
45 let start = Instant::now();
46 let file = file()?;
47 let elapsed = start.elapsed();
48 if !matches.is_present("no-dump") {
49 println!("{}", syntax_tree(&file));
50 }
51 eprintln!("parsing: {:?}", elapsed);
52 ::std::mem::forget(file);
53 }
54 ("symbols", _) => {
55 let file = file()?;
56 for s in file_structure(&file) {
57 println!("{:?}", s);
58 }
59 }
60 ("render-test", Some(matches)) => {
61 let file = matches.value_of("file").unwrap();
62 let file = Path::new(file);
63 let line: usize = matches.value_of("line").unwrap().parse()?;
64 let line = line - 1;
65 let (test, tree) = render_test(file, line)?;
66 println!("{}\n{}", test, tree);
67 }
68 _ => unreachable!(),
69 }
70 Ok(())
71}
72
73fn file() -> Result<File> {
74 let text = read_stdin()?;
75 Ok(File::parse(&text))
76}
77
78fn read_stdin() -> Result<String> {
79 let mut buff = String::new();
80 ::std::io::stdin().read_to_string(&mut buff)?;
81 Ok(buff)
82}
83
84fn render_test(file: &Path, line: usize) -> Result<(String, String)> {
85 let text = fs::read_to_string(file)?;
86 let tests = collect_tests(&text);
87 let test = tests.into_iter().find(|(start_line, t)| {
88 *start_line <= line && line <= *start_line + t.text.lines().count()
89 });
90 let test = match test {
91 None => bail!("No test found at line {} at {}", line, file.display()),
92 Some((_start_line, test)) => test,
93 };
94 let file = File::parse(&test.text);
95 let tree = syntax_tree(&file);
96 Ok((test.text, tree))
97}