QBOX Framework – Guia Completo
Sobreestendido (Ox) é a linha de base moderna para servidores FiveM. Este guia mostra como instalar, configurar e migrar com segurança para inventário de bois, boi_lib, boi_alvo, e oxmysqlVocê obterá código copiável e colável, padrões opinativos e padrões testados em batalha para interface do usuário, interações e dados. Inclui manuais para qb-inventário → ox_inventário e mysql-async → oxmysql. Faça backup do seu servidor e banco de dados antes de qualquer alteração.
TL;DR: Qual componente do Ox para quê?
| Componente | Propósito | APIs principais | Uso típico | Caminho de Migração | Pegadinhas comuns |
|---|---|---|---|---|---|
| inventário de bois | Inventário e itens, estoques, lojas | Adicionar item, RemoverItem, RegisterStash, RegisterShop | Itens de jogador, reservas de empregos, lojas de vendedores | qb-inventário → ox_inventário | Esquema de item incorreto, invs duplicadas em execução, ausentes garantir ordem |
| boi_lib | Utilitários, UI, ajudantes | adicionarComando, registrarContexto/mostrarContexto, caixa de diálogo de entrada, barra de progresso, zonas/pontos | Menus, avisos, limites de taxa, lógica de zona | N / D | Misturando bibliotecas de UI, sem esperar retornos de chamada |
| boi_alvo | Segmentação de interação | addBoxZone, addSphereZone, adicionarEntidade, adicionarModelo | Alvos de visão em adereços/pedais/zonas | qtarget → ox_target (opcional) | Zonas sobrepostas, condições de trabalho ausentes |
| oxmysql | Driver MySQL | consulta, solteiro, escalar, inserir, preparar, transação | Persistência de BD, tabelas de classificação, auditorias | mysql-async → oxmysql | Consultas não indexadas, concat de strings inseguras |
Dica: Comece com oxmysql e boi_lib, então migre inventário e alvo. Valide cada etapa em um servidor de preparação.
Relacionado: https://fivemx.com/frameworks/ · https://fivemx.com/framework-conversion/
Pré-requisitos e linha de base
- Artefato de servidor recente, administrador do tx, e uma estrutura (QBCore ou ESX).
- O Node.js não é necessário para o Ox, mas sua pilha NUI (se houver) pode usá-lo.
- Ordem de início dos recursos:
oxmysql→boi_lib→inventário de bois→ o resto. Coloque boi_alvo precoce entre bibliotecas de UI/interação. - Lista de verificação:
- O firewall permite tráfego de banco de dados; o usuário do banco de dados tem menos privilégios.
- Defina convars de produção vs. desenvolvimento; habilite avisos de consulta lenta no preparo.
- Backups para configurações de banco de dados e recursos.
Relacionado: https://fivemx.com/how-to-install-qbcore/ · https://fivemx.com/how-to-customize-qbcore-scripts/ · https://fivemx.com/qbcore-scripts/
Instalar e configurar: ox_inventory
Instalar
Adicione o recurso e certifique-se de que depois boi_lib.
-- recursos/[ox]/ox_inventory/fxmanifest.lua (trecho) versão_fx 'cerúleo' jogo 'gta5' lua54 'sim' scripts_compartilhados { '@ox_lib/init.lua', 'config.lua' } scripts_cliente { 'cliente/*.lua' } scripts_servidor { '@oxmysql/lib/MySQL.lua', 'servidor/*.lua' }
servidor.cfg:
garantir oxmysql garantir ox_lib garantir ox_inventory
Configuração principal
Defina itens (peso, pilha, metadados). Caminho típico: ox_inventory/dados/itens.lua.
retornar { água = { rótulo = 'Garrafa de água', peso = 200, pilha = verdadeiro, fechar = verdadeiro, descrição = 'Mantenha-se hidratado.' }, sanduíche = { rótulo = 'Sanduíche', peso = 300, pilha = verdadeiro } }
Registre um esconderijo e um comprar no início do servidor:
-- server/stash_shop.lua CreateThread(function() exports.ox_inventory:RegisterStash('pd_evidence', 'Provas policiais', 100, 100000, false, {police = 2}) exports.ox_inventory:RegisterShop('corner_store', { name = '24/7 Market', inventory = { { name = 'water', price = 8 }, { name = 'sandwich', price = 12 } } }) end)
Noções básicas de interface do usuário
- Arrastar e soltar, dividir, empilhar; teclas de atalho configuráveis.
- Usar metadados para seriados, qualidades, expiração.
Teste rápido
Dê a si mesmo um item e abra o inventário:
-- server/debug.lua RegisterCommand('giveme', função(fonte) exports.ox_inventory:AddItem(fonte, 'água', 1) fim, verdadeiro)
Erros comuns
Aviso: Fazer não Execute dois inventários ao mesmo tempo. Desabilite completamente o qb-inventory antes de habilitar o ox_inventory.
Dica: Item de correspondência nomes exatamente entre trabalhos/criação e dados de inventário.
Relacionado: https://fivemx.com/fivem-inventory-scripts/ · https://fivemx.com/qbcore-scripts/
Instalar e configurar: ox_lib
Essenciais
Essencial Ferramentas que você usará em todos os lugares:
-- Comandos lib.addCommand('healme', { help = 'Cure-se (somente administrador).', restricted = 'group.admin' }, function(origem) TriggerClientEvent('fivemx:heal', origem) fim) -- Menus de contexto lib.registerContext({ id = 'shop_menu', title = 'Mercado 24/7', options = { { title = 'Comprar água ($8)', event = 'fivemx:comprar', args = { item = 'água', preço = 8 } }, { title = 'Comprar sanduíche ($12)', event = 'fivemx:comprar', args = { item = 'sanduíche', preço = 12 } } } }) -- mais tarde lib.showContext('shop_menu')
Mini livro de receitas
- Caixa de diálogo de entrada & progresso com fluxo aguardável:
-- entrada local do cliente = lib.inputDialog('Craft Coffee', { { tipo = 'número', rótulo = 'Grãos (g)', padrão = 18, min = 1, máx = 60 } }) se entrada então local ok = lib.progressBar({ duração = 3500, rótulo = 'Preparando…', useWhileDead = false, canCancel = true }) se ok então TriggerServerEvent('fivemx:craft:coffee', entrada[1]) fim fim
- Retornos de chamada (o servidor valida, o cliente aguarda):
-- servidor lib.callback.register('fivemx:buyItem', function(src, item, price) -- valida trabalho/coordenadas/etc. e então cobra + concede -- retorna verdadeiro/falso e a mensagem retorna exports.ox_inventory:AddItem(src, item, 1) end) -- sucesso local do cliente = lib.callback.await('fivemx:buyItem', false, 'water', 8)
Relacionado: https://fivemx.com/frameworks/ · https://fivemx.com/framework-conversion/
Instalar e configurar: ox_target
Entidades e ossos
Anexar ações a ações específicas pedestres/veículos/objetos ou seus ossos.
-- direcionar uma entidade por modelo exports.ox_target:addModel(`prop_vend_soda_02`, { { name = 'vending_buy', icon = 'fa-solid fa-bottle-water', label = 'Comprar uma bebida', onSelect = function(data) TriggerEvent('fivemx:openVending') end } })
Zonas
Crie caixas/esferas/polígonos 3D com condições de trabalho.
-- Zona de caixa na frente da caixa registradora exports.ox_target:addBoxZone({ coords = vec3(25.7, -1347.3, 29.5), size = vec3(1.6, 1.2, 1.0), rotation = 0.0, debug = false, options = { { label = 'Open Shop', icon = 'fa-solid fa-store', groups = { police = 0, ambulance = 0 }, -- anyone; exemplo de filtro de grupo onSelect = function() lib.showContext('shop_menu') end } } })
Exemplos
- Alvo de esconderijo para evidências policiais.
- Criação de empregos controlados dentro de uma oficina.
Relacionado: https://fivemx.com/qbcore-scripts/ · https://fivemx.com/fivem-inventory-scripts/
Instalar e configurar: oxmysql
Por que oxmysql
- Instruções preparadas, pooling, API async/await.
- Melhor desempenho e segurança do que string-concat SQL.
Folha de dicas da API
-- ler muitas linhas locais = MySQL.query.await('SELECT id, name FROM players WHERE job = ?', { 'police' }) -- ler uma única linha local player = MySQL.single.await('SELECT * FROM players WHERE identifier = ?', { identifier }) -- valor escalar local count = MySQL.scalar.await('SELECT COUNT(*) FROM stash_items WHERE stash = ?', { 'pd_evidence' }) -- inserir id local = MySQL.insert.await('INSERT INTO logs (event, source) VALUES (?, ?)', { 'buy_water', src }) -- informações locais preparadas e armazenadas em cache = MySQL.prepare.await('SELECT label, weight FROM items WHERE name = ?', { 'water' }) -- transação MySQL.transaction.await(function() MySQL.query.await('UPDATE accounts DEFINIR dinheiro = dinheiro - ? ONDE identificador = ?', { 12, identificador }) MySQL.query.await('INSERIR EM compras (identificador, item) VALORES (?, ?)', { identificador, 'sanduíche' }) fim)
Índices e higiene de esquema
ALTER TABLE jogadores ADD INDEX idx_players_identifier (identificador); ALTER TABLE compras ADD INDEX idx_purchases_identifier_created (identificador, criado_em);
Tratamento de erros
Dica: Habilite avisos de consulta lenta no preparo e adicione índices adequados antes do lançamento.
Relacionado: https://fivemx.com/mysql-async-to-oxmysql/ · https://fivemx.com/sql-identifiers-migration/ · https://fivemx.com/converting-fivem-scripts/
Manuais de Migração (prontos para copiar e colar)
qb-inventário → ox_inventário
Mapeamento de conceitos
| Conceito | qb-inventário | inventário de bois |
|---|---|---|
| Unid | qb-core/compartilhado/itens.lua | ox_inventory/dados/itens.lua |
| Esconderijos | Lógica de esconderijo de trabalho/jogador em scripts | RegisterStash(id, rótulo, slots, peso, proprietário, grupos, coordenadas) |
| Lojas | qb-shops ou customizados | RegisterShop(id, { inventário = {..} }) |
Passos
- Desabilite qb-inventory e quaisquer UIs dependentes de inventário.
- Instalar boi_lib, inventário de bois, oxmysql nessa ordem.
- Itens de porta →
dados/itens.lua(preservar nomes/pesos/metadados). - Substituir chamadas de adição/remoção de itens por
exports.ox_inventory:AdicionarItem/RemoverItem. - Registre stashes/lojas no lado do servidor; migre dados salvos do stash, se aplicável.
- Teste em preparação; verifique arrastar/empilhar/dividir e esconderijos de trabalhos.
Lista de verificação (antes/depois)
| Área | Antes | Depois | Risco |
|---|---|---|---|
| Recursos | qb-inventário habilitado | qb-inventory removido, ox_inventory garantido | Baixo |
| Unid | itens em qb compartilhados | itens em dados/itens.lua | Médio (nomeação) |
| Esconderijos | implícito | explícito RegisterStash | Baixo |
| Lojas | lojas de qb | RegisterShop | Baixo |
Exemplo: adicionar/remover substituir
-- antes (pseudocódigo qb-inventory) -- QBCore.Functions.AddItem(fonte, 'água', 1) -- depois (ox_inventory) exports.ox_inventory:AddItem(fonte, 'água', 1) exports.ox_inventory:RemoveItem(fonte, 'sanduíche', 1)
Relacionado: https://fivemx.com/fivem-inventory-scripts/
mysql-async → oxmysql
Padrões de pesquisa/substituição
| chamada mysql-async | equivalente oxmysql |
|---|---|
MySQL.Async.fetchAll(sql, parâmetros, cb) | MySQL.query(sql, parâmetros) / .aguardar |
MySQL.Async.fetchScalar(sql, parâmetros, cb) | MySQL.scalar(sql, parâmetros) / .aguardar |
MySQL.Async.execute(sql, parâmetros, cb) | MySQL.query(sql, parâmetros) ou MySQL.update/inserir / .aguardar |
concat de strings "..var.." | ? marcadores de posição com matriz de parâmetros |
| manual INICIAR/COMMITIR | MySQL.transaction.await(função() ... fim) |
Exemplo de refatoração
-- antes de MySQL.Async.fetchAll('SELECT * FROM usuários ONDE identificador = @id', { ['@id'] = identificador }, função(linhas) -- usar linhas fim) -- depois de linhas locais = MySQL.query.await('SELECT * FROM usuários ONDE identificador = ?', { identificador })
Declarações preparadas
usuário local = MySQL.prepare.await('SELECIONE id, trabalho DE usuários ONDE identificador = ?', { identificador })
Aviso: Nunca confie na entrada do cliente. Sempre valide na servidor e use marcadores de posição.
Relacionado: https://fivemx.com/mysql-async-to-oxmysql/ · https://fivemx.com/sql-identifiers-migration/ · https://fivemx.com/converting-fivem-scripts/
Padrões que vendem: criando empregos e UI com a pilha Ox
Um trabalho de entrega mínimo que vincula boi_alvo (interagir), boi_lib (IU), inventário de bois (recompensas) e oxmysql (auditoria).
-- client/jobs_delivery.lua local drop = vec3(120.4, -1039.2, 29.2) exports.ox_target:addBoxZone({ coords = drop, size = vec3(1.4, 1.0, 1.0), rotation = 340.0, options = { { name = 'deliver_crate', label = 'Entregar caixa', icon = 'fa-solid fa-box', onSelect = function() local ok = lib.progressBar({ duration = 4000, label = 'Deixando…' }) if ok then TriggerServerEvent('fivemx:job:deliverCrate') end end } } })
-- server/jobs_delivery.lua RegisterNetEvent('fivemx:job:deliverCrate', function() local src = source -- limite de taxa por minuto (muito simples) local ok = exports.ox_inventory:AddItem(src, 'water', 1) se ok então MySQL.insert.await('INSERT INTO job_logs (identifier, event) VALUES (?, ?)', { GetPlayerIdentifier(src, 0), 'deliver_crate' }) TriggerClientEvent('ox_lib:notify', src, { title = 'Entrega', description = 'Você recebeu Água x1', type = 'success' }) end end)
Relacionado: https://fivemx.com/qbcore-scripts/ · https://fivemx.com/fivem-inventory-scripts/
Desempenho e Segurança
- Elimine as interações de alvos; evite zonas sobrepostas.
- Armazena em cache leituras frequentes; índice colunas usadas em WHERE/JOIN.
- Mantenha os tiques do servidor baixos; mova os loops pesados para fora do thread principal.
- Segurança: valide o lado do servidor, limite a taxa de ações econômicas, registre eventos confidenciais.
Dica: Ative avisos de consulta lenta no preparo; envie índices com migrações.
Relacionado: https://fivemx.com/converting-fivem-scripts/ · https://fivemx.com/sql-identifiers-migration/
Depuração e teste de equipamentos
- Adicionar depuração comandos protegidos por permissões.
- Registre falhas no banco de dados e faça curto-circuito em erros.
- Teste o hot-reload reiniciando recursos individuais (não a pilha inteira).
lib.addCommand('oxping', { help = 'Verificação de integridade', restricted = 'group.admin' }, function(src) local ok = MySQL.scalar.await('SELECT 1') == 1 TriggerClientEvent('ox_lib:notify', src, { title = 'Ox Health', description = ok e 'DB OK' ou 'DB FAIL', type = ok e 'success' ou 'error' }) end)
Relacionado: https://fivemx.com/frameworks/ · https://fivemx.com/framework-conversion/
Recursos internos e próximos passos
- Estruturas: https://fivemx.com/frameworks/ · https://fivemx.com/framework-conversion/
- QBCore: https://fivemx.com/how-to-install-qbcore/ · https://fivemx.com/how-to-customize-qbcore-scripts/ · https://fivemx.com/qbcore-scripts/
- Migrações: https://fivemx.com/mysql-async-to-oxmysql/ · https://fivemx.com/sql-identifiers-migration/ · https://fivemx.com/converting-fivem-scripts/
- Centro de inventário: https://fivemx.com/fivem-inventory-scripts/
Navegue pela loja para scripts testados que seguem esses padrões.
Perguntas frequentes
Ox_inventory é mais rápido que qb-inventory?
Em geral, sim. Ele enfatiza a eficiência da interface do usuário e das operações do lado do servidor, com padrões sensatos para pilhas, pesos e metadados.
Posso misturar qb-inventory e ox_inventory?
Não recomendado. Interrompa o qb-inventory completamente antes de habilitar o ox_inventory para evitar manipuladores duplicados e dessincronização de itens.
Preciso reescrever o SQL para oxmysql?
Principalmente pesquisar/substituir. Substituir concat de strings por espaços reservados, adotar *.aguarde APIs e adicionar índices ausentes.
Como posso proteger interações ox_target?
Usar grupos/job verifica o lado do cliente, mas sempre revalida no servidor (distância, trabalho, propriedade do item) antes das recompensas.
E quanto à compatibilidade com o ESX?
A pilha Ox é independente de framework. Mapeie eventos ESX para manipuladores de servidor e mantenha os nomes de inventário consistentes.
Como faço benchmark de chamadas de banco de dados?
Use EXPLAIN, ative avisos de consulta lenta e compare os tempos antes/depois de adicionar índices.
Onde defino itens para ox_inventory?
Em ox_inventory/dados/itens.lua. Mantenha os rótulos curtos e os pesos realistas.
Posso manter o qtarget enquanto migro para o ox_target?
Temporariamente, mas evite zonas sobrepostas. Migre recurso por recurso e remova o qtarget quando a paridade for atingida.
Como faço para migrar dados do stash?
Criar equivalente RegisterStash entradas e execute SQL para renomear os IDs antigos do stash para as novas chaves, se necessário. Teste em preparação.
Como defino pesos e limites?
Pesos vivem em itens.lua. As capacidades de estoque/loja são parte de RegisterStash/RegisterShop argumentos.
Como faço para limitar a taxa de compras ou trabalhos?
Usar lib.addCommand/callbacks com resfriamentos simples na memória e validação no lado do servidor.
O oxmysql suporta transações?
Sim - envolva sequências atômicas em MySQL.transaction.await(função() ... fim).
Como lidar com NUI com Ox?
O Ox funciona bem com qualquer NUI; basta manter uma lógica de interface de usuário pesada no lado do cliente e validações no lado do servidor.
Qual é a ordem de migração mais segura?
oxmysql → ox_lib → ox_inventory → ox_target. Valide após cada etapa.
Registro de alterações e créditos
| Versão | Data | Notas |
|---|---|---|
| v1.0 | 2025-09-05 | Publicação inicial com manuais de instalação, configuração e migração. |
Última atualização: 2025-09-05
Créditos e fontes: Documentação extensa (ox_inventory, ox_lib, ox_target), referência oxmysql, documentação Cfx.re e melhores práticas da comunidade.
Conclusão e próximos passos
Ambas as estruturas podem administrar uma cidade de alto nível. A diferença está no legado que você deseja transmitir e no quão padronizado você deseja que seu futuro seja.
Próximos passos:
- Explorar Scripts QBOX → https://fivemx.com/qbox-scripts/
- Explorar Scripts QBCore → https://fivemx.com/qbcore-scripts/
- Leia mais em Conversão de estrutura → https://fivemx.com/framework-conversion
Referências externas (saiba mais)
- QBOX GitHub (qbx_core) → https://github.com/Qbox-project/qbx_core
- QBCore GitHub (qb-core) → https://github.com/qbcore-framework/qb-core
- Documentação FiveM — Manifesto de Recursos (fxmanifest.lua) → https://docs.fivem.net/docs/scripting-reference/resource-manifest/resource-manifest/






