# In-game delivery

Learn how purchases reach the character, with the player online or offline, what each framework delivers, and how to resend a delivery that failed.

Source: https://fivedash.fivex.gg/docs/en/store/in-game-delivery

When a player pays in the store, the FiveDash resource on the server delivers the purchase in the city: the VIP, the car in the garage, the money in the bank, the item in the backpack. If the player is offline, the purchase waits for them to join. This page explains the whole path, what each framework does, and what to do when something doesn't arrive. It's for whoever runs the server and the store.

## Before you start

* **Plan:** automatic delivery comes with the Store on every plan (Plus, Pro and Ultra).
* **Resource:** the `fivedash` resource installed and connected to the dashboard, with its key in `config.lua`. See [Install the resource](https://fivedash.fivex.gg/docs/en/getting-started/install-resource).
* **Database:** the server needs a MySQL driver started: `oxmysql`, `mysql-async` or `ghmattimysql`. The store keeps its deliveries in the city's database.
* **Delivery on:** `Enabled = true` in `fivedash/loja.lua`.
* **Permission:**

| Action                                                | Page                  | Level         |
| ----------------------------------------------------- | --------------------- | ------------- |
| See orders and each delivery's state                  | **Store → Orders**    | **View**      |
| Initial setup (choose how the buyer says who gets it) | **Store → Overview**  | **Configure** |
| Mark as delivered and resend to the city              | **Store → Orders**    | **Manage**    |
| Gift a product                                        | **Store → Customers** | **Manage**    |

## How it works

### The order is paid

Once the payment is confirmed, FiveDash turns each of the product's deliveries into an exact action (group, vehicle, money, item or command) and sends it to the city's server. Changing the product later doesn't change what that order delivers.

### The server stores it before answering

The resource writes each delivery to the `fivedash_store_deliveries` table in the city's database before confirming. A restart, a crash or a player who only joins next week loses nothing.

### Delivered now or waiting for the player

Whatever works with the player offline (it depends on the framework, see below) is delivered right away. Whatever needs the character in the city, like items and wallet money, waits for them to join.

### The dashboard follows along

The resource tells the dashboard each delivery's state on every sync. The order in **Store → Orders** moves to **Delivered** when everything arrives, or **Failed** when something goes wrong.

### The player is told

With `Notify = true`, the player sees "Your purchase #N has arrived" on screen, with what they got.

> A delivery is never given twice. Each one has a fixed identifier, and before delivering, the server "claims" it in the database: if two attempts race, only one delivers.

## Who gets the purchase

In the store setup, on the **In-game delivery** step, you answer **How does the buyer say who gets it?**:

| Option                | How it works                                                                                                                                            |
| --------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------- |
| By the framework's ID | The player types their ID at checkout, and the city checks whose it is before payment. The field's name comes from the framework (see the table below). |
| **Discord account**   | The player signs in with Discord, and the purchase goes to the character of the city account linked to it.                                              |

What each framework calls the ID:

| Framework                  | ID the player uses                           |
| -------------------------- | -------------------------------------------- |
| ESX                        | ID (the `id` in the `users` table)           |
| QBCore                     | Citizen ID                                   |
| Qbox                       | Citizen ID                                   |
| ox_core                    | State ID                                     |
| vRP / vRPex                | ID (the `id` in `vrp_users`)                 |
| Creative Network Enchanted | Passport ("Passaporte" in Portuguese cities) |

Before payment, the checkout asks the city whether the ID exists and shows the character's name. An ID that doesn't exist, or a Discord account with no character, is refused. If the server doesn't answer in time (offline, restarting), the sale isn't blocked: the city checks when the order arrives.

## When the store stops selling

The store only sells while the server says delivery is ready. If it isn't, the website stops selling and **Store → Overview** shows **Sales paused: delivery in the city is off**.

| Situation                       | What the dashboard says                                                                                                        | How to fix it                                                                                                          |
| ------------------------------- | ------------------------------------------------------------------------------------------------------------------------------ | ---------------------------------------------------------------------------------------------------------------------- |
| The resource never connected    | Install the FiveDash resource on the server: it's what delivers purchases in the city.                                         | [Install the resource](https://fivedash.fivex.gg/docs/en/getting-started/install-resource) and use **Connect server**. |
| Old resource, without the store | The FiveDash resource on the server is from before the store. Restart the server so it updates.                                | Restart the server or type `restart fivedash`.                                                                         |
| Delivery turned off             | Delivery is turned off in the server's loja.lua (Enabled = false). The store doesn't sell until it's on.                       | Change to `Enabled = true` and run `restart fivedash`.                                                                 |
| No MySQL driver                 | The server has no MySQL driver started (oxmysql, mysql-async or ghmattimysql): the store keeps its deliveries in the database. | Start one of those resources before `fivedash`.                                                                        |

> A server that is offline doesn't pause the store. Purchases wait in the queue and arrive when it's back.

## Player online and offline

| Delivery type           | ESX           | QBCore        | Qbox          | ox_core       | vRP / vRPex   | Creative      |
| ----------------------- | ------------- | ------------- | ------------- | ------------- | ------------- | ------------- |
| **VIP or role**         | Right away    | Right away    | Right away    | Right away    | Waits to join | Right away    |
| **Vehicle**             | Right away    | Right away    | Right away    | Right away    | Right away    | Right away    |
| **Money** in the bank   | Right away    | Right away    | Right away    | Right away    | Right away    | Right away    |
| **Money** in the wallet | Waits to join | Waits to join | Right away    | Waits to join | Waits to join | Waits to join |
| **Item**                | Waits to join | Waits to join | Waits to join | Waits to join | Waits to join | Waits to join |
| **Command**             | Right away    | Right away    | Right away    | Right away    | Right away    | Right away    |

"Right away" works with the player online or offline. "Waits to join" stays queued with the reason "Waiting for the player to join the city".

### Retries and the queue

| Situation                                      | What the server does                                                                                                                                                                                  |
| ---------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| The player picks their character               | Waits `SpawnDelay` seconds (default 10) and delivers what was waiting.                                                                                                                                |
| Backpack full                                  | The delivery stays queued with the reason "Inventory full: arrives once the player frees up space" and is tried again every minute while they're in the city.                                         |
| The player is already in the city              | Every minute the server retries the deliveries of players who are online.                                                                                                                             |
| Several deliveries for the same character      | They run one after another, in the product's order. Up to 4 characters receive at the same time.                                                                                                      |
| The server stopped in the middle of a delivery | On the next boot the delivery becomes **Failed** with the reason "The server stopped in the middle of this delivery: check in game whether it arrived before resending". It's never redone by itself. |
| A paid order that never reached the server     | The dashboard sends it again on each sync, for up to 7 days after payment.                                                                                                                            |
| Order refunded or marked as delivered          | Whatever was still waiting in the city is dropped. What was already delivered stays.                                                                                                                  |

### Quantity

If the player buys more than one unit, VIP days and money and item amounts add up (VIP up to 3,650 days), and a command runs once per unit (up to 100 times per delivery).

## Timed VIPs

A **VIP or role** with a **Duration** in days is removed by itself when it runs out. The server keeps the expiry dates in the `fivedash_store_groups` table.

| Situation                       | What happens                                                                                                                                                                         |
| ------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| Bought again before it runs out | The days add on top of what's left.                                                                                                                                                  |
| Bought as **Permanent**         | Stays forever, even if it had an expiry before.                                                                                                                                      |
| Group the team gave by hand     | FiveDash never times it or takes it away.                                                                                                                                            |
| Ran out                         | The server checks every minute, removes the group and, if the player is in the city, tells them: "Your `vip_gold` has ended. Renew it in the city's store." (with the group's name). |

### ACE groups

On ESX, QBCore and Qbox, a group name that isn't one of the framework's jobs or gangs becomes an ACE group on the player's Rockstar license: `group.<name>` on ESX and Qbox, `qbcore.<name>` on QBCore. FiveDash keeps these groups in the `fivedash_ace_groups` table and adds them again on every boot. Give the group its permissions in `server.cfg`:

```bash
add_ace group.vip vip allow
```

Scripts check them with `IsPlayerAceAllowed`.

## Commands

The **Command** delivery runs a line in the server console. Before running it, the server fills in the variables:

| Variable       | Becomes                                          |
| -------------- | ------------------------------------------------ |
| `{id}`         | The character's ID in the city                   |
| `{discord}`    | The buyer's Discord ID                           |
| `{pedido}`     | The order number                                 |
| `{quantidade}` | Currencies only: the total bought plus the bonus |

The server's safety rules:

* One line is one command: `;` and line breaks are refused.
* These commands never run from the store: `quit`, `stop`, `start`, `restart`, `ensure`, `refresh`, `exec`, `set`, `sets`, `setr`, `seta`, `rcon_password`, `sv_licensekey`, `sv_hostname`, `sv_maxclients`, `endpoint_add_tcp`, `endpoint_add_udp`, `load_server_icon`, `fivedash`.
* With `AllowedCommands` filled in `loja.lua`, only commands that start with one of the list's entries run.
* A command with `{id}` fails if the order has no player ID.

> Without a recognized framework, the server only delivers **Command**. In that case `{id}` is the ID the buyer typed.

## What each framework does

The resource detects the framework by itself (`Framework = "auto"` in `config.lua`). See also [Frameworks](https://fivedash.fivex.gg/docs/en/developers/frameworks).

### ESX

ID: the `id` in the `users` table.

| Type            | How it's delivered                                                                                                                                                                                                                                   |
| --------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **VIP or role** | If it exists in `job_grades` (`police`, or `police.2` for grade 2), it becomes the job: `setJob` online, or straight into `users` offline. Any other name becomes the ACE group `group.<name>`. When it runs out, the job goes back to `unemployed`. |
| **Vehicle**     | A row in `owned_vehicles`, stored, with a free plate. If the `vehicles` table has a `model` column, the model must be in it.                                                                                                                         |
| **Money**       | Bank online (`addAccountMoney`) or offline (`users.accounts`). Wallet online only.                                                                                                                                                                   |
| **Item**        | Online only. Uses `ox_inventory` when it runs; otherwise ESX's inventory (`canCarryItem` and `addInventoryItem`).                                                                                                                                    |

On-screen notice: `esx:showNotification`.

### QBCore

ID: Citizen ID (`citizenid` in the `players` table).

| Type            | How it's delivered                                                                                                                                                                                                                                                                                    |
| --------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **VIP or role** | A job from `QBCore.Shared.Jobs` (`police` or `police.2`) or a gang from `Shared.Gangs` becomes the character's job or gang (`SetJob` / `SetGang`), online or offline. Any other name becomes the ACE group `qbcore.<name>`. Old qb-core versions without offline players wait for the player to join. |
| **Vehicle**     | A row in `player_vehicles` in the `pillboxgarage` garage. The model must be in `qb-core/shared/vehicles.lua`.                                                                                                                                                                                         |
| **Money**       | Bank online or offline. Wallet (`cash`) online only.                                                                                                                                                                                                                                                  |
| **Item**        | Online only. Uses `ox_inventory` when it runs; otherwise `qb-inventory`.                                                                                                                                                                                                                              |

On-screen notice: `QBCore:Notify`.

### Qbox

ID: Citizen ID.

| Type            | How it's delivered                                                                                                                                                 |
| --------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| **VIP or role** | A job or gang through `AddPlayerToJob` / `AddPlayerToGang`, online or offline (a character can have several). Any other name becomes the ACE group `group.<name>`. |
| **Vehicle**     | `qbx_vehicles`' `CreatePlayerVehicle` (without it, a row in `player_vehicles` in `pillboxgarage`). The model must be in `qbx_core/shared/vehicles.lua`.            |
| **Money**       | `AddMoney` to the bank or wallet, online or offline.                                                                                                               |
| **Item**        | Online only, through `ox_inventory`.                                                                                                                               |

On-screen notice: `ox_lib:notify`.

### ox_core

ID: State ID.

| Type            | How it's delivered                                                                                                                               |
| --------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ |
| **VIP or role** | An ox_core group (`police` or `police.2`; grades start at 1) that exists in `ox_group_grades`: `setGroup` online, or `character_groups` offline. |
| **Vehicle**     | `CreateVehicle` owned by the character, stored in the garage set by the `ox:defaultVehicleStore` convar (default `impound`).                     |
| **Money**       | Bank: `addBalance` on the character's default account, online or offline. Wallet: `ox_inventory`'s `money` item, online only.                    |
| **Item**        | Online only, through `ox_inventory`.                                                                                                             |

On-screen notice: `ox_lib:notify`.

### vRP / vRPex

ID: the `id` in `vrp_users`. Covers vRPex and forks like ZIRIX (not Creative).

| Type            | How it's delivered                                                                                                    |
| --------------- | --------------------------------------------------------------------------------------------------------------------- |
| **VIP or role** | Online only, through `addUserGroup`. The group must exist in `vrp/cfg/groups.lua`.                                    |
| **Vehicle**     | A row in `vrp_user_vehicles`, online or offline. Fails if the ID already has that vehicle.                            |
| **Money**       | Bank: `giveBankMoney` online, or `vrp_user_moneys.bank` offline. Wallet: `giveMoney`, online only.                    |
| **Item**        | Online only, through `giveInventoryItem`, checking the backpack's weight. The item must exist in `vrp/cfg/items.lua`. |

On-screen notice: the `Notify` event.

### Creative Network Enchanted

ID: Passport (the `id` in the `characters` table; an account has several).

| Type            | How it's delivered                                                                                                                                                                |
| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **VIP or role** | `SetPermission`, online or offline. The group must exist in `vrp/config/Groups.lua`.                                                                                              |
| **Vehicle**     | Goes into the `vehicles` table through the base's own query, online or offline. The model must exist in `vrp/config/Vehicle.lua`. Fails if the passport already has that vehicle. |
| **Money**       | Bank: `GiveBank`, online or offline. Wallet: the `dollar` item, online only.                                                                                                      |
| **Item**        | Online only. The item must exist in `vrp/config/Item.lua`. If the weight doesn't fit, it waits; with no free slot, the base drops the item on the ground next to the player.      |

On-screen notice: the `Notify` event.

## Configure the server

### loja.lua

The `fivedash/loja.lua` file is created on first boot and only the server reads it. After changing something, run `restart fivedash`. Updates never remove or change what's in it.

| Field             | What it does                                                                                                               | Default  |
| ----------------- | -------------------------------------------------------------------------------------------------------------------------- | -------- |
| `Enabled`         | Turns delivery on in this city. Off, the store's website stops selling until you turn it back on.                          | `true`   |
| `Notify`          | Shows the player a notice when the purchase arrives and when a VIP runs out.                                               | `true`   |
| `NotifyTitle`     | The notice's title, up to 40 characters. With `"Loja"`, the title follows the city's language ("Store" in English cities). | `"Loja"` |
| `Announce`        | Announces to the whole city who bought what. Gifts from the team aren't announced.                                         | `false`  |
| `SpawnDelay`      | Seconds between the player picking their character and the delivery (gives the inventory time to load). 0 to 120.          | `10`     |
| `AllowedCommands` | Commands the store may run. Empty allows any, except the blocked ones. To lock it, list the start of each.                 | `{}`     |

```lua
Loja = {
	Enabled = true,
	Notify = true,
	NotifyTitle = "Loja",
	Announce = false,
	SpawnDelay = 10,
	AllowedCommands = { "givecoins", "addcar" },
}
```

### config.lua

| Field        | What it does                                                                                                      | Default  |
| ------------ | ----------------------------------------------------------------------------------------------------------------- | -------- |
| `Key`        | The dashboard key, from **Server → Game connection → Connect server**. Don't share this file.                     | `""`     |
| `Framework`  | `"auto"` detects it. To force one: `"creative-enchanted"`, `"qbox"`, `"qbcore"`, `"esx"`, `"ox-core"` or `"vrp"`. | `"auto"` |
| `AutoUpdate` | Installs new versions of the resource by itself. The new version applies on the next restart.                     | `true`   |
| `Debug`      | Prints every sync and command in the console.                                                                     | `false`  |

### Console commands

| Command                                                | What it does                                                                                                                                       |
| ------------------------------------------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------- |
| `fivedash`                                             | The resource's state: framework, connection, version and deliveries waiting.                                                                       |
| `fivedash store` (or `fivedash loja`)                  | The store's state: on or off, what it delivers and by which ID, how many deliveries are waiting, and how many were delivered or failed since boot. |
| `fivedash store deliver` (or `fivedash loja entregar`) | Runs now whatever is waiting for players who are already in the city.                                                                              |
| `fivedash detect`                                      | Detects the framework again.                                                                                                                       |
| `restart fivedash`                                     | Reloads `loja.lua` and `config.lua`, and applies an update that was already downloaded.                                                            |

## When a delivery fails

In **Store → Orders**, the order shows **Delivery failed** and each delivery's reason.

### Read the reason

Open the order. Each delivery shows **delivered**, **queued** or **failed**, with the reason the city sent.

### Fix it and resend

If the ID was wrong, fix it in **Game ID** and click **Resend to the city**. Only the deliveries that failed go back to the queue; what already arrived isn't delivered again.

### Or close it by hand

If the team handed it over in the game, click **Mark as delivered**. Whatever was still waiting in the city is dropped.

Common reasons:

| Reason                                                                          | What to do                                                                      |
| ------------------------------------------------------------------------------- | ------------------------------------------------------------------------------- |
| The ID doesn't exist in the city                                                | Fix the ID and resend.                                                          |
| The buyer's Discord account has no character in the city                        | Ask for the ID and resend with it.                                              |
| The group, vehicle or item doesn't exist in the city (with the file to look in) | Add it to the framework or fix the name in the product, then resend.            |
| The command isn't in AllowedCommands in loja.lua                                | Add the command's start to `AllowedCommands` and resend.                        |
| The server stopped in the middle of this delivery                               | Check in game whether it arrived. If not, resend; if it did, mark as delivered. |
| The city's framework can't deliver this through FiveDash yet                    | Use a **Command** delivery.                                                     |

## FAQ

**The player bought while offline. When does it arrive?**
Whatever works offline arrives right away. Items and wallet money arrive `SpawnDelay` seconds after they pick their character.

**Can I restart the server with deliveries in the queue?**
Yes. They're in the city's database and carry on after boot.

**Can a player receive twice if I click resend twice?**
No. Only what failed goes back to the queue, and each delivery is given only once.

**Why didn't the player's VIP run out?**
If the team had given the group by hand before the purchase, FiveDash doesn't put an expiry on it.

## Next steps

[Products](https://fivedash.fivex.gg/docs/en/store/products)Set up each product's deliveries.
[Orders](https://fivedash.fivex.gg/docs/en/store/orders)Follow and resend deliveries.
[Install the resource](https://fivedash.fivex.gg/docs/en/getting-started/install-resource)Connect the server to FiveDash.
[Frameworks](https://fivedash.fivex.gg/docs/en/developers/frameworks)Technical details for each framework.
