@quenty/maid 3.4.0 → 3.4.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +11 -0
- package/package.json +2 -2
- package/src/Shared/Maid.lua +74 -49
- package/src/Shared/MaidTaskUtils.lua +12 -10
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,17 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
## [3.4.1](https://github.com/Quenty/NevermoreEngine/compare/@quenty/maid@3.4.0...@quenty/maid@3.4.1) (2025-04-05)
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
### Bug Fixes
|
|
10
|
+
|
|
11
|
+
* Add types to packages ([2374fb2](https://github.com/Quenty/NevermoreEngine/commit/2374fb2b043cfbe0e9b507b3316eec46a4e353a0))
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
6
17
|
# [3.4.0](https://github.com/Quenty/NevermoreEngine/compare/@quenty/maid@3.3.0...@quenty/maid@3.4.0) (2024-10-04)
|
|
7
18
|
|
|
8
19
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@quenty/maid",
|
|
3
|
-
"version": "3.4.
|
|
3
|
+
"version": "3.4.1",
|
|
4
4
|
"description": "Easily cleanup event listeners and objects in Roblox",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"Roblox",
|
|
@@ -29,5 +29,5 @@
|
|
|
29
29
|
"publishConfig": {
|
|
30
30
|
"access": "public"
|
|
31
31
|
},
|
|
32
|
-
"gitHead": "
|
|
32
|
+
"gitHead": "78c3ac0ab08dd18085b6e6e6e4f745e76ed99f68"
|
|
33
33
|
}
|
package/src/Shared/Maid.lua
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
|
|
1
|
+
--!strict
|
|
2
|
+
--[[
|
|
2
3
|
Manages the cleaning of events and other things. Useful for
|
|
3
4
|
encapsulating state and make deconstructors easy.
|
|
4
5
|
|
|
@@ -18,29 +19,46 @@
|
|
|
18
19
|
maid:DoCleaning()
|
|
19
20
|
```
|
|
20
21
|
|
|
22
|
+
@ignore
|
|
21
23
|
@class Maid
|
|
22
|
-
]
|
|
24
|
+
]]
|
|
23
25
|
-- luacheck: pop
|
|
24
26
|
|
|
25
27
|
local Maid = {}
|
|
26
28
|
Maid.ClassName = "Maid"
|
|
27
29
|
|
|
28
|
-
|
|
30
|
+
export type MaidTask = (() -> ()) | Instance | thread | Maid | any
|
|
31
|
+
|
|
32
|
+
export type Maid = typeof(setmetatable(
|
|
33
|
+
{} :: {
|
|
34
|
+
Add: <T>(self: Maid, task: T) -> T,
|
|
35
|
+
GiveTask: (self: Maid, task: MaidTask) -> number,
|
|
36
|
+
GivePromise: <T>(self: Maid, promise: T) -> T,
|
|
37
|
+
DoCleaning: (self: Maid) -> (),
|
|
38
|
+
Destroy: (self: Maid) -> (),
|
|
39
|
+
_tasks: { [any]: MaidTask },
|
|
40
|
+
[string | number | { [any]: any } | Instance]: MaidTask?,
|
|
41
|
+
},
|
|
42
|
+
Maid
|
|
43
|
+
))
|
|
44
|
+
|
|
45
|
+
--[[
|
|
29
46
|
Constructs a new Maid object
|
|
30
47
|
|
|
31
48
|
```lua
|
|
32
49
|
local maid = Maid.new()
|
|
33
50
|
```
|
|
34
51
|
|
|
52
|
+
@ignore
|
|
35
53
|
@return Maid
|
|
36
|
-
]
|
|
37
|
-
function Maid.new()
|
|
54
|
+
]]
|
|
55
|
+
function Maid.new(): Maid
|
|
38
56
|
return setmetatable({
|
|
39
|
-
_tasks = {}
|
|
40
|
-
}, Maid)
|
|
57
|
+
_tasks = {},
|
|
58
|
+
}, Maid) :: Maid
|
|
41
59
|
end
|
|
42
60
|
|
|
43
|
-
--[
|
|
61
|
+
--[[
|
|
44
62
|
Returns true if the class is a maid, and false otherwise.
|
|
45
63
|
|
|
46
64
|
```lua
|
|
@@ -48,14 +66,15 @@ end
|
|
|
48
66
|
print(Maid.isMaid(nil)) --> false
|
|
49
67
|
```
|
|
50
68
|
|
|
69
|
+
@ignore
|
|
51
70
|
@param value any
|
|
52
71
|
@return boolean
|
|
53
|
-
]
|
|
54
|
-
function Maid.isMaid(value)
|
|
72
|
+
]]
|
|
73
|
+
function Maid.isMaid(value: any): boolean
|
|
55
74
|
return type(value) == "table" and value.ClassName == "Maid"
|
|
56
75
|
end
|
|
57
76
|
|
|
58
|
-
--[
|
|
77
|
+
--[[
|
|
59
78
|
Returns Maid[key] if not part of Maid metatable
|
|
60
79
|
|
|
61
80
|
```lua
|
|
@@ -67,10 +86,11 @@ end
|
|
|
67
86
|
print(maid._current) --> nil
|
|
68
87
|
```
|
|
69
88
|
|
|
89
|
+
@ignore
|
|
70
90
|
@param index any
|
|
71
91
|
@return MaidTask
|
|
72
|
-
]
|
|
73
|
-
function Maid
|
|
92
|
+
]]
|
|
93
|
+
function Maid.__index(self: Maid, index: any)
|
|
74
94
|
if Maid[index] then
|
|
75
95
|
return Maid[index]
|
|
76
96
|
else
|
|
@@ -78,7 +98,7 @@ function Maid:__index(index)
|
|
|
78
98
|
end
|
|
79
99
|
end
|
|
80
100
|
|
|
81
|
-
--[
|
|
101
|
+
--[[
|
|
82
102
|
Add a task to clean up. Tasks given to a maid will be cleaned when
|
|
83
103
|
maid[index] is set to a different value.
|
|
84
104
|
|
|
@@ -94,10 +114,11 @@ end
|
|
|
94
114
|
Maid[key] = nil Removes a named task.
|
|
95
115
|
```
|
|
96
116
|
|
|
117
|
+
@ignore
|
|
97
118
|
@param index any
|
|
98
119
|
@param newTask MaidTask
|
|
99
|
-
]
|
|
100
|
-
function Maid
|
|
120
|
+
]]
|
|
121
|
+
function Maid.__newindex(self: Maid, index: any, newTask: MaidTask)
|
|
101
122
|
if Maid[index] ~= nil then
|
|
102
123
|
error(string.format("Cannot use '%s' as a Maid key", tostring(index)), 2)
|
|
103
124
|
end
|
|
@@ -112,16 +133,15 @@ function Maid:__newindex(index, newTask)
|
|
|
112
133
|
tasks[index] = newTask
|
|
113
134
|
|
|
114
135
|
if job then
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
elseif jobType == "table" then
|
|
136
|
+
if typeof(job) == "function" then
|
|
137
|
+
(job :: any)()
|
|
138
|
+
elseif typeof(job) == "table" then
|
|
119
139
|
if type(job.Destroy) == "function" then
|
|
120
140
|
job:Destroy()
|
|
121
141
|
end
|
|
122
|
-
elseif
|
|
142
|
+
elseif typeof(job) == "Instance" then
|
|
123
143
|
job:Destroy()
|
|
124
|
-
elseif
|
|
144
|
+
elseif typeof(job) == "thread" then
|
|
125
145
|
local cancelled
|
|
126
146
|
if coroutine.running() ~= job then
|
|
127
147
|
cancelled = pcall(function()
|
|
@@ -134,60 +154,63 @@ function Maid:__newindex(index, newTask)
|
|
|
134
154
|
task.cancel(job)
|
|
135
155
|
end)
|
|
136
156
|
end
|
|
137
|
-
elseif
|
|
157
|
+
elseif typeof(job) == "RBXScriptConnection" then
|
|
138
158
|
job:Disconnect()
|
|
139
159
|
end
|
|
140
160
|
end
|
|
141
161
|
end
|
|
142
162
|
|
|
143
|
-
--[
|
|
163
|
+
--[[
|
|
144
164
|
Gives a task to the maid for cleanup and returns the resulting value
|
|
145
165
|
|
|
166
|
+
@ignore
|
|
146
167
|
@param task MaidTask -- An item to clean
|
|
147
168
|
@return MaidTask
|
|
148
|
-
]
|
|
149
|
-
function Maid
|
|
169
|
+
]]
|
|
170
|
+
function Maid.Add<T>(self: Maid, task: T): T
|
|
150
171
|
if not task then
|
|
151
172
|
error("Task cannot be false or nil", 2)
|
|
152
173
|
end
|
|
153
174
|
|
|
154
|
-
self[#self._tasks+1] = task
|
|
175
|
+
self[#(self._tasks :: any) + 1] = task
|
|
155
176
|
|
|
156
|
-
if type(task) == "table" and
|
|
177
|
+
if type(task) == "table" and not task.Destroy then
|
|
157
178
|
warn("[Maid.Add] - Gave table task without .Destroy\n\n" .. debug.traceback())
|
|
158
179
|
end
|
|
159
180
|
|
|
160
181
|
return task
|
|
161
182
|
end
|
|
162
183
|
|
|
163
|
-
--[
|
|
184
|
+
--[[
|
|
164
185
|
Gives a task to the maid for cleanup, but uses an incremented number as a key.
|
|
165
186
|
|
|
187
|
+
@ignore
|
|
166
188
|
@param task MaidTask -- An item to clean
|
|
167
189
|
@return number -- taskId
|
|
168
|
-
]
|
|
169
|
-
function Maid
|
|
190
|
+
]]
|
|
191
|
+
function Maid.GiveTask(self: Maid, task: MaidTask): number
|
|
170
192
|
if not task then
|
|
171
193
|
error("Task cannot be false or nil", 2)
|
|
172
194
|
end
|
|
173
195
|
|
|
174
|
-
local taskId = #self._tasks+1
|
|
196
|
+
local taskId = #(self._tasks :: any) + 1
|
|
175
197
|
self[taskId] = task
|
|
176
198
|
|
|
177
|
-
if type(task) == "table" and
|
|
199
|
+
if type(task) == "table" and not task.Destroy then
|
|
178
200
|
warn("[Maid.GiveTask] - Gave table task without .Destroy\n\n" .. debug.traceback())
|
|
179
201
|
end
|
|
180
202
|
|
|
181
203
|
return taskId
|
|
182
204
|
end
|
|
183
205
|
|
|
184
|
-
--[
|
|
206
|
+
--[[
|
|
185
207
|
Gives a promise to the maid for clean.
|
|
186
208
|
|
|
209
|
+
@ignore
|
|
187
210
|
@param promise Promise<T>
|
|
188
211
|
@return Promise<T>
|
|
189
|
-
]
|
|
190
|
-
function Maid
|
|
212
|
+
]]
|
|
213
|
+
function Maid.GivePromise(self: Maid, promise: any): any
|
|
191
214
|
if not promise:IsPending() then
|
|
192
215
|
return promise
|
|
193
216
|
end
|
|
@@ -203,7 +226,7 @@ function Maid:GivePromise(promise)
|
|
|
203
226
|
return newPromise
|
|
204
227
|
end
|
|
205
228
|
|
|
206
|
-
--[
|
|
229
|
+
--[[
|
|
207
230
|
Cleans up all tasks and removes them as entries from the Maid.
|
|
208
231
|
|
|
209
232
|
:::note
|
|
@@ -218,12 +241,14 @@ end
|
|
|
218
241
|
However, adding tasks while cleaning is not generally a good idea, as if you add a
|
|
219
242
|
function that adds itself, this will loop indefinitely.
|
|
220
243
|
:::
|
|
221
|
-
|
|
222
|
-
|
|
244
|
+
|
|
245
|
+
@ignore
|
|
246
|
+
]]
|
|
247
|
+
function Maid.DoCleaning(self: Maid)
|
|
223
248
|
local tasks = self._tasks
|
|
224
249
|
|
|
225
250
|
-- Disconnect all events first as we know this is safe
|
|
226
|
-
for index, job in
|
|
251
|
+
for index, job in tasks do
|
|
227
252
|
if typeof(job) == "RBXScriptConnection" then
|
|
228
253
|
tasks[index] = nil
|
|
229
254
|
job:Disconnect()
|
|
@@ -234,14 +259,13 @@ function Maid:DoCleaning()
|
|
|
234
259
|
local index, job = next(tasks)
|
|
235
260
|
while job ~= nil do
|
|
236
261
|
tasks[index] = nil
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
elseif jobType == "table" and type(job.Destroy) == "function" then
|
|
262
|
+
if typeof(job) == "function" then
|
|
263
|
+
(job :: any)()
|
|
264
|
+
elseif typeof(job) == "table" and type(job.Destroy) == "function" then
|
|
241
265
|
job:Destroy()
|
|
242
|
-
elseif
|
|
266
|
+
elseif typeof(job) == "Instance" then
|
|
243
267
|
job:Destroy()
|
|
244
|
-
elseif
|
|
268
|
+
elseif typeof(job) == "thread" then
|
|
245
269
|
local cancelled
|
|
246
270
|
if coroutine.running() ~= job then
|
|
247
271
|
cancelled = pcall(function()
|
|
@@ -255,19 +279,20 @@ function Maid:DoCleaning()
|
|
|
255
279
|
task.cancel(toCancel)
|
|
256
280
|
end)
|
|
257
281
|
end
|
|
258
|
-
elseif
|
|
282
|
+
elseif typeof(job) == "RBXScriptConnection" then
|
|
259
283
|
job:Disconnect()
|
|
260
284
|
end
|
|
261
285
|
index, job = next(tasks)
|
|
262
286
|
end
|
|
263
287
|
end
|
|
264
288
|
|
|
265
|
-
--[
|
|
289
|
+
--[[
|
|
266
290
|
Alias for [Maid.DoCleaning()](/api/Maid#DoCleaning)
|
|
267
291
|
|
|
292
|
+
@ignore
|
|
268
293
|
@function Destroy
|
|
269
294
|
@within Maid
|
|
270
|
-
]
|
|
295
|
+
]]
|
|
271
296
|
Maid.Destroy = Maid.DoCleaning
|
|
272
297
|
|
|
273
298
|
return Maid
|
|
@@ -8,12 +8,15 @@
|
|
|
8
8
|
@type Destructable Instance | { Destroy: function }
|
|
9
9
|
@within MaidTaskUtils
|
|
10
10
|
]=]
|
|
11
|
+
export type Destructable = Instance | any
|
|
11
12
|
|
|
12
13
|
--[=[
|
|
13
14
|
An object that can be cleaned up
|
|
14
15
|
@type MaidTask function | thread | Destructable | RBXScriptConnection
|
|
15
16
|
@within MaidTaskUtils
|
|
16
17
|
]=]
|
|
18
|
+
export type MaidTask = (() -> ()) | thread | Instance | Destructable | RBXScriptConnection
|
|
19
|
+
|
|
17
20
|
local MaidTaskUtils = {}
|
|
18
21
|
|
|
19
22
|
--[=[
|
|
@@ -22,7 +25,7 @@ local MaidTaskUtils = {}
|
|
|
22
25
|
@param job any
|
|
23
26
|
@return boolean
|
|
24
27
|
]=]
|
|
25
|
-
function MaidTaskUtils.isValidTask(job)
|
|
28
|
+
function MaidTaskUtils.isValidTask(job: any): boolean
|
|
26
29
|
local jobType = typeof(job)
|
|
27
30
|
return jobType == "function"
|
|
28
31
|
or jobType == "thread"
|
|
@@ -36,17 +39,16 @@ end
|
|
|
36
39
|
|
|
37
40
|
@param job MaidTask -- Task to execute
|
|
38
41
|
]=]
|
|
39
|
-
function MaidTaskUtils.doTask(job)
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
elseif jobType == "table" then
|
|
42
|
+
function MaidTaskUtils.doTask(job: MaidTask)
|
|
43
|
+
if typeof(job) == "function" then
|
|
44
|
+
(job :: any)()
|
|
45
|
+
elseif typeof(job) == "table" then
|
|
44
46
|
if type(job.Destroy) == "function" then
|
|
45
47
|
job:Destroy()
|
|
46
48
|
end
|
|
47
|
-
elseif
|
|
49
|
+
elseif typeof(job) == "Instance" then
|
|
48
50
|
job:Destroy()
|
|
49
|
-
elseif
|
|
51
|
+
elseif typeof(job) == "thread" then
|
|
50
52
|
local cancelled
|
|
51
53
|
if coroutine.running() ~= job then
|
|
52
54
|
cancelled = pcall(function()
|
|
@@ -59,7 +61,7 @@ function MaidTaskUtils.doTask(job)
|
|
|
59
61
|
task.cancel(job)
|
|
60
62
|
end)
|
|
61
63
|
end
|
|
62
|
-
elseif
|
|
64
|
+
elseif typeof(job) == "RBXScriptConnection" then
|
|
63
65
|
job:Disconnect()
|
|
64
66
|
else
|
|
65
67
|
error(string.format("[MaidTaskUtils.doTask] - Bad job of type %q", typeof(job)))
|
|
@@ -78,7 +80,7 @@ end
|
|
|
78
80
|
@param job MaidTask -- Job to delay execution
|
|
79
81
|
@return () -> () -- function that will execute the job delayed
|
|
80
82
|
]=]
|
|
81
|
-
function MaidTaskUtils.delayed(time, job)
|
|
83
|
+
function MaidTaskUtils.delayed(time: number, job: MaidTask)
|
|
82
84
|
assert(type(time) == "number", "Bad time")
|
|
83
85
|
assert(MaidTaskUtils.isValidTask(job), "Bad job")
|
|
84
86
|
|