eslint-plugin-reforged
This page is generated from packages/eslint-plugin-reforged/CHANGELOG.md by docs:collect. Edit the source, not this page.
1.0.0-alpha.3
Minor Changes
- #319
eb8f2aeThanks @wyller! -no-legacy-w3ts-namesreports the w3ts use of a member that kept its name but not its signature (the rename map's entries whose new name is the old one), with the entry's note: an argument the new parameter does not take (cache.store(missionKey, key, hero.handle)), a result used where the new type does not fit (Unit.fromHandle(cache.restoreUnit(...))), and a result checked for a missing value when the new type cannot be missing (restoreUnitnow throws where it returnedundefined). A call written for the new signature is not reported.
1.0.0-alpha.2
Patch Changes
- #317
bc110a5Thanks @wyller! -Item.playeris renamedItem.getOwner(), named likeItem.setOwnerandUnit.getOwner; it returns the owner as aMapPlayer, orundefined, asItem.playerdid. The rename map listsItem.playeras an accessor whose getter isItem.getOwner, sono-legacy-w3ts-namessuggests the callitem.getOwner()for a read ofitem.player.Camera.setCameraOrientControlleris renamedCamera.setOrientController, like its twinCamera.setTargetController; it takes the same arguments. The lint plugin'slocal-safe.jsonlistsCamera.setOrientControllerin place of the old name, sono-game-state-in-local-branchstill lets it through inside a local branch. - Updated dependencies [
5678711,bc110a5]:- reforged-ts@1.0.0-alpha.10
1.0.0-alpha.1
Patch Changes
-
#208
e30077cThanks @phmilk! -no-game-state-in-local-branchlets the new visual and text Wrapper members of reforged-ts through inside a local branch, as it does their Natives:Camera.setFieldControlledByInputand theCamera.typesetter,CameraSetup#type,Sound.playThematicMusic,endThematicMusicandsetThematicMusicVolume,Frame#setTextAreaAutoScroll,Destructable#setVertexColor, and the text membersMapPlayer#displayText,displayTimedTextanddisplayTimedTextFrom, whichno-percent-in-display-stringsnow checks too. -
#208
9ddf666Thanks @phmilk! -no-unsafe-nativesbansTriggerWaitForSound, a trigger action wait likeTriggerSleepAction: it yields the running thread until the sound ends. The rule suggests continuing in a timer callback when the sound ends instead. -
#209
29057aeThanks @phmilk! - Every rule'smeta.docs.urlpoints at the rule's page under the Lint rules guide of the docs site,https://phmilk.github.io/reforged-ts/docs/<docs version>/guides/lint-rules/<rule>, which the site serves from the page the plugin ships indocs/. The previoushttps://phmilk.github.io/reforged-ts/<docs version>/lint/<rule>URLs led to no page. -
#209
7aa0edeThanks @phmilk! - The README's "For AI agents" line links the documentation of this version as Markdown for a language model:llms.txt, one link per page, andllms-full.txt, every page in one file. A prerelease links the working tree's docs,https://phmilk.github.io/reforged-ts/docs/next/llms.txt; a stable release links the docs version of its library minor,/docs/<major.minor>/llms.txt. -
Updated dependencies [
7aa0ede,4e6e5f4]:- reforged-ts@1.0.0-alpha.1
- reforged-types@1.0.0-alpha.1
1.0.0-alpha.0
Major Changes
-
#159
05eda1aThanks @phmilk! - First release under this name, for Warcraft III 3.0.0 and later.reforged-tsis the fork of w3ts 3.0.2;reforged-types,reforged-testandeslint-plugin-reforgedare new packages. -
#159
fc96e92Thanks @phmilk! - The rename map has a no-renames marker. A major that removes and renames no public symbol records{ "kind": "noRenames", "versions": { "from", "to" }, "note" }inmigration/renames.jsoninstead of entries, so its version pair is seen as considered;migration/renames.schema.jsonaccepts it.no-legacy-w3ts-namesskips the marker when it reads the map.For
eslint-plugin-reforgedthis is a major: the shape of a data file it reads from another package changed, and an earlier version of the plugin throws aDataFileErrorat load on a rename map that holds the marker. Forreforged-tsit is a minor: the schema accepts one more kind of item and every existing entry keeps its shape.
Minor Changes
-
#121
667e252Thanks @wyller! - Initial release: the lint layer of the Guards. Twelve type-aware rules report the Warcraft III scripting pitfalls (desync, crash, leak) of a Map project before it compiles: six errors and six warnings, all enabled byconfigs.recommended.The plugin.
eslint-plugin-reforgedexports the plugin object (meta,rules,configs). A Map project enables every rule by spreadingconfigs.recommendedafter typescript-eslint's type-checked presets; the config registers the plugin asreforgedand sets no parser and no project options. Every rule'smeta.docs.urlpoints tohttps://phmilk.github.io/reforged-ts/<docs version>/lint/<rule>, and one page per rule ships indocs/.Optional packages. The plugin reads the data files of
reforged-ts(migration/renames.json) andreforged-types(async-natives.json) from the Map project's own installation, found from the project root: the working directory, orcreatePlugin({ projectRoot }). When the package is missing, the plugin prints one warning at load naming the package and the rules, and registers those rules disabled. A file present with an unexpected shape throws aDataFileErrornaming the field.Its cost over typescript-eslint's type-checked preset, measured on the fixture project (
pnpm --filter eslint-plugin-reforged measure-cost), is about 10%.Errors
no-game-state-in-local-branch(error). Reports game state changed inside a branch that runs for the local player only: the consequent of anif, a conditional or&&/||whose test readsGetLocalPlayer(),MapPlayer.fromLocal()orplayer.isLocal()(directly, in an equality, or through oneconst), theelsebranch of a negated test, the function passed toMapPlayer.runLocal, and functions defined there. Inside it, the rule reports a Native or Wrapper member thatdata/local-safe.jsondoes not list, a creation,Filter/Condition,ForGroup/ForForce,GetRandomInt/GetRandomReal/SetRandomSeedandMath.random. Visual calls (frames, camera, sound, vertex colours), text displays and the pure Natives (converters, math and string Natives) pass; pure computation and calls to project functions are not reported. A value getter such asGetUnitXand the frame lookups (BlzGetFrameByName) are reported. Theallowoption adds names treated as visual. No fix and no suggestion.no-dotted-asset-paths(error). Reports a string literal, or a template literal without substitutions, whose file name ends in.mdx,.mdl,.blp,.ddsor.tga(case-insensitive) and holds another dot before the extension, which the game does not read since 3.0.0. A suggestion replaces the inner dots with underscores. Optionextensionsreplaces the list.Creations. Two rules report creations, the Handles a Map project makes: a Wrapper's
create*static, or a Native listed in the plugin's revieweddata/creation-natives.json(Create*,BlzCreate*,AddSpecialEffect*,AddLightning*,DialogCreate,Location, ...) that returns a Handle type other than a registration type. Lookups and conversions (Player,GetTriggerUnit,Convert*) are never creations.no-handles-at-module-top-level(error). Reports a creation at module top level, which a TSTL bundle runs in the Lua root: top-level initialisers, class static initialisers, immediately invoked functions and object literals evaluated at load. The message points to theInit.onGlobalsstage. No fix and no suggestion.no-legacy-w3ts-names(error). Reports the w3ts 3.x names reforged-ts renamed or removed, from the rename map the library publishes (reforged-ts/migration/renames.json): an import fromw3ts, an imported export, a member or static access on a library class (matched through the type checker, so a project class of the same name is not reported), and anewof a library class. The message gives the replacement and the entry's note; a removed symbol reads as removed. One-to-one entries are fixed: the package name in imports,new Unit(...)toUnit.create(...), and same-signature member renames, importing the class when the receiver changes. The other renames are suggestions, one per replacement.no-unsafe-natives(error). Reports a call to a Native on the plugin's ban list,data/unsafe-natives.json:TriggerSleepAction,PolledWait,DestroyEffectAfterTimeBJ,CreateTimerBJ,StartTimerBJ,GetLastCreatedTimerBJ,SelectGroupForPlayerBJandSmartCameraPanBJ. The message gives the entry's reason and replacement. The callee must resolve, through the type checker, to the Native declared inreforged-types: a project function of the same name is not reported. Optionallowremoves entries for a project. A ban list with an unexpected shape throws at plugin load, naming the field.no-unused-handle-result(error). Reports an expression statement that discards a creation or aFilter/Conditionboolexpr, which then leaks.Timer.afterand the other statics not namedcreate*are never reported. No fix.Warnings
no-async-value-as-state(warning). Reports a value that differs between clients flowing into game state. The sources are a call whose resolved declaration carries the@asyncdoc tag (the Natives ofreforged-types, andreforged-tsmembers such asMapPlayer.fromLocal), a read of an@asyncgetter ofreforged-ts, and Lua'sos.clock,os.time,os.dateandos.difftime. The value is state when it reaches, directly or through oneconst, an argument of a call that is neither a text sink nor a visual entry ofdata/local-safe.json, a module-level or exported variable, or a table key. A pure Native of the allowlist (R2S,R2I, ...) passes the value on through its result. An argument ofnew SyncRequest(...)orrequest.start(...)is not state. The message names the sync System. No fix.no-unordered-iteration(warning). Reports what typescript-to-lua compiles to Lua'spairs, whose order differs between clients:for...in,Object.keys,Object.values,Object.entries, direct calls topairsandnext, andfor...ofover aLuaTable,LuaMaporLuaSet.MapandSetkeep insertion order in the runtime library and are not reported. The message namesSyncedMap/SyncedSetandfor...ofover an array.no-handle-id-as-data(warning). Reports a call toGetHandleId, and a read of a Wrapper'sidaccessor, whose value does not reach a text-display Native: in a Lua map the id of the same Handle can differ between clients, so a key, a comparison or state built on it desyncs. Key by the Handle or Wrapper itself. The rule follows the value into a display call through a template, a concatenation,String()/tostring,I2S/R2S/R2SWand oneconst;MapPlayer#id(the player slot) is not reported.no-percent-in-display-strings(warning). Reports a string literal or template with a lone%that reaches a text-display Native: the display Natives (DisplayTextToPlayer,DisplayTimedTextToPlayer,DisplayTimedTextFromPlayer,DisplayTextToForce,DisplayTimedTextToForce,BJDebugMsg),print,BlzFrameSetText,BlzFrameAddTextand theFramememberssetText,addTextandtext. The rule follows the string through a template literal, a concatenation,String(),tostringorI2S/R2S/R2SW, and oneconst. A suggestion doubles the%, which the game displays as%.prefer-handle-map(warning). Reportsnew Mapandnew Setwhose key type is a Wrapper, written or inferred: the table keeps its entry after the Handle is destroyed. A suggestion changes the constructor toHandleMap/HandleSet; the author adds the import.WeakMapandWeakSetare not reported.no-self-recursion(warning). Reports a function declaration, function expression,constarrow or method that calls itself by name in its own body, outside nested functions. The message says the stock Lua 5.3 stack limits are unverified for the game's build.Data files
The allowlist.
data/local-safe.jsonlists the Natives and library members that only change what the local player sees or hears (visual: frame setters, vertex colours, the camera, sounds and music) or that display a string (text), and the Natives whose result depends on their arguments alone (pure:I2S,R2S,SquareRoot,SubString, ...), each with its reason. A file with an unexpected shape throws at plugin load, naming the field.async-natives.json. The plugin reads the list of async Natives from the Map project's own installation ofreforged-types. Without it, the plugin warns once at load and disables the rule; a list with an unexpected shape throws aDataFileErrornaming the field.