> ## Documentation Index
> Fetch the complete documentation index at: https://rsg.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# 📜 Shared Configuration

> Complete guide to configuring jobs, items, vehicles, gangs, and utilities in RSG Framework

## Introduction

The shared files in `rsg-core` contain all the core configuration data for your server including jobs, items, vehicles, gangs, weapons, and utility functions. These files are shared between client and server, making the data accessible on both sides without additional network calls.

**Location**: `resources/[framework]/rsg-core/shared/`

<Check>
  Shared files are loaded on both client and server automatically. Changes require a server restart!
</Check>

***

## Core Features

### 📦 Centralized Configuration

* **Jobs**: Define all server jobs with grades and payments
* **Items**: Configure inventory items with properties and metadata
* **Vehicles**: Set up vehicle shops and pricing
* **Gangs**: Create gang hierarchies and structures
* **Weapons**: Define weapon properties and ammo types
* **Utilities**: Helper functions for common operations

### 🔄 Shared Access

* **Client & Server**: Data available on both sides
* **No Network Calls**: Instant access without events
* **Consistent Data**: Single source of truth
* **Easy Management**: Edit in one place, affects everywhere

### ⚙️ Flexible System

* **Add Custom Jobs**: Create new job types
* **Define Items**: Add new items with decay, quality, etc.
* **Vehicle Categories**: Organize vehicles by type
* **Gang System**: Set up gang hierarchies
* **Utility Functions**: String manipulation, math helpers

***

## Utility Functions

### Location

**File**: `rsg-core/shared/main.lua`

### Starter Items

Define default items for new players:

```lua theme={null}
RSGShared.StarterItems = {
    bread = { amount = 5, item = 'bread' },
    water = { amount = 5, item = 'water' },
}
```

**Customization**:

```lua theme={null}
-- Give different starter items
RSGShared.StarterItems = {
    bread = { amount = 10, item = 'bread' },
    water = { amount = 10, item = 'water' },
    bandage = { amount = 3, item = 'bandage' },
    dollar = { amount = 50, item = 'dollar' }  -- Starting cash if using money items
}
```

### String Functions

#### RandomStr

Generate random string of specified length:

```lua theme={null}
RSGShared.RandomStr(length)
```

**Example**:

```lua theme={null}
local randomString = RSGShared.RandomStr(8)
-- Result: "aBcDeFgH"

-- Use for unique IDs
local transactionId = 'TXN_'.. RSGShared.RandomStr(12)
-- Result: "TXN_XyZ123AbCdEf"
```

#### RandomInt

Generate random number string:

```lua theme={null}
RSGShared.RandomInt(length)
```

**Example**:

```lua theme={null}
local randomNumber = RSGShared.RandomInt(6)
-- Result: "482719"

-- Use for PINs, codes
local pinCode = RSGShared.RandomInt(4)
-- Result: "1234"
```

#### SplitStr

Split string by delimiter:

```lua theme={null}
RSGShared.SplitStr(str, delimiter)
```

**Example**:

```lua theme={null}
local parts = RSGShared.SplitStr("John,Doe,30", ",")
-- Result: { "John", "Doe", "30" }

-- Parse player names
local fullName = "John Marston"
local names = RSGShared.SplitStr(fullName, " ")
local firstname = names[1]  -- "John"
local lastname = names[2]   -- "Marston"
```

#### Trim

Remove whitespace from string:

```lua theme={null}
RSGShared.Trim(value)
```

**Example**:

```lua theme={null}
local clean = RSGShared.Trim("  Hello World  ")
-- Result: "Hello World"

-- Useful for user input
local playerInput = "  John  "
local cleanName = RSGShared.Trim(playerInput)
-- Result: "John"
```

#### FirstToUpper

Capitalize first letter:

```lua theme={null}
RSGShared.FirstToUpper(value)
```

**Example**:

```lua theme={null}
local capitalized = RSGShared.FirstToUpper("john")
-- Result: "John"

-- Format names
local firstname = RSGShared.FirstToUpper(string.lower("JOHN"))
-- Result: "John"
```

#### Round

Round number to decimal places:

