This is the source code for the maddie480.ovh website, an app running on Java 21 using Eclipse Jetty.
The src
folder contains the source for everything provided by the Java servlet:
- the Everest Update Checker frontend service, exposing files produced by the Update Checker
- the Celeste custom entity catalog, and its API version
- the everest.yaml validator
- an online version of Olympus News
- the Everest Update Checker status page
- the Celeste font generator
- the Celeste Mod Structure Verifier
- the #celeste_news_network subscription service - the Mastodon/Twitter update checking code is not part of the frontend and can be found on the Random Backend Stuff repository
- the help page for the Mod Structure Verifier bot
- the "Show Arbitrary Mods on Profile" GameBanana app
- the Discord Games Bot - the "bot" is actually a webhook that gets called by Discord
- the Discord Custom Slash Commands app
- the Discord Timezone Bot - this repository only includes the "without timezone roles" variant; the one with timezone roles needs a bot user to work, and as such is part of the backend
- Some GameBanana-related APIs extending the official API, described below
- the BananaBot app for Discord - allows searching for Celeste mods on GameBanana, using the same search as Olympus and the Banana Mirror Browser
- the Everest and Olympus versions list APIs
- ... and some other things of more limited use that are on the website.
The front-vue
folder contains the source for more dynamic frontend parts made in Vue.js:
- the Banana Mirror Browser, a website that can substitute to the GameBanana Celeste section if it is down. Files and images are hosted on 0x0ade's server. Mod info and files on this server are kept up-to-date by the Everest update checker.
- the Celeste Map Tree Viewer, a tool allowing you to see the raw contents of your map .bin as a tree, in order to find out what it is or search for a specific entity, trigger, decal or styleground.
- the Celeste Wipe Converter, a service to turn custom Celeste screen wipes into a format the game can use (with the Maddie's Helping Hand mod).
- the Celeste File Searcher, a tool to find in which Celeste mod(s) a file is on GameBanana, based on its path in the zip.
If you want to check how the update checker's everest_update.yaml file is generated, check the Everest Update Checker Server repo instead.
This API uses the mod search database generated by the Everest Update Checker server to find mods based on keywords. This searches Celeste mods only.
It is used by Olympus, the Everest installer and mod manager, to search Celeste mods on GameBanana.
To use this API, call https://maddie480.ovh/celeste/gamebanana-search?q=[search]
. The answer is in JSON format, and is a list of the top 20 matches. For example:
$ curl "https://maddie480.ovh/celeste/gamebanana-search?q=spring+collab+2020&full=true"
[
{
"CategoryId": 4632,
"Screenshots": [
"https://images.gamebanana.com/img/ss/mods/5fcaf5f6990f6.jpg",
"https://images.gamebanana.com/img/ss/mods/5fcaf5ffe2893.jpg"
],
"Description": "Made by KawaiiDawn",
"Views": 3456,
"GameBananaType": "Mod",
"GameBananaId": 53717,
"Text": "NOTE: THIS RANDOMIZER WILL SOON BE OBSOLETED BY ANOTHER COLLAB RANDOMIZER THAT IS FARTHER IN PROGRESS THAN THIS ONE, BE SURE TO DISABLE THIS MOD WHEN THAT MOD COMES OUT (You can still enjoy this until that comes out, think of this as a preview ;D)<br>Bigkahuna is making the updated one btw<br><br>This mod adds in randomizer options for maps from the 2020 Celeste Community Spring Collab. Currently, only beginner maps are available, but I am still actively working to add in every map. If you have any questions feel free to post here or message me on discord: ?KawaiiDawn?#2795<br>FINISHED:<br>Beginner Maps<br>PLANNED:<br>Intermediate Maps, Advanced Maps, Expert Maps, Grandmaster Maps<br>KNOWN ISSUES:<br>Crystal Enigma causes the game to crash at the randomizer menu, so that map is currently absent from the list of available maps.<br>Screens from certain maps may appear much less often, I don't know why this happens.<br>The game randomizes the custom tileset slots, but I plan to keep this as I think randomized tilesets is a neat feature.<br>Some rooms may be impossible. I went through every room, but there still may be issues in some. Contact me if you find an impossible room.",
"Name": "2020 Spring Collab Randomizer (v0.1)",
"PageURL": "https://gamebanana.com/mods/53717",
"MirroredScreenshots": [
"https://celestemodupdater.0x0a.de/banana-mirror-images/img_ss_mods_5fcaf5f6990f6.png",
"https://celestemodupdater.0x0a.de/banana-mirror-images/img_ss_mods_5fcaf5ffe2893.png"
],
"CreatedDate": 1607137213,
"Author": "KawaiiDawn",
"CategoryName": "Other/Misc",
"Downloads": 209,
"Likes": 1,
"Files": [
{
"Description": "",
"HasEverestYaml": true,
"Size": 8859,
"CreatedDate": 1607136797,
"Downloads": 209,
"URL": "https://gamebanana.com/dl/499384",
"Name": "sc2020rando.zip"
}
]
},
[...]
]
This API allows to get a sorted list of most downloaded, liked or viewed Celeste mods on GameBanana.
If you want to retrieve the latest mod with no type filter, it is recommended to use the real GameBanana API instead, for more up-to-date information.
The URL is https://maddie480.ovh/celeste/gamebanana-list?sort=[sort]&type=[type]&category=[category]&subcategory=[subcategory]&page=[page]
where:
sort
is the info to sort on (mandatory). It can belatest
,likes
,views
ordownloads
type
(oritemtype
) is the GameBanana type to filter on (optional and case-insensitive). For exampleMap
,Gamefile
orTool
category
is the GameBanana mod category ID to filter on (optional), this is returned by the GameBanana categories list API. For example6800
subcategory
is the GameBanana mod subcategory ID to filter on (optional), this is returned by the GameBanana subcategories list API. For example6801
page
is the page to get, first page being 1 (optional, default is 1). Each page contains 20 elements.
The output format is the same as the GameBanana search API, see the previous section. You also get the total amount of mods in the list, as a X-Total-Count
header.
Hit the following URL: https://maddie480.ovh/celeste/gamebanana-featured
to get a list of all mods that are shown in the front page of Celeste.
The output is JSON, in the same as the GameBanana search API (see the corresponding section).
Each mod has a Featured
key if it is featured. The Category
is one of the following:
today
: Best of todayweek
: Best of this weekmonth
: Best of this month3month
: Best of 3 months6month
: Best of 6 monthsyear
: Best of this yearalltime
: Best of all time
This API sorts the mods in the same order as they are on the website: by Category
(following the order above) then by Position
.
This API provides info on a mod, based on its itemtype
and itemid
, in the same as the GameBanana search API (see the corresponding section).
The URL is https://maddie480.ovh/celeste/gamebanana-info?itemtype=[itemtype]&itemid=[itemid]
:
$ curl "https://maddie480.ovh/celeste/gamebanana-info?itemtype=Mod&itemid=150813"
{
"CategoryId":6800,
"Screenshots":[
"https://images.gamebanana.com/img/ss/mods/5f590aced2b97.jpg",
"https://images.gamebanana.com/img/ss/mods/5f46e9ee53c9b.jpg"
],
"Description":"A collaboration involving 100+ people to commemorate Celeste",
"Views":511063,
"GameBananaType":"Mod",
"TokenizedName":[
"the",
"2020",
"celeste",
"spring",
"community",
"collab"
],
"UpdatedDate":1668375864,
"GameBananaId":150813,
"Featured":{
"Position":0,
"Category":"alltime"
},
"Text":"<span class=\"GreenColor\"><b>The 2020 Celeste Spring Collab is a project that has been in the making for over 8 months with 100+ people involved. <\/b>After waiting patiently for so long, we're proud to present you the final product!<br><\/span> [...]",
"ModifiedDate":1668375829,
"Name":"The 2020 Celeste Spring Community Collab",
"PageURL":"https://gamebanana.com/mods/150813",
"MirroredScreenshots":[
"https://celestemodupdater.0x0a.de/banana-mirror-images/img_ss_mods_5f590aced2b97.png",
"https://celestemodupdater.0x0a.de/banana-mirror-images/img_ss_mods_5f46e9ee53c9b.png"
],
"CreatedDate":1599670994,
"Author":"Spring Collab 2020 Team",
"CategoryName":"Maps",
"Downloads":100049,
"Likes":154,
"Files":[
{
"Description":"v1.7.5",
"HasEverestYaml":true,
"Size":56290503,
"CreatedDate":1668375774,
"Downloads":12687,
"URL":"https://gamebanana.com/dl/890982",
"Name":"springcollab2020_bdf5e.zip"
},
{
"Description":"Audio v1.0.0",
"HasEverestYaml":true,
"Size":513411848,
"CreatedDate":1599575103,
"Downloads":26737,
"URL":"https://gamebanana.com/dl/484937",
"Name":"springcollab2020audio_135a4.zip"
},
{
"Description":"Outdated - Old Grandmaster HS",
"HasEverestYaml":true,
"Size":159602,
"CreatedDate":1616693898,
"Downloads":918,
"URL":"https://gamebanana.com/dl/539975",
"Name":"springcollab2020oldgmhs_ee692.zip"
}
]
}
This API allows getting a list of GameBanana item types that have at least one Celeste mod in it (contrary to the official GameBanana v2 API for this), along with how many mods there are for each category.
The counts returned by this API might not match the numbers displayed on the GameBanana website; that's because GameBanana counts mods that do not show up in the list.
Each entry can have an itemtype
and a categoryid
, that can be used as type
and category
parameters on the list API.
The URL is https://maddie480.ovh/celeste/gamebanana-categories
and the result looks like:
- formatted: All
count: 1406
- itemtype: Mod
categoryid: 15655
formatted: Assets
count: 26
- itemtype: Mod
categoryid: 4633
formatted: Dialog
count: 20
- itemtype: Mod
categoryid: 1501
formatted: Effects
count: 5
- itemtype: Tool
formatted: Tools
count: 30
...
This API allows getting a list of GameBanana categories for a given item type (Mod
, Tool
or Wip
), or a list of subcategories for a given category (6800
is Maps for example).
When only passing an item type, the returned id
can be used as a category
filter for the list API. When passing a category id, the id
can be used as a subcategory
filter.
Note that the count for "All" might not match the sum of count for all subcategories. That's because mods can belong to the root category directly, without being in any subcategory.
The URL is https://maddie480.ovh/celeste/gamebanana-subcategories
. For example, the result for https://maddie480.ovh/celeste/gamebanana-subcategories?itemtype=Mod&categoryId=6800
looks like:
- name: All
count: 2368
- id: 6802
name: Campaign
count: 320
- id: 6803
name: Collab/Contest
count: 166
- id: 15667
name: Multiplayer
count: 18
- id: 6801
name: Standalone
count: 1398
And the result for https://maddie480.ovh/celeste/gamebanana-subcategories?itemtype=Tool
looks like:
- name: All
count: 56
- id: 653
name: Ahorn Plugin
count: 6
- id: 1098
name: Lönn Plugin
count: 13
- id: 1654
name: Mod Installer
count: 4
- id: 575
name: Other/Misc
count: 32
- id: 859
name: Twitch Integration
count: 1
Note that this API works for all GameBanana categories, not only Celeste ones.
This API uses the "get mods for a category" API from GameBanana, then turns the result in an RSS format.
Usage is very similar to the "vanilla" GameBanana API, since it calls it directly behind the scenes: for example, getting the latest Celeste helpers (https://gamebanana.com/mods/cats/5081 ➡️ ID is 5081) is done with
https://gamebanana.com/apiv8/Mod/ByCategory?_csvProperties=@gbprofile&_aCategoryRowIds[]=5081&_sOrderBy=_tsDateAdded,DESC&_nPerpage=10
You can get them in the RSS format by just replacing the URL and carrying over all query params except _csvProperties
:
https://maddie480.ovh/gamebanana/rss-feed?_aCategoryRowIds[]=5081&_sOrderBy=_tsDateAdded,DESC&_nPerpage=10
You can copy this URL replacing 5081
with the category of your choice to get a feed for the latest mods in this category.
To include mod updates (and not only new mods), replace _tsDateAdded
with _tsDateUpdated
.
If the GameBanana API returns an error (for example if you pass an invalid parameter), this API will return it as is.
Click here to get redirected to a random Celeste map.
This API is available at https://maddie480.ovh/celeste/everest-versions
, and returns all the Everest versions available, in JSON format. For example:
[
{
"branch": "dev",
"version": 4677,
"date": "2024-03-10T01:13:55.5595113Z",
"description": "Remove debug print from splash font loader",
"author": "Kalobi",
"commit": "d14853ab51c8104dcf374548bf88d4a393a0f421",
"isNative": true,
"mainDownload": "https://dev.azure.com/EverestAPI/Everest/_apis/build/builds/3977/artifacts?artifactName=main&api-version=5.0&%24format=zip",
"mainFileSize": 78248455,
"olympusBuildDownload": "https://dev.azure.com/EverestAPI/Everest/_apis/build/builds/3977/artifacts?artifactName=olympus-build&api-version=5.0&%24format=zip",
"olympusBuildFileSize": 77912947,
"olympusMetaDownload": "https://dev.azure.com/EverestAPI/Everest/_apis/build/builds/3977/artifacts?artifactName=olympus-meta&api-version=5.0&%24format=zip",
"olympusMetaFileSize": 269
},
[...]
]
version
is the Everest version number.branch
is eitherdev
,beta
orstable
. Other branches might be created to test specific features in the future.date
is the date at which the version was published, in ISO 8601 format.commit
is the hash of the commit that was used to build this version.isNative
indicates whether this is a .NET Core build. Non-native builds are called "legacy" in Olympus.mainDownload
is the download for use by Everest to install an update.olympusMetaDownload
is the download that Olympus uses to get the build size.olympusBuildDownload
is the download for use by Olympus to install Everest.mainFileSize
,olympusBuildFileSize
andolympusMetaFileSize
are the sizes of the respective files in bytes.
Two extra fields are specified for automatic builds made after a single change on the dev
branch (commit or pull request merge):
author
is the author of the change (GitHub username), either the author of the commit or the creator of the pull request.description
is the description of the change, either the message of the commit or the title of the pull request.
If the version of Everest/Olympus you are calling this API from supports installing native builds (.NET Core builds), you should pass the supportsNativeBuilds=true
query parameter to include them.
This API is available at https://maddie480.ovh/celeste/olympus-versions
, and returns all the Olympus versions available, in JSON format. For example:
[
{
"date": "2023-09-14T22:04:54.9319239Z",
"windowsDownload": "https://dev.azure.com/EverestAPI/Olympus/_apis/build/builds/3518/artifacts?artifactName=windows.main&api-version=5.0&%24format=zip",
"macosDownload": "https://dev.azure.com/EverestAPI/Olympus/_apis/build/builds/3518/artifacts?artifactName=macos.main&api-version=5.0&%24format=zip",
"linuxDownload": "https://dev.azure.com/EverestAPI/Olympus/_apis/build/builds/3518/artifacts?artifactName=linux.main&api-version=5.0&%24format=zip"
"changelog": "Make sure Lonn is run with the same Love2d install as Olympus itself on Linux",
"branch": "main",
"version": "23.09.14.03"
},
[...]
]
version
is the Olympus version number.branch
is eitherwindows-init
,main
orstable
.windows-init
is the version initially installed by the Windows installer, andmain
is the development branch.windowsDownload
,macDownload
andlinuxDownload
are download links for each platform.date
is the date at which the version was published, in ISO 8601 format.changelog
is the changelog of the version, pulled straight from thechangelog.txt
file on the repository. (That's where in-app update changelogs come from.)
This API is available at https://maddie480.ovh/celeste/loenn-versions
. It is a mirror of the GitHub API giving information on the latest Lönn release, refreshed once an hour.
The original API is available here. Check the GitHub docs for more info about the format of the response.
This API is available at https://maddie480.ovh/celeste/helper-list
. It gives a list of everest.yaml Name
s for helper mods, in JSON format.
It is automatically generated based on the "Helpers" category on GameBanana, with some exceptions manually added.
This API is available at https://maddie480.ovh/celeste/mod_ids_to_names.json
. It gives a dictionary that allows to find the titles of the GameBanana
pages from everest.yaml Name
s, in JSON format:
{
"CSRC Frog": "CSRC Complete",
"viewpoint-dreampoint-point": "Minute Viewpoint",
"WitheredPassage": "Withered Passage - Red Booster Contest Submission",
"IAccidentallyFourCassetteBlocks": "I Accidentally Four Cassette Blocks",
"resverie story contest": "Madeline's Floriography",
"Aftermath Ch3":"Aftermath Ch3: Internal Void",
[...]
}