Volver al blog
Tutorial6 min de lectura

Guía de ox_inventory: el inventario de FiveM imprescindible en 2026

Domina ox_inventory en tu servidor FiveM. Aprende a instalarlo, configurar objetos, usar exports e integrarlo con frameworks QBCore, ESX o standalone.

Agency Scripts

Fundador y desarrollador principal en Agency Scripts

¿Qué es ox_inventory?

ox_inventory es un sistema de inventario moderno y de alto rendimiento para FiveM que se ha convertido en la opción estándar para los servidores de roleplay serios. Creado por el equipo de Overextended, reemplaza soluciones de inventario más antiguas con un sistema más rápido, flexible y fácil de ampliar. Incluye una interfaz elegante basada en React, gestión de armas integrada, compatibilidad con la creación de objetos, tiendas, almacenes y una API potente que los desarrolladores de scripts pueden usar para crear interacciones personalizadas con objetos. Tanto si estás creando un servidor nuevo como si migras desde otro inventario, conocer ox_inventory a fondo te convertirá en un mejor desarrollador de FiveM.

Instalación y configuración

ox_inventory requiere ox_lib como dependencia y funciona con los frameworks ESX y QBCore, así como con configuraciones standalone. La instalación consiste en descargar el resource, importar el esquema SQL a tu base de datos y configurar el puente del framework. El archivo de configuración controla todo, desde los límites de peso del inventario hasta los temporizadores de deterioro de los objetos.

-- Configuration snippet from ox_inventory
return {
    playerslots = 50,
    playerweight = 30000,
    playerweaponslots = 5,

    decay = true,
    decayInterval = 60,

    trunkslots = 50,
    trunkweight = 60000,
    gloveboxslots = 5,
    gloveboxweight = 5000,
}

Registrar objetos personalizados

Los objetos de ox_inventory se definen en el archivo data/items.lua . Cada objeto necesita un nombre único, una etiqueta, un peso y, de forma opcional, un tamaño de pila, una tasa de deterioro, una descripción y controladores de eventos del lado del cliente o del servidor. Comprender el esquema completo de definición de objetos te permite crear objetos que hagan exactamente lo que necesitan tus scripts.

-- data/items.lua
return {
    ['water_bottle'] = {
        label = 'Water Bottle',
        weight = 500,
        stack = true,
        close = true,
        description = 'A refreshing bottle of water',
        client = {
            image = 'water_bottle.png',
        }
    },

    ['lockpick'] = {
        label = 'Lockpick',
        weight = 200,
        stack = true,
        close = true,
        degrade = 300,
        description = 'Used to pick locks. Breaks after use.',
    },

    ['driver_license'] = {
        label = 'Driver License',
        weight = 0,
        stack = false,
        consume = 0,
        description = 'Issued by the DMV',
        client = {
            image = 'driver_license.png',
        }
    },
}

Usar la API de servidor de ox_inventory

Los exports del lado del servidor son la parte más utilizada de ox_inventory, ya que permiten añadir y quitar objetos, consultar el contenido del inventario y manipular metadatos. Usa siempre la API del lado del servidor para manipular objetos y evitar que los tramposos exploten el sistema.

-- Server-side: Adding items to a player
RegisterNetEvent('myresource:giveReward', function(itemName, count)
    local src = source
    local success = exports.ox_inventory:AddItem(src, itemName, count)

    if success then
        TriggerClientEvent('ox_lib:notify', src, {
            title = 'Item Received',
            description = count .. 'x ' .. itemName,
            type = 'success'
        })
    else
        TriggerClientEvent('ox_lib:notify', src, {
            title = 'Inventory Full',
            description = 'Could not add item to inventory',
            type = 'error'
        })
    end
end)

-- Server-side: Check if player has required items
local function HasRequiredItems(src, requirements)
    for _, req in ipairs(requirements) do
        local count = exports.ox_inventory:GetItemCount(src, req.name)
        if count < req.amount then
            return false, req.name, req.amount - count
        end
    end
    return true
end

-- Server-side: Remove multiple items in a transaction
local function ConsumeRecipeItems(src, recipe)
    for _, ingredient in ipairs(recipe.ingredients) do
        local removed = exports.ox_inventory:RemoveItem(
            src, ingredient.name, ingredient.amount
        )
        if not removed then
            print(('[ERROR] Failed to remove %s from player %d'):format(
                ingredient.name, src
            ))
            return false
        end
    end
    return true
end

Trabajar con metadatos de objetos

Los metadatos de objetos son una de las funciones más potentes de ox_inventory. Te permiten adjuntar datos arbitrarios a instancias individuales de objetos, lo que posibilita asignar números de serie únicos a las armas, fechas de caducidad a la comida, nombres de jugadores a los documentos de identidad y propiedades personalizadas a cualquier objeto.