```lua theme={null}
RSGShared.Round(value, numDecimalPlaces)
```

**Example**:

```lua theme={null}
local rounded = RSGShared.Round(3.14159, 2)
-- Result: 3.14

-- Round money
local price = 123.456
local finalPrice = RSGShared.Round(price, 2)
-- Result: 123.46

-- Round to integer
local wholeNumber = RSGShared.Round(3.7)
-- Result: 4
```

### Vehicle Functions

#### ChangeVehicleExtra

Toggle vehicle extras:

```lua theme={null}
RSGShared.ChangeVehicleExtra(vehicle, extra, enable)
```

**Example**:

```lua theme={null}
-- CLIENT SIDE
local vehicle = GetVehiclePedIsIn(PlayerPedId(), false)

-- Enable extra 1
RSGShared.ChangeVehicleExtra(vehicle, 1, true)

-- Disable extra 2
RSGShared.ChangeVehicleExtra(vehicle, 2, false)
```

#### SetDefaultVehicleExtras

Set multiple vehicle extras:

```lua theme={null}
RSGShared.SetDefaultVehicleExtras(vehicle, config)
```

**Example**:

```lua theme={null}
-- CLIENT SIDE
local vehicle = GetVehiclePedIsIn(PlayerPedId(), false)

-- Configure extras
local extraConfig = {
    [1] = true,   -- Enable extra 1
    [2] = false,  -- Disable extra 2
    [3] = true    -- Enable extra 3
}

RSGShared.SetDefaultVehicleExtras(vehicle, extraConfig)
```

***

## Items Configuration

### Location

**File**: `rsg-core/shared/items.lua`

### Item Structure

Complete item definition with all properties:

```lua theme={null}
RSGShared.Items = {
    ['bread'] = {
        name = 'bread',                        -- Item identifier (must match key)
        label = 'Bread',                       -- Display name
        weight = 100,                          -- Weight in grams
        type = 'item',                         -- Type: 'item' or 'weapon'
        image = 'consumable_bread_roll.png',   -- Image in rsg-inventory/html/images
        unique = false,                        -- Each item takes own slot if true
        useable = true,                        -- Can be used (needs callback)
        shouldClose = true,                    -- Close inventory on use
        combinable = nil,                      -- Crafting combinations (optional)
        description = 'Fresh baked bread',     -- Tooltip description
        decay = 300,                           -- Decay time in minutes (optional)
        delete = true,                         -- Auto-delete at 0% quality (optional)
        info = {                               -- Default metadata (v2.7.3+)
            quality = 100
        }
    },
}
```

### Item Properties Reference

| Property      | Type    | Required | Description                                   |
| ------------- | ------- | -------- | --------------------------------------------- |
| `name`        | string  | Yes      | Item spawn name (must match table key)        |
| `label`       | string  | Yes      | Display name in inventory                     |
| `weight`      | number  | Yes      | Item weight in grams                          |
| `type`        | string  | Yes      | `'item'` or `'weapon'`                        |
| `image`       | string  | Yes      | Image filename (in rsg-inventory/html/images) |
| `unique`      | boolean | Yes      | If true, items don't stack                    |
| `useable`     | boolean | Yes      | If true, item can be used                     |
| `shouldClose` | boolean | Yes      | Close inventory when used                     |
| `description` | string  | Yes      | Item tooltip text                             |
| `decay`       | number  | No       | Minutes from 100% to 0% quality               |
| `delete`      | boolean | No       | Auto-remove at 0% quality                     |
| `combinable`  | table   | No       | Crafting recipe combinations                  |
| `ammotype`    | string  | Weapons  | Ammo type for weapons                         |
| `info`        | table   | No       | Default metadata (v2.7.3+)                    |

### Item Type Examples

#### Consumable Food

```lua theme={null}
['bread'] = {
    name = 'bread',
    label = 'Bread',
    weight = 100,
    type = 'item',
    image = 'consumable_bread_roll.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'Fresh baked bread',
    decay = 300,        -- 5 hours
    delete = true
},

['cooked_meat'] = {
    name = 'cooked_meat',
    label = 'Cooked Meat',
    weight = 400,
    type = 'item',
    image = 'consumable_meat_cooked.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'Perfectly cooked meat',
    decay = 480,        -- 8 hours
    delete = true
},
```

