Files
esx_core/mysql-async
EbenSantuy 5b591a94b5 This I made for people who cant configure the esx_kashacters and to fix all the issue ! thanks to KASH to make this nice Feature
Thanks You KASH (github.com/KASHZIN)Who The Original Develop This ESX_KASHACTERS RELEASE And To for the tutorial XxFri3ndlyxX (github.com/XxFri3ndlyxX)

this tutorial i made little bit use XxFri3ndlyxX tutorial

1.Step One [ essentialmode\client\main.lua ]

Delete Or Replace This !
--[[Citizen.CreateThread(function()
	while true do
		Citizen.Wait(0)

		if NetworkIsSessionStarted() then
			TriggerServerEvent('es:firstJoinProper')
			TriggerEvent('es:allowedToSpawn')
			return
		end
	end
end)]]--

2.Step Two [ es_extended [ LINE : 457 ] client/main.lua ]
This To Fix Cant Open Inventory When You Die And Get Revived

Change You Menu interactions to this !
``` ---Menu interactions
Citizen.CreateThread(function()
	while true do
		
		Citizen.Wait(0)

		if IsControlJustReleased(0, 289) and IsInputDisabled(0) and not ESX.UI.Menu.IsOpen('default', 'es_extended', 'inventory') then
			ESX.ShowInventory()
		end

	end
end)```

3. Step Three 
To Get Your esx_kashacters work you need do this on your database

SELECT * FROM INFORMATION_SCHEMA.COLUMNS WHERE COLUMN_NAME = 'owner'
And This
SELECT * FROM INFORMATION_SCHEMA.COLUMNS WHERE COLUMN_NAME = 'indentifier'
Credit @Xnubil

6. Step Six [Fix Datastore]
Duplicate Your esx_datastore or add This line on your esx_datastore server\main.lua

-- Fix was taken from this link --
-- https://forum.fivem.net/t/release-esx-kashacters-multi-character/251613/448?u=xxfri3ndlyxx --
AddEventHandler('esx:playerLoaded', function(source)

  local result = MySQL.Sync.fetchAll('SELECT * FROM datastore')

	for i=1, #result, 1 do
		local name   = result[i].name
		local label  = result[i].label
		local shared = result[i].shared

		local result2 = MySQL.Sync.fetchAll('SELECT * FROM datastore_data WHERE name = @name', {
			['@name'] = name
		})

		if shared == 0 then

			table.insert(DataStoresIndex, name)
			DataStores[name] = {}

			for j=1, #result2, 1 do
				local storeName  = result2[j].name
				local storeOwner = result2[j].owner
				local storeData  = (result2[j].data == nil and {} or json.decode(result2[j].data))
				local dataStore  = CreateDataStore(storeName, storeOwner, storeData)

				table.insert(DataStores[name], dataStore)
			end
		end
	end

	local _source = source
	local xPlayer = ESX.GetPlayerFromId(_source)
  	local dataStores = {}
  
	for i=1, #DataStoresIndex, 1 do
		local name      = DataStoresIndex[i]
		local dataStore = GetDataStore(name, xPlayer.identifier)

		if dataStore == nil then
			MySQL.Async.execute('INSERT INTO datastore_data (name, owner, data) VALUES (@name, @owner, @data)',
			{
				['@name']  = name,
				['@owner'] = xPlayer.identifier,
				['@data']  = '{}'
			})

			dataStore = CreateDataStore(name, xPlayer.identifier, {})
			table.insert(DataStores[name], dataStore)
		end

		table.insert(dataStores, dataStore)
	end

	xPlayer.set('dataStores', dataStores)
end)

Download Link : https://github.com/XxFri3ndlyxX/esx_datastore
Credits : https://github.com/XxFri3ndlyxX

5. Step Five [ Fix Ambulance ]
This To Fix Die Tele And When Your Get Revived You Cant Open any Menu only F2

Download My File the esx_ambulancejob (or download the lastest version esx_ambulancejob :v)

6. Step Six [ Fix your esx_kashacters identifier ]
Download My mysql-async And start on your server.cfg

