Skip to content

Commit

Permalink
Merge pull request LuaLS#3015 from TIMONz1535/TIMONz1535-patch-2
Browse files Browse the repository at this point in the history
Improve generic pattern to support "`T`.*-"
  • Loading branch information
sumneko authored Jan 2, 2025
2 parents 208542c + 002f4a8 commit cb964c6
Show file tree
Hide file tree
Showing 3 changed files with 103 additions and 34 deletions.
9 changes: 9 additions & 0 deletions changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,15 @@

## Unreleased
<!-- Add all new changes here. They will be moved under a version at release -->
* `CHG` [#3014] Generic pattern now supports definition after capture
```lua
---@generic T
---@param t `T`.Cat
---@return T
local function f(t) end

local t = f('Smile') --> t is `Smile.Cat`
```
* `NEW` Test CLI: `--name=<testname>` `-n=<testname>`: run specify unit test
* `FIX` Fixed the error that the configuration file pointed to by the `--configpath` option was not read and loaded.

Expand Down
64 changes: 35 additions & 29 deletions script/parser/luadoc.lua
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,13 @@ EChar <- 'a' -> ea
/ ([0-9] [0-9]? [0-9]?) -> Char10
/ ('u{' {X16*} '}') -> CharUtf8
Symbol <- ({} {
[:|,;<>()?+#{}]
[:|,;<>()?+#{}*]
/ '[]'
/ '...'
/ '['
/ ']'
/ '-' !'-'
/ '.' !'..'
} {})
-> Symbol
]], {
Expand Down Expand Up @@ -720,57 +721,63 @@ local function parseString(parent)
return str
end

local function parseCode(parent)
local tp, content = peekToken()
if not tp or tp ~= 'code' then
return nil
end
nextToken()
local code = {
type = 'doc.type.code',
start = getStart(),
finish = getFinish(),
parent = parent,
[1] = content,
}
return code
end

local function parseCodePattern(parent)
local tp, pattern = peekToken()
if not tp or tp ~= 'name' then
if not tp or (tp ~= 'name' and tp ~= 'code') then
return nil
end
local codeOffset
local finishOffset
local content
for i = 2, 8 do
local i = 1
if tp == 'code' then
codeOffset = i
content = pattern
pattern = '%s'
end
while true do
i = i + 1
local next, nextContent = peekToken(i)
if not next or TokenFinishs[Ci+i-1] + 1 ~= TokenStarts[Ci+i] then
if codeOffset then
finishOffset = i
finishOffset = i-1
break
end
---不连续的name,无效的
return nil
end
if next == 'code' then
if codeOffset and content ~= nextContent then
if next == 'name' then
pattern = pattern .. nextContent
elseif next == 'code' then
if codeOffset then
-- 暂时不支持多generic
return nil
end
codeOffset = i
pattern = pattern .. "%s"
pattern = pattern .. '%s'
content = nextContent
elseif next ~= 'name' then
return nil
elseif codeOffset then
-- should be match with Parser "name" mask
if next == 'integer' then
pattern = pattern .. nextContent
elseif next == 'symbol' and (nextContent == '.' or nextContent == '*' or nextContent == '-') then
pattern = pattern .. nextContent
else
return nil
end
else
pattern = pattern .. nextContent
return nil
end
end
nextToken()
local start = getStart()
for _ = 2, finishOffset do
nextToken()
if finishOffset == 1 then
-- code only, no pattern
pattern = nil
else
for _ = 2, finishOffset do
nextToken()
end
end
local code = {
type = 'doc.type.code',
Expand Down Expand Up @@ -834,7 +841,6 @@ function parseTypeUnit(parent)
or parseTable(parent)
or parseTuple(parent)
or parseString(parent)
or parseCode(parent)
or parseInteger(parent)
or parseBoolean(parent)
or parseParen(parent)
Expand Down
64 changes: 59 additions & 5 deletions test/definition/luadoc.lua
Original file line number Diff line number Diff line change
Expand Up @@ -239,7 +239,7 @@ TEST [[
AAAA = {};
function AAAA:<!SSDF!>()
end
AAAA.a.<?SSDF?>
Expand Down Expand Up @@ -304,6 +304,19 @@ local v1 = Generic(Foo)
print(v1.<?bar1?>)
]]

TEST [[
---@class Foo
local Foo = {}
function Foo:<!bar1!>() end
---@generic T
---@param arg1 `T`
---@return T
function Generic(arg1) print(arg1) end
local v1 = Generic("Foo")
print(v1.<?bar1?>)
]]

TEST [[
---@class n.Foo
Expand All @@ -320,27 +333,68 @@ print(v1.<?bar1?>)
]]

TEST [[
---@class Foo
---@class n.Foo
local Foo = {}
function Foo:<!bar1!>() end
---@generic T
---@param arg1 `T`
---@param arg1 n.`T`
---@return T
function Generic(arg1) print(arg1) end
local v1 = Generic("Foo")
print(v1.<?bar1?>)
]]

TEST [[
---@class Foo*
local Foo = {}
function Foo:bar1() end
---@generic T
---@param arg1 `T`*
---@return T
function Generic(arg1) print(arg1) end
local v1 = Generic(Foo)
print(v1.<?bar1?>)
]]

TEST [[
---@class n.Foo
---@class Foo*
local Foo = {}
function Foo:<!bar1!>() end
---@generic T
---@param arg1 n.`T`
---@param arg1 `T`*
---@return T
function Generic(arg1) print(arg1) end
local v1 = Generic("Foo")
print(v1.<?bar1?>)
]]

TEST [[
---@class n.Foo.2
local Foo = {}
function Foo:bar1() end
---@generic T
---@param arg1 n.`T`.2
---@return T
function Generic(arg1) print(arg1) end
local v1 = Generic(Foo)
print(v1.<?bar1?>)
]]

TEST [[
---@class n.Foo.2
local Foo = {}
function Foo:<!bar1!>() end
---@generic T
---@param arg1 n.`T`.2
---@return T
function Generic(arg1) print(arg1) end
Expand Down

0 comments on commit cb964c6

Please sign in to comment.