summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--changelog.md1
-rw-r--r--script/vm/compiler.lua52
-rw-r--r--test/type_inference/init.lua8
3 files changed, 49 insertions, 12 deletions
diff --git a/changelog.md b/changelog.md
index 40d7630d..eb1aaf78 100644
--- a/changelog.md
+++ b/changelog.md
@@ -24,6 +24,7 @@
local y = x--[[@as integer]] -- y is `integer` here
```
* `NEW` generic: resolve `T[]` by `table<integer, type>` or `---@field [integer] type`
+* `NEW` resolve `class[1]` by `---@field [integer] type`
* `NEW` diagnostic: `missing-parameter`
* `CHG` diagnostic: no longer mark `redundant-parameter` as `Unnecessary`
* `FIX` diagnostic: `unused-function` does not recognize recursion
diff --git a/script/vm/compiler.lua b/script/vm/compiler.lua
index 76766734..cebe01cb 100644
--- a/script/vm/compiler.lua
+++ b/script/vm/compiler.lua
@@ -199,22 +199,50 @@ function vm.getClassFields(suri, object, key, ref, pushResult)
-- check ---@field
local hasFounded = {}
for _, field in ipairs(set.fields) do
- if type(key) == 'table' then
- local fieldNode = vm.compileNode(field.field)
- if vm.isSubType(suri, key.name, fieldNode) then
- if not searchedFields[key] then
+ local fieldKey = guide.getKeyName(field)
+ if fieldKey then
+ -- ---@field x boolean -> class.x
+ if key == nil
+ or fieldKey == key then
+ if not searchedFields[fieldKey] then
pushResult(field)
- hasFounded[key] = true
+ hasFounded[fieldKey] = true
end
end
- else
- local fieldKey = guide.getKeyName(field)
- if fieldKey then
- if key == nil
- or fieldKey == key then
- if not searchedFields[fieldKey] then
+ end
+ if not hasFounded[fieldKey] then
+ local keyType = type(key)
+ if keyType == 'table' then
+ -- ---@field [integer] boolean -> class[integer]
+ local fieldNode = vm.compileNode(field.field)
+ if vm.isSubType(suri, key.name, fieldNode) then
+ local nkey = '|' .. key.name
+ if not searchedFields[nkey] then
pushResult(field)
- hasFounded[fieldKey] = true
+ hasFounded[nkey] = true
+ end
+ end
+ else
+ local typeName
+ if keyType == 'number' then
+ if math.tointeger(key) then
+ typeName = 'integer'
+ else
+ typeName = 'number'
+ end
+ elseif keyType == 'boolean'
+ or keyType == 'string' then
+ typeName = keyType
+ end
+ if typeName then
+ -- ---@field [integer] boolean -> class[1]
+ local fieldNode = vm.compileNode(field.field)
+ if vm.isSubType(suri, typeName, fieldNode) then
+ local nkey = '|' .. typeName
+ if not searchedFields[nkey] then
+ pushResult(field)
+ hasFounded[nkey] = true
+ end
end
end
end
diff --git a/test/type_inference/init.lua b/test/type_inference/init.lua
index e7560a12..270eb7ce 100644
--- a/test/type_inference/init.lua
+++ b/test/type_inference/init.lua
@@ -1810,3 +1810,11 @@ local t
t.<?x?>
]]
+
+TEST 'boolean' [[
+---@class A
+---@field [integer] boolean
+local t
+
+local <?x?> = t[1]
+]]