-- Server: Create a driver license with metadata
RegisterNetEvent('myresource:issueLicense', function(targetId, licenseType)
    local src = source

    local metadata = {
        type = licenseType,
        issued = os.date('%Y-%m-%d'),
        issuedBy = GetPlayerName(src),
        holder = GetPlayerName(targetId),
        expires = os.date('%Y-%m-%d', os.time() + 30 * 86400),
    }

    exports.ox_inventory:AddItem(targetId, 'driver_license', 1, metadata)
end)

-- Client: Reading metadata when using an item
exports('driver_license', function(data, slot)
    local item = exports.ox_inventory:GetSlot(slot)
    if not item or not item.metadata then return end

    local meta = item.metadata
    lib.notify({
        title = 'Driver License',
        description = ('Holder: %s\nType: %s\nExpires: %s'):format(
            meta.holder or 'Unknown',
            meta.type or 'Standard',
            meta.expires or 'N/A'
        ),
        type = 'inform'
    })
end)

Crear tiendas personalizadas

ox_inventory incluye un sistema de tiendas integrado que puedes configurar con catálogos de objetos personalizados, precios, restricciones por trabajo y ubicaciones. Las tiendas se definen en data/shops.lua y pueden asociarse a vendedores ped, ubicaciones de blips o activarse mediante programación.

-- data/shops.lua
return {
    ['hardware_store'] = {
        name = 'Hardware Store',
        inventory = {
            { name = 'lockpick',    price = 150,  count = 10 },
            { name = 'screwdriver', price = 80,   count = 20 },
            { name = 'radio',       price = 250,  count = 5  },
            { name = 'repairkit',   price = 1000, count = 5  },
        },
        locations = {
            vec3(45.6, -1749.3, 29.6),
            vec3(2747.8, 3472.9, 55.7),
        },
        targets = {
            ped = 's_m_y_hardware_01',
            scenario = 'WORLD_HUMAN_STAND_IMPATIENT',
            distance = 2.5,
        },
    },
}

Sistema de almacenes y contenedores personalizados

Los almacenes son contenedores de almacenamiento persistentes a los que los jugadores pueden acceder en ubicaciones específicas. ox_inventory admite almacenes personales vinculados al identificador de un jugador, almacenes compartidos accesibles para cualquiera y almacenes restringidos por trabajo para salas de pruebas de la policía y depósitos hospitalarios.

-- Server: Register a custom stash for a property
local function CreatePropertyStash(propertyId, owner)
    local stashId = ('property_%s'):format(propertyId)

    exports.ox_inventory:RegisterStash(
        stashId,
        ('Property #%s Storage'):format(propertyId),
        100,     -- slots
        200000,  -- max weight
        owner    -- owner identifier (or false for shared)
    )

    return stashId
end

-- Client: Open a stash when interacting with a storage point
RegisterNetEvent('myresource:openPropertyStorage', function(propertyId)
    local stashId = ('property_%s'):format(propertyId)
    exports.ox_inventory:openInventory('stash', stashId)
end)

Buenas prácticas para la integración con ox_inventory

  • Valida siempre en el servidor. Nunca confíes en las comprobaciones del inventario del lado del cliente. Usa exports del servidor como GetItemCount y RemoveItem para toda la lógica crítica del juego.
  • Usa los metadatos con moderación. Aunque los metadatos son potentes, almacenar demasiados datos en cada objeto aumenta el tamaño de la base de datos y el tráfico de red. Almacena solo lo que realmente necesites.
  • Gestiona con elegancia los inventarios llenos. Comprueba siempre el valor de retorno de AddItem y avisa claramente al jugador cuando su inventario esté lleno.
  • Usa el desgaste de los objetos para mayor realismo. La propiedad degrade crea sumideros naturales de objetos que mantienen tu economía equilibrada. Establece tiempos de desgaste adecuados para los productos perecederos y las herramientas.
  • Aprovecha el sistema de creación integrado. En lugar de crear tu propia lógica de creación, usa las mesas de creación de ox_inventory, que gestionan automáticamente las comprobaciones, la eliminación y la creación de objetos.
  • Mantén la coherencia en las imágenes de los objetos. Coloca todas las imágenes de los objetos en web/images/ con nombres de archivo coincidentes. Usa archivos PNG de 100x100 con fondos transparentes para obtener el aspecto más limpio.

¿Listo para empezar?

Consigue los scripts en nuestra tienda, o únete al Discord para soporte, novedades y un adelanto de lo que viene.