#### Tools & Equipment

```lua theme={null}
['pickaxe'] = {
    name = 'pickaxe',
    label = 'Pickaxe',
    weight = 2000,
    type = 'item',
    image = 'tool_pickaxe.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'Mining pickaxe for extracting ore',
    decay = 10080,      -- 7 days
    delete = false      -- Keep broken tool
},

['lasso'] = {
    name = 'lasso',
    label = 'Lasso',
    weight = 500,
    type = 'item',
    image = 'tool_lasso.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'Rope lasso for catching animals or people'
},
```

#### Money Items

```lua theme={null}
['dollar'] = {
    name = 'dollar',
    label = 'Dollars',
    weight = 1,
    type = 'item',
    image = 'dollar.png',
    unique = false,
    useable = false,
    shouldClose = false,
    description = 'US Dollar currency'
},

['blood_dollar'] = {
    name = 'blood_dollar',
    label = 'Bloodstained Dollars',
    weight = 1,
    type = 'item',
    image = 'bloodmoney.png',
    unique = false,
    useable = false,
    shouldClose = false,
    description = 'Blood-stained money from illegal activities'
},
```

#### Weapon Items

```lua theme={null}
['weapon_revolver_cattleman'] = {
    name = 'weapon_revolver_cattleman',
    label = 'Cattleman Revolver',
    weight = 1000,
    type = 'weapon',
    ammotype = 'AMMO_REVOLVER',
    image = 'weapon_revolver_cattleman.png',
    unique = true,
    useable = false,
    description = 'A reliable six-shooter revolver'
},

['ammorevolver'] = {
    name = 'ammorevolver',
    label = 'Revolver Ammo',
    weight = 10,
    type = 'item',
    ammotype = 'AMMO_REVOLVER',
    image = 'ammo_revolver.png',
    unique = false,
    useable = false,
    description = 'Ammunition for revolvers'
},
```

#### Items with Default Metadata

```lua theme={null}
-- v2.7.3+ Feature
['bottle'] = {
    name = 'bottle',
    label = 'Glass Bottle',
    weight = 200,
    type = 'item',
    image = 'item_bottle.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'An empty glass bottle',
    info = {
        liquid = 'empty',
        volume = 0,
        maxVolume = 500
    }
},

['horse_brush'] = {
    name = 'horse_brush',
    label = 'Horse Brush',
    weight = 300,
    type = 'item',
    image = 'tool_horsebrush.png',
    unique = false,
    useable = true,
    shouldClose = true,
    description = 'Brush for grooming horses',
    decay = 20160,  -- 14 days
    delete = false,
    info = {
        durability = 100,
        uses = 0
    }
},
```

***

## Jobs Configuration

### Location

**File**: `rsg-core/shared/jobs.lua`

### Job Structure

Complete job definition:

```lua theme={null}
RSGShared = RSGShared or {}
RSGShared.ForceJobDefaultDutyAtLogin = true  -- Force duty state on login

RSGShared.Jobs = {
    unemployed = {
        name = 'unemployed',
        label = 'Civilian',
        defaultDuty = true,
        offDutyPay = false,
        grades = {
            ['0'] = {
                name = 'Freelancer',
                payment = 3
            }
        }
    },

    vallaw = {
        name = 'vallaw',
        label = 'Valentine Law Enforcement',
        type = 'leo',
        defaultDuty = false,
        offDutyPay = false,
        grades = {
            ['0'] = { name = 'Recruit', payment = 10 },
            ['1'] = { name = 'Deputy', payment = 25 },
            ['2'] = { name = 'Sheriff', isboss = true, payment = 50 }
        }
    },
}
```

### Job Properties

| Property      | Type    | Required | Description                       |
| ------------- | ------- | -------- | --------------------------------- |
| `name`        | string  | Yes      | Internal job identifier           |
| `label`       | string  | Yes      | Display name                      |
| `type`        | string  | No       | Job category (`'leo'`, `'medic'`) |
| `defaultDuty` | boolean | Yes      | Auto clock-in on login            |
| `offDutyPay`  | boolean | Yes      | Pay when off-duty                 |
| `grades`      | table   | Yes      | Grade/rank levels                 |

### Grade Properties

| Property  | Type    | Required | Description         |
| --------- | ------- | -------- | ------------------- |
| `name`    | string  | Yes      | Grade display name  |
| `payment` | number  | Yes      | Paycheck amount     |
| `isboss`  | boolean | No       | Access to boss menu |

### Default Jobs

The framework includes these jobs by default:

**Law Enforcement** (`type = 'leo'`):

* `vallaw` - Valentine Law Enforcement
* `rholaw` - Rhodes Law Enforcement
* `blklaw` - Blackwater Law Enforcement
* `strlaw` - Strawberry Law Enforcement
* `stdenlaw` - Saint Denis Law Enforcement

**Medical** (`type = 'medic'`):

* `valmedic` - Valentine Medic
* `sdmedic` - Saint Denis Medic

**Civilian**:

* `unemployed` - Default job for all players

### Creating Custom Jobs

```lua theme={null}
-- Example: Blacksmith job
blacksmith = {
    name = 'blacksmith',
    label = 'Blacksmith',
    type = 'crafting',
    defaultDuty = true,
    offDutyPay = false,
    grades = {
        ['0'] = { name = 'Apprentice', payment = 15 },
        ['1'] = { name = 'Journeyman', payment = 30 },
        ['2'] = { name = 'Master Smith', isboss = true, payment = 60 }
    }
},

-- Example: Rancher job
rancher = {
    name = 'rancher',
    label = 'Rancher',
    type = 'farming',
    defaultDuty = true,
    offDutyPay = true,  -- Ranchers always get paid
    grades = {
        ['0'] = { name = 'Ranch Hand', payment = 20 },
        ['1'] = { name = 'Foreman', payment = 40 },
        ['2'] = { name = 'Ranch Owner', isboss = true, payment = 80 }
    }
},
```

***

## Vehicles Configuration

### Location

**File**: `rsg-core/shared/vehicles.lua`

### Vehicle Structure

```lua theme={null}
RSGShared = RSGShared or {}
RSGShared.Vehicles = RSGShared.Vehicles or {}

local Vehicles = {
    CART01 = {
        name = 'Wooden Cart 1',
        brand = 'Unknown',
        model = 'CART01',
        price = 100,
        category = 'carts',
        hash = joaat('CART01'),
        shop = 'valentine_stable'
    },

    A_C_HORSE_AMERICANPAINT_GREYOVERO = {
        name = 'American Paint - Grey Overo',
        brand = 'Horse',
        model = 'A_C_HORSE_AMERICANPAINT_GREYOVERO',
        price = 500,
        category = 'horses',
        hash = joaat('A_C_HORSE_AMERICANPAINT_GREYOVERO'),
        shop = 'valentine_stable'
    },
}

-- Auto-populate RSGShared.Vehicles table
for i = 1, #Vehicles do
    RSGShared.Vehicles[Vehicles[i].model] = {
        spawncode = Vehicles[i].model,
        name = Vehicles[i].name,
        brand = Vehicles[i].brand,
        model = Vehicles[i].model,
        price = Vehicles[i].price,
        category = Vehicles[i].category,
        hash = joaat(Vehicles[i].model),
        shop = Vehicles[i].shop
    }
end
```

### Vehicle Properties

| Property   | Type   | Description                  |
| ---------- | ------ | ---------------------------- |
| `name`     | string | Display name                 |
| `brand`    | string | Manufacturer/breed           |
| `model`    | string | Spawn code                   |
| `price`    | number | Purchase price               |
| `category` | string | Category for shops           |
| `hash`     | number | Model hash (auto-calculated) |
| `shop`     | string | Shop identifier              |

### Vehicle Categories

Common categories:

* `'horses'` - Horse mounts
* `'carts'` - Wagons and carts
* `'coaches'` - Stagecoaches
* `'boats'` - Watercraft

***

## Gangs Configuration

### Location

**File**: `rsg-core/shared/gangs.lua`

### Gang Structure

```lua theme={null}
RSGShared = RSGShared or {}
RSGShared.Gangs = {
    none = {
        label = 'No Gang',
        grades = {
            ['0'] = { name = 'Unaffiliated' }
        }
    },

    odriscoll = {
        label = 'O\'Driscoll Boys',
        grades = {
            ['0'] = { name = 'Recruit' },
            ['1'] = { name = 'Enforcer' },
            ['2'] = { name = 'Shot Caller' },
            ['3'] = { name = 'Boss', isboss = true }
        }
    },
}
```

### Default Gangs

* `none` - No gang affiliation
* `odriscoll` - O'Driscoll Boys
* `lemoyne` - Lemoyne Raiders
* `murfree` - Murfree Brood
* `skinner` - Skinner Brothers
* `laramie` - Laramie Gang
* `dellobo` - Del Lobo Gang
* `night` - Night Folk
* `foreman` - Foreman Brothers
* `anderson` - Anderson Boys
* `watson` - Watson's Boys

### Creating Custom Gangs

```lua theme={null}
-- Example: Custom gang
mystic_gang = {
    label = 'Mystic Riders',
    grades = {
        ['0'] = { name = 'Prospect' },
        ['1'] = { name = 'Member' },
        ['2'] = { name = 'Road Captain' },
        ['3'] = { name = 'Vice President' },
        ['4'] = { name = 'President', isboss = true }
    }
},
```

***

## Weapons Configuration

### Location

**File**: `rsg-core/shared/weapons.lua`

### Weapon Structure

```lua theme={null}
RSGShared = RSGShared or {}
RSGShared.Weapons = {
    [`weapon_revolver_cattleman`] = {
        name = 'weapon_revolver_cattleman',
        label = 'Cattleman Revolver',
        weapontype = 'Revolver',
        ammotype = 'AMMO_REVOLVER',
        damagereason = 'Shot with Cattleman Revolver'
    },

    [`weapon_rifle_boltaction`] = {
        name = 'weapon_rifle_boltaction',
        label = 'Bolt Action Rifle',
        weapontype = 'Rifle',
        ammotype = 'AMMO_RIFLE',
        damagereason = 'Shot with Bolt Action Rifle'
    },
}
```

<Info>
  Weapons must also be defined in `shared/items.lua` as inventory items with `type = 'weapon'`!
</Info>

***

## Best Practices

<Tip>
  **Restart Required**: All shared file changes require a full server restart to take effect
</Tip>

<Warning>
  **Unique Keys**: Ensure all items, jobs, and gangs have unique identifiers (names)
</Warning>

<Check>
  **Test Thoroughly**: Test all new jobs, items, and vehicles before deploying to production
</Check>

### Configuration Tips

1. **Consistent Naming**: Use lowercase with underscores (`my_custom_item`)
2. **Clear Labels**: Use descriptive display names
3. **Balanced Payments**: Keep job payments balanced for economy
4. **Weight System**: 1000g = 1kg, keep items realistic
5. **Image Files**: Ensure all images exist in rsg-inventory/html/images

### Common Mistakes

❌ **Don't**:

```lua theme={null}
-- Mismatched key and name
['my_item'] = {
    name = 'myitem',  -- WRONG! Should match key
    -- ...
}

-- Forgetting quotes on grade keys
grades = {
    [0] = { name = 'Grade' }  -- WRONG! Should be '0'
}
```

✅ **Do**:

```lua theme={null}
-- Matching key and name
['my_item'] = {
    name = 'my_item',  -- Correct!
    -- ...
}

-- Proper grade key format
grades = {
    ['0'] = { name = 'Grade' }  -- Correct!
}
```

***

## Next Steps

* [Item Decay System](/inventory/item-decay) - Configure item quality degradation
* [Money System](/essentials/money-system) - Set up money types and banks
* [Configuration Guide](/essentials/configuration) - Configure server settings
* [Inventory Functions](/inventory/functions) - Work with items programmatically

***

Need help? Join the [RSG Framework Discord](https://discord.gg/rsg-redm-framework-914413479157448744)!
