How Integrations Work#
Garbage Job reaches every other resource through a small bridge — a framework file, an inventory file, one file per vehicle-keys resource — and those files ship unencrypted, so you can read and adapt them. Some layers are picked by looking at what is running; the rest are one line in config/config.lua.
Layer | Supported | Without it |
|---|---|---|
Framework |
| Required. Without one the job NPC is never spawned. |
Target |
| A keypress next to the foreman, the container and the truck. |
Vehicle keys | Nine resources, detected — listed below. | The truck is handed over without a key. |
Inventory |
| There is always one: the framework's. |
Fuel | Any resource with a | The truck keeps whatever fuel it spawns with. |
Clothing |
| Set |
Notifications | The job's own, or any resource through | — |
3D prompts |
| Plain text drawn by the game. |
Parties |
| Crews are invited from the job panel. |
Housing |
| No Housing Tour. |
Job payouts |
| Route pay goes straight into the player's cash. |
Quests |
| No quest is handed out. |
Logs | Discord webhooks | Nothing is logged. Off by default. |
Database |
| Required. |
Detection only sees resources that are already started. A detected resource that starts after Garbage Job is not found — keep every
ensureit should find aboveensure qs-garbagejobinserver.cfg.
Frameworks#
The framework is detected at the top of config/config.lua:
local frameworks = {
['es_extended'] = 'esx',
['qb-core'] = 'qb',
['qbx_core'] = 'qb',
}Qbox runs through its QBCore compatibility, which is why it shares the QBCore bridge. Route pay and leaderboard prizes go to the cash account — money on ESX, cash on QBCore. Names on the leaderboard come from the users table's first and last name on ESX, and from players.charinfo on QBCore and Qbox.
Every call the job makes to the framework — identifiers, the job, money, items, spawning and deleting the truck — lives in client/framework/ and server/framework/. A renamed or forked core is adapted there, without touching anything else.
Target#
Config.Target = true
Config.TargetScript = "ox" -- "ox" for ox_target, "qb" for qb-targetOn | Option |
|---|---|
The foreman | Start working — opens the job panel. |
The current container | Pick up garbage |
The truck, while carrying a bag | Deposit garbage |
A dirty container | Clean Dumpster |
The options are written in client/target.lua, which is editable — icons, distances and zone sizes are there, and the labels are the TARGET_ keys in the translation file. Handing the truck back at the depot stays a keypress either way.
Vehicle Keys#
The keys resource is detected on its own — the first one found running is used, and none when there is no match. The player who takes the route out receives the truck's keys, and they are taken back when the truck is removed on the resources that support it.
Resource | Keys removed with the truck |
|---|---|
| Yes |
| Yes |
| No — the keys belong to a plate that disappears with the truck. |
| No |
| No |
Each one is a small file in client/vehiclekeys/ with two functions. For a keys resource that is not listed, put its calls in client/vehiclekeys/none.lua — the file that runs when nothing is detected:
-- client/vehiclekeys/none.lua
if Config.Vehiclekeys ~= 'none' then
return
end
function AddVehiclekeys(vehicle, plate, item)
exports['my_keys']:GiveKeys(plate)
end
function RemoveVehiclekeys(vehicle, plate)
exports['my_keys']:RemoveKeys(plate)
endInventory and Loot#
Loot goes to the inventory that is actually running — ox_inventory first, then qs-inventory, and the framework's own when neither is. There is nothing to set; the items in Config.DropItems only have to exist in it — see Installation.
On qs-inventory, also set Config.QuasarInventory = true: the inventory is locked while the work outfit goes on and comes off.
qs-inventory quests#
With qs-inventory running, every collector is handed a Garbage Progress quest when they load in — Complete 4 routes, rewarding 300 — and every experience grant, from a route or a cleaned container, adds 25 to its progress. Its title, description and reward are in server/missions.lua.
Fuel#
Config.Fuel = true
Config.FuelExport = exports['LegacyFuel']When the truck spawns, the job calls SetFuel(vehicle, 100.0) on that export, so any fuel resource with a SetFuel export works — point Config.FuelExport at it, for example exports['cdn-fuel'] or exports['ps-fuel'].
Notifications and Prompts#
Notifications#
With Config.DefaultNotifications = true the job shows its own notifications, styled like the panel. Set it to false and every notification is handed to SendTextMessage in config/config.lua, where you call your own resource:
Config.DefaultNotifications = false
function SendTextMessage(msg, type) -- type: 'info' · 'error' · 'success'
lib.notify({ description = msg, type = type })
endPrompts#
With Config.DrawText3D = true, the [E] prompts are drawn in the world — through qs-textui automatically when it is running, as plain game text when it is not. With false they become a key hint on screen, always drawn by the job's own interface.
Clothing#
Framework | Outfit put on with | Own clothes restored with |
|---|---|---|
ESX |
|
|
QBCore · Qbox |
|
|
If your clothing resource does not answer those events, adapt the calls in client/clothing.lua — a commented line for illenium-appearance's reload is already there — or set Config.Clothing = false and let the crew work in their own clothes.
qs-party#
With qs-party running, a crew can come from your party system. Opening the panel as part of a party loads that party as the crew, as long as every member can work and none is already on a route; a party bigger than Config.MaxPartyMembers is refused. The party's leader is the crew's leader — the one who starts the route and hands the truck back.
Without qs-party, crews are built from the panel with invitations, as described in Usage.
qs-housing#
When qs-housing is running, the job asks it for its dump spots on start, shuffles them and builds the Housing Tour from Config.HousingTask.spotsCount of them, then sends it to every player — and to every player who joins later. The console confirms it:
[qs-garbagejob] housing route built with 10 stops.No line means qs-housing returned no spots, and the tour stays out of the panel.
qs-job-management#
With qs-job-management running, a finished route's money is paid through it, under the garbage_collector job, instead of straight into the player's cash. Leaderboard prizes are still paid in cash.
Discord Logs#
Off by default. Paste a webhook into Url, set Enabled = true and choose the events:
Event | Sent when |
|---|---|
| A crew leader takes a route out, with the crew's names. |
| A route is paid, with the crew size, the pay and the experience. |
| A crew member leaves, is removed or disconnects — with their role and the crew size. |
| Money is handed to a player for a route. |
| Experience is granted, with the level before and after. |
Config.Webhooks = {
Enabled = true,
Url = 'https://discord.com/api/webhooks/...',
Name = 'qs-garbagejob', -- how the bot presents itself
Avatar = '', -- an image URL, or '' for none
Timestamp = true,
Events = {
MissionStarted = true,
MissionFinished = true,
MissionAbandoned = true,
MoneyPaid = 'https://discord.com/api/webhooks/...', -- a staff channel of its own
ExperienceGiven = false, -- never sent
},
}Each event takes true (the shared Url), false (off) or a URL of its own. Every embed is coloured by event and carries the player's name, server ID and identifier in its footer.
Languages#
Nine complete translations ship in config/translations.lua: English (en), Spanish (es), French (fr), German (de), Portuguese (pt), Italian (it), Russian (ru), Turkish (tr) and Chinese (cn). Set Config.Language at the top of that file.
To add another, copy the ['en'] block under a new code, translate the text between the quotes, and set Config.Language to that code. A key you leave out is shown as the key itself, so copy the whole block. The interface — panel, leaderboard, guide and minigame — reads the same file.