7. Step Seven [ Fix Your Identifier And Spawn] 
Download My esx_kashacters Modified And start on your server.cfg
Thats All Identifier [esx_kashacters\server\main.lua] maybe thats all
you need in Roleplay Server if you wan to change just change it 

===--------------------------------------------------------------------===

Okey Thats All Make My esx_kashacters work properly if you wanna ask
My Discord : Blue.#5108

Thank you Again to KASH And XxFri3ndlyxX ! :)
ENJOY YOUR ESX_KASHACTERS
2019-07-17 15:26:07 +07:00
..

MySQL Async Library for FiveM

This library intends to provide function to connect to a MySQL library in a Sync and Async Way.

Disclaimer

This mod does not replace EssentialMode, it offers instead a way of connecting to MySQL from lua-scripts, but it will never contain any gameplay logic. It will remain a simple wrapper around MySQL functions.

All feedback is appreciated in order to deliver a stable release.

Installation

Install the content of this repository in the resources/mysql-async folder. Name of the folder matters, do not use a different name (otherwise you must have knowledge on how this works and make the appropriate changes)

Once installed, you will need to add this line of code in the resource file of each mod needing a MySQL client:

server_script '@mysql-async/lib/MySQL.lua'

Warning

On Linux servers, users need to stick with the old mysql-async 2.x at least for the moment, due to some issues the linux server has with v8/javascript.

It can be downloaded from https://github.com/brouznouf/fivem-mysql-async/tree/2.0 or the release section. Note that the connection_string is different for 3.0.0 and 2.x.

Configuration

Add this convar to your server configuration and change the values according to your MySQL installation:

set mysql_connection_string "mysql://username:password@host/database?dateStrings=true"

Further options can be found under https://github.com/mysqljs/mysql#connection-options

Usage

Waiting for MySQL to be ready

You need to encapsulate your code into MySQL.ready to be sure that the mod will be available and initialized before your first request.

MySQL.ready(function ()
    print(MySQL.Sync.fetchScalar('SELECT @parameters', {
        ['@parameters'] =  'string'
    }))
end)

Async

MySQL.Async.execute(string query, array params, function callback)

Works like MySQL.Sync.execute but will return immediatly instead of waiting for the execution of the query. To exploit the result of an async method you must use a callback function:

MySQL.Async.execute('SELECT SLEEP(10)', {}, function(rowsChanged)
    print(rowsChanged)
end)

MySQL.Async.fetchAll(string query, array params, function callback)

Works like MySQL.Sync.fetchAll and provide callback like the MySQL.Async.execute method:

MySQL.Async.fetchAll('SELECT * FROM player', {}, function(players)
    print(players[1].name)
end)

MySQL.Async.fetchScalar(string query, array params, function callback)

Same as before for the fetchScalar method.

MySQL.Async.fetchScalar("SELECT COUNT(1) FROM players", function(countPlayer)
    print(countPlayer)
end

Sync

Sync functions can block the main thread, always prefer the Async version if possible, there is very rare use case for you to use this.

MySQL.Sync.execute(string query, array params) : int

Execute a mysql query which should not send any result (like a Insert / Delete / Update), and will return the number of affected rows.

MySQL.Sync.execute("UPDATE player SET name=@name WHERE id=@id", {['@id'] = 10, ['@name'] = 'foo'})

MySQL.Sync.fetchAll(string query, array params) : object[]

Fetch results from MySQL and returns them in the form of an Array of Objects:

local players = MySQL.Sync.fetchAll('SELECT id, name FROM player')
print(players[1].id)

MySQL.Sync.fetchScalar(string query, array params) : mixed

Fetch the first field of the first row in a query:

local countPlayer = MySQL.Sync.fetchScalar("SELECT COUNT(1) FROM players")

Features

  • Async / Sync
  • It uses the https://github.com/mysqljs/mysql library to provide a connection to your mysql server.
  • Create and close a connection for each query, the underlying library use a connection pool so only the mysql auth is done each time, old tcp connections are keeped in memory for performance reasons

Credits

Some parts of this library, and also my understanding were directly inspired by "Essential Mode", thanks to them to have begin to work on this, which allows guy like me to not start from scratch every time...