Skip to content

Commit 2d5b2cb

Browse files
committed
add vm.getDefFields
1 parent e0ff9a8 commit 2d5b2cb

File tree

6 files changed

+136
-17
lines changed

6 files changed

+136
-17
lines changed

script/core/diagnostics/undefined-field.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ return function (uri, callback)
5555
local fields = {}
5656
local empty = true
5757
for _, docClass in ipairs(allDocClass) do
58-
local refs = vm.getFieldsOfDocClassAnyNotGet(docClass)
58+
local refs = vm.getDefFields(docClass)
5959

6060
for _, ref in ipairs(refs) do
6161
local name = vm.getKeyName(ref)

script/parser/guide.lua

Lines changed: 55 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,7 @@ end
2929

3030
local m = {}
3131

32-
m.ANY = {"ANY"}
33-
34-
m.ANYNOTGET = {"ANYNOTGET"}
32+
m.ANY = {"<ANY>"}
3533

3634
local blockTypes = {
3735
['while'] = true,
@@ -1401,6 +1399,16 @@ function m.searchFields(status, obj, key)
14011399
m.cleanResults(status.results)
14021400
end
14031401

1402+
function m.searchDefFields(status, obj, key)
1403+
local simple = m.getSimple(obj)
1404+
if not simple then
1405+
return
1406+
end
1407+
simple[#simple+1] = key or m.ANY
1408+
m.searchSameFields(status, simple, 'deffield')
1409+
m.cleanResults(status.results)
1410+
end
1411+
14041412
function m.getObjectValue(obj)
14051413
while obj.type == 'paren' do
14061414
obj = obj.exp
@@ -1436,7 +1444,7 @@ end
14361444

14371445
function m.checkSameSimpleInValueInMetaTable(status, mt, start, pushQueue)
14381446
local newStatus = m.status(status)
1439-
m.searchFields(newStatus, mt, '__index')
1447+
m.searchDefFields(newStatus, mt, '__index')
14401448
local refsStatus = m.status(status)
14411449
for i = 1, #newStatus.results do
14421450
local indexValue = m.getObjectValue(newStatus.results[i])
@@ -1684,7 +1692,8 @@ function m.checkSameSimpleByDoc(status, obj, start, pushQueue, mode)
16841692
end
16851693
return true
16861694
elseif obj.type == 'doc.field' then
1687-
if mode ~= 'field' then
1695+
if mode ~= 'field'
1696+
and mode ~= 'deffield' then
16881697
return m.checkSameSimpleByDoc(status, obj.extends, start, pushQueue, mode)
16891698
end
16901699
elseif obj.type == 'doc.type.array' then
@@ -2309,6 +2318,30 @@ function m.pushResult(status, mode, ref, simple)
23092318
or ref.type == 'doc.field' then
23102319
results[#results+1] = ref
23112320
end
2321+
elseif mode == 'deffield' then
2322+
if ref.type == 'setfield'
2323+
or ref.type == 'tablefield' then
2324+
results[#results+1] = ref
2325+
elseif ref.type == 'setmethod' then
2326+
results[#results+1] = ref
2327+
elseif ref.type == 'setindex'
2328+
or ref.type == 'tableindex' then
2329+
results[#results+1] = ref
2330+
elseif ref.type == 'setglobal' then
2331+
results[#results+1] = ref
2332+
elseif ref.type == 'function' then
2333+
results[#results+1] = ref
2334+
elseif ref.type == 'table' then
2335+
results[#results+1] = ref
2336+
elseif ref.type == 'call' then
2337+
if ref.node.special == 'rawset' then
2338+
results[#results+1] = ref
2339+
end
2340+
elseif ref.type == 'doc.type.function'
2341+
or ref.type == 'doc.class.name'
2342+
or ref.type == 'doc.field' then
2343+
results[#results+1] = ref
2344+
end
23122345
end
23132346
end
23142347

@@ -2317,7 +2350,7 @@ function m.checkSameSimpleName(ref, sm)
23172350
return true
23182351
end
23192352

2320-
if sm == m.ANYNOTGET and not m.isGet(ref) then
2353+
if sm == m.ANY_DEF and m.isSet(ref) then
23212354
return true
23222355
end
23232356

@@ -2663,13 +2696,16 @@ function m.searchRefs(status, obj, mode)
26632696
end
26642697

26652698
-- 检查单步引用
2699+
tracy.ZoneBeginN('searchRefs getStepRef')
26662700
local res = m.getStepRef(status, obj, mode)
26672701
if res then
26682702
for i = 1, #res do
26692703
status.results[#status.results+1] = res[i]
26702704
end
26712705
end
2706+
tracy.ZoneEnd()
26722707
-- 检查simple
2708+
tracy.ZoneBeginN('searchRefs searchSameFields')
26732709
if status.depth <= 100 then
26742710
local simple = m.getSimple(obj)
26752711
if simple then
@@ -2683,6 +2719,7 @@ function m.searchRefs(status, obj, mode)
26832719
logWarn('status.depth overflow')
26842720
end
26852721
end
2722+
tracy.ZoneEnd()
26862723

26872724
m.cleanResults(status.results)
26882725

@@ -4103,8 +4140,8 @@ function m.requestDefinition(obj, interface, deep)
41034140
return status.results, status.share.count
41044141
end
41054142

4106-
--- 请求对象的域
4107-
---@param filterKey nil|string|table nilfields不做限制;stringfields必须同名;table取值为guild.ANYSETfields必须满足isSet()
4143+
--- 请求对象的字段
4144+
---@param filterKey nil|string|table
41084145
function m.requestFields(obj, interface, deep, filterKey)
41094146
local status = m.status(nil, interface, deep)
41104147

@@ -4113,6 +4150,16 @@ function m.requestFields(obj, interface, deep, filterKey)
41134150
return status.results, status.share.count
41144151
end
41154152

4153+
--- 请求对象的定义字段
4154+
---@param filterKey nil|string|table
4155+
function m.requestDefFields(obj, interface, deep, filterKey)
4156+
local status = m.status(nil, interface, deep)
4157+
4158+
m.searchDefFields(status, obj, filterKey)
4159+
4160+
return status.results, status.share.count
4161+
end
4162+
41164163
--- 请求对象的类型推测
41174164
function m.requestInfer(obj, interface, deep)
41184165
local status = m.status(nil, interface, deep)

script/vm/eachField.lua

Lines changed: 49 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,27 @@ local function getFields(source, deep, filterKey)
2525
return results
2626
end
2727

28+
local function getDefFields(source, deep, filterKey)
29+
local unlock = vm.lock('eachDefField', source)
30+
if not unlock then
31+
return {}
32+
end
33+
34+
while source.type == 'paren' do
35+
source = source.exp
36+
if not source then
37+
return {}
38+
end
39+
end
40+
deep = config.config.intelliSense.searchDepth + (deep or 0)
41+
42+
await.delay()
43+
local results = guide.requestDefFields(source, vm.interface, deep, filterKey)
44+
45+
unlock()
46+
return results
47+
end
48+
2849
local function getFieldsBySource(source, deep, filterKey)
2950
deep = deep or -999
3051
local cache = vm.getCache('eachField')[source]
@@ -38,6 +59,19 @@ local function getFieldsBySource(source, deep, filterKey)
3859
return cache
3960
end
4061

62+
local function getDefFieldsBySource(source, deep, filterKey)
63+
deep = deep or -999
64+
local cache = vm.getCache('eachDefField')[source]
65+
if not cache or cache.deep < deep then
66+
cache = getDefFields(source, deep, filterKey)
67+
cache.deep = deep
68+
if not filterKey then
69+
vm.getCache('eachDefField')[source] = cache
70+
end
71+
end
72+
return cache
73+
end
74+
4175
function vm.getFields(source, deep)
4276
if source.special == '_G' then
4377
return vm.getGlobals '*'
@@ -56,13 +90,20 @@ function vm.getFields(source, deep)
5690
end
5791
end
5892

59-
function vm.getFieldsOfDocClassAnyNotGet(source, deep)
60-
if not guide.isDocClass(source) then
61-
return {}
93+
function vm.getDefFields(source, deep)
94+
if source.special == '_G' then
95+
return vm.getGlobalSets '*'
96+
end
97+
if guide.isGlobal(source) then
98+
local name = guide.getKeyName(source)
99+
if not name then
100+
return {}
101+
end
102+
local cache = vm.getCache('eachDefFieldOfGlobal')[name]
103+
or getDefFieldsBySource(source, deep)
104+
vm.getCache('eachDefFieldOfGlobal')[name] = cache
105+
return cache
106+
else
107+
return getDefFieldsBySource(source, deep)
62108
end
63-
64-
local cache = vm.getCache('eachFieldOfDocClass')[source]
65-
or getFieldsBySource(source, deep, guide.ANYNOTGET)
66-
vm.getCache('eachFieldOfDocClass')[source] = cache
67-
return cache
68109
end

test.lua

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,4 +82,5 @@ loadAllLibs()
8282
main()
8383

8484
log.debug('测试完成')
85+
require 'bee.thread'.sleep(1)
8586
os.exit()

test/full/init.lua

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,3 +11,4 @@ end
1111
require 'full.normal'
1212
require 'full.example'
1313
require 'full.dirty'
14+
require 'full.self'

test/full/self.lua

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
local files = require 'files'
2+
local fsu = require 'fs-utility'
3+
local furi = require 'file-uri'
4+
local diag = require 'provider.diagnostic'
5+
local config = require 'config'
6+
files.removeAll()
7+
8+
fsu.scanDirectory(ROOT, function (path)
9+
if path:extension():string() ~= '.lua' then
10+
return
11+
end
12+
local uri = furi.encode(path:string())
13+
local text = fsu.loadFile(path)
14+
files.setText(uri, text)
15+
files.open(uri)
16+
end)
17+
18+
config.config.diagnostics.disable['undefined-field'] = true
19+
config.config.diagnostics.disable['redundant-parameter'] = true
20+
diag.start()
21+
22+
local clock = os.clock()
23+
24+
for uri in files.eachFile() do
25+
diag.doDiagnostic(uri)
26+
end
27+
28+
local passed = os.clock() - clock
29+
print('基准全量诊断用时:', passed)

0 commit comments

Comments
 (0)