mirror of
https://github.com/erg-lang/erg.git
synced 2025-08-04 18:58:30 +00:00
fix: import resolution
This commit is contained in:
parent
0274b458b4
commit
24141ea3f3
4 changed files with 153 additions and 45 deletions
|
@ -26,7 +26,7 @@ use erg_common::spawn::spawn_new_thread;
|
|||
use erg_common::str::Str;
|
||||
use erg_common::traits::{ExitStatus, New, Runnable, Stream};
|
||||
|
||||
use erg_parser::ast::{Expr, InlineModule, VarName, AST};
|
||||
use erg_parser::ast::{ClassAttr, Expr, InlineModule, Record, RecordAttrOrIdent, VarName, AST};
|
||||
use erg_parser::build_ast::{ASTBuildable, ASTBuilder as DefaultASTBuilder};
|
||||
use erg_parser::parse::SimpleParser;
|
||||
|
||||
|
@ -440,9 +440,31 @@ impl<ASTBuilder: ASTBuildable, HIRBuilder: Buildable>
|
|||
fn check_import(&mut self, expr: &mut Expr, cfg: &ErgConfig) -> ResolveResult<()> {
|
||||
let mut errs = vec![];
|
||||
match expr {
|
||||
Expr::Call(call) if call.additional_operation().is_some_and(|op| op.is_import()) => {
|
||||
if let Err(err) = self.register(expr, cfg) {
|
||||
errs.extend(err);
|
||||
Expr::Call(call) => {
|
||||
for pos in call.args.pos_args.iter_mut() {
|
||||
if let Err(err) = self.check_import(&mut pos.expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
if let Some(var) = call.args.var_args.as_mut() {
|
||||
if let Err(err) = self.check_import(&mut var.expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
for kw in call.args.kw_args.iter_mut() {
|
||||
if let Err(err) = self.check_import(&mut kw.expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
if let Some(kw_var) = call.args.kw_var_args.as_mut() {
|
||||
if let Err(err) = self.check_import(&mut kw_var.expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
if call.additional_operation().is_some_and(|op| op.is_import()) {
|
||||
if let Err(err) = self.register(expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Def(def) => {
|
||||
|
@ -452,6 +474,80 @@ impl<ASTBuilder: ASTBuildable, HIRBuilder: Buildable>
|
|||
}
|
||||
}
|
||||
}
|
||||
Expr::ClassDef(class_def) => {
|
||||
for expr in class_def.def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
for methods in class_def.methods_list.iter_mut() {
|
||||
for attr in methods.attrs.iter_mut() {
|
||||
if let ClassAttr::Def(def) = attr {
|
||||
for chunk in def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Methods(methods) => {
|
||||
for attr in methods.attrs.iter_mut() {
|
||||
if let ClassAttr::Def(def) = attr {
|
||||
for chunk in def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::PatchDef(patch_def) => {
|
||||
for expr in patch_def.def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(expr, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
for methods in patch_def.methods_list.iter_mut() {
|
||||
for attr in methods.attrs.iter_mut() {
|
||||
if let ClassAttr::Def(def) = attr {
|
||||
for chunk in def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Record(Record::Normal(rec)) => {
|
||||
for attr in rec.attrs.iter_mut() {
|
||||
for chunk in attr.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Record(Record::Mixed(rec)) => {
|
||||
for attr in rec.attrs.iter_mut() {
|
||||
if let RecordAttrOrIdent::Attr(def) = attr {
|
||||
for chunk in def.body.block.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Lambda(lambda) => {
|
||||
for chunk in lambda.body.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
errs.extend(err);
|
||||
}
|
||||
}
|
||||
}
|
||||
Expr::Dummy(chunks) => {
|
||||
for chunk in chunks.iter_mut() {
|
||||
if let Err(err) = self.check_import(chunk, cfg) {
|
||||
|
|
|
@ -912,20 +912,6 @@ impl Context {
|
|||
Visibility::BUILTIN_PUBLIC,
|
||||
None,
|
||||
);
|
||||
let T = type_q(TY_T);
|
||||
let list_t = no_var_func(
|
||||
vec![],
|
||||
vec![kw(KW_ITERABLE, poly(ITERABLE, vec![ty_tp(T.clone())]))],
|
||||
array_t(T, TyParam::erased(Nat)),
|
||||
)
|
||||
.quantify();
|
||||
self.register_builtin_py_impl(
|
||||
FUNC_LIST,
|
||||
list_t,
|
||||
Immutable,
|
||||
Visibility::BUILTIN_PUBLIC,
|
||||
None,
|
||||
);
|
||||
}
|
||||
|
||||
pub(super) fn init_builtin_operators(&mut self) {
|
||||
|
|
|
@ -323,10 +323,10 @@ impl KwArg {
|
|||
#[pyclass]
|
||||
#[derive(Clone, Debug, PartialEq, Eq, Hash)]
|
||||
pub struct Args {
|
||||
pos_args: Vec<PosArg>,
|
||||
pub(crate) var_args: Option<Box<PosArg>>,
|
||||
kw_args: Vec<KwArg>,
|
||||
pub(crate) kw_var_args: Option<Box<PosArg>>,
|
||||
pub pos_args: Vec<PosArg>,
|
||||
pub var_args: Option<Box<PosArg>>,
|
||||
pub kw_args: Vec<KwArg>,
|
||||
pub kw_var_args: Option<Box<PosArg>>,
|
||||
// these are for ELS
|
||||
pub paren: Option<(Token, Token)>,
|
||||
}
|
||||
|
|
|
@ -768,6 +768,32 @@ impl Desugarer {
|
|||
}
|
||||
}
|
||||
|
||||
fn desugar_pattern_of_methods(&mut self, methods: Methods) -> Methods {
|
||||
let mut new_attrs = Vec::with_capacity(methods.attrs.len());
|
||||
for attr in methods.attrs.into_iter() {
|
||||
match attr {
|
||||
ClassAttr::Def(def) => {
|
||||
let mut new = vec![];
|
||||
self.desugar_def_pattern(def, &mut new);
|
||||
let Expr::Def(def) = new.remove(0) else {
|
||||
todo!("{new:?}")
|
||||
};
|
||||
new_attrs.push(ClassAttr::Def(def));
|
||||
}
|
||||
_ => {
|
||||
new_attrs.push(attr);
|
||||
}
|
||||
}
|
||||
}
|
||||
Methods::new(
|
||||
methods.id,
|
||||
methods.class,
|
||||
*methods.class_as_expr,
|
||||
methods.vis,
|
||||
ClassAttrs::from(new_attrs),
|
||||
)
|
||||
}
|
||||
|
||||
// TODO: nested function pattern
|
||||
/// `[i, j] = [1, 2]` -> `i = 1; j = 2`
|
||||
/// `[i, j] = l` -> `i = l[0]; j = l[1]`
|
||||
|
@ -784,30 +810,26 @@ impl Desugarer {
|
|||
Expr::Def(def) => {
|
||||
self.desugar_def_pattern(def, &mut new);
|
||||
}
|
||||
Expr::ClassDef(class_def) => {
|
||||
// self.desugar_def_pattern(class_def.def, &mut new);
|
||||
let methods = class_def
|
||||
.methods_list
|
||||
.into_iter()
|
||||
.map(|methods| self.desugar_pattern_of_methods(methods))
|
||||
.collect();
|
||||
new.push(Expr::ClassDef(ClassDef::new(class_def.def, methods)));
|
||||
}
|
||||
Expr::PatchDef(patch_def) => {
|
||||
// self.desugar_def_pattern(patch_def.def, &mut new);
|
||||
let methods = patch_def
|
||||
.methods_list
|
||||
.into_iter()
|
||||
.map(|methods| self.desugar_pattern_of_methods(methods))
|
||||
.collect();
|
||||
new.push(Expr::PatchDef(PatchDef::new(patch_def.def, methods)));
|
||||
}
|
||||
Expr::Methods(methods) => {
|
||||
let mut new_attrs = Vec::with_capacity(methods.attrs.len());
|
||||
for attr in methods.attrs.into_iter() {
|
||||
match attr {
|
||||
ClassAttr::Def(def) => {
|
||||
let mut new = vec![];
|
||||
self.desugar_def_pattern(def, &mut new);
|
||||
let Expr::Def(def) = new.remove(0) else {
|
||||
todo!("{new:?}")
|
||||
};
|
||||
new_attrs.push(ClassAttr::Def(def));
|
||||
}
|
||||
_ => {
|
||||
new_attrs.push(attr);
|
||||
}
|
||||
}
|
||||
}
|
||||
let methods = Methods::new(
|
||||
methods.id,
|
||||
methods.class,
|
||||
*methods.class_as_expr,
|
||||
methods.vis,
|
||||
ClassAttrs::from(new_attrs),
|
||||
);
|
||||
let methods = self.desugar_pattern_of_methods(methods);
|
||||
new.push(Expr::Methods(methods));
|
||||
}
|
||||
Expr::Dummy(dummy) => {
|
||||
|
@ -815,6 +837,10 @@ impl Desugarer {
|
|||
let new_dummy = self.desugar_pattern(dummy.into_iter());
|
||||
new.push(Expr::Dummy(Dummy::new(loc, new_dummy)));
|
||||
}
|
||||
Expr::Compound(compound) => {
|
||||
let new_compound = self.desugar_pattern(compound.into_iter());
|
||||
new.push(Expr::Compound(Compound::new(new_compound)));
|
||||
}
|
||||
other => {
|
||||
new.push(self.rec_desugar_lambda_pattern(other));
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue