use std::path::Path;
use thiserror::Error;
use crate::graph::{build_project_ir, GraphPersistenceOptions};
use crate::ir::ProjectIr;
use crate::pipeline::ScanOptions;
use crate::scanner::{scan_and_parse, FileScanConfig, ScannerError};
pub use crate::graph::ExtractOptions;
impl From<&ScanOptions> for crate::graph::ExtractOptions {
fn from(opts: &ScanOptions) -> Self {
Self {
verbose_imports: opts.graph.verbose_imports,
max_parse_warnings_per_file: opts.graph.max_parse_warnings_per_file,
}
}
}
impl From<&GraphPersistenceOptions> for crate::graph::ExtractOptions {
fn from(opts: &GraphPersistenceOptions) -> Self {
Self {
verbose_imports: opts.verbose_imports,
max_parse_warnings_per_file: opts.max_parse_warnings_per_file,
}
}
}
#[derive(Debug, Error)]
pub enum ExtractError {
#[error("scan/parse failed: {0}")]
Scanner(#[from] ScannerError),
}
pub fn build_project_ir_from_files(
root: &Path,
files: &[crate::scanner::ParsedFile],
options: &ExtractOptions,
) -> ProjectIr {
build_project_ir(root, files, options)
}
pub fn scan_and_build_ir(
root: &Path,
options: &ExtractOptions,
scan: &ScanOptions,
) -> Result<ProjectIr, ExtractError> {
let mut config = FileScanConfig::new(root);
config.follow_symlinks = scan.follow_symlinks;
config.max_file_size = scan.max_file_size;
let files = scan_and_parse(&config)?;
Ok(build_project_ir_from_files(root, &files, options))
}
pub fn parse_files_to_ir(
root: &Path,
parse_targets: &[String],
options: &ExtractOptions,
scan: &ScanOptions,
) -> Result<ProjectIr, ExtractError> {
let mut config = FileScanConfig::new(root);
config.follow_symlinks = scan.follow_symlinks;
config.max_file_size = scan.max_file_size;
let paths: Vec<_> = parse_targets.iter().map(std::path::PathBuf::from).collect();
let files = crate::scanner_incremental::scan_and_parse_incremental_vector(&config, &paths)?;
Ok(build_project_ir_from_files(root, &files, options))
}