ElRaulxX Posted January 31, 2013 Report Share Posted January 31, 2013 He visto que muchos preguntáis como utilizar querys de sql en quest. Le dije a keko que haría este mini tutorial, y aquí lo tenéis. Primero de todo decir que esta función no viene por defecto en el metin y es por eso que algunos usuarios la han hecho ellos mismos, pues la utilidad de esta función es muy grande. Tengo contado tres personas que han publicado esta función: Hanashi, mijago y yuko. Quizá han sido publicadas más, pero solamente recuerdo estas. A mi parecer, la más practica que he visto hasta ahora es la última versión de mijago y es la que utilizaremos en este Minicurso. Primero de todo, debemos declarar estas dos funciones en nuestro questlib.lua mysql_query = function(query) if not pre then local rt = io.open('CONFIG','r'):read('*all') pre,_= string.gsub(rt,'.+PLAYER_SQL:%s(%S+)%s(%S+)%s(%S+)%s(%S+).+','-h%1 -u%2 -p%3 -D%4') end math.randomseed(os.time()) local fi,t,out = 'mysql_data_'..math.random(10^9)+math.random(2^4,2^10),{},{} os.execute('mysql '..pre..' --e='..string.format('%q',query)..' > '..fi) -- für MySQL51 -- os.execute('mysql '..pre..' -e'..string.format('%q',query)..' > '..fi) -- für MySQL55 for av in io.open(fi,'r'):lines() do table.insert(t,split(av,'t')) end; os.remove(fi); for i = 2, table.getn(t) do table.foreach(t[i],function(a,b) out[i-1] = out[i-1] or {} out[i-1][a] = tonumber(b) or b or 'NULL' out[t[1][a]] = out[t[1][a]] or {} out[t[1][a]][i-1] = tonumber(b) or b or 'NULL' end) end return outendfunction split(str, delim, maxNb) if str == nil then return str end if string.find(str, delim) == nil then return { str } end if maxNb == nil or maxNb < 1 then maxNb = 0 end local result = {} local pat = "(.-)" .. delim .. "()" local nb = 0 local lastPos for part, pos in string.gfind(str, pat) do nb = nb + 1 result[nb] = part lastPos = pos if nb == maxNb then break end end if nb ~= maxNb then result[nb + 1] = string.sub(str, lastPos) end return resultend ATENCION! Si en nuestro servidor tenemos instalado la versión 5.5 de MySQL debemos borrar esto: os.execute('mysql '..pre..' --e='..string.format('%q',query)..' > '..fi) -- für MySQL51 y quitar las -- de aquí: --os.execute('mysql '..pre..' -e'..string.format('%q',query)..' > '..fi) -- für MySQL55 La razón es simple, la sintaxis de esta versión de MySQL es distinta. Ahora tenemos que añadir en quest_functions la función: mysql_query La función split no hace falta añadirla en este archivo ya que se utiliza internamente en mysql_query. Bien, ahora ya tenemos instalada la función de mysql. Ahora lo más importante: ¿cómo se usa? Tenemos esta tabla: Como vemos, la tabla se llama 'tablatest' y se encuentra en la db 'test'. Esta tabla posee tres campos, que son 'campo1', 'campo2' y 'campo3'. Con la función mysql_query llamaremos, añadiremos o modificaremos valores de esta tabla. La sintaxis de mysql_query es la misma que cualquier otra query de mysql que utilicemos (de navicat, php...). Sino sabéis la sintaxis os aconsejo que miréis cursos para aprender. La sintaxis es muy sencilla y no tiene complicación, solo se necesita mirar un poco y lo dominaréis perfectamente. Existen miles de cursos y tutoriales por internet de mysql, tan solo debéis buscarlos.ATENCION: Para utilizar sentencias que retornen algún tipo de valor (select) debemos asignar la función a una variable. Las demás (update, insert into...) tan solo tenemos que utilizarla como cualquier otra función. Bien, empecemos. Comenzaremos llamando toda la tabla. local read = mysql_query("SELECT * FROM test.tablatest") Esto almacenará en la variable la siguiente tabla: local read = {[campo1] = {"texto1","texto2","texto3"},[campo2] = {"texto4","texto5","texto6"},[campo3] = {"texto7","texto8","texto9"}} Teniendo esto en cuenta, y sabiendo un poco de tablas y arrays en lua está todo solucionado. Queremos mostrar en pantalla 'texto5' que está almacenado en nuestra tabla. Lo llamaremos de esta manera. local read = mysql_query("SELECT * FROM test.tablatest")say(read.campo2[2])--esto muestra texto5 Ahora queremos llamar 'texto9': local read = mysql_query("SELECT * FROM test.tablatest")say(read.campo3[3])--esto muestra texto9 Ahora queremos llamar 'texto1': local read = mysql_query("SELECT * FROM test.tablatest")say(read.campo1[1])--esto muestra texto1 Aquí no voy a ponerme a explicar arrays porqué no trata de eso el curso, pero creo que mirando los ejemplos y pensando un poco lo entenderéis. Ahora también podemos añadir una condición: local read = mysql_query("SELECT * FROM test.tablatest WHERE campo2 = 'texto5'") Esto almacenará en la variable la siguiente tabla: local read = {[campo2] = {"texto4","texto5","texto6"}} Y ahora podemos llamarlo de la misma manera que en el ejemplo anterior. Esto nos mostrará 'texto6' en pantalla. local read = mysql_query("SELECT * FROM test.tablatest WHERE campo2 = 'texto5'")say(read.campo2[3])--esto muestra texto6 Y para hacerla verdaderamente útil podemos llamar a variables o funciones. local var = "texto5"local read = mysql_query("SELECT * FROM test.tablatest WHERE campo2 = '"..var.."'")say(read.campo2[3])--esto muestra texto6 Algo importante que hay que decir es que esta función siempre crea tablas y por lo tanto siempre deberemos llamarlo de la misma manera, aunque haya seleccionado un solo valor. local read = mysql_query("SELECT campo1 FROM test.tablatest WHERE campo1 = 'texto1'")say(read.campo1[1])--esto muestra texto1 Creo que con estos ejemplos ya podéis ver como funciona un select (la verdad es que es bastante difícil explicarlo teniendo en cuenta que no tenéis conocimientos de tablas, pero al menos lo he intentado xd). La mejor manera que veáis su uso es que vayáis haciendo pruebas en navicat y luego trasladarlo a una quest. Y ahora la segunda parte. Si queremos añadir nuevos valores lo hacemos de esta manera: mysql_query("INSERT INTO test.tablatest VALUES ('texto10','texto11','texto12')") o como hemos hecho antes: local v1 = "texto10"local v2 = "texto11"local v3 = "texto12"mysql_query("INSERT INTO test.tablatest VALUES ('"..v1.."','"..v2.."','"..v3.."')") Y nos quedará la tabla así: Y si queremos modificar valores: mysql_query("UPDATE test.tablatest SET campo1='prueba' WHERE campo1='texto10'") local x = "prueba"local y = "texto10"mysql_query("UPDATE test.tablatest SET campo1='"..x.."' WHERE campo1='"..y.."'") Y nos quedaría esto: Sabiendo de mysql no debería ser ninguna complicación, el problema es que no sepáis Cuando publiquemos el capítulo de arrays y tablas lo entenderéis todo mejor, no os preocupéis. Y creo que eso es todo. Saludos! fuuton97, danielnire, ahynoa and 6 others 9 Link to comment Share on other sites More sharing options...
KeKo Posted January 31, 2013 Report Share Posted January 31, 2013 Al final la hiciste :raisins: Muy buena guia, mezclando mysql con quest se pueden hacer un monton de cosas útiles y gracias a tu minicurso sera mucho mas facil para muchos Kompulsor 1 Link to comment Share on other sites More sharing options...
PACI Posted January 31, 2013 Report Share Posted January 31, 2013 Si por ejemplo, hiciese: local a = select("Triton", "Baron", "Salir") if a == 1 then mysql_query("UPDATE player.item_proto SET refine_item='270' WHERE vnum='169'") elseif a == 2 then mysql_query("UPDATE player.item_proto SET refine_item='260' WHERE vnum='169'") end Entonces, haria como si el jugador escogiese la arma que quisiese obtener despues de transformar la primera, me equivoco? Link to comment Share on other sites More sharing options...
KeKo Posted January 31, 2013 Report Share Posted January 31, 2013 Si por ejemplo, hiciese: local a = select("Triton", "Baron", "Salir") if a == 1 then mysql_query("UPDATE player.item_proto SET refine_item='270' WHERE vnum='169'") elseif a == 2 then mysql_query("UPDATE player.item_proto SET refine_item='260' WHERE vnum='169'") end Entonces, haria como si el jugador escogiese la arma que quisiese obtener despues de transformar la primera, me equivoco? No existe ningun refine_item si no refined_vnum en el item_proto (aunque imagino que seria solo un ejemplo) pero sí que cambiaría al arma a la que forjaria con esa query. Sin embargo, no estoi seguro de que se pueda cambiar el campo refined_vnum sin tener que hacer un reboot despues en el servidor aunque sea via mysql_query, sería cosa de probarlo. Link to comment Share on other sites More sharing options...
PACI Posted January 31, 2013 Report Share Posted January 31, 2013 No existe ningun refine_item si no refined_vnum en el item_proto (aunque imagino que seria solo un ejemplo) pero sí que cambiaría al arma a la que forjaria con esa query. Sin embargo, no estoi seguro de que se pueda cambiar el campo refined_vnum sin tener que hacer un reboot despues en el servidor aunque sea via mysql_query, sería cosa de probarlo. Entonces no hay manera de hacer eso sin tener que dar reboot ?O crear por ejemplo una 2ª columna de refined_vnum y por quest hacer ese tipo de seleccion ? Link to comment Share on other sites More sharing options...
fuuton97 Posted January 31, 2013 Report Share Posted January 31, 2013 Excelente, guía. Link to comment Share on other sites More sharing options...
Ðro Posted October 20, 2013 Report Share Posted October 20, 2013 Buenas tardes, Tengo una dudita y es la siguiente, necesito saber la ip de x personaje, pero no se como iria la query para saber la ip dependiendo del nombre del pj, a ver si me echan una mano con eso. Gracias de antemano. EDIT: Ya la hice, esta es: local localip = mysql_query("SELECT ip FROM player.player WHERE name = '"..pc.get_name().."'") Link to comment Share on other sites More sharing options...
Recommended Posts