Getting started
Requirements
- Node.js
- pnpm
- A text editor
- We suggest Visual Studio Code, but you can use whatever you’d like.
- Git
- If Git is new to you, you may want to use a GUI client like GitHub Desktop.
Suggested knowledge
- JavaScript/TypeScript
- If you’re not comfortable with TypeScript, you can use JavaScript. It is strongly recommended to use TypeScript.
- React (if you plan to modify the UI)
- You should be comfortable with the component model and how props work. Some old UI uses class components, but most use function components.
- If you plan to write your own components, you should know how to manage React state and JSX.
- Reading and writing regexes (if you plan to write patches)
- We suggest regex101 as a good resource for learning regex.
You don’t need to be an expert (or have worked) in the above subjects, but it makes creating extensions much easier. We believe in learning by doing, so don’t be afraid to ask for help in our Discord server or reference other extensions.
Reading how other extensions work can be a huge resource, so we encourage you to reference the moonlight core extensions and the extensions on the official repository if you’re stuck. Just remember to respect the licensing of the extension!
Setting up the sample extension
A sample extension is provided to start development quickly:
- Pre-configured build system (esbuild)
- TypeScript support
- Example usage of Node.js code
- Example patch & Webpack modules
It is configured like a monorepo, so multiple extensions can live in the same Git repository. This is not required.
You can view it here.
Set up the repository
On GitHub, click “Use this template” on the sample extension repository to create a new repository.
In the repository settings, make sure GitHub Actions is enabled for this repository, and that the GitHub Pages source is set to GitHub Actions:
- GitHub Actions: “Code and automation” > “Actions” > “General” > “Actions permissions”
- GitHub Pages: “Code and automation” > “Pages” > “Build and deployment” > “Source”
Clone the repository with your favorite Git client.
Clean up the sample extension
First, remove the files that aren’t needed:
- Delete
README.md
, and optionally replace it with your own. - Modify
LICENSE
if you would like to use a different license. moonlight is licensed under the GNU Lesser General Public License (LGPL-3.0-or-later
).
Next, decide what you’ll rename everything to:
- Pick a name for your extension. This will be displayed to the user in Moonbase. We suggest a short but informational one.
- Avoid using gimmick names where possible
except if you can’t resist it. - Treat it as a proper noun (“Native Fixes” instead of “Native fixes”).
- Avoid using gimmick names where possible
- Pick an ID for your extension. We suggest using the name of your extension in
camelCase
:- Context Menu ->
contextMenu
- Moonbase ->
moonbase
- No Hide Token ->
noHideToken
- Context Menu ->
Now, change the branding of the extension:
- Change the name in
package.json
.- If your repository will just have one extension in it, set it to the extension ID.
- If your repository will hold multiple extensions, we suggest picking a generic name like
moonlight-extensions
.
- Rename the
sampleExtension
folder insrc
to your extension ID. - Change the
meta
field inmanifest.json
:- Change
name
to your user-facing extension name. - Change
tagline
to a short explanation of your extension. - Change or delete
description
to a longer explanation of your extension. If you have any important notes about the extension’s functionality, add them here. - Change
authors
to contain your username. - Change
source
to the URL of your Git repository.
- Change
- Replace all uses of
sampleExtension
with your extension ID in the following files:manifest.json
index.tsx
webpackModules/entrypoint.ts
env.d.ts
(located at the root folder)
Build and run the extension
- Install dependencies:
pnpm i
- Build the extensions:
pnpm run build
- Build in watch mode, so your extension is built when you make changes:
pnpm run dev
- This command will need to be restarted if you edit the extension manifest, add/remove an entrypoint, or add/remove a Webpack module.
- If you delete an extension, entrypoint, or Webpack module, you should run
pnpm run clean
to clean up the remaining build output.
Use the “Extension search paths” setting in Moonbase (or set devSearchPaths
in your moonlight config) to add the dist
folder next to your code. If you don’t have a dist
folder, you need to build the extension first.
After restarting your client, the extension will load.
What’s next?
Congrats on making it this far! There’s a lot more to learn about how moonlight works:
- Read about Webpack modules, and learn how to write your own patches & make your own Webpack modules.
- Read the cookbook for common patterns you may want to use.
- Set up DevTools to make reverse engineering Discord easier.
- Read common pitfalls so you know to avoid them.
- When your extension is ready, submit to the official repository or distribute the extension on a custom repository.
If you need any help, don’t be afraid to ask in our Discord server.
Publishing to GitHub Pages
Your repository will be published to https://<username>.github.io/<repository>/repo.json
. Every time a commit is made to the main branch, the extensions will be built on GitHub Actions and published automatically.
It is suggested to only use this if you do not plan to submit to the official repository. You can also delete the .github/workflows/deploy.yml
file if you do not want this (or if you aren’t using GitHub).