mirror of
https://github.com/erg-lang/erg.git
synced 2025-09-28 12:14:43 +00:00
chore: add --use-pylyzer
option
This commit is contained in:
parent
e8d98e5431
commit
e7bc8b10ae
3 changed files with 50 additions and 29 deletions
|
@ -179,6 +179,7 @@ pub struct ErgConfig {
|
||||||
pub packages: ArcArray<Package>,
|
pub packages: ArcArray<Package>,
|
||||||
pub effect_check: bool,
|
pub effect_check: bool,
|
||||||
pub ownership_check: bool,
|
pub ownership_check: bool,
|
||||||
|
pub use_pylyzer: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for ErgConfig {
|
impl Default for ErgConfig {
|
||||||
|
@ -206,6 +207,7 @@ impl Default for ErgConfig {
|
||||||
packages: ArcArray::from([]),
|
packages: ArcArray::from([]),
|
||||||
effect_check: true,
|
effect_check: true,
|
||||||
ownership_check: true,
|
ownership_check: true,
|
||||||
|
use_pylyzer: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -340,6 +342,9 @@ impl ErgConfig {
|
||||||
None,
|
None,
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
"--use-pylyzer" => {
|
||||||
|
cfg.use_pylyzer = true;
|
||||||
|
}
|
||||||
"--use-local-package" => {
|
"--use-local-package" => {
|
||||||
let name = args
|
let name = args
|
||||||
.next()
|
.next()
|
||||||
|
|
|
@ -630,36 +630,39 @@ impl<ASTBuilder: ASTBuildable, HIRBuilder: Buildable>
|
||||||
if self.cfg.input.path() == path.as_path() {
|
if self.cfg.input.path() == path.as_path() {
|
||||||
return Ok(path);
|
return Ok(path);
|
||||||
}
|
}
|
||||||
let (out, err) = if self.cfg.mode == ErgMode::LanguageServer || self.cfg.quiet_repl {
|
if self.cfg.use_pylyzer {
|
||||||
(Stdio::null(), Stdio::null())
|
let (out, err) = if self.cfg.mode == ErgMode::LanguageServer || self.cfg.quiet_repl
|
||||||
} else {
|
|
||||||
(Stdio::inherit(), Stdio::inherit())
|
|
||||||
};
|
|
||||||
// pylyzer is a static analysis tool for Python (https://github.com/mtshiba/pylyzer).
|
|
||||||
// It can convert a Python script to an Erg AST for code analysis.
|
|
||||||
// There is also an option to output the analysis result as `d.er`. Use this if the system have pylyzer installed.
|
|
||||||
// A type definition file may be generated even if not all type checks succeed.
|
|
||||||
if let Ok(status) = Command::new("pylyzer")
|
|
||||||
.arg("--dump-decl")
|
|
||||||
.arg(path.to_str().unwrap_or_default())
|
|
||||||
.stdout(out)
|
|
||||||
.stderr(err)
|
|
||||||
.spawn()
|
|
||||||
.and_then(|mut child| child.wait())
|
|
||||||
{
|
|
||||||
if let Some(path) = self
|
|
||||||
.cfg
|
|
||||||
.input
|
|
||||||
.resolve_decl_path(Path::new(&__name__[..]), &self.cfg)
|
|
||||||
{
|
{
|
||||||
let size = metadata(&path).or(Err(()))?.len();
|
(Stdio::null(), Stdio::null())
|
||||||
// if pylyzer crashed
|
} else {
|
||||||
if !status.success() && size == 0 {
|
(Stdio::inherit(), Stdio::inherit())
|
||||||
// The presence of the decl file indicates that the analysis is in progress or completed,
|
};
|
||||||
// so if pylyzer crashes in the middle of the analysis, delete the file.
|
// pylyzer is a static analysis tool for Python (https://github.com/mtshiba/pylyzer).
|
||||||
remove_file(&path).unwrap();
|
// It can convert a Python script to an Erg AST for code analysis.
|
||||||
} else {
|
// There is also an option to output the analysis result as `d.er`. Use this if the system have pylyzer installed.
|
||||||
return Ok(path);
|
// A type definition file may be generated even if not all type checks succeed.
|
||||||
|
if let Ok(status) = Command::new("pylyzer")
|
||||||
|
.arg("--dump-decl")
|
||||||
|
.arg(path.to_str().unwrap_or_default())
|
||||||
|
.stdout(out)
|
||||||
|
.stderr(err)
|
||||||
|
.spawn()
|
||||||
|
.and_then(|mut child| child.wait())
|
||||||
|
{
|
||||||
|
if let Some(path) = self
|
||||||
|
.cfg
|
||||||
|
.input
|
||||||
|
.resolve_decl_path(Path::new(&__name__[..]), &self.cfg)
|
||||||
|
{
|
||||||
|
let size = metadata(&path).or(Err(()))?.len();
|
||||||
|
// if pylyzer crashed
|
||||||
|
if !status.success() && size == 0 {
|
||||||
|
// The presence of the decl file indicates that the analysis is in progress or completed,
|
||||||
|
// so if pylyzer crashes in the middle of the analysis, delete the file.
|
||||||
|
remove_file(&path).unwrap();
|
||||||
|
} else {
|
||||||
|
return Ok(path);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
|
use erg_common::consts::DEBUG_MODE;
|
||||||
use erg_common::pathutil::NormalizedPathBuf;
|
use erg_common::pathutil::NormalizedPathBuf;
|
||||||
use erg_common::set;
|
use erg_common::set;
|
||||||
use erg_common::set::Set;
|
use erg_common::set::Set;
|
||||||
|
@ -95,6 +96,12 @@ impl ModuleGraph {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn add_node_if_none(&mut self, path: &NormalizedPathBuf) {
|
pub fn add_node_if_none(&mut self, path: &NormalizedPathBuf) {
|
||||||
|
if path.is_dir() {
|
||||||
|
if DEBUG_MODE {
|
||||||
|
panic!("path is a directory: {path}");
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
if self.0.iter().all(|n| &n.id != path) {
|
if self.0.iter().all(|n| &n.id != path) {
|
||||||
let node = Node::new(path.clone(), (), set! {});
|
let node = Node::new(path.clone(), (), set! {});
|
||||||
self.0.push(node);
|
self.0.push(node);
|
||||||
|
@ -107,6 +114,12 @@ impl ModuleGraph {
|
||||||
referrer: &NormalizedPathBuf,
|
referrer: &NormalizedPathBuf,
|
||||||
depends_on: NormalizedPathBuf,
|
depends_on: NormalizedPathBuf,
|
||||||
) -> Result<(), IncRefError> {
|
) -> Result<(), IncRefError> {
|
||||||
|
if depends_on.is_dir() {
|
||||||
|
if DEBUG_MODE {
|
||||||
|
panic!("path is a directory: {depends_on}");
|
||||||
|
}
|
||||||
|
return Ok(());
|
||||||
|
}
|
||||||
self.add_node_if_none(referrer);
|
self.add_node_if_none(referrer);
|
||||||
if referrer == &depends_on {
|
if referrer == &depends_on {
|
||||||
return Ok(());
|
return Ok(());
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue