summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author最萌小汐 <sumneko@hotmail.com>2020-07-24 20:20:48 +0800
committer最萌小汐 <sumneko@hotmail.com>2020-07-24 20:20:48 +0800
commit1e11d151c29b1e107c09ef694ed9fe2d929b6fc9 (patch)
tree4422f8eb37333b7b0e4f3884ce8ae0da82911290
parentad0db70b2eb45f956e7e301fddf133025e58c7d9 (diff)
downloadlua-language-server-1e11d151c29b1e107c09ef694ed9fe2d929b6fc9.zip
更多的定义穿透
-rw-r--r--script-beta/core/definition.lua16
-rw-r--r--script-beta/parser/guide.lua24
-rw-r--r--script-beta/service/service.lua4
-rw-r--r--script-beta/vm/eachRef.lua39
-rw-r--r--script-beta/vm/guideInterface.lua2
-rw-r--r--test-beta/crossfile/definition.lua50
6 files changed, 97 insertions, 38 deletions
diff --git a/script-beta/core/definition.lua b/script-beta/core/definition.lua
index 896fa85f..e51d12aa 100644
--- a/script-beta/core/definition.lua
+++ b/script-beta/core/definition.lua
@@ -7,16 +7,24 @@ local findSource = require 'core.find-source'
local function sortResults(results)
-- 先按照顺序排序
table.sort(results, function (a, b)
- return a.target.start < b.target.start
+ local u1 = guide.getRoot(a).uri
+ local u2 = guide.getRoot(b).uri
+ if u1 == u2 then
+ return a.target.start < b.target.start
+ else
+ return u1 < u2
+ end
end)
-- 如果2个结果处于嵌套状态,则取范围小的那个
- local lf
+ local lf, lu
for i = #results, 1, -1 do
local res = results[i].target
- local f = res.finish
- if lf and f > lf then
+ local f = res.finish
+ local uri = guide.getRoot(res).uri
+ if lf and f > lf and uri == lu then
table.remove(results, i)
else
+ lu = uri
lf = f
end
end
diff --git a/script-beta/parser/guide.lua b/script-beta/parser/guide.lua
index 9ea0a60f..f5a0c2c7 100644
--- a/script-beta/parser/guide.lua
+++ b/script-beta/parser/guide.lua
@@ -943,15 +943,24 @@ end
-- 根据函数调用的返回值,获取:调用的函数,参数列表,自己是第几个返回值
function m.getCallValue(source)
- local value = source.value
- if not value or value.type ~= 'select' then
+ local value = m.getObjectValue(source)
+ if not value then
return
end
- local call = value.vararg
- if call.type ~= 'call' then
+ local call, index
+ if value.type == 'call' then
+ call = value
+ index = 1
+ elseif value.type == 'select' then
+ call = value.vararg
+ index = value.index
+ if call.type ~= 'call' then
+ return
+ end
+ else
return
end
- return call.node, call.args, value.index
+ return call.node, call.args, index
end
function m.getNextRef(ref)
@@ -1266,13 +1275,13 @@ function m.checkSameSimple(status, simple, data, mode, results, queue)
m.searchSameFieldsCrossMethod(status, ref, i, queue)
-- 穿透赋值
m.searchSameFieldsInValue(status, ref, i, queue)
+ -- 检查形如 a = f() 的分支情况,需要业务层传入 interface.call
+ m.checkSameSimpleInCall(status, ref, i, queue)
if i == #simple then
break
end
-- 检查形如 a = {} 的分支情况
m.checkSameSimpleInBranch(status, ref, i, queue)
- -- 检查形如 a = f() 的分支情况,需要业务层传入 interface.call
- m.checkSameSimpleInCall(status, ref, i, queue)
ref = m.getNextRef(ref)
if not ref then
return
@@ -1375,7 +1384,6 @@ function m.searchSameFields(status, simple, mode)
if status.lock[data.obj] then
mark[data.obj] = true
end
- status.lock[data.obj] = true
end
for i = 1, #queue do
local data = queue[i]
diff --git a/script-beta/service/service.lua b/script-beta/service/service.lua
index 9226492a..f8a2d761 100644
--- a/script-beta/service/service.lua
+++ b/script-beta/service/service.lua
@@ -4,7 +4,6 @@ local await = require 'await'
local timer = require 'timer'
local proto = require 'proto'
local vm = require 'vm'
-local files = require 'files'
local m = {}
m.type = 'service'
@@ -121,9 +120,6 @@ function m.startTimer()
if await.step() then
goto CONTINUE
end
- if files.refresh() then
- goto CONTINUE
- end
thread.sleep(0.001)
timer.update()
end
diff --git a/script-beta/vm/eachRef.lua b/script-beta/vm/eachRef.lua
index c5d3c845..8df63022 100644
--- a/script-beta/vm/eachRef.lua
+++ b/script-beta/vm/eachRef.lua
@@ -1,27 +1,30 @@
local vm = require 'vm.vm'
local guide = require 'parser.guide'
-local function eachRef(source)
- local results = guide.requestReference(source)
+local function eachRef(source, results)
+ results = results or {}
+ local lock = vm.lock('eachDef', source)
+ if not lock then
+ return results
+ end
+
+ local myResults = guide.requestReference(source)
+ vm.mergeResults(results, myResults)
+
+ lock()
+
return results
end
+function vm.getRefs(source)
+ local cache = vm.cache.eachRef[source] or eachRef(source)
+ vm.cache.eachDef[source] = cache
+ return cache
+end
+
function vm.eachRef(source, callback)
- local cache = vm.cache.eachRef[source]
- if cache ~= nil then
- for i = 1, #cache do
- callback(cache[i])
- end
- return
- end
- local unlock = vm.lock('eachRef', source)
- if not unlock then
- return
- end
- cache = eachRef(source) or false
- vm.cache.eachRef[source] = cache
- unlock()
- for i = 1, #cache do
- callback(cache[i])
+ local results = vm.getRefs(source)
+ for i = 1, #results do
+ callback(results[i])
end
end
diff --git a/script-beta/vm/guideInterface.lua b/script-beta/vm/guideInterface.lua
index ca949d59..f3ce2740 100644
--- a/script-beta/vm/guideInterface.lua
+++ b/script-beta/vm/guideInterface.lua
@@ -13,7 +13,7 @@ function m.searchFileReturn(results, ast, index)
if exp.type == 'table' then
vm.mergeResults(results, { exp })
else
- local newRes = vm.getDefs(exp)
+ local newRes = vm.getRefs(exp)
if #newRes > 0 then
vm.mergeResults(results, newRes)
else
diff --git a/test-beta/crossfile/definition.lua b/test-beta/crossfile/definition.lua
index 03bb6404..a642f68d 100644
--- a/test-beta/crossfile/definition.lua
+++ b/test-beta/crossfile/definition.lua
@@ -120,7 +120,7 @@ TEST {
TEST {
{
path = 'a.lua',
- content = 'local <!t!> = 1; return t',
+ content = 'local <!t!> = 1; return <!t!>',
},
{
path = 'b.lua',
@@ -146,7 +146,7 @@ end
TEST {
{
path = 'a.lua',
- content = 'local <!t!> = 1; return t',
+ content = 'local <!t!> = 1; return <!t!>',
},
{
path = 'b.lua',
@@ -357,7 +357,7 @@ TEST {
content = [[
local function <!f!>()
end
- return f
+ return <!f!>
]]
},
{
@@ -451,6 +451,50 @@ TEST {
}
}
+TEST {
+ {
+ path = 'a.lua',
+ content = [[
+ local m = {}
+ function m.<!func!>()
+ end
+ return m
+ ]]
+ },
+ {
+ path = 'b.lua',
+ content = [[
+ local x = require 'a'
+ print(x.<?func?>)
+ ]]
+ }
+}
+
+TEST {
+ {
+ path = 'a.lua',
+ content = [[
+ return <!function ()
+ end!>
+ ]]
+ },
+ {
+ path = 'middle.lua',
+ content = [[
+ return {
+ <!func!> = require 'a'
+ }
+ ]]
+ },
+ {
+ path = 'b.lua',
+ content = [[
+ local x = require 'middle'
+ print(x.<?func?>)
+ ]]
+ }
+}
+
--TEST {
-- {
-- path = 'a.lua',