Skip to Content
Mizu SmartShopConfigurations

Configurations

⚙️
config.lua
All settings live in config.lua at the root of the resource. Changes take effect on resource restart.

General

Config.Locale = 'en' -- 'en', 'de', 'es', 'fr', 'it', 'pl', 'pt', 'tr' Config.Theme = 'default' -- 'default', 'green', 'yellow', 'silver', 'red' Config.TargetSystem = 'none' -- 'none', 'qb-target', 'ox-target' Config.LogType = 'discord' -- 'discord' or 'fivemanage' Config.DynamicPriceInterval = 30 -- Minutes between price updates (global default) Config.WebhookURL = '' Config.FivemanageToken = ''

Config.Locale

Controls which locale file is loaded. Ships with 'en' (English), 'de' (German), 'es' (Spanish), 'fr' (French), 'it' (Italian), 'pl' (Polish), 'pt' (Portuguese), and 'tr' (Turkish).

Config.Theme

Controls the UI color preset: 'default', 'green', 'yellow', 'silver', 'red'.

Config.TargetSystem

Controls how players interact with shops.

ValueBehavior
'none'Built-in 3D markers + E key
'qb-target'qb-target box zones
'ox-target'ox_target sphere zones

Config.LogType

Controls where checkout logs are sent: 'discord' or 'fivemanage'.

Config.WebhookURL

Discord webhook URL. Only used when LogType = 'discord'. Leave empty to disable.

Config.FivemanageToken

FiveManage API token. Only used when LogType = 'fivemanage'. Leave empty to disable.

Config.DynamicPriceInterval

Global interval (in minutes) between dynamic price refreshes. Default: 30. Individual shops can override this with their own DynamicPriceInterval field.

⚠️
Security

Do not commit real webhook URLs or API tokens to public repositories. Keep credentials out of version control.


Shops

Each entry inside Config.Shops defines one shop.

Config.Shops = { ['247_supermarket'] = { name = '24/7 Supermarket', coords = vector3(25.68, -1346.58, 29.49), DynamicPricing = true, -- enable dynamic pricing DynamicPriceRange = 30, -- ±30% price fluctuation --DynamicPriceInterval = 30, -- override global interval (minutes) Blipname = 'Supermarket', BlipSprite = 52, BlipColor = 2, BlipMinimapOnly = true, MarkerType = 1, MarkerSize = vector3(1.0, 1.0, 0.5), MarkerColor = { r = 30, g = 150, b = 30, a = 100 }, PedModel = 'mp_m_shopkeep_01', -- spawn a ped instead of marker PedHeading = 146.37, -- facing direction (0-360) PedScenario = '', -- idle animation items = { { name = 'water_bottle', label = 'Juice', price = 5, image = 'berriesjuice.png', maxQty = 999, category = 'Food & Snacks' } } } }

Shop fields

FieldDescription
nameDisplay name shown in the UI and logs
coordsMain shop position (target zones, markers, logs)
JobRestrictionOptional. String or table of job names. Remove to make public
DynamicPricingOptional. true to enable fluctuating prices for this shop
DynamicPriceRangeOptional. ± percentage for price fluctuation (default: 30)
DynamicPriceIntervalOptional. Override global refresh interval in minutes
-- Single job JobRestriction = 'police' -- Multiple jobs JobRestriction = { 'police', 'sheriff' }

Blip settings

Remove Blipname from a shop to disable its blip entirely.

FieldDescription
BlipnameMap label. Remove to disable the blip
BlipSpriteGTA blip sprite ID
BlipColorGTA blip color ID
BlipMinimapOnlytrue = minimap only, false = full map blip
💡
Tip

Blips for job-restricted shops are only visible to players with the matching job. Blips refresh automatically on job change.


Marker settings

These are only used when Config.TargetSystem = 'none'.

FieldDescription
MarkerTypeGTA marker type ID. Remove to disable the marker
MarkerSizevector3 scale
MarkerPosOptional custom position. Falls back to coords
MarkerColorRGBA table: { r = 30, g = 150, b = 30, a = 100 }

Ped settings

Shops can spawn an NPC ped instead of a marker. When PedModel is set, the marker is hidden and the ped becomes the interaction point.

FieldDescription
PedModelPed model name (e.g. 'mp_m_shopkeep_01'). Remove to disable
PedHeadingFacing direction 0360
PedScenarioOptional idle animation (e.g. 'WORLD_HUMAN_STAND_IMPATIENT'). Leave empty for none
PedModel = 'mp_m_shopkeep_01', PedHeading = 146.37, PedScenario = 'WORLD_HUMAN_STAND_IMPATIENT',

Peds are invincible, frozen, and passive. They work with qb-target, ox_target, and E-key fallback. Job-restricted peds are only visible to authorized players.


Items

Each shop has an items table.

items = { { name = 'weapon_pistol', label = 'Combat Pistol', price = 0, image = 'pistol.png', maxQty = 1, grade = 0 } }
FieldDescription
nameInternal item name used by your framework / inventory
labelDisplay name in the UI
pricePrice per unit
imageImage filename. Must match your inventory image path
maxQtyMax amount per checkout
gradeOptional. Minimum job grade required. Hidden + blocked if player grade is lower
categoryOptional. Category name for tab filtering. Items without a category show under “All”
minPriceOptional. Minimum price for dynamic pricing (overrides DynamicPriceRange)
maxPriceOptional. Maximum price for dynamic pricing (overrides DynamicPriceRange)

When at least one item in a shop has a category, the UI shows category tabs above the item grid. Items without a category always appear in every tab.

items = { { name = 'water_bottle', label = 'Juice', price = 5, image = 'juice.png', maxQty = 999, category = 'Food & Snacks' }, { name = 'repairkit', label = 'Repair Kit', price = 250, image = 'lockpick.png', maxQty = 10, category = 'Equipment' }, { name = 'vanbottle', label = 'Gin', price = 500, image = 'vanbottle.png', maxQty = 5, minPrice = 555, maxPrice = 666 }, -- dynamic pricing override }

Notifications

The default implementation auto-detects QBCore, ox_lib, ESX, or falls back to native GTA notifications. Replace it to use your own notification system.

Config.Notify = function(msg, type, title) local notifyTitle = title or 'SmartShop' if GetResourceState('qb-core') == 'started' then local QBCore = exports['qb-core']:GetCoreObject() QBCore.Functions.Notify(msg, type) elseif GetResourceState('ox_lib') == 'started' then exports.ox_lib:notify({ title = notifyTitle, description = msg, type = type }) elseif GetResourceState('es_extended') == 'started' then local ESX = exports['es_extended']:getSharedObject() ESX.ShowNotification(msg) else SetNotificationTextEntry('STRING') AddTextComponentString(msg) DrawNotification(0, 1) end end

QBox is covered by the ox_lib check since QBox uses ox_lib for notifications.

ParameterDescription
msgThe message text
type'success', 'error', or your system’s equivalent
titleOptional shop or system title

saved_shops.json

This file is managed automatically by the admin panel and /smartshopcreate command. Do not edit it manually unless you know what you’re doing.

The file stores two types of entries:

TypeFlagDescription
Override_override: trueField-level changes to a config.lua shop
Dynamic_dynamic: trueA shop created entirely in-game

On resource start, config.lua shops load first, then saved_shops.json is merged on top. Override entries only replace the fields they contain — all other fields keep their config.lua values. Dynamic entries are added as new shops.

Deleting saved_shops.json resets everything back to the pure config.lua state.

Last updated on