diff --git a/LICENSE b/LICENSE
index c933ca0..175443c 100644
--- a/LICENSE
+++ b/LICENSE
@@ -1,21 +1,595 @@
-MIT License
+GNU General Public License
+==========================
-Copyright (c) 2023 Araxia Online
+_Version 3, 29 June 2007_
+_Copyright © 2007 Free Software Foundation, Inc. <>_
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
+Everyone is permitted to copy and distribute verbatim copies of this license
+document, but changing it is not allowed.
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
+## Preamble
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
+The GNU General Public License is a free, copyleft license for software and other
+kinds of works.
+
+The licenses for most software and other practical works are designed to take away
+your freedom to share and change the works. By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change all versions of a
+program--to make sure it remains free software for all its users. We, the Free
+Software Foundation, use the GNU General Public License for most of our software; it
+applies also to any other work released this way by its authors. You can apply it to
+your programs, too.
+
+When we speak of free software, we are referring to freedom, not price. Our General
+Public Licenses are designed to make sure that you have the freedom to distribute
+copies of free software (and charge for them if you wish), that you receive source
+code or can get it if you want it, that you can change the software or use pieces of
+it in new free programs, and that you know you can do these things.
+
+To protect your rights, we need to prevent others from denying you these rights or
+asking you to surrender the rights. Therefore, you have certain responsibilities if
+you distribute copies of the software, or if you modify it: responsibilities to
+respect the freedom of others.
+
+For example, if you distribute copies of such a program, whether gratis or for a fee,
+you must pass on to the recipients the same freedoms that you received. You must make
+sure that they, too, receive or can get the source code. And you must show them these
+terms so they know their rights.
+
+Developers that use the GNU GPL protect your rights with two steps: **(1)** assert
+copyright on the software, and **(2)** offer you this License giving you legal permission
+to copy, distribute and/or modify it.
+
+For the developers' and authors' protection, the GPL clearly explains that there is
+no warranty for this free software. For both users' and authors' sake, the GPL
+requires that modified versions be marked as changed, so that their problems will not
+be attributed erroneously to authors of previous versions.
+
+Some devices are designed to deny users access to install or run modified versions of
+the software inside them, although the manufacturer can do so. This is fundamentally
+incompatible with the aim of protecting users' freedom to change the software. The
+systematic pattern of such abuse occurs in the area of products for individuals to
+use, which is precisely where it is most unacceptable. Therefore, we have designed
+this version of the GPL to prohibit the practice for those products. If such problems
+arise substantially in other domains, we stand ready to extend this provision to
+those domains in future versions of the GPL, as needed to protect the freedom of
+users.
+
+Finally, every program is threatened constantly by software patents. States should
+not allow patents to restrict development and use of software on general-purpose
+computers, but in those that do, we wish to avoid the special danger that patents
+applied to a free program could make it effectively proprietary. To prevent this, the
+GPL assures that patents cannot be used to render the program non-free.
+
+The precise terms and conditions for copying, distribution and modification follow.
+
+## TERMS AND CONDITIONS
+
+### 0. Definitions
+
+“This License” refers to version 3 of the GNU General Public License.
+
+“Copyright” also means copyright-like laws that apply to other kinds of
+works, such as semiconductor masks.
+
+“The Program” refers to any copyrightable work licensed under this
+License. Each licensee is addressed as “you”. “Licensees” and
+“recipients” may be individuals or organizations.
+
+To “modify” a work means to copy from or adapt all or part of the work in
+a fashion requiring copyright permission, other than the making of an exact copy. The
+resulting work is called a “modified version” of the earlier work or a
+work “based on” the earlier work.
+
+A “covered work” means either the unmodified Program or a work based on
+the Program.
+
+To “propagate” a work means to do anything with it that, without
+permission, would make you directly or secondarily liable for infringement under
+applicable copyright law, except executing it on a computer or modifying a private
+copy. Propagation includes copying, distribution (with or without modification),
+making available to the public, and in some countries other activities as well.
+
+To “convey” a work means any kind of propagation that enables other
+parties to make or receive copies. Mere interaction with a user through a computer
+network, with no transfer of a copy, is not conveying.
+
+An interactive user interface displays “Appropriate Legal Notices” to the
+extent that it includes a convenient and prominently visible feature that **(1)**
+displays an appropriate copyright notice, and **(2)** tells the user that there is no
+warranty for the work (except to the extent that warranties are provided), that
+licensees may convey the work under this License, and how to view a copy of this
+License. If the interface presents a list of user commands or options, such as a
+menu, a prominent item in the list meets this criterion.
+
+### 1. Source Code
+
+The “source code” for a work means the preferred form of the work for
+making modifications to it. “Object code” means any non-source form of a
+work.
+
+A “Standard Interface” means an interface that either is an official
+standard defined by a recognized standards body, or, in the case of interfaces
+specified for a particular programming language, one that is widely used among
+developers working in that language.
+
+The “System Libraries” of an executable work include anything, other than
+the work as a whole, that **(a)** is included in the normal form of packaging a Major
+Component, but which is not part of that Major Component, and **(b)** serves only to
+enable use of the work with that Major Component, or to implement a Standard
+Interface for which an implementation is available to the public in source code form.
+A “Major Component”, in this context, means a major essential component
+(kernel, window system, and so on) of the specific operating system (if any) on which
+the executable work runs, or a compiler used to produce the work, or an object code
+interpreter used to run it.
+
+The “Corresponding Source” for a work in object code form means all the
+source code needed to generate, install, and (for an executable work) run the object
+code and to modify the work, including scripts to control those activities. However,
+it does not include the work's System Libraries, or general-purpose tools or
+generally available free programs which are used unmodified in performing those
+activities but which are not part of the work. For example, Corresponding Source
+includes interface definition files associated with source files for the work, and
+the source code for shared libraries and dynamically linked subprograms that the work
+is specifically designed to require, such as by intimate data communication or
+control flow between those subprograms and other parts of the work.
+
+The Corresponding Source need not include anything that users can regenerate
+automatically from other parts of the Corresponding Source.
+
+The Corresponding Source for a work in source code form is that same work.
+
+### 2. Basic Permissions
+
+All rights granted under this License are granted for the term of copyright on the
+Program, and are irrevocable provided the stated conditions are met. This License
+explicitly affirms your unlimited permission to run the unmodified Program. The
+output from running a covered work is covered by this License only if the output,
+given its content, constitutes a covered work. This License acknowledges your rights
+of fair use or other equivalent, as provided by copyright law.
+
+You may make, run and propagate covered works that you do not convey, without
+conditions so long as your license otherwise remains in force. You may convey covered
+works to others for the sole purpose of having them make modifications exclusively
+for you, or provide you with facilities for running those works, provided that you
+comply with the terms of this License in conveying all material for which you do not
+control copyright. Those thus making or running the covered works for you must do so
+exclusively on your behalf, under your direction and control, on terms that prohibit
+them from making any copies of your copyrighted material outside their relationship
+with you.
+
+Conveying under any other circumstances is permitted solely under the conditions
+stated below. Sublicensing is not allowed; section 10 makes it unnecessary.
+
+### 3. Protecting Users' Legal Rights From Anti-Circumvention Law
+
+No covered work shall be deemed part of an effective technological measure under any
+applicable law fulfilling obligations under article 11 of the WIPO copyright treaty
+adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention
+of such measures.
+
+When you convey a covered work, you waive any legal power to forbid circumvention of
+technological measures to the extent such circumvention is effected by exercising
+rights under this License with respect to the covered work, and you disclaim any
+intention to limit operation or modification of the work as a means of enforcing,
+against the work's users, your or third parties' legal rights to forbid circumvention
+of technological measures.
+
+### 4. Conveying Verbatim Copies
+
+You may convey verbatim copies of the Program's source code as you receive it, in any
+medium, provided that you conspicuously and appropriately publish on each copy an
+appropriate copyright notice; keep intact all notices stating that this License and
+any non-permissive terms added in accord with section 7 apply to the code; keep
+intact all notices of the absence of any warranty; and give all recipients a copy of
+this License along with the Program.
+
+You may charge any price or no price for each copy that you convey, and you may offer
+support or warranty protection for a fee.
+
+### 5. Conveying Modified Source Versions
+
+You may convey a work based on the Program, or the modifications to produce it from
+the Program, in the form of source code under the terms of section 4, provided that
+you also meet all of these conditions:
+
+* **a)** The work must carry prominent notices stating that you modified it, and giving a
+relevant date.
+* **b)** The work must carry prominent notices stating that it is released under this
+License and any conditions added under section 7. This requirement modifies the
+requirement in section 4 to “keep intact all notices”.
+* **c)** You must license the entire work, as a whole, under this License to anyone who
+comes into possession of a copy. This License will therefore apply, along with any
+applicable section 7 additional terms, to the whole of the work, and all its parts,
+regardless of how they are packaged. This License gives no permission to license the
+work in any other way, but it does not invalidate such permission if you have
+separately received it.
+* **d)** If the work has interactive user interfaces, each must display Appropriate Legal
+Notices; however, if the Program has interactive interfaces that do not display
+Appropriate Legal Notices, your work need not make them do so.
+
+A compilation of a covered work with other separate and independent works, which are
+not by their nature extensions of the covered work, and which are not combined with
+it such as to form a larger program, in or on a volume of a storage or distribution
+medium, is called an “aggregate” if the compilation and its resulting
+copyright are not used to limit the access or legal rights of the compilation's users
+beyond what the individual works permit. Inclusion of a covered work in an aggregate
+does not cause this License to apply to the other parts of the aggregate.
+
+### 6. Conveying Non-Source Forms
+
+You may convey a covered work in object code form under the terms of sections 4 and
+5, provided that you also convey the machine-readable Corresponding Source under the
+terms of this License, in one of these ways:
+
+* **a)** Convey the object code in, or embodied in, a physical product (including a
+physical distribution medium), accompanied by the Corresponding Source fixed on a
+durable physical medium customarily used for software interchange.
+* **b)** Convey the object code in, or embodied in, a physical product (including a
+physical distribution medium), accompanied by a written offer, valid for at least
+three years and valid for as long as you offer spare parts or customer support for
+that product model, to give anyone who possesses the object code either **(1)** a copy of
+the Corresponding Source for all the software in the product that is covered by this
+License, on a durable physical medium customarily used for software interchange, for
+a price no more than your reasonable cost of physically performing this conveying of
+source, or **(2)** access to copy the Corresponding Source from a network server at no
+charge.
+* **c)** Convey individual copies of the object code with a copy of the written offer to
+provide the Corresponding Source. This alternative is allowed only occasionally and
+noncommercially, and only if you received the object code with such an offer, in
+accord with subsection 6b.
+* **d)** Convey the object code by offering access from a designated place (gratis or for
+a charge), and offer equivalent access to the Corresponding Source in the same way
+through the same place at no further charge. You need not require recipients to copy
+the Corresponding Source along with the object code. If the place to copy the object
+code is a network server, the Corresponding Source may be on a different server
+(operated by you or a third party) that supports equivalent copying facilities,
+provided you maintain clear directions next to the object code saying where to find
+the Corresponding Source. Regardless of what server hosts the Corresponding Source,
+you remain obligated to ensure that it is available for as long as needed to satisfy
+these requirements.
+* **e)** Convey the object code using peer-to-peer transmission, provided you inform
+other peers where the object code and Corresponding Source of the work are being
+offered to the general public at no charge under subsection 6d.
+
+A separable portion of the object code, whose source code is excluded from the
+Corresponding Source as a System Library, need not be included in conveying the
+object code work.
+
+A “User Product” is either **(1)** a “consumer product”, which
+means any tangible personal property which is normally used for personal, family, or
+household purposes, or **(2)** anything designed or sold for incorporation into a
+dwelling. In determining whether a product is a consumer product, doubtful cases
+shall be resolved in favor of coverage. For a particular product received by a
+particular user, “normally used” refers to a typical or common use of
+that class of product, regardless of the status of the particular user or of the way
+in which the particular user actually uses, or expects or is expected to use, the
+product. A product is a consumer product regardless of whether the product has
+substantial commercial, industrial or non-consumer uses, unless such uses represent
+the only significant mode of use of the product.
+
+“Installation Information” for a User Product means any methods,
+procedures, authorization keys, or other information required to install and execute
+modified versions of a covered work in that User Product from a modified version of
+its Corresponding Source. The information must suffice to ensure that the continued
+functioning of the modified object code is in no case prevented or interfered with
+solely because modification has been made.
+
+If you convey an object code work under this section in, or with, or specifically for
+use in, a User Product, and the conveying occurs as part of a transaction in which
+the right of possession and use of the User Product is transferred to the recipient
+in perpetuity or for a fixed term (regardless of how the transaction is
+characterized), the Corresponding Source conveyed under this section must be
+accompanied by the Installation Information. But this requirement does not apply if
+neither you nor any third party retains the ability to install modified object code
+on the User Product (for example, the work has been installed in ROM).
+
+The requirement to provide Installation Information does not include a requirement to
+continue to provide support service, warranty, or updates for a work that has been
+modified or installed by the recipient, or for the User Product in which it has been
+modified or installed. Access to a network may be denied when the modification itself
+materially and adversely affects the operation of the network or violates the rules
+and protocols for communication across the network.
+
+Corresponding Source conveyed, and Installation Information provided, in accord with
+this section must be in a format that is publicly documented (and with an
+implementation available to the public in source code form), and must require no
+special password or key for unpacking, reading or copying.
+
+### 7. Additional Terms
+
+“Additional permissions” are terms that supplement the terms of this
+License by making exceptions from one or more of its conditions. Additional
+permissions that are applicable to the entire Program shall be treated as though they
+were included in this License, to the extent that they are valid under applicable
+law. If additional permissions apply only to part of the Program, that part may be
+used separately under those permissions, but the entire Program remains governed by
+this License without regard to the additional permissions.
+
+When you convey a copy of a covered work, you may at your option remove any
+additional permissions from that copy, or from any part of it. (Additional
+permissions may be written to require their own removal in certain cases when you
+modify the work.) You may place additional permissions on material, added by you to a
+covered work, for which you have or can give appropriate copyright permission.
+
+Notwithstanding any other provision of this License, for material you add to a
+covered work, you may (if authorized by the copyright holders of that material)
+supplement the terms of this License with terms:
+
+* **a)** Disclaiming warranty or limiting liability differently from the terms of
+sections 15 and 16 of this License; or
+* **b)** Requiring preservation of specified reasonable legal notices or author
+attributions in that material or in the Appropriate Legal Notices displayed by works
+containing it; or
+* **c)** Prohibiting misrepresentation of the origin of that material, or requiring that
+modified versions of such material be marked in reasonable ways as different from the
+original version; or
+* **d)** Limiting the use for publicity purposes of names of licensors or authors of the
+material; or
+* **e)** Declining to grant rights under trademark law for use of some trade names,
+trademarks, or service marks; or
+* **f)** Requiring indemnification of licensors and authors of that material by anyone
+who conveys the material (or modified versions of it) with contractual assumptions of
+liability to the recipient, for any liability that these contractual assumptions
+directly impose on those licensors and authors.
+
+All other non-permissive additional terms are considered “further
+restrictions” within the meaning of section 10. If the Program as you received
+it, or any part of it, contains a notice stating that it is governed by this License
+along with a term that is a further restriction, you may remove that term. If a
+license document contains a further restriction but permits relicensing or conveying
+under this License, you may add to a covered work material governed by the terms of
+that license document, provided that the further restriction does not survive such
+relicensing or conveying.
+
+If you add terms to a covered work in accord with this section, you must place, in
+the relevant source files, a statement of the additional terms that apply to those
+files, or a notice indicating where to find the applicable terms.
+
+Additional terms, permissive or non-permissive, may be stated in the form of a
+separately written license, or stated as exceptions; the above requirements apply
+either way.
+
+### 8. Termination
+
+You may not propagate or modify a covered work except as expressly provided under
+this License. Any attempt otherwise to propagate or modify it is void, and will
+automatically terminate your rights under this License (including any patent licenses
+granted under the third paragraph of section 11).
+
+However, if you cease all violation of this License, then your license from a
+particular copyright holder is reinstated **(a)** provisionally, unless and until the
+copyright holder explicitly and finally terminates your license, and **(b)** permanently,
+if the copyright holder fails to notify you of the violation by some reasonable means
+prior to 60 days after the cessation.
+
+Moreover, your license from a particular copyright holder is reinstated permanently
+if the copyright holder notifies you of the violation by some reasonable means, this
+is the first time you have received notice of violation of this License (for any
+work) from that copyright holder, and you cure the violation prior to 30 days after
+your receipt of the notice.
+
+Termination of your rights under this section does not terminate the licenses of
+parties who have received copies or rights from you under this License. If your
+rights have been terminated and not permanently reinstated, you do not qualify to
+receive new licenses for the same material under section 10.
+
+### 9. Acceptance Not Required for Having Copies
+
+You are not required to accept this License in order to receive or run a copy of the
+Program. Ancillary propagation of a covered work occurring solely as a consequence of
+using peer-to-peer transmission to receive a copy likewise does not require
+acceptance. However, nothing other than this License grants you permission to
+propagate or modify any covered work. These actions infringe copyright if you do not
+accept this License. Therefore, by modifying or propagating a covered work, you
+indicate your acceptance of this License to do so.
+
+### 10. Automatic Licensing of Downstream Recipients
+
+Each time you convey a covered work, the recipient automatically receives a license
+from the original licensors, to run, modify and propagate that work, subject to this
+License. You are not responsible for enforcing compliance by third parties with this
+License.
+
+An “entity transaction” is a transaction transferring control of an
+organization, or substantially all assets of one, or subdividing an organization, or
+merging organizations. If propagation of a covered work results from an entity
+transaction, each party to that transaction who receives a copy of the work also
+receives whatever licenses to the work the party's predecessor in interest had or
+could give under the previous paragraph, plus a right to possession of the
+Corresponding Source of the work from the predecessor in interest, if the predecessor
+has it or can get it with reasonable efforts.
+
+You may not impose any further restrictions on the exercise of the rights granted or
+affirmed under this License. For example, you may not impose a license fee, royalty,
+or other charge for exercise of rights granted under this License, and you may not
+initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging
+that any patent claim is infringed by making, using, selling, offering for sale, or
+importing the Program or any portion of it.
+
+### 11. Patents
+
+A “contributor” is a copyright holder who authorizes use under this
+License of the Program or a work on which the Program is based. The work thus
+licensed is called the contributor's “contributor version”.
+
+A contributor's “essential patent claims” are all patent claims owned or
+controlled by the contributor, whether already acquired or hereafter acquired, that
+would be infringed by some manner, permitted by this License, of making, using, or
+selling its contributor version, but do not include claims that would be infringed
+only as a consequence of further modification of the contributor version. For
+purposes of this definition, “control” includes the right to grant patent
+sublicenses in a manner consistent with the requirements of this License.
+
+Each contributor grants you a non-exclusive, worldwide, royalty-free patent license
+under the contributor's essential patent claims, to make, use, sell, offer for sale,
+import and otherwise run, modify and propagate the contents of its contributor
+version.
+
+In the following three paragraphs, a “patent license” is any express
+agreement or commitment, however denominated, not to enforce a patent (such as an
+express permission to practice a patent or covenant not to sue for patent
+infringement). To “grant” such a patent license to a party means to make
+such an agreement or commitment not to enforce a patent against the party.
+
+If you convey a covered work, knowingly relying on a patent license, and the
+Corresponding Source of the work is not available for anyone to copy, free of charge
+and under the terms of this License, through a publicly available network server or
+other readily accessible means, then you must either **(1)** cause the Corresponding
+Source to be so available, or **(2)** arrange to deprive yourself of the benefit of the
+patent license for this particular work, or **(3)** arrange, in a manner consistent with
+the requirements of this License, to extend the patent license to downstream
+recipients. “Knowingly relying” means you have actual knowledge that, but
+for the patent license, your conveying the covered work in a country, or your
+recipient's use of the covered work in a country, would infringe one or more
+identifiable patents in that country that you have reason to believe are valid.
+
+If, pursuant to or in connection with a single transaction or arrangement, you
+convey, or propagate by procuring conveyance of, a covered work, and grant a patent
+license to some of the parties receiving the covered work authorizing them to use,
+propagate, modify or convey a specific copy of the covered work, then the patent
+license you grant is automatically extended to all recipients of the covered work and
+works based on it.
+
+A patent license is “discriminatory” if it does not include within the
+scope of its coverage, prohibits the exercise of, or is conditioned on the
+non-exercise of one or more of the rights that are specifically granted under this
+License. You may not convey a covered work if you are a party to an arrangement with
+a third party that is in the business of distributing software, under which you make
+payment to the third party based on the extent of your activity of conveying the
+work, and under which the third party grants, to any of the parties who would receive
+the covered work from you, a discriminatory patent license **(a)** in connection with
+copies of the covered work conveyed by you (or copies made from those copies), or **(b)**
+primarily for and in connection with specific products or compilations that contain
+the covered work, unless you entered into that arrangement, or that patent license
+was granted, prior to 28 March 2007.
+
+Nothing in this License shall be construed as excluding or limiting any implied
+license or other defenses to infringement that may otherwise be available to you
+under applicable patent law.
+
+### 12. No Surrender of Others' Freedom
+
+If conditions are imposed on you (whether by court order, agreement or otherwise)
+that contradict the conditions of this License, they do not excuse you from the
+conditions of this License. If you cannot convey a covered work so as to satisfy
+simultaneously your obligations under this License and any other pertinent
+obligations, then as a consequence you may not convey it at all. For example, if you
+agree to terms that obligate you to collect a royalty for further conveying from
+those to whom you convey the Program, the only way you could satisfy both those terms
+and this License would be to refrain entirely from conveying the Program.
+
+### 13. Use with the GNU Affero General Public License
+
+Notwithstanding any other provision of this License, you have permission to link or
+combine any covered work with a work licensed under version 3 of the GNU Affero
+General Public License into a single combined work, and to convey the resulting work.
+The terms of this License will continue to apply to the part which is the covered
+work, but the special requirements of the GNU Affero General Public License, section
+13, concerning interaction through a network will apply to the combination as such.
+
+### 14. Revised Versions of this License
+
+The Free Software Foundation may publish revised and/or new versions of the GNU
+General Public License from time to time. Such new versions will be similar in spirit
+to the present version, but may differ in detail to address new problems or concerns.
+
+Each version is given a distinguishing version number. If the Program specifies that
+a certain numbered version of the GNU General Public License “or any later
+version” applies to it, you have the option of following the terms and
+conditions either of that numbered version or of any later version published by the
+Free Software Foundation. If the Program does not specify a version number of the GNU
+General Public License, you may choose any version ever published by the Free
+Software Foundation.
+
+If the Program specifies that a proxy can decide which future versions of the GNU
+General Public License can be used, that proxy's public statement of acceptance of a
+version permanently authorizes you to choose that version for the Program.
+
+Later license versions may give you additional or different permissions. However, no
+additional obligations are imposed on any author or copyright holder as a result of
+your choosing to follow a later version.
+
+### 15. Disclaimer of Warranty
+
+THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
+EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY OF ANY KIND, EITHER
+EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE
+QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE
+DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
+
+### 16. Limitation of Liability
+
+IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY
+COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS
+PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL,
+INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
+PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE
+OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE
+WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+### 17. Interpretation of Sections 15 and 16
+
+If the disclaimer of warranty and limitation of liability provided above cannot be
+given local legal effect according to their terms, reviewing courts shall apply local
+law that most closely approximates an absolute waiver of all civil liability in
+connection with the Program, unless a warranty or assumption of liability accompanies
+a copy of the Program in return for a fee.
+
+_END OF TERMS AND CONDITIONS_
+
+## How to Apply These Terms to Your New Programs
+
+If you develop a new program, and you want it to be of the greatest possible use to
+the public, the best way to achieve this is to make it free software which everyone
+can redistribute and change under these terms.
+
+To do so, attach the following notices to the program. It is safest to attach them
+to the start of each source file to most effectively state the exclusion of warranty;
+and each file should have at least the “copyright” line and a pointer to
+where the full notice is found.
+
+
+ Copyright (C)
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program does terminal interaction, make it output a short notice like this
+when it starts in an interactive mode:
+
+ Copyright (C)
+ This program comes with ABSOLUTELY NO WARRANTY; for details type 'show w'.
+ This is free software, and you are welcome to redistribute it
+ under certain conditions; type 'show c' for details.
+
+The hypothetical commands `show w` and `show c` should show the appropriate parts of
+the General Public License. Of course, your program's commands might be different;
+for a GUI interface, you would use an “about box”.
+
+You should also get your employer (if you work as a programmer) or school, if any, to
+sign a “copyright disclaimer” for the program, if necessary. For more
+information on this, and how to apply and follow the GNU GPL, see
+<>.
+
+The GNU General Public License does not permit incorporating your program into
+proprietary programs. If your program is a subroutine library, you may consider it
+more useful to permit linking proprietary applications with the library. If this is
+what you want to do, use the GNU Lesser General Public License instead of this
+License. But first, please read
+<>.
diff --git a/ets.env b/ets.env
new file mode 100644
index 0000000..a8d0a4a
--- /dev/null
+++ b/ets.env
@@ -0,0 +1,33 @@
+# ETS Build Settings
+# In order for the build to work correctly all build setting values must be set
+# The program does not have defaults and builds will fail.
+
+# Root folder where built modules will be stored.
+ETS_BUILD_ROOT="./dist"
+
+# directory where transpiled lua modules will be built for deployment
+ETS_MODULE_DIR="module"
+
+# Build directory of where common tstl lualibraries if needed by modules
+ETS_COMMON_DIR="common"
+
+# Root where all TS Modules are found from root of project
+ETS_MODULES_TS_DIR="modules"
+
+# deployment dev settings
+DEV_HOST=
+DEV_PATH=
+DEV_USER=
+DEV_PASS=
+#DEV_PORT=
+#DEV_PRIVATE_KEY=
+#DEV_PRIVATE_KEY_PASS=
+
+# deploy prod settings
+PROD_HOST=
+PROD_PATH=
+PROD_USER=
+PROD_PASS=
+#PROD_PORT=
+#PROD_PRIVATE_KEY=
+#PROD_PRIVATE_KEY_PASS=
\ No newline at end of file
diff --git a/modules/classes/account.ts b/modules/classes/account.ts
new file mode 100644
index 0000000..066e49e
--- /dev/null
+++ b/modules/classes/account.ts
@@ -0,0 +1,35 @@
+/**
+ * Class for find out information about an account
+ */
+export type BasicCharacter = {
+ guid: number,
+ name: string
+}
+
+export class AccountInfo {
+ private accountId: number;
+
+ constructor(accountId: number) {
+ this.accountId = accountId;
+ }
+
+ GetAccountMoney(): number {
+ const result = CharDBQuery(`SELECT SUM(Money) as AccountMoney from acore_characters.characters WHERE account = ${this.accountId}`);
+ const row = result.GetRow() as Record;
+ return row.AccountMoney;
+ }
+
+ GetCharacters(): BasicCharacter[] {
+ const result = CharDBQuery(`SELECT guid, name from characters WHERE account = ${this.accountId}`);
+ const characters: BasicCharacter[] = [];
+
+ for(let i=0; i < result.GetRowCount(); i++) {
+ const row = result.GetRow();
+ characters.push({ guid: row.guid as number, name: row.name as string });
+ result.NextRow();
+ }
+
+ return characters;
+ }
+
+}
\ No newline at end of file
diff --git a/modules/classes/money.ts b/modules/classes/money.ts
new file mode 100644
index 0000000..95bda14
--- /dev/null
+++ b/modules/classes/money.ts
@@ -0,0 +1,32 @@
+import { AccountInfo } from "./account";
+
+export const GOLD_TO_COPPER = 10000;
+
+/**
+ * Converts a copper cost to gold
+ * @param cost Cost of item in copper
+ * @returns number
+ */
+export function ToGold(cost: number) : number {
+ return Math.floor(cost / GOLD_TO_COPPER);
+}
+
+/**
+ * Converts a gold cost to copper
+ * @param gold Cost of item in gold
+ * @returns number
+ */
+export function ToCopper(gold: number) : number {
+ return gold*GOLD_TO_COPPER;
+}
+
+/**
+ * Gets a scaling tax for players to help with balancing the economy for guild features.
+ * @param player Player
+ * @param tax amount of tax against player to levy number (0-100)
+ * @returns number result in copper
+ */
+export function GetPlayerTax(player: Player, tax: number) : number {
+ const account = new AccountInfo(player.GetAccountId());
+ return (tax/100) * account.GetAccountMoney();
+}
diff --git a/modules/classes/stats.ts b/modules/classes/stats.ts
new file mode 100644
index 0000000..e97dd92
--- /dev/null
+++ b/modules/classes/stats.ts
@@ -0,0 +1,143 @@
+declare function GetGameTime(): number;
+
+/**
+ * This is used to track custom stats for players inside of other modules
+ * REQUIRES SQL TABLES TO BE CREATED
+ */
+
+/**
+ * Config
+ */
+const PLAYER_TYPE = 'player';
+export const StatEvents = {
+ TOKEN_CREATED: 'token_created',
+ TICKETS_AWARDED: 'darkmoon_tickets_awarded',
+};
+
+/**
+ * Adds stats to database based on type of stat.
+ */
+export class Stats {
+
+ stats = new Map();
+ entity: StatEntity;
+
+ constructor(entity: StatEntity) {
+ this.entity = entity;
+ this.load();
+ }
+
+ static GetStatsByType(type: string, name: string) : Map {
+ const result = CharDBQuery(`SELECT id, name, value, updated FROM ${type}_stats WHERE name = '${name}'`);
+ const stats = new Map();
+ if(!result) {
+ return stats;
+ }
+ for(let i=0; i < result.GetRowCount(); i++) {
+ const row = result.GetRow();
+ stats.set(row.id as number, row.value as number);
+ result.NextRow();
+ }
+ return stats;
+ };
+
+ load() : boolean {
+ const result = CharDBQuery(`SELECT id, name, value, updated FROM ${this.entity.type}_stats WHERE id = ${this.entity.id}`);
+ if(!result) {
+ return false;
+ }
+ for(let i=0; i < result.GetRowCount(); i++) {
+ const row = result.GetRow();
+ const stat: Stat = {
+ name: row.name as string,
+ type: this.entity.type,
+ value: row.value as number,
+ updated: row.updated as number,
+ loaded: true
+ }
+ this.stats.set(stat.name, stat);
+ result.NextRow();
+ }
+ return true;
+ }
+
+ save() : void {
+
+ for(const stat of this.stats.values()) {
+ if(!stat.loaded) {
+ CharDBExecute(`INSERT INTO ${this.entity.type}_stats (id, name, value, updated) VALUES (${this.entity.id}, '${stat.name}', ${stat.value}, ${stat.updated})`);
+ PrintDebug(`Inserted ${stat.name} for ${this.entity.type} ${this.entity.id} with value ${stat.value}`);
+ } else {
+ CharDBExecute(`UPDATE ${this.entity.type}_stats SET value = ${stat.value}, updated = ${stat.updated} WHERE id = ${this.entity.id} AND name = '${stat.name}'`);
+ PrintDebug(`Updated ${stat.name} for ${this.entity.type} ${this.entity.id} to ${stat.value}`);
+ }
+ }
+ }
+
+ getStat(name: string) : Stat | undefined {
+ return this.stats.get(name);
+ }
+
+ setStat(name: string, value: number) : void {
+ const stat = this.stats.get(name);
+ if(stat) {
+ stat.value = value;
+ stat.updated = GetGameTime();
+ } else {
+ this.stats.set(name, {
+ name: name,
+ type: PLAYER_TYPE,
+ value: value,
+ updated: GetGameTime(),
+ loaded: false
+ });
+ }
+ }
+
+ increment(name: string, amount: number = 1) : void {
+ const stat = this.stats.get(name);
+ if(stat) {
+ stat.value += amount;
+ stat.updated = GetGameTime();
+ } else {
+ this.stats.set(name, {
+ name: name,
+ type: PLAYER_TYPE,
+ value: 0,
+ updated: GetGameTime(),
+ loaded: false
+ });
+ }
+ }
+}
+
+/**
+ * Custom player stats that will be
+ */
+export class PlayerStats extends Stats {
+
+ player: Player;
+ playerStats: Stat[] = [];
+
+ constructor(player: Player) {
+ super({
+ id: player.GetGUID(),
+ type: PLAYER_TYPE
+ });
+ this.player = player;
+ }
+
+}
+
+interface StatEntity {
+ type: string,
+ id: number
+}
+
+interface Stat {
+ type: string,
+ name: string,
+ value: number,
+ updated: number,
+ loaded: boolean
+}
\ No newline at end of file
diff --git a/modules/classes/triggers.ts b/modules/classes/triggers.ts
new file mode 100644
index 0000000..c5de134
--- /dev/null
+++ b/modules/classes/triggers.ts
@@ -0,0 +1,41 @@
+/* @noSelfInFile */
+
+/**
+ * This is used to set feature flags and player triggers
+ * REQUIRE SQL TABLES TO BE CREATED
+ */
+
+type TriggerInput = {
+ triggerName: string,
+ characterGuid: number,
+ isSet: boolean
+}
+
+/**
+ * Sets a player trigger boolean that can be retieved later as needed
+ * @param charTrigger TriggerInput
+ */
+export function SetTrigger(charTrigger: TriggerInput) {
+ let sql = `INSERT INTO player_trigger (triggerName, characterGuid, isSet) `+
+ `VALUES ("${charTrigger.triggerName}", ${charTrigger.characterGuid}, ${charTrigger.isSet})`+
+ `ON DUPLICATE KEY UPDATE isSet=${charTrigger.isSet}`;
+ CharDBExecute(sql);
+}
+
+/**
+ * Will return the value of the trigger if it exists, otherwise it will return false
+ * @param charGuid number
+ * @param triggerName string
+ * @returns boolean
+ */
+export function GetTrigger(charGuid: number, triggerName: string) {
+ let sql = `SELECT isSet from player_trigger WHERE triggerName="${triggerName}" and characterGuid=${charGuid}`;
+ const result = CharDBQuery(sql);
+
+ if(result && result.GetRowCount() > 0) {
+ return result.GetBool(0)
+ } else {
+ return false;
+ }
+
+}
diff --git a/modules/classes/ui-utils.ts b/modules/classes/ui-utils.ts
new file mode 100644
index 0000000..503d73c
--- /dev/null
+++ b/modules/classes/ui-utils.ts
@@ -0,0 +1,18 @@
+export function colors(name: string) {
+ const colors = {
+ GREY: "|cff999999",
+ RED: "|cffff0000",
+ WHITE: "|cffFFFFFF",
+ GREEN: "|cff1eff00",
+ PURPLE: "|cff9F3FFF",
+ BLUE: "|cff0070dd",
+ ORANGE: "|cffFF8400",
+ };
+
+ const keyName = name.toUpperCase();
+ if(colors[keyName]) {
+ return colors[keyName];
+ } else {
+ return colors.WHITE;
+ }
+}
\ No newline at end of file
diff --git a/modules/gameplay/achievement-tokens.readme.md b/modules/gameplay/achievement-tokens.readme.md
new file mode 100644
index 0000000..5027b24
--- /dev/null
+++ b/modules/gameplay/achievement-tokens.readme.md
@@ -0,0 +1,10 @@
+## Achievement-Tokens
+
+**Requires acore_world.item_template sql**
+```bash
+sql/gameplay/db_world/achievement-tokens.sql
+```
+
+You can set your own item token name by modifying the achievements-token.sql
+
+This is used to grant additional currency that can be used for stores or other in-game special options, when an achievement is awarded.
\ No newline at end of file
diff --git a/modules/gameplay/achievement-tokens.ts b/modules/gameplay/achievement-tokens.ts
new file mode 100644
index 0000000..f29f83f
--- /dev/null
+++ b/modules/gameplay/achievement-tokens.ts
@@ -0,0 +1,61 @@
+/**
+ * REQUIRES DB acore_world.item_template to be updated for custom tokens
+ */
+
+/**
+ * CONFIG OPTIONS
+ * @returns
+ */
+
+// Reward 1 token per every 5 achievement points earned.
+const AWARD_RATE = 5;
+
+// Token Id of the currency you want to aware the players.
+const TOKEN_ID = 910001;
+
+// Character GUID of the character that will be sending the tokens vai mail
+const REWARD_CHAR_GUID = 2506;
+
+/**
+ * On Achivement complete the system will reward the player with tokens based on the AWARD_RATE
+ * set above
+ * Default is 5 Achievement Points = 1 Token
+ *
+ * IE)
+ * 10 Achievement Points = 2 Tokens
+ * 50 Achievement Points = 10 Tokens
+ *
+ * @param event : number
+ * @param player : Player
+ * @param achievement : Achievement
+ * @returns boolean
+ */
+const achievementComplete: player_event_on_achievement_complete = (event, player, achievement) => {
+
+ const id = achievement.GetId();
+ const query = WorldDBQuery(`SELECT Points from achievements where ID=${id}`);
+ const points = query.GetUInt32(0);
+
+ if(points != undefined) {
+ const tokens = Math.ceil(points / AWARD_RATE);
+ SendMail(
+ `Your achievement token reward!`,
+ `You earned it now spend it!`,
+ player.GetGUIDLow(),
+ REWARD_CHAR_GUID,
+ MailStationery.MAIL_STATIONERY_DEFAULT,
+ 0,
+ 0,
+ 0,
+ TOKEN_ID,
+ tokens
+ );
+ }
+
+ return true;
+};
+
+RegisterPlayerEvent(
+ PlayerEvents.PLAYER_EVENT_ON_ACHIEVEMENT_COMPLETE,
+ (...args) => achievementComplete(...args)
+);
\ No newline at end of file
diff --git a/modules/gameplay/worgoblin.readme.md b/modules/gameplay/worgoblin.readme.md
new file mode 100644
index 0000000..010351b
--- /dev/null
+++ b/modules/gameplay/worgoblin.readme.md
@@ -0,0 +1,5 @@
+## Worgoblin Instructions
+
+Requires custom installation of client patches, sql, and server patches in order to function.
+The module itself will not fo anything if installed without it, but will not cause any errors either.
+
diff --git a/modules/gameplay/worgoblin.ts b/modules/gameplay/worgoblin.ts
new file mode 100644
index 0000000..98bd05b
--- /dev/null
+++ b/modules/gameplay/worgoblin.ts
@@ -0,0 +1,32 @@
+import { ToCopper } from "../classes/money";
+
+/**
+ * This will change the starting zone for Worgren and Goblins
+ * and provides additional racials for Worgren because they are missing some.
+ *
+ * REQUIRES WORGOBLIN MOD INSTALLATION AND PATCHES TO BE APPLIED
+ * SEE README FOR INSTALLATION INSTRUCTIONS
+ */
+
+RegisterPlayerEvent(PlayerEvents.PLAYER_EVENT_ON_FIRST_LOGIN, (event, player) => {
+
+ // Worgren get additional racials and start at level 20 in Duskwood
+ if(player.GetRace() == 12 ) {
+ // Since we do not have all Worgren spells will give them another racial fitting of their class.
+ player.LearnSpell(20577); // Cannibalize
+
+ // learn spell blood fury
+ player.LearnSpell(33697);
+
+ player.SetLevel(20);
+ player.Teleport(0, -10728.057617, -1131.120850, 27.594067, 1.180833);
+ player.ModifyMoney(ToCopper(100));
+ }
+
+ // If we are a goblin then start off at level 20 in Ratchet
+ if(player.GetRace() == 9) {
+ player.SetLevel(20);
+ player.ModifyMoney(ToCopper(100));
+ player.Teleport(1, -1049.596, -3645.963, 23.878, 4.468);
+ }
+});
\ No newline at end of file
diff --git a/package-lock.json b/package-lock.json
new file mode 100644
index 0000000..7f6fb20
--- /dev/null
+++ b/package-lock.json
@@ -0,0 +1,658 @@
+{
+ "name": "wow.ets.modules",
+ "version": "1.0.0",
+ "lockfileVersion": 3,
+ "requires": true,
+ "packages": {
+ "": {
+ "name": "wow.ets.modules",
+ "version": "1.0.0",
+ "license": "MIT",
+ "dependencies": {
+ "wow-eluna-ts-module": "^1.6.6"
+ }
+ },
+ "node_modules/@araxiaonline/wow-wotlk-declarations": {
+ "version": "3.3.5-3",
+ "resolved": "https://registry.npmjs.org/@araxiaonline/wow-wotlk-declarations/-/wow-wotlk-declarations-3.3.5-3.tgz",
+ "integrity": "sha512-iZ85TJWDgWwqMf7dWB/x42bwTorqGdHqxBhkySyUbp/zhe5oq/AKok9RG5+FTsRNFhuWiWR0z2Aoi9yK2QjARQ=="
+ },
+ "node_modules/@cspotcode/source-map-support": {
+ "version": "0.8.1",
+ "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz",
+ "integrity": "sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==",
+ "dependencies": {
+ "@jridgewell/trace-mapping": "0.3.9"
+ },
+ "engines": {
+ "node": ">=12"
+ }
+ },
+ "node_modules/@jridgewell/resolve-uri": {
+ "version": "3.1.1",
+ "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz",
+ "integrity": "sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==",
+ "engines": {
+ "node": ">=6.0.0"
+ }
+ },
+ "node_modules/@jridgewell/sourcemap-codec": {
+ "version": "1.4.15",
+ "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz",
+ "integrity": "sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg=="
+ },
+ "node_modules/@jridgewell/trace-mapping": {
+ "version": "0.3.9",
+ "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz",
+ "integrity": "sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==",
+ "dependencies": {
+ "@jridgewell/resolve-uri": "^3.0.3",
+ "@jridgewell/sourcemap-codec": "^1.4.10"
+ }
+ },
+ "node_modules/@tsconfig/node10": {
+ "version": "1.0.9",
+ "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.9.tgz",
+ "integrity": "sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA=="
+ },
+ "node_modules/@tsconfig/node12": {
+ "version": "1.0.11",
+ "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.11.tgz",
+ "integrity": "sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag=="
+ },
+ "node_modules/@tsconfig/node14": {
+ "version": "1.0.3",
+ "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.3.tgz",
+ "integrity": "sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow=="
+ },
+ "node_modules/@tsconfig/node16": {
+ "version": "1.0.4",
+ "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.4.tgz",
+ "integrity": "sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA=="
+ },
+ "node_modules/@types/node": {
+ "version": "20.10.5",
+ "resolved": "https://registry.npmjs.org/@types/node/-/node-20.10.5.tgz",
+ "integrity": "sha512-nNPsNE65wjMxEKI93yOP+NPGGBJz/PoN3kZsVLee0XMiJolxSekEVD8wRwBUBqkwc7UWop0edW50yrCQW4CyRw==",
+ "peer": true,
+ "dependencies": {
+ "undici-types": "~5.26.4"
+ }
+ },
+ "node_modules/@typescript-to-lua/language-extensions": {
+ "version": "1.19.0",
+ "resolved": "https://registry.npmjs.org/@typescript-to-lua/language-extensions/-/language-extensions-1.19.0.tgz",
+ "integrity": "sha512-Os5wOKwviTD4LeqI29N0btYOjokSJ97iCf45EOjIABlb5IwNQy7AE/AqZJobRw3ywHH8+KzJUMkEirWPzh2tUA=="
+ },
+ "node_modules/acorn": {
+ "version": "8.11.2",
+ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.2.tgz",
+ "integrity": "sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==",
+ "bin": {
+ "acorn": "bin/acorn"
+ },
+ "engines": {
+ "node": ">=0.4.0"
+ }
+ },
+ "node_modules/acorn-walk": {
+ "version": "8.3.1",
+ "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.1.tgz",
+ "integrity": "sha512-TgUZgYvqZprrl7YldZNoa9OciCAyZR+Ejm9eXzKCmjsF5IKp/wgQ7Z/ZpjpGTIUPwrHQIcYeI8qDh4PsEwxMbw==",
+ "engines": {
+ "node": ">=0.4.0"
+ }
+ },
+ "node_modules/arg": {
+ "version": "4.1.3",
+ "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz",
+ "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA=="
+ },
+ "node_modules/asn1": {
+ "version": "0.2.6",
+ "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.6.tgz",
+ "integrity": "sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==",
+ "dependencies": {
+ "safer-buffer": "~2.1.0"
+ }
+ },
+ "node_modules/bcrypt-pbkdf": {
+ "version": "1.0.2",
+ "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz",
+ "integrity": "sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w==",
+ "dependencies": {
+ "tweetnacl": "^0.14.3"
+ }
+ },
+ "node_modules/buildcheck": {
+ "version": "0.0.6",
+ "resolved": "https://registry.npmjs.org/buildcheck/-/buildcheck-0.0.6.tgz",
+ "integrity": "sha512-8f9ZJCUXyT1M35Jx7MkBgmBMo3oHTTBIPLiY9xyL0pl3T5RwcPEY8cUHr5LBNfu/fk6c2T4DJZuVM/8ZZT2D2A==",
+ "optional": true,
+ "engines": {
+ "node": ">=10.0.0"
+ }
+ },
+ "node_modules/commander": {
+ "version": "7.2.0",
+ "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz",
+ "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==",
+ "engines": {
+ "node": ">= 10"
+ }
+ },
+ "node_modules/cpu-features": {
+ "version": "0.0.9",
+ "resolved": "https://registry.npmjs.org/cpu-features/-/cpu-features-0.0.9.tgz",
+ "integrity": "sha512-AKjgn2rP2yJyfbepsmLfiYcmtNn/2eUvocUyM/09yB0YDiz39HteK/5/T4Onf0pmdYDMgkBoGvRLvEguzyL7wQ==",
+ "hasInstallScript": true,
+ "optional": true,
+ "dependencies": {
+ "buildcheck": "~0.0.6",
+ "nan": "^2.17.0"
+ },
+ "engines": {
+ "node": ">=10.0.0"
+ }
+ },
+ "node_modules/create-require": {
+ "version": "1.1.1",
+ "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz",
+ "integrity": "sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ=="
+ },
+ "node_modules/cross-spawn": {
+ "version": "7.0.3",
+ "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz",
+ "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==",
+ "dependencies": {
+ "path-key": "^3.1.0",
+ "shebang-command": "^2.0.0",
+ "which": "^2.0.1"
+ },
+ "engines": {
+ "node": ">= 8"
+ }
+ },
+ "node_modules/diff": {
+ "version": "4.0.2",
+ "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz",
+ "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==",
+ "engines": {
+ "node": ">=0.3.1"
+ }
+ },
+ "node_modules/dotenv": {
+ "version": "9.0.2",
+ "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-9.0.2.tgz",
+ "integrity": "sha512-I9OvvrHp4pIARv4+x9iuewrWycX6CcZtoAu1XrzPxc5UygMJXJZYmBsynku8IkrJwgypE5DGNjDPmPRhDCptUg==",
+ "engines": {
+ "node": ">=10"
+ }
+ },
+ "node_modules/duplexer": {
+ "version": "0.1.2",
+ "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz",
+ "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg=="
+ },
+ "node_modules/enhanced-resolve": {
+ "version": "5.15.0",
+ "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.15.0.tgz",
+ "integrity": "sha512-LXYT42KJ7lpIKECr2mAXIaMldcNCh/7E0KBKOu4KSfkHmP+mZmSs+8V5gBAqisWBy0OO4W5Oyys0GO1Y8KtdKg==",
+ "dependencies": {
+ "graceful-fs": "^4.2.4",
+ "tapable": "^2.2.0"
+ },
+ "engines": {
+ "node": ">=10.13.0"
+ }
+ },
+ "node_modules/event-stream": {
+ "version": "3.3.4",
+ "resolved": "https://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz",
+ "integrity": "sha512-QHpkERcGsR0T7Qm3HNJSyXKEEj8AHNxkY3PK8TS2KJvQ7NiSHe3DDpwVKKtoYprL/AreyzFBeIkBIWChAqn60g==",
+ "dependencies": {
+ "duplexer": "~0.1.1",
+ "from": "~0",
+ "map-stream": "~0.1.0",
+ "pause-stream": "0.0.11",
+ "split": "0.3",
+ "stream-combiner": "~0.0.4",
+ "through": "~2.3.1"
+ }
+ },
+ "node_modules/from": {
+ "version": "0.1.7",
+ "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz",
+ "integrity": "sha512-twe20eF1OxVxp/ML/kq2p1uc6KvFK/+vs8WjEbeKmV2He22MKm7YF2ANIt+EOqhJ5L3K/SuuPhk0hWQDjOM23g=="
+ },
+ "node_modules/fs-extra": {
+ "version": "11.2.0",
+ "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.2.0.tgz",
+ "integrity": "sha512-PmDi3uwK5nFuXh7XDTlVnS17xJS7vW36is2+w3xcv8SVxiB4NyATf4ctkVY5bkSjX0Y4nbvZCq1/EjtEyr9ktw==",
+ "dependencies": {
+ "graceful-fs": "^4.2.0",
+ "jsonfile": "^6.0.1",
+ "universalify": "^2.0.0"
+ },
+ "engines": {
+ "node": ">=14.14"
+ }
+ },
+ "node_modules/function-bind": {
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz",
+ "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==",
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
+ },
+ "node_modules/graceful-fs": {
+ "version": "4.2.11",
+ "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz",
+ "integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ=="
+ },
+ "node_modules/hasown": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.0.tgz",
+ "integrity": "sha512-vUptKVTpIJhcczKBbgnS+RtcuYMB8+oNzPK2/Hp3hanz8JmpATdmmgLgSaadVREkDm+e2giHwY3ZRkyjSIDDFA==",
+ "dependencies": {
+ "function-bind": "^1.1.2"
+ },
+ "engines": {
+ "node": ">= 0.4"
+ }
+ },
+ "node_modules/is-core-module": {
+ "version": "2.13.1",
+ "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.13.1.tgz",
+ "integrity": "sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw==",
+ "dependencies": {
+ "hasown": "^2.0.0"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
+ },
+ "node_modules/isexe": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz",
+ "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="
+ },
+ "node_modules/jsonfile": {
+ "version": "6.1.0",
+ "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz",
+ "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==",
+ "dependencies": {
+ "universalify": "^2.0.0"
+ },
+ "optionalDependencies": {
+ "graceful-fs": "^4.1.6"
+ }
+ },
+ "node_modules/lodash": {
+ "version": "4.17.21",
+ "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz",
+ "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="
+ },
+ "node_modules/lua-types": {
+ "version": "2.13.1",
+ "resolved": "https://registry.npmjs.org/lua-types/-/lua-types-2.13.1.tgz",
+ "integrity": "sha512-rRwtvX6kS+5MpuO3xpvKsnYjdSDDI064Qq1OqX8gY+r+0l7m3dFLiZPDFoHqH22jaBpEvcHcPs6+WD7qkdmFsA=="
+ },
+ "node_modules/make-error": {
+ "version": "1.3.6",
+ "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz",
+ "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw=="
+ },
+ "node_modules/map-stream": {
+ "version": "0.1.0",
+ "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz",
+ "integrity": "sha512-CkYQrPYZfWnu/DAmVCpTSX/xHpKZ80eKh2lAkyA6AJTef6bW+6JpbQZN5rofum7da+SyN1bi5ctTm+lTfcCW3g=="
+ },
+ "node_modules/nan": {
+ "version": "2.18.0",
+ "resolved": "https://registry.npmjs.org/nan/-/nan-2.18.0.tgz",
+ "integrity": "sha512-W7tfG7vMOGtD30sHoZSSc/JVYiyDPEyQVso/Zz+/uQd0B0L46gtC+pHha5FFMRpil6fm/AoEcRWyOVi4+E/f8w==",
+ "optional": true
+ },
+ "node_modules/node-cleanup": {
+ "version": "2.1.2",
+ "resolved": "https://registry.npmjs.org/node-cleanup/-/node-cleanup-2.1.2.tgz",
+ "integrity": "sha512-qN8v/s2PAJwGUtr1/hYTpNKlD6Y9rc4p8KSmJXyGdYGZsDGKXrGThikLFP9OCHFeLeEpQzPwiAtdIvBLqm//Hw=="
+ },
+ "node_modules/node-scp": {
+ "version": "0.0.23",
+ "resolved": "https://registry.npmjs.org/node-scp/-/node-scp-0.0.23.tgz",
+ "integrity": "sha512-He+Jxt1WwuAZBfdPxoq+wQSrXMSHobB4+oo1LUDhKGqzbub7D/Q6JpDja3SzFvaxIhhnhgituP91BU97viCMjA==",
+ "dependencies": {
+ "ssh2": "^1.14.0"
+ }
+ },
+ "node_modules/path-key": {
+ "version": "3.1.1",
+ "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz",
+ "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==",
+ "engines": {
+ "node": ">=8"
+ }
+ },
+ "node_modules/path-parse": {
+ "version": "1.0.7",
+ "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz",
+ "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw=="
+ },
+ "node_modules/pause-stream": {
+ "version": "0.0.11",
+ "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz",
+ "integrity": "sha512-e3FBlXLmN/D1S+zHzanP4E/4Z60oFAa3O051qt1pxa7DEJWKAyil6upYVXCWadEnuoqa4Pkc9oUx9zsxYeRv8A==",
+ "dependencies": {
+ "through": "~2.3"
+ }
+ },
+ "node_modules/picomatch": {
+ "version": "2.3.1",
+ "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz",
+ "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==",
+ "engines": {
+ "node": ">=8.6"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/jonschlinkert"
+ }
+ },
+ "node_modules/ps-tree": {
+ "version": "1.2.0",
+ "resolved": "https://registry.npmjs.org/ps-tree/-/ps-tree-1.2.0.tgz",
+ "integrity": "sha512-0VnamPPYHl4uaU/nSFeZZpR21QAWRz+sRv4iW9+v/GS/J5U5iZB5BNN6J0RMoOvdx2gWM2+ZFMIm58q24e4UYA==",
+ "dependencies": {
+ "event-stream": "=3.3.4"
+ },
+ "bin": {
+ "ps-tree": "bin/ps-tree.js"
+ },
+ "engines": {
+ "node": ">= 0.10"
+ }
+ },
+ "node_modules/resolve": {
+ "version": "1.22.8",
+ "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz",
+ "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==",
+ "dependencies": {
+ "is-core-module": "^2.13.0",
+ "path-parse": "^1.0.7",
+ "supports-preserve-symlinks-flag": "^1.0.0"
+ },
+ "bin": {
+ "resolve": "bin/resolve"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
+ },
+ "node_modules/safer-buffer": {
+ "version": "2.1.2",
+ "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
+ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="
+ },
+ "node_modules/shebang-command": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
+ "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==",
+ "dependencies": {
+ "shebang-regex": "^3.0.0"
+ },
+ "engines": {
+ "node": ">=8"
+ }
+ },
+ "node_modules/shebang-regex": {
+ "version": "3.0.0",
+ "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz",
+ "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==",
+ "engines": {
+ "node": ">=8"
+ }
+ },
+ "node_modules/source-map": {
+ "version": "0.7.4",
+ "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.4.tgz",
+ "integrity": "sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA==",
+ "engines": {
+ "node": ">= 8"
+ }
+ },
+ "node_modules/split": {
+ "version": "0.3.3",
+ "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz",
+ "integrity": "sha512-wD2AeVmxXRBoX44wAycgjVpMhvbwdI2aZjCkvfNcH1YqHQvJVa1duWc73OyVGJUc05fhFaTZeQ/PYsrmyH0JVA==",
+ "dependencies": {
+ "through": "2"
+ },
+ "engines": {
+ "node": "*"
+ }
+ },
+ "node_modules/ssh2": {
+ "version": "1.15.0",
+ "resolved": "https://registry.npmjs.org/ssh2/-/ssh2-1.15.0.tgz",
+ "integrity": "sha512-C0PHgX4h6lBxYx7hcXwu3QWdh4tg6tZZsTfXcdvc5caW/EMxaB4H9dWsl7qk+F7LAW762hp8VbXOX7x4xUYvEw==",
+ "hasInstallScript": true,
+ "dependencies": {
+ "asn1": "^0.2.6",
+ "bcrypt-pbkdf": "^1.0.2"
+ },
+ "engines": {
+ "node": ">=10.16.0"
+ },
+ "optionalDependencies": {
+ "cpu-features": "~0.0.9",
+ "nan": "^2.18.0"
+ }
+ },
+ "node_modules/stream-combiner": {
+ "version": "0.0.4",
+ "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz",
+ "integrity": "sha512-rT00SPnTVyRsaSz5zgSPma/aHSOic5U1prhYdRy5HS2kTZviFpmDgzilbtsJsxiroqACmayynDN/9VzIbX5DOw==",
+ "dependencies": {
+ "duplexer": "~0.1.1"
+ }
+ },
+ "node_modules/string-argv": {
+ "version": "0.3.2",
+ "resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz",
+ "integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==",
+ "engines": {
+ "node": ">=0.6.19"
+ }
+ },
+ "node_modules/supports-preserve-symlinks-flag": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz",
+ "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==",
+ "engines": {
+ "node": ">= 0.4"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
+ },
+ "node_modules/tapable": {
+ "version": "2.2.1",
+ "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz",
+ "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==",
+ "engines": {
+ "node": ">=6"
+ }
+ },
+ "node_modules/through": {
+ "version": "2.3.8",
+ "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz",
+ "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg=="
+ },
+ "node_modules/ts-node": {
+ "version": "10.9.2",
+ "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz",
+ "integrity": "sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==",
+ "dependencies": {
+ "@cspotcode/source-map-support": "^0.8.0",
+ "@tsconfig/node10": "^1.0.7",
+ "@tsconfig/node12": "^1.0.7",
+ "@tsconfig/node14": "^1.0.0",
+ "@tsconfig/node16": "^1.0.2",
+ "acorn": "^8.4.1",
+ "acorn-walk": "^8.1.1",
+ "arg": "^4.1.0",
+ "create-require": "^1.1.0",
+ "diff": "^4.0.1",
+ "make-error": "^1.1.1",
+ "v8-compile-cache-lib": "^3.0.1",
+ "yn": "3.1.1"
+ },
+ "bin": {
+ "ts-node": "dist/bin.js",
+ "ts-node-cwd": "dist/bin-cwd.js",
+ "ts-node-esm": "dist/bin-esm.js",
+ "ts-node-script": "dist/bin-script.js",
+ "ts-node-transpile-only": "dist/bin-transpile.js",
+ "ts-script": "dist/bin-script-deprecated.js"
+ },
+ "peerDependencies": {
+ "@swc/core": ">=1.2.50",
+ "@swc/wasm": ">=1.2.50",
+ "@types/node": "*",
+ "typescript": ">=2.7"
+ },
+ "peerDependenciesMeta": {
+ "@swc/core": {
+ "optional": true
+ },
+ "@swc/wasm": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/tsc-watch": {
+ "version": "6.0.4",
+ "resolved": "https://registry.npmjs.org/tsc-watch/-/tsc-watch-6.0.4.tgz",
+ "integrity": "sha512-cHvbvhjO86w2aGlaHgSCeQRl+Aqw6X6XN4sQMPZKF88GoP30O+oTuh5lRIJr5pgFWrRpF1AgXnJJ2DoFEIPHyg==",
+ "dependencies": {
+ "cross-spawn": "^7.0.3",
+ "node-cleanup": "^2.1.2",
+ "ps-tree": "^1.2.0",
+ "string-argv": "^0.3.1"
+ },
+ "bin": {
+ "tsc-watch": "dist/lib/tsc-watch.js"
+ },
+ "engines": {
+ "node": ">=12.12.0"
+ },
+ "peerDependencies": {
+ "typescript": "*"
+ }
+ },
+ "node_modules/tweetnacl": {
+ "version": "0.14.5",
+ "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz",
+ "integrity": "sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA=="
+ },
+ "node_modules/typescript": {
+ "version": "5.2.2",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.2.2.tgz",
+ "integrity": "sha512-mI4WrpHsbCIcwT9cF4FZvr80QUeKvsUsUvKDoR+X/7XHQH98xYD8YHZg7ANtz2GtZt/CBq2QJ0thkGJMHfqc1w==",
+ "peer": true,
+ "bin": {
+ "tsc": "bin/tsc",
+ "tsserver": "bin/tsserver"
+ },
+ "engines": {
+ "node": ">=14.17"
+ }
+ },
+ "node_modules/typescript-to-lua": {
+ "version": "1.22.0",
+ "resolved": "https://registry.npmjs.org/typescript-to-lua/-/typescript-to-lua-1.22.0.tgz",
+ "integrity": "sha512-6rMbWj/NsNQ/phNFVtMZj5LdHucUPdrmKP4VFsynM7SGtm2zR2RMLnZcJM3unrDb1VCAR6FnL7GJoKp77yM5qw==",
+ "dependencies": {
+ "@typescript-to-lua/language-extensions": "1.19.0",
+ "enhanced-resolve": "^5.8.2",
+ "picomatch": "^2.3.1",
+ "resolve": "^1.15.1",
+ "source-map": "^0.7.3"
+ },
+ "bin": {
+ "tstl": "dist/tstl.js"
+ },
+ "engines": {
+ "node": ">=16.10.0"
+ },
+ "peerDependencies": {
+ "typescript": "5.2.2"
+ }
+ },
+ "node_modules/undici-types": {
+ "version": "5.26.5",
+ "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz",
+ "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==",
+ "peer": true
+ },
+ "node_modules/universalify": {
+ "version": "2.0.1",
+ "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.1.tgz",
+ "integrity": "sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==",
+ "engines": {
+ "node": ">= 10.0.0"
+ }
+ },
+ "node_modules/v8-compile-cache-lib": {
+ "version": "3.0.1",
+ "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz",
+ "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg=="
+ },
+ "node_modules/which": {
+ "version": "2.0.2",
+ "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz",
+ "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==",
+ "dependencies": {
+ "isexe": "^2.0.0"
+ },
+ "bin": {
+ "node-which": "bin/node-which"
+ },
+ "engines": {
+ "node": ">= 8"
+ }
+ },
+ "node_modules/wow-eluna-ts-module": {
+ "version": "1.6.7",
+ "resolved": "https://registry.npmjs.org/wow-eluna-ts-module/-/wow-eluna-ts-module-1.6.7.tgz",
+ "integrity": "sha512-CK59WXHRKB54xb6FR5zS+TUTM4Tv5QMWG05CPRCWdY4QX9XtxXPek3uXlOlpx1WvbwNl3VUSOeb5PqTg7h4QxA==",
+ "dependencies": {
+ "@araxiaonline/wow-wotlk-declarations": "^3.3.5-3",
+ "@typescript-to-lua/language-extensions": "^1.19.0",
+ "commander": "^7.2.0",
+ "dotenv": "^9.0.2",
+ "fs-extra": "^11.1.1",
+ "lodash": "^4.17.21",
+ "lua-types": "^2.10.1",
+ "node-scp": "^0.0.23",
+ "ts-node": "^10.9.1",
+ "tsc-watch": "^6.0.4",
+ "typescript-to-lua": "^1.19.0"
+ },
+ "bin": {
+ "eluna-reload": ".bin/send-reload-eluna.sh",
+ "ets": ".bin/ets.js"
+ }
+ },
+ "node_modules/yn": {
+ "version": "3.1.1",
+ "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz",
+ "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==",
+ "engines": {
+ "node": ">=6"
+ }
+ }
+ }
+}
diff --git a/package.json b/package.json
new file mode 100644
index 0000000..d30080e
--- /dev/null
+++ b/package.json
@@ -0,0 +1,33 @@
+{
+ "name": "wow.ets.modules",
+ "version": "1.0.0",
+ "description": "WoW ETS Module list for use with wow-eluna-ts-module and Azerothcore eluna ",
+ "main": "index.js",
+ "scripts": {
+ "test": "echo \"Error: no test specified\" && exit 1"
+ },
+ "repository": {
+ "type": "git",
+ "url": "git+https://github.com/araxiaonline/wow.ets.modules.git"
+ },
+ "keywords": [
+ "wow-eluna-ts-module",
+ "azerothcore",
+ "eluna",
+ "typescript",
+ "world",
+ "of",
+ "warcraft",
+ "wow",
+ "addons"
+ ],
+ "author": "ben-of-codecraft",
+ "license": "MIT",
+ "bugs": {
+ "url": "https://github.com/araxiaonline/wow.ets.modules/issues"
+ },
+ "homepage": "https://github.com/araxiaonline/wow.ets.modules#readme",
+ "dependencies": {
+ "wow-eluna-ts-module": "^1.6.6"
+ }
+}
diff --git a/plugins/aio-plugin.ts b/plugins/aio-plugin.ts
new file mode 100644
index 0000000..949da47
--- /dev/null
+++ b/plugins/aio-plugin.ts
@@ -0,0 +1,29 @@
+import * as ts from "typescript";
+import * as tstl from "typescript-to-lua";
+
+/**
+ * This plugin will add AIO to the transpile process from TS assuming
+ * there is a Global installation of AIO installed in the directory, which is
+ * that follows Rochet2's instructions.
+ */
+const plugin: tstl.Plugin = {
+ beforeEmit(
+ program: ts.Program,
+ options: tstl.CompilerOptions,
+ emitHost: tstl.EmitHost,
+ result: tstl.EmitFile[],
+ ) {
+
+ for (const file of result) {
+
+ if(file.code.includes("aio = {}")) {
+ console.log(`installing AIO for this file ${file.outputPath}`);
+ file.code = file.code.replace("-- @ts-expect-error", "");
+ file.code = file.code.replace("aio = {}", "local AIO = AIO or require(\"AIO\")");
+ file.code = file.code.replace(/aio\./g, "AIO.");
+ }
+ }
+ }
+};
+
+export default plugin;
\ No newline at end of file
diff --git a/sql/modules/classes/db_character/stats.sql b/sql/modules/classes/db_character/stats.sql
new file mode 100644
index 0000000..a9fd53c
--- /dev/null
+++ b/sql/modules/classes/db_character/stats.sql
@@ -0,0 +1,10 @@
+-- file: modules/classes/stats.ts
+DROP TABLE IF EXISTS `player_stats`;
+CREATE TABLE `player_stats` (
+ `id` int NOT NULL,
+ `name` varchar(150) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NOT NULL,
+ `value` int DEFAULT '0',
+ `updated` int DEFAULT NULL,
+ PRIMARY KEY (`id`,`name`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
+
diff --git a/sql/modules/classes/db_character/triggers.sql b/sql/modules/classes/db_character/triggers.sql
new file mode 100644
index 0000000..ad90282
--- /dev/null
+++ b/sql/modules/classes/db_character/triggers.sql
@@ -0,0 +1,11 @@
+-- file: modules/classes/triggers.ts
+DROP TABLE IF EXISTS `player_trigger`;
+CREATE TABLE `player_trigger` (
+ `triggerId` int unsigned NOT NULL AUTO_INCREMENT,
+ `triggerName` varchar(128) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
+ `characterGuid` int unsigned NOT NULL,
+ `isSet` tinyint(1) DEFAULT '0',
+ PRIMARY KEY (`triggerId`),
+ UNIQUE KEY `triggerName` (`triggerName`,`characterGuid`),
+ KEY `characterGuid` (`characterGuid`)
+) ENGINE=InnoDB AUTO_INCREMENT=54 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci
\ No newline at end of file
diff --git a/sql/modules/gameplay/db_world/achievement-tokens.sql b/sql/modules/gameplay/db_world/achievement-tokens.sql
new file mode 100644
index 0000000..3ff158f
--- /dev/null
+++ b/sql/modules/gameplay/db_world/achievement-tokens.sql
@@ -0,0 +1,4 @@
+-- file: modules/gameplay/db_world/achievement-tokens.ts
+DELETE FROM `item_template` WHERE (`entry` = 910001);
+INSERT INTO `item_template` (`entry`, `class`, `subclass`, `SoundOverrideSubclass`, `name`, `displayid`, `Quality`, `Flags`, `FlagsExtra`, `BuyCount`, `BuyPrice`, `SellPrice`, `InventoryType`, `AllowableClass`, `AllowableRace`, `ItemLevel`, `RequiredLevel`, `RequiredSkill`, `RequiredSkillRank`, `requiredspell`, `requiredhonorrank`, `RequiredCityRank`, `RequiredReputationFaction`, `RequiredReputationRank`, `maxcount`, `stackable`, `ContainerSlots`, `StatsCount`, `stat_type1`, `stat_value1`, `stat_type2`, `stat_value2`, `stat_type3`, `stat_value3`, `stat_type4`, `stat_value4`, `stat_type5`, `stat_value5`, `stat_type6`, `stat_value6`, `stat_type7`, `stat_value7`, `stat_type8`, `stat_value8`, `stat_type9`, `stat_value9`, `stat_type10`, `stat_value10`, `ScalingStatDistribution`, `ScalingStatValue`, `dmg_min1`, `dmg_max1`, `dmg_type1`, `dmg_min2`, `dmg_max2`, `dmg_type2`, `armor`, `holy_res`, `fire_res`, `nature_res`, `frost_res`, `shadow_res`, `arcane_res`, `delay`, `ammo_type`, `RangedModRange`, `spellid_1`, `spelltrigger_1`, `spellcharges_1`, `spellppmRate_1`, `spellcooldown_1`, `spellcategory_1`, `spellcategorycooldown_1`, `spellid_2`, `spelltrigger_2`, `spellcharges_2`, `spellppmRate_2`, `spellcooldown_2`, `spellcategory_2`, `spellcategorycooldown_2`, `spellid_3`, `spelltrigger_3`, `spellcharges_3`, `spellppmRate_3`, `spellcooldown_3`, `spellcategory_3`, `spellcategorycooldown_3`, `spellid_4`, `spelltrigger_4`, `spellcharges_4`, `spellppmRate_4`, `spellcooldown_4`, `spellcategory_4`, `spellcategorycooldown_4`, `spellid_5`, `spelltrigger_5`, `spellcharges_5`, `spellppmRate_5`, `spellcooldown_5`, `spellcategory_5`, `spellcategorycooldown_5`, `bonding`, `description`, `PageText`, `LanguageID`, `PageMaterial`, `startquest`, `lockid`, `Material`, `sheath`, `RandomProperty`, `RandomSuffix`, `block`, `itemset`, `MaxDurability`, `area`, `Map`, `BagFamily`, `TotemCategory`, `socketColor_1`, `socketContent_1`, `socketColor_2`, `socketContent_2`, `socketColor_3`, `socketContent_3`, `socketBonus`, `GemProperties`, `RequiredDisenchantSkill`, `ArmorDamageModifier`, `duration`, `ItemLimitCategory`, `HolidayId`, `ScriptName`, `DisenchantID`, `FoodType`, `minMoneyLoot`, `maxMoneyLoot`, `flagsCustom`, `VerifiedBuild`) VALUES
+(910001, 15, 4, -1, 'Araxia Token', 32278, 2, 134217728, 0, 1, 0, 0, 0, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 500, 500, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1000, 0, 0, 0, 0, 0, 0, -1, 0, -1, 0, 0, 0, 0, -1, 0, -1, 0, 0, 0, 0, -1, 0, -1, 0, 0, 0, 0, -1, 0, -1, 0, 0, 0, 0, -1, 0, -1, 1, 'Use to buy the rarest goods in the realm', 0, 0, 0, 0, 0, -1, 0, 0, 0, 0, 0, 0, 0, 0, 8192, 0, 0, 0, 0, 0, 0, 0, 0, 0, -1, 0, 0, 0, 0, '', 0, 0, 0, 0, 0, 0);
diff --git a/tsconfig.json b/tsconfig.json
new file mode 100644
index 0000000..ec9b655
--- /dev/null
+++ b/tsconfig.json
@@ -0,0 +1,43 @@
+{
+ "$schema": "./tstl.schema.json",
+ "compilerOptions": {
+ "strict": false,
+ "target": "esnext",
+ "outDir": "./dist",
+ "skipLibCheck": true,
+ "lib": [
+ "esnext",
+ "DOM"
+ ],
+ "moduleResolution": "node",
+ "types": [
+ "lua-types/5.2",
+ "@typescript-to-lua/language-extensions",
+ "wow-eluna-ts-module",
+ "@araxiaonline/wow-wotlk-declarations"
+ ],
+ "rootDir": "modules"
+ },
+ "include": [
+ "modules/**/*.ts"
+ ],
+ "exclude": [
+ "node_modules",
+ "**/node_modules",
+ "test",
+ "**/*spec.ts",
+ "**/__tests__",
+ "**/__mocks__"
+ ],
+ "tstl": {
+ "luaTarget": "5.2",
+ "noHeader": true,
+ "luaLibImport": "require",
+ "luaBundleEntry": "./modules/index.ts",
+ "luaPlugins": [
+ {
+ "name": "./plugins/aio-plugin.ts"
+ }
+ ]
+ }
+}
\ No newline at end of file
diff --git a/tstl.schema.json b/tstl.schema.json
new file mode 100644
index 0000000..25dd934
--- /dev/null
+++ b/tstl.schema.json
@@ -0,0 +1,111 @@
+{
+ "title": "tsconfig.json with TSTL",
+ "description": "JSON schema for the TypeScript compiler's configuration file with TSTL",
+ "$schema": "http://json-schema.org/draft-07/schema",
+ "allOf": [
+ {
+ "$ref": "https://json.schemastore.org/tsconfig"
+ }
+ ],
+ "properties": {
+ "tstl": {
+ "description": "TypeScriptToLua compiler options.",
+ "type": "object",
+ "definitions": {
+ "//": {
+ "reference": "https://typescripttolua.github.io/docs/configuration#custom-options"
+ }
+ },
+ "properties": {
+ "buildMode": {
+ "description": "Use buildMode: \"library\" to build publishable library packages.",
+ "type": "string",
+ "default": "library",
+ "enum": ["default", "library"]
+ },
+ "extension": {
+ "description": "File extension for the resulting Lua files. Defaults to \".lua\"",
+ "type": "string"
+ },
+ "lua51AllowTryCatchInAsyncAwait": {
+ "description": "Disable the warning that try/catch is not allowed in async functions in Lua 5.1, in case you are using a patched 5.1 lua version that supports this.",
+ "type": "boolean",
+ "default": false
+ },
+ "luaBundle": {
+ "description": "The name of the lua file to bundle output lua to. Requires luaBundleEntry.",
+ "type": "string",
+ "default": ""
+ },
+ "luaBundleEntry": {
+ "description": "The entry *.ts file that will be executed when entering the luaBundle. Requires luaBundle.",
+ "type": "string"
+ },
+ "luaLibImport": {
+ "description": "Specifies how js standard features missing in lua are imported.",
+ "type": "string",
+ "default": "require",
+ "enum": ["none", "inline", "require", "require-minimal"]
+ },
+ "luaTarget": {
+ "description": "Specifies the Lua version you want to generate code for.",
+ "type": "string",
+ "default": "universal",
+ "enum": ["5.0", "universal", "5.1", "5.2", "5.3", "5.4", "JIT"]
+ },
+ "noImplicitGlobalVariables": {
+ "description": "Always declare all root-level variables as local, even if the file is not a module and they would be global in TypeScript.",
+ "type": "boolean",
+ "default": false
+ },
+ "noImplicitSelf": {
+ "description": "If true, treats all project files as if they were prefixed with\n/** @noSelfInFile **/.",
+ "type": "boolean",
+ "default": false
+ },
+ "noHeader": {
+ "description": "Specify if a header will be added to compiled files.",
+ "type": "boolean",
+ "default": false
+ },
+ "noResolvePaths": {
+ "description": "An array of import paths that should not be resolved but copied verbatim to output lua.",
+ "type": "array"
+ },
+ "sourceMapTraceback": {
+ "description": "Applies the source map to show source TS files and lines in error tracebacks.",
+ "default": false,
+ "type": "boolean"
+ },
+ "tstlVerbose": {
+ "description": "Give verbose tstl output, helpful when diagnosing tstl issues.",
+ "type": "boolean",
+ "default": false
+ },
+ "luaPlugins": {
+ "description": "List of TypeScriptToLua plugins.",
+ "type": "array",
+ "items": {
+ "description": "Describes TypeScriptToLua plugin",
+ "type": "object",
+ "required": ["name"],
+ "properties": {
+ "name": {
+ "description": "Path to the JS file, that contains the plugin code",
+ "type": "string"
+ },
+ "import": {
+ "type": "string"
+ }
+ }
+ }
+ },
+ "measurePerformance": {
+ "description": "Measure and report performance of the tstl compiler.",
+ "type": "boolean"
+ }
+ }
+ }
+ },
+ "allowTrailingCommas": true
+}
\ No newline at end of file