Skip to content

Commit 20135c6

Browse files
committed
fix: infer self
1 parent 935c27d commit 20135c6

File tree

3 files changed

+53
-11
lines changed

3 files changed

+53
-11
lines changed

crates/emmylua_code_analysis/src/diagnostic/test/param_type_check_test.rs

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1420,7 +1420,7 @@ mod test {
14201420
}
14211421

14221422
#[test]
1423-
fn test_key_of() {
1423+
fn test_keyof() {
14241424
let mut ws = VirtualWorkspace::new();
14251425
ws.def(
14261426
r#"
@@ -1454,4 +1454,28 @@ mod test {
14541454
"#,
14551455
));
14561456
}
1457+
1458+
#[test]
1459+
fn test_origin_self() {
1460+
let mut ws = VirtualWorkspace::new();
1461+
ws.def(
1462+
r#"
1463+
---@class Runner
1464+
---@field onCollectStart? fun(self:self)
1465+
1466+
---@type Runner
1467+
runner = {}
1468+
1469+
"#,
1470+
);
1471+
assert!(ws.check_code_for(
1472+
DiagnosticCode::ParamTypeMismatch,
1473+
r#"
1474+
local originOnCollectStart = runner.onCollectStart
1475+
runner.onCollectStart = function(self)
1476+
originOnCollectStart(self)
1477+
end
1478+
"#,
1479+
));
1480+
}
14571481
}

crates/emmylua_code_analysis/src/semantic/generic/instantiate_type/instantiate_func_generic.rs

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use std::{collections::HashSet, ops::Deref, sync::Arc};
22

3-
use emmylua_parser::LuaDocTypeList;
3+
use emmylua_parser::{LuaAstNode, LuaDocTypeList};
44
use emmylua_parser::{LuaCallExpr, LuaExpr};
55
use internment::ArcIntern;
66

@@ -23,6 +23,7 @@ use crate::{
2323
infer_expr,
2424
},
2525
};
26+
use crate::{LuaMemberOwner, LuaSemanticDeclId, SemanticDeclLevel, infer_node_semantic_decl};
2627

2728
use super::TypeSubstitutor;
2829

@@ -231,16 +232,32 @@ pub fn infer_self_type(
231232
cache: &mut LuaInferCache,
232233
call_expr: &LuaCallExpr,
233234
) -> Option<LuaType> {
234-
let prefix_expr = call_expr.get_prefix_expr();
235-
if let Some(prefix_expr) = prefix_expr
236-
&& let LuaExpr::IndexExpr(index) = prefix_expr
237-
{
238-
let self_expr = index.get_prefix_expr();
239-
if let Some(self_expr) = self_expr {
235+
let prefix_expr = call_expr.get_prefix_expr()?;
236+
match prefix_expr {
237+
LuaExpr::IndexExpr(index) => {
238+
let self_expr = index.get_prefix_expr()?;
240239
let self_type = infer_expr(db, cache, self_expr).ok()?;
241240
let self_type = build_self_type(db, &self_type);
242241
return Some(self_type);
243242
}
243+
LuaExpr::NameExpr(name) => {
244+
let semantic_decl_id = infer_node_semantic_decl(
245+
db,
246+
cache,
247+
name.syntax().clone(),
248+
SemanticDeclLevel::default(),
249+
)?;
250+
if let LuaSemanticDeclId::Member(member_id) = semantic_decl_id {
251+
let owner = db.get_member_index().get_current_owner(&member_id)?;
252+
if let LuaMemberOwner::Type(id) = owner {
253+
let typ = LuaType::Ref(id.clone());
254+
let self_type = build_self_type(db, &typ);
255+
return Some(self_type);
256+
}
257+
return None;
258+
}
259+
}
260+
_ => {}
244261
}
245262

246263
None

crates/emmylua_code_analysis/src/semantic/semantic_info/infer_expr_semantic_decl.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ use emmylua_parser::{
66
use crate::{
77
DbIndex, LuaDeclId, LuaDeclOrMemberId, LuaInferCache, LuaInstanceType, LuaIntersectionType,
88
LuaMemberId, LuaMemberKey, LuaMemberOwner, LuaSemanticDeclId, LuaType, LuaTypeCache,
9-
LuaTypeDeclId, LuaUnionType,
9+
LuaTypeDeclId, LuaUnionType, TypeOps,
1010
semantic::{
1111
infer::find_self_decl_or_member_id, member::get_buildin_type_map_type_id,
1212
semantic_info::resolve_global_decl_id,
@@ -78,7 +78,8 @@ fn infer_name_expr_semantic_decl(
7878
.get_type_index()
7979
.get_type_cache(&decl_id.into())
8080
.unwrap_or(&LuaTypeCache::InferType(LuaType::Unknown));
81-
let is_ref_object = decl_type.is_function() || decl_type.is_table();
81+
let remove_nil_type = TypeOps::Remove.apply(db, &decl_type, &LuaType::Nil);
82+
let is_ref_object = remove_nil_type.is_function() || remove_nil_type.is_table();
8283
if decl.is_local() && !is_ref_object {
8384
return Some(LuaSemanticDeclId::LuaDecl(decl_id));
8485
}
@@ -89,7 +90,7 @@ fn infer_name_expr_semantic_decl(
8990

9091
if let Some(value_expr_id) = decl.get_value_syntax_id() {
9192
match value_expr_id.get_kind() {
92-
LuaSyntaxKind::NameExpr | LuaSyntaxKind::IndexExpr if decl_type.is_function() => {
93+
LuaSyntaxKind::NameExpr | LuaSyntaxKind::IndexExpr if remove_nil_type.is_function() => {
9394
let file_id = decl.get_file_id();
9495
let tree = db.get_vfs().get_syntax_tree(&file_id)?;
9596
// second infer

0 commit comments

Comments
 (0)