mirror of
https://github.com/KeymonSoft/jRDC-Multi.git
synced 2026-04-17 21:06:24 +00:00
- VERSION 5.08.30
- Se cambiaron los 4 handlers de B4A a uno solo que toma el DB de la ruta automáticamente. - Se agregaron validaciones del numero de parametros y si el query no los requiere o se dan de mas o de menos, manda un error especificando eso, ya no se reciben errores directos de la base de datos, esto fue tanto para B4A como para JSON. - Se modificó el Readme.md para incluir todos estos cambios.
This commit is contained in:
@@ -30,7 +30,6 @@ Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|||||||
Dim con As SQL
|
Dim con As SQL
|
||||||
Try
|
Try
|
||||||
con = Connector.GetConnection("DB1")
|
con = Connector.GetConnection("DB1")
|
||||||
Log("Metodo: " & method)
|
|
||||||
If method = "query2" Then
|
If method = "query2" Then
|
||||||
q = ExecuteQuery2("DB1", con, in, resp)
|
q = ExecuteQuery2("DB1", con, in, resp)
|
||||||
'#if VERSION1
|
'#if VERSION1
|
||||||
|
|||||||
@@ -4,158 +4,260 @@ ModulesStructureVersion=1
|
|||||||
Type=Class
|
Type=Class
|
||||||
Version=10.3
|
Version=10.3
|
||||||
@EndOfDesignText@
|
@EndOfDesignText@
|
||||||
'Handler class for JSON requests from Web Clients (JavaScript/axios)
|
' Handler class for JSON requests from Web Clients (JavaScript/axios)
|
||||||
'VERSION 14 (Validación de Parámetros): Chequea que el número de '?' coincida con los parámetros recibidos.
|
' VERSIÓN 16 (Comentarios y Mensajes en Español):
|
||||||
|
' - Se añaden comentarios detallados a la versión con mensajes de error en español.
|
||||||
|
' - Revisa que el 'query' exista en config.properties antes de continuar.
|
||||||
|
' - Asegura que la conexión a la BD se cierre en todos los 'Return' para evitar fugas.
|
||||||
Sub Class_Globals
|
Sub Class_Globals
|
||||||
Private Connector As RDCConnector
|
' Declara una variable privada para mantener una instancia del conector RDC.
|
||||||
|
' Este objeto maneja la comunicación con la base de datos.
|
||||||
|
Private Connector As RDCConnector
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
|
' Subrutina de inicialización de la clase. Se llama cuando se crea un objeto de esta clase.
|
||||||
|
' En este caso, no se necesita ninguna inicialización específica.
|
||||||
Public Sub Initialize
|
Public Sub Initialize
|
||||||
|
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
|
' Este es el método principal que maneja las peticiones HTTP entrantes (req) y prepara la respuesta (resp).
|
||||||
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
||||||
' --- Headers CORS ---
|
Log("============== DB1JsonHandler ==============")
|
||||||
resp.SetHeader("Access-Control-Allow-Origin", "*")
|
' --- Headers CORS (Cross-Origin Resource Sharing) ---
|
||||||
resp.SetHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS")
|
' Estos encabezados son necesarios para permitir que un cliente web (ej. una página con JavaScript)
|
||||||
resp.SetHeader("Access-Control-Allow-Headers", "Content-Type")
|
' que se encuentra en un dominio diferente pueda hacer peticiones a este servidor.
|
||||||
|
resp.SetHeader("Access-Control-Allow-Origin", "*") ' Permite peticiones desde cualquier origen.
|
||||||
|
resp.SetHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS") ' Métodos HTTP permitidos.
|
||||||
|
resp.SetHeader("Access-Control-Allow-Headers", "Content-Type") ' Encabezados permitidos en la petición.
|
||||||
|
|
||||||
If req.Method = "OPTIONS" Then Return
|
' El método OPTIONS es una "petición de comprobación previa" (preflight request) que envían los navegadores
|
||||||
|
' para verificar los permisos CORS antes de enviar la petición real (ej. POST).
|
||||||
|
' Si es una petición OPTIONS, simplemente terminamos la ejecución sin procesar nada más.
|
||||||
|
If req.Method = "OPTIONS" Then Return
|
||||||
|
|
||||||
Dim DB As String = "DB1"
|
' Establece "DB1" como el nombre de la base de datos por defecto.
|
||||||
Connector = Main.Connectors.Get(DB)
|
Dim DB As String = "DB1"
|
||||||
Dim con As SQL
|
' Obtiene el objeto conector para la base de datos por defecto desde el objeto Main.
|
||||||
|
Connector = Main.Connectors.Get(DB)
|
||||||
|
' Declara una variable para la conexión SQL.
|
||||||
|
Dim con As SQL
|
||||||
|
|
||||||
Try
|
' Inicia un bloque Try...Catch para manejar posibles errores durante la ejecución.
|
||||||
Dim jsonString As String = req.GetParameter("j")
|
Try
|
||||||
If jsonString = Null Or jsonString = "" Then
|
' Obtiene el valor del parámetro 'j' de la petición. Se espera que contenga una cadena JSON.
|
||||||
SendErrorResponse(resp, 400, "Missing 'j' parameter")
|
Dim jsonString As String = req.GetParameter("j")
|
||||||
Return
|
' Verifica si el parámetro 'j' es nulo o está vacío.
|
||||||
End If
|
If jsonString = Null Or jsonString = "" Then
|
||||||
|
' Si falta el parámetro, envía una respuesta de error 400 (Bad Request) y termina la ejecución.
|
||||||
Dim parser As JSONParser
|
SendErrorResponse(resp, 400, "Falta el parametro 'j' en el URL")
|
||||||
parser.Initialize(jsonString)
|
Return
|
||||||
Dim RootMap As Map = parser.NextObject
|
|
||||||
|
|
||||||
Dim execType As String = RootMap.GetDefault("exec", "")
|
|
||||||
Dim queryName As String = RootMap.Get("query")
|
|
||||||
Dim paramsMap As Map = RootMap.Get("params")
|
|
||||||
|
|
||||||
If RootMap.Get("dbx") <> Null Then DB = RootMap.Get("dbx") ' Si se especifica, usamos la BD indicada, si no, usamos "DB1".
|
|
||||||
|
|
||||||
' Log("RootMap: " & RootMap)
|
|
||||||
' Log("LA BD: " & DB)
|
|
||||||
' Log(Main.listaDeCP.size)
|
|
||||||
' Log("Contiene: " & Main.listaDeCP.IndexOf(DB))
|
|
||||||
|
|
||||||
If Main.listaDeCP.IndexOf(DB) = -1 Then
|
|
||||||
SendErrorResponse(resp, 400, "Invalid 'DB' name. The '" & DB & "' name is not valid.")
|
|
||||||
|
|
||||||
End If
|
End If
|
||||||
|
|
||||||
Dim paramKeys As List
|
' Crea un objeto JSONParser para analizar la cadena JSON.
|
||||||
paramKeys.Initialize
|
Dim parser As JSONParser
|
||||||
If paramsMap <> Null And paramsMap.IsInitialized Then
|
parser.Initialize(jsonString)
|
||||||
For Each key As String In paramsMap.Keys
|
' Convierte la cadena JSON en un objeto Map, que es como un diccionario (clave-valor).
|
||||||
paramKeys.Add(key)
|
Dim RootMap As Map = parser.NextObject
|
||||||
Next
|
|
||||||
End If
|
|
||||||
paramKeys.Sort(True)
|
|
||||||
|
|
||||||
Dim orderedParams As List
|
' Extrae los datos necesarios del JSON.
|
||||||
orderedParams.Initialize
|
Dim execType As String = RootMap.GetDefault("exec", "") ' Tipo de ejecución: "executeQuery" o "executeCommand".
|
||||||
For Each key As String In paramKeys
|
Dim queryName As String = RootMap.Get("query") ' Nombre del comando SQL (definido en config.properties).
|
||||||
orderedParams.Add(paramsMap.Get(key))
|
Dim paramsMap As Map = RootMap.Get("params") ' Un mapa con los parámetros para la consulta.
|
||||||
Next
|
' Log(RootMap)
|
||||||
|
' Verifica si en el JSON se especificó un nombre de base de datos diferente con la clave "dbx".
|
||||||
|
If RootMap.Get("dbx") <> Null Then DB = RootMap.Get("dbx") ' Si se especifica, usamos la BD indicada, si no, se queda "DB1".
|
||||||
|
|
||||||
con = Connector.GetConnection(DB)
|
' Valida que el nombre de la base de datos (DB) exista en la lista de conexiones configuradas en Main.
|
||||||
Dim sqlCommand As String = Connector.GetCommand(DB, queryName)
|
If Main.listaDeCP.IndexOf(DB) = -1 Then
|
||||||
|
SendErrorResponse(resp, 400, "Parametro 'DB' invalido. El nombre '" & DB & "' no es válido.")
|
||||||
|
' Se añade Return para detener la ejecución si la BD no es válida.
|
||||||
|
Return
|
||||||
|
End If
|
||||||
|
|
||||||
If execType.ToLowerCase = "executequery" Then
|
' Prepara una lista para almacenar las claves de los parámetros.
|
||||||
Dim rs As ResultSet
|
Dim paramKeys As List
|
||||||
|
paramKeys.Initialize
|
||||||
|
' Si el mapa de parámetros existe y está inicializado...
|
||||||
|
If paramsMap <> Null And paramsMap.IsInitialized Then
|
||||||
|
' ...itera sobre todas las claves y las añade a la lista 'paramKeys'.
|
||||||
|
For Each key As String In paramsMap.Keys
|
||||||
|
paramKeys.Add(key)
|
||||||
|
Next
|
||||||
|
End If
|
||||||
|
' Ordena las claves alfabéticamente. Esto es crucial para asegurar que los parámetros
|
||||||
|
' se pasen a la consulta SQL en un orden consistente y predecible.
|
||||||
|
paramKeys.Sort(True)
|
||||||
|
|
||||||
If sqlCommand.Contains("?") Then
|
' Prepara una lista para almacenar los valores de los parámetros en el orden correcto.
|
||||||
' =================================================================
|
Dim orderedParams As List
|
||||||
' === VALIDACIÓN DE CONTEO DE PARÁMETROS ==========================
|
orderedParams.Initialize
|
||||||
' =================================================================
|
' Itera sobre la lista de claves ya ordenada.
|
||||||
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
For Each key As String In paramKeys
|
||||||
Dim receivedParams As Int = orderedParams.Size
|
' Añade el valor correspondiente a cada clave a la lista 'orderedParams'.
|
||||||
If expectedParams <> receivedParams Then
|
orderedParams.Add(paramsMap.Get(key))
|
||||||
SendErrorResponse(resp, 400, $"Parameter count mismatch. The command '${queryName}' expects ${expectedParams} parameter(s), but received ${receivedParams}."$)
|
Next
|
||||||
Return ' Detenemos la ejecución antes de tocar la BD
|
|
||||||
End If
|
|
||||||
' =================================================================
|
|
||||||
rs = con.ExecQuery2(sqlCommand, orderedParams)
|
|
||||||
Else
|
|
||||||
rs = con.ExecQuery(sqlCommand)
|
|
||||||
End If
|
|
||||||
|
|
||||||
' --- Procesamiento de resultados (sin cambios) ---
|
' Obtiene una conexión a la base de datos del pool de conexiones.
|
||||||
Dim ResultList As List
|
con = Connector.GetConnection(DB)
|
||||||
ResultList.Initialize
|
' Obtiene la cadena SQL del archivo de configuración usando el nombre de la consulta (queryName).
|
||||||
Dim jrs As JavaObject = rs
|
Dim sqlCommand As String = Connector.GetCommand(DB, queryName)
|
||||||
Dim rsmd As JavaObject = jrs.RunMethod("getMetaData", Null)
|
|
||||||
Dim cols As Int = rsmd.RunMethod("getColumnCount", Null)
|
|
||||||
|
|
||||||
Do While rs.NextRow
|
' <<< INICIO NUEVA VALIDACIÓN: VERIFICAR SI EL COMANDO EXISTE >>>
|
||||||
Dim RowMap As Map
|
' Comprueba si el comando SQL (query) especificado en el JSON fue encontrado en el archivo de configuración.
|
||||||
RowMap.Initialize
|
If sqlCommand = Null Or sqlCommand = "null" Or sqlCommand.Trim = "" Then
|
||||||
For i = 1 To cols
|
' Si no se encontró el comando, crea un mensaje de error claro.
|
||||||
Dim ColumnName As String = rsmd.RunMethod("getColumnName", Array(i))
|
Dim errorMessage As String = $"El comando '${queryName}' no fue encontrado en el config.properties de '${DB}'."$
|
||||||
Dim value As Object = jrs.RunMethod("getObject", Array(i))
|
' Registra el error en el log del servidor para depuración.
|
||||||
RowMap.Put(ColumnName, value)
|
Log(errorMessage)
|
||||||
Next
|
' Envía una respuesta de error 400 (Bad Request) al cliente en formato JSON.
|
||||||
ResultList.Add(RowMap)
|
SendErrorResponse(resp, 400, errorMessage)
|
||||||
Loop
|
' Cierra la conexión a la base de datos antes de salir para evitar fugas de conexión.
|
||||||
rs.Close
|
If con <> Null And con.IsInitialized Then con.Close
|
||||||
|
' Detiene la ejecución del método Handle para esta petición.
|
||||||
|
Return
|
||||||
|
End If
|
||||||
|
' <<< FIN NUEVA VALIDACIÓN >>>
|
||||||
|
|
||||||
SendSuccessResponse(resp, CreateMap("result": ResultList))
|
' Comprueba el tipo de ejecución solicitado ("executeQuery" o "executeCommand").
|
||||||
Else If execType.ToLowerCase = "executecommand" Then
|
If execType.ToLowerCase = "executequery" Then
|
||||||
If sqlCommand.Contains("?") Then
|
' Declara una variable para almacenar el resultado de la consulta.
|
||||||
' =================================================================
|
Dim rs As ResultSet
|
||||||
' === VALIDACIÓN DE CONTEO DE PARÁMETROS (para Comandos) ==========
|
|
||||||
' =================================================================
|
|
||||||
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
|
||||||
Dim receivedParams As Int = orderedParams.Size
|
|
||||||
If expectedParams <> receivedParams Then
|
|
||||||
SendErrorResponse(resp, 400, $"Parameter count mismatch. The command '${queryName}' expects ${expectedParams} parameter(s), but received ${receivedParams}."$)
|
|
||||||
Return ' Detenemos la ejecución
|
|
||||||
End If
|
|
||||||
' =================================================================
|
|
||||||
End If
|
|
||||||
|
|
||||||
con.ExecNonQuery2(sqlCommand, orderedParams)
|
' Si el comando SQL contiene placeholders ('?'), significa que espera parámetros.
|
||||||
SendSuccessResponse(resp, CreateMap("message": "Command executed successfully"))
|
If sqlCommand.Contains("?") Then
|
||||||
|
' =================================================================
|
||||||
|
' === VALIDACIÓN DE CONTEO DE PARÁMETROS ==========================
|
||||||
|
' =================================================================
|
||||||
|
' Calcula cuántos parámetros espera la consulta contando el número de '?'.
|
||||||
|
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
||||||
|
' Obtiene cuántos parámetros se recibieron.
|
||||||
|
Dim receivedParams As Int = orderedParams.Size
|
||||||
|
' Compara si la cantidad de parámetros esperados y recibidos es diferente.
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
' Si no coinciden, envía un error 400 detallado.
|
||||||
|
SendErrorResponse(resp, 400, $"Número de parametros equivocado para '${queryName}'. Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$)
|
||||||
|
' Cierra la conexión antes de salir para evitar fugas.
|
||||||
|
If con <> Null And con.IsInitialized Then con.Close
|
||||||
|
' Detiene la ejecución para evitar un error en la base de datos.
|
||||||
|
Return
|
||||||
|
End If
|
||||||
|
' =================================================================
|
||||||
|
' Ejecuta la consulta pasando el comando SQL y la lista ordenada de parámetros.
|
||||||
|
rs = con.ExecQuery2(sqlCommand, orderedParams)
|
||||||
|
Else
|
||||||
|
' Si no hay '?', ejecuta la consulta directamente sin parámetros.
|
||||||
|
rs = con.ExecQuery(sqlCommand)
|
||||||
|
End If
|
||||||
|
|
||||||
Else
|
' --- Procesamiento de resultados ---
|
||||||
SendErrorResponse(resp, 400, "Invalid 'exec' value. Use '" & execType & "' is not valid.")
|
' Prepara una lista para almacenar todas las filas del resultado.
|
||||||
End If
|
Dim ResultList As List
|
||||||
|
ResultList.Initialize
|
||||||
|
' Usa un objeto JavaObject para acceder a los metadatos del resultado (info de columnas).
|
||||||
|
Dim jrs As JavaObject = rs
|
||||||
|
Dim rsmd As JavaObject = jrs.RunMethod("getMetaData", Null)
|
||||||
|
' Obtiene el número de columnas en el resultado.
|
||||||
|
Dim cols As Int = rsmd.RunMethod("getColumnCount", Null)
|
||||||
|
|
||||||
Catch
|
' Itera sobre cada fila del resultado (ResultSet).
|
||||||
Log(LastException)
|
Do While rs.NextRow
|
||||||
SendErrorResponse(resp, 500, LastException.Message)
|
' Crea un mapa para almacenar los datos de la fila actual (columna -> valor).
|
||||||
End Try
|
Dim RowMap As Map
|
||||||
|
RowMap.Initialize
|
||||||
|
' Itera sobre cada columna de la fila.
|
||||||
|
For i = 1 To cols
|
||||||
|
' Obtiene el nombre de la columna.
|
||||||
|
Dim ColumnName As String = rsmd.RunMethod("getColumnName", Array(i))
|
||||||
|
' Obtiene el valor de la columna.
|
||||||
|
Dim value As Object = jrs.RunMethod("getObject", Array(i))
|
||||||
|
' Añade la pareja (nombre_columna, valor) al mapa de la fila.
|
||||||
|
RowMap.Put(ColumnName, value)
|
||||||
|
Next
|
||||||
|
' Añade el mapa de la fila a la lista de resultados.
|
||||||
|
ResultList.Add(RowMap)
|
||||||
|
Loop
|
||||||
|
' Cierra el ResultSet para liberar recursos de la base de datos.
|
||||||
|
rs.Close
|
||||||
|
|
||||||
|
' Envía una respuesta de éxito con la lista de resultados en formato JSON.
|
||||||
|
SendSuccessResponse(resp, CreateMap("result": ResultList))
|
||||||
|
|
||||||
|
Else If execType.ToLowerCase = "executecommand" Then
|
||||||
|
' Si es un comando (INSERT, UPDATE, DELETE), también valida los parámetros.
|
||||||
|
If sqlCommand.Contains("?") Then
|
||||||
|
' =================================================================
|
||||||
|
' === VALIDACIÓN DE CONTEO DE PARÁMETROS (para Comandos) ==========
|
||||||
|
' =================================================================
|
||||||
|
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
||||||
|
Dim receivedParams As Int = orderedParams.Size
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
SendErrorResponse(resp, 400, $"Número de parametros equivocado para '${queryName}'. Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$)
|
||||||
|
' Cierra la conexión antes de salir.
|
||||||
|
If con <> Null And con.IsInitialized Then con.Close
|
||||||
|
' Detiene la ejecución.
|
||||||
|
Return
|
||||||
|
End If
|
||||||
|
' =================================================================
|
||||||
|
End If
|
||||||
|
|
||||||
|
' Ejecuta el comando que no devuelve resultados (NonQuery) con sus parámetros.
|
||||||
|
con.ExecNonQuery2(sqlCommand, orderedParams)
|
||||||
|
' Envía una respuesta de éxito con un mensaje de confirmación.
|
||||||
|
SendSuccessResponse(resp, CreateMap("message": "Command executed successfully"))
|
||||||
|
|
||||||
|
Else
|
||||||
|
' Si el valor de 'exec' no es ni "executeQuery" ni "executeCommand", envía un error.
|
||||||
|
SendErrorResponse(resp, 400, "Parametro 'exec' inválido. '" & execType & "' no es un valor permitido.")
|
||||||
|
End If
|
||||||
|
|
||||||
|
Catch
|
||||||
|
' Si ocurre cualquier error inesperado en el bloque Try...
|
||||||
|
' Registra la excepción completa en el log del servidor para diagnóstico.
|
||||||
|
Log(LastException)
|
||||||
|
' Envía una respuesta de error 500 (Internal Server Error) con el mensaje de la excepción.
|
||||||
|
SendErrorResponse(resp, 500, LastException.Message)
|
||||||
|
End Try
|
||||||
|
|
||||||
If con <> Null And con.IsInitialized Then
|
' Este bloque se ejecuta siempre al final, haya habido error o no, *excepto si se usó Return antes*.
|
||||||
con.Close
|
' Comprueba si el objeto de conexión fue inicializado y sigue abierto.
|
||||||
End If
|
If con <> Null And con.IsInitialized Then
|
||||||
|
' Cierra la conexión para devolverla al pool y que pueda ser reutilizada.
|
||||||
|
' Esto es fundamental para no agotar las conexiones a la base de datos.
|
||||||
|
con.Close
|
||||||
|
End If
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
|
|
||||||
' --- Subrutinas de ayuda para respuestas JSON (sin cambios) ---
|
' --- Subrutinas de ayuda para respuestas JSON ---
|
||||||
|
|
||||||
|
' Construye y envía una respuesta JSON de éxito.
|
||||||
Private Sub SendSuccessResponse(resp As ServletResponse, dataMap As Map)
|
Private Sub SendSuccessResponse(resp As ServletResponse, dataMap As Map)
|
||||||
dataMap.Put("success", True)
|
' Añade el campo "success": true al mapa de datos para indicar que todo salió bien.
|
||||||
Dim jsonGenerator As JSONGenerator
|
dataMap.Put("success", True)
|
||||||
jsonGenerator.Initialize(dataMap)
|
' Crea un generador de JSON.
|
||||||
resp.ContentType = "application/json"
|
Dim jsonGenerator As JSONGenerator
|
||||||
resp.Write(jsonGenerator.ToString)
|
jsonGenerator.Initialize(dataMap)
|
||||||
|
' Establece el tipo de contenido de la respuesta a "application/json".
|
||||||
|
resp.ContentType = "application/json"
|
||||||
|
' Escribe la cadena JSON generada en el cuerpo de la respuesta HTTP.
|
||||||
|
resp.Write(jsonGenerator.ToString)
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
|
' Construye y envía una respuesta JSON de error.
|
||||||
Private Sub SendErrorResponse(resp As ServletResponse, statusCode As Int, errorMessage As String)
|
Private Sub SendErrorResponse(resp As ServletResponse, statusCode As Int, errorMessage As String)
|
||||||
Dim resMap As Map = CreateMap("success": False, "error": errorMessage)
|
' Personaliza el mensaje de error si es un error común de parámetros de Oracle o JDBC.
|
||||||
Dim jsonGenerator As JSONGenerator
|
If errorMessage.Contains("Índice de columnas no válido") Or errorMessage.Contains("ORA-17003") Then errorMessage = "NUMERO DE PARAMETROS EQUIVOCADO: " & errorMessage
|
||||||
jsonGenerator.Initialize(resMap)
|
' Crea un mapa con el estado de error y el mensaje.
|
||||||
resp.Status = statusCode
|
Dim resMap As Map = CreateMap("success": False, "error": errorMessage)
|
||||||
resp.ContentType = "application/json"
|
' Genera la cadena JSON a partir del mapa.
|
||||||
resp.Write(jsonGenerator.ToString)
|
Dim jsonGenerator As JSONGenerator
|
||||||
End Sub
|
jsonGenerator.Initialize(resMap)
|
||||||
|
' Establece el código de estado HTTP (ej. 400 para error del cliente, 500 para error del servidor).
|
||||||
|
resp.Status = statusCode
|
||||||
|
' Establece el tipo de contenido y escribe la respuesta de error.
|
||||||
|
resp.ContentType = "application/json"
|
||||||
|
resp.Write(jsonGenerator.ToString)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -55,6 +55,7 @@ Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Private Sub ExecuteQuery2 (DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
Private Sub ExecuteQuery2 (DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
|
Log("==== ExecuteQuery2 ==== ")
|
||||||
Dim ser As B4XSerializator
|
Dim ser As B4XSerializator
|
||||||
Dim m As Map = ser.ConvertBytesToObject(Bit.InputStreamToBytes(in))
|
Dim m As Map = ser.ConvertBytesToObject(Bit.InputStreamToBytes(in))
|
||||||
Dim cmd As DBCommand = m.Get("command")
|
Dim cmd As DBCommand = m.Get("command")
|
||||||
@@ -162,7 +163,7 @@ Private Sub ExecuteBatch(DB As String, con As SQL, in As InputStream, resp As Se
|
|||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Private Sub ExecuteQuery (DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
Private Sub ExecuteQuery (DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
' Log("==== ExecuteQuery ==== ")
|
Log("==== ExecuteQuery ==== ")
|
||||||
Dim clientVersion As Float = ReadObject(in) 'ignore
|
Dim clientVersion As Float = ReadObject(in) 'ignore
|
||||||
Dim queryName As String = ReadObject(in)
|
Dim queryName As String = ReadObject(in)
|
||||||
Dim limit As Int = ReadInt(in)
|
Dim limit As Int = ReadInt(in)
|
||||||
|
|||||||
@@ -1,130 +0,0 @@
|
|||||||
B4J=true
|
|
||||||
Group=Default Group
|
|
||||||
ModulesStructureVersion=1
|
|
||||||
Type=Class
|
|
||||||
Version=10.3
|
|
||||||
@EndOfDesignText@
|
|
||||||
'Handler class for JSON requests from Web Clients (JavaScript/axios)
|
|
||||||
'VERSION 13 (Corrección Final): Soluciona "Miembro desconocido" usando jrs.RunMethod.
|
|
||||||
Sub Class_Globals
|
|
||||||
Private Connector As RDCConnector
|
|
||||||
End Sub
|
|
||||||
|
|
||||||
Public Sub Initialize
|
|
||||||
End Sub
|
|
||||||
|
|
||||||
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|
||||||
' --- Headers CORS ---
|
|
||||||
resp.SetHeader("Access-Control-Allow-Origin", "*")
|
|
||||||
resp.SetHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS")
|
|
||||||
resp.SetHeader("Access-Control-Allow-Headers", "Content-Type")
|
|
||||||
|
|
||||||
If req.Method = "OPTIONS" Then Return
|
|
||||||
|
|
||||||
Dim DB As String = "DB1"
|
|
||||||
Connector = Main.Connectors.Get(DB)
|
|
||||||
Dim con As SQL
|
|
||||||
|
|
||||||
Try
|
|
||||||
Dim jsonString As String = req.GetParameter("j")
|
|
||||||
If jsonString = Null Or jsonString = "" Then
|
|
||||||
SendErrorResponse(resp, 400, "Missing 'j' parameter")
|
|
||||||
Return
|
|
||||||
End If
|
|
||||||
|
|
||||||
Dim parser As JSONParser
|
|
||||||
parser.Initialize(jsonString)
|
|
||||||
Dim RootMap As Map = parser.NextObject
|
|
||||||
|
|
||||||
Dim execType As String = RootMap.GetDefault("exec", "")
|
|
||||||
Dim queryName As String = RootMap.Get("query")
|
|
||||||
Dim paramsMap As Map = RootMap.Get("params")
|
|
||||||
|
|
||||||
Dim paramKeys As List
|
|
||||||
paramKeys.Initialize
|
|
||||||
If paramsMap <> Null And paramsMap.IsInitialized Then
|
|
||||||
For Each key As String In paramsMap.Keys
|
|
||||||
paramKeys.Add(key)
|
|
||||||
Next
|
|
||||||
End If
|
|
||||||
paramKeys.Sort(True)
|
|
||||||
|
|
||||||
Dim orderedParams As List
|
|
||||||
orderedParams.Initialize
|
|
||||||
For Each key As String In paramKeys
|
|
||||||
orderedParams.Add(paramsMap.Get(key))
|
|
||||||
Next
|
|
||||||
|
|
||||||
con = Connector.GetConnection(DB)
|
|
||||||
Dim sqlCommand As String = Connector.GetCommand(DB, queryName)
|
|
||||||
|
|
||||||
If execType.ToLowerCase = "executequery" Then
|
|
||||||
Dim rs As ResultSet
|
|
||||||
|
|
||||||
If sqlCommand.Contains("?") Then
|
|
||||||
rs = con.ExecQuery2(sqlCommand, orderedParams)
|
|
||||||
Else
|
|
||||||
rs = con.ExecQuery(sqlCommand)
|
|
||||||
End If
|
|
||||||
|
|
||||||
Dim ResultList As List
|
|
||||||
ResultList.Initialize
|
|
||||||
Dim jrs As JavaObject = rs
|
|
||||||
|
|
||||||
Dim rsmd As JavaObject = jrs.RunMethod("getMetaData", Null)
|
|
||||||
Dim cols As Int = rsmd.RunMethod("getColumnCount", Null)
|
|
||||||
|
|
||||||
Do While rs.NextRow
|
|
||||||
Dim RowMap As Map
|
|
||||||
RowMap.Initialize
|
|
||||||
For i = 1 To cols
|
|
||||||
Dim ColumnName As String = rsmd.RunMethod("getColumnName", Array(i))
|
|
||||||
' =================================================================
|
|
||||||
' === CORRECCIÓN "MIEMBRO DESCONOCIDO" ============================
|
|
||||||
' =================================================================
|
|
||||||
Dim value As Object = jrs.RunMethod("getObject", Array(i))
|
|
||||||
RowMap.Put(ColumnName, value)
|
|
||||||
Next
|
|
||||||
ResultList.Add(RowMap)
|
|
||||||
Loop
|
|
||||||
rs.Close
|
|
||||||
|
|
||||||
SendSuccessResponse(resp, CreateMap("result": ResultList))
|
|
||||||
|
|
||||||
Else If execType.ToLowerCase = "executecommand" Then
|
|
||||||
con.ExecNonQuery2(sqlCommand, orderedParams)
|
|
||||||
SendSuccessResponse(resp, CreateMap("message": "Command executed successfully"))
|
|
||||||
|
|
||||||
Else
|
|
||||||
SendErrorResponse(resp, 400, "Invalid 'exec' value. Use '" & execType & "' is not valid.")
|
|
||||||
End If
|
|
||||||
|
|
||||||
Catch
|
|
||||||
Log(LastException)
|
|
||||||
SendErrorResponse(resp, 500, LastException.Message)
|
|
||||||
End Try
|
|
||||||
|
|
||||||
If con <> Null And con.IsInitialized Then
|
|
||||||
con.Close
|
|
||||||
End If
|
|
||||||
End Sub
|
|
||||||
|
|
||||||
|
|
||||||
' --- Subrutinas de ayuda para respuestas JSON (sin cambios) ---
|
|
||||||
Private Sub SendSuccessResponse(resp As ServletResponse, dataMap As Map)
|
|
||||||
dataMap.Put("success", True)
|
|
||||||
Dim jsonGenerator As JSONGenerator
|
|
||||||
jsonGenerator.Initialize(dataMap)
|
|
||||||
resp.ContentType = "application/json"
|
|
||||||
resp.Write(jsonGenerator.ToString)
|
|
||||||
End Sub
|
|
||||||
|
|
||||||
Private Sub SendErrorResponse(resp As ServletResponse, statusCode As Int, errorMessage As String)
|
|
||||||
If errorMessage.Contains("Índice de columnas no válido") Or errorMessage.Contains("ORA-17003") Then errorMessage = "NUMERO DE PARAMETROS EQUIVOCADO: " & errorMessage
|
|
||||||
Dim resMap As Map = CreateMap("success": False, "error": errorMessage)
|
|
||||||
Dim jsonGenerator As JSONGenerator
|
|
||||||
jsonGenerator.Initialize(resMap)
|
|
||||||
resp.Status = statusCode
|
|
||||||
resp.ContentType = "application/json"
|
|
||||||
resp.Write(jsonGenerator.ToString)
|
|
||||||
End Sub
|
|
||||||
609
DBHandlerGenerico.bas
Normal file
609
DBHandlerGenerico.bas
Normal file
@@ -0,0 +1,609 @@
|
|||||||
|
B4J=true
|
||||||
|
Group=Default Group
|
||||||
|
ModulesStructureVersion=1
|
||||||
|
Type=Class
|
||||||
|
Version=10.3
|
||||||
|
@EndOfDesignText@
|
||||||
|
' Handler genérico para peticiones desde clientes B4A/B4i (DBRequestManager)
|
||||||
|
' Determina la base de datos a utilizar dinámicamente a partir de la URL de la petición.
|
||||||
|
' Versión con validación de parámetros y errores en texto plano.
|
||||||
|
Sub Class_Globals
|
||||||
|
' Estas constantes y variables solo se compilan si se usa la #if VERSION1,
|
||||||
|
' lo que sugiere que es para dar soporte a una versión antigua del protocolo de comunicación.
|
||||||
|
' #if VERSION1
|
||||||
|
' Constantes para identificar los tipos de datos en la serialización personalizada (protocolo V1).
|
||||||
|
Private const T_NULL = 0, T_STRING = 1, T_SHORT = 2, T_INT = 3, T_LONG = 4, T_FLOAT = 5 _
|
||||||
|
,T_DOUBLE = 6, T_BOOLEAN = 7, T_BLOB = 8 As Byte
|
||||||
|
' Utilidades para convertir entre tipos de datos y arrays de bytes.
|
||||||
|
Private bc As ByteConverter
|
||||||
|
' Utilidad para comprimir/descomprimir streams de datos (usado en V1).
|
||||||
|
Private cs As CompressedStreams
|
||||||
|
' #end if
|
||||||
|
|
||||||
|
' Mapa para convertir tipos de columna JDBC de fecha/hora a métodos de obtención de datos.
|
||||||
|
Private DateTimeMethods As Map
|
||||||
|
' Objeto que gestiona las conexiones a las diferentes bases de datos definidas en config.properties.
|
||||||
|
Private Connector As RDCConnector
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Se ejecuta una vez cuando se crea una instancia de esta clase.
|
||||||
|
Public Sub Initialize
|
||||||
|
' Inicializa el mapa que asocia los códigos de tipo de columna de fecha/hora de JDBC
|
||||||
|
' con los nombres de los métodos correspondientes para leerlos correctamente.
|
||||||
|
DateTimeMethods = CreateMap(91: "getDate", 92: "getTime", 93: "getTimestamp")
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Método principal que maneja cada petición HTTP que llega a este servlet.
|
||||||
|
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
||||||
|
' === INICIO DE LA LÓGICA DINÁMICA ===
|
||||||
|
' Extrae la URI completa de la petición (ej. /DB1/endpoint).
|
||||||
|
Dim URI As String = req.RequestURI
|
||||||
|
' Variable para almacenar la "llave" o identificador de la base de datos (ej. "DB1").
|
||||||
|
Dim dbKey As String
|
||||||
|
|
||||||
|
' Comprueba si la URI tiene contenido y empieza con "/".
|
||||||
|
If URI.Length > 1 And URI.StartsWith("/") Then
|
||||||
|
' Extrae la parte de la URI que viene después del primer "/".
|
||||||
|
dbKey = URI.Substring(1)
|
||||||
|
' Si la llave contiene más "/", se queda solo con la primera parte.
|
||||||
|
' Esto permite URLs como /DB1/clientes o /DB2/productos, extrayendo "DB1" o "DB2".
|
||||||
|
If dbKey.Contains("/") Then
|
||||||
|
dbKey = dbKey.SubString2(0, dbKey.IndexOf("/"))
|
||||||
|
End If
|
||||||
|
Else
|
||||||
|
' Si la URI está vacía o es "/", usa "DB1" como la base de datos por defecto.
|
||||||
|
dbKey = "DB1"
|
||||||
|
End If
|
||||||
|
|
||||||
|
' Convierte la llave a mayúsculas para que no sea sensible a mayúsculas/minúsculas (ej. "db1" se convierte en "DB1").
|
||||||
|
dbKey = dbKey.ToUpperCase
|
||||||
|
|
||||||
|
' Verifica si la llave de la base de datos extraída existe en la configuración de conectores.
|
||||||
|
If Main.Connectors.ContainsKey(dbKey) = False Then
|
||||||
|
' Si no existe, crea un mensaje de error claro.
|
||||||
|
Dim ErrorMsg As String = $"Invalid DB key specified in URL: '${dbKey}'. Valid keys are: ${Main.listaDeCP}"$
|
||||||
|
' Registra el error en el log del servidor.
|
||||||
|
Log(ErrorMsg)
|
||||||
|
' Envía una respuesta de error 400 (Bad Request) al cliente en formato de texto plano.
|
||||||
|
SendPlainTextError(resp, 400, ErrorMsg)
|
||||||
|
' Termina la ejecución de este método.
|
||||||
|
Return
|
||||||
|
End If
|
||||||
|
' === FIN DE LA LÓGICA DINÁMICA ===
|
||||||
|
|
||||||
|
Log("********************* " & dbKey & " ********************")
|
||||||
|
' Guarda el tiempo de inicio para medir la duración de la petición.
|
||||||
|
Dim start As Long = DateTime.Now
|
||||||
|
' Variable para almacenar el nombre del comando SQL a ejecutar.
|
||||||
|
Dim q As String
|
||||||
|
' Obtiene el stream de entrada de la petición, que contiene los datos enviados por el cliente.
|
||||||
|
Dim in As InputStream = req.InputStream
|
||||||
|
' Obtiene el parámetro "method" de la URL (ej. ?method=query2).
|
||||||
|
Dim method As String = req.GetParameter("method")
|
||||||
|
' Obtiene el conector correspondiente a la base de datos seleccionada.
|
||||||
|
Connector = Main.Connectors.Get(dbKey)
|
||||||
|
' Declara la variable para la conexión a la base de datos.
|
||||||
|
Dim con As SQL
|
||||||
|
Try
|
||||||
|
' Obtiene una conexión del pool de conexiones.
|
||||||
|
con = Connector.GetConnection(dbKey)
|
||||||
|
Log("Metodo: " & method)
|
||||||
|
' Determina qué función ejecutar basándose en el parámetro "method".
|
||||||
|
If method = "query2" Then
|
||||||
|
' Ejecuta una consulta usando el protocolo más nuevo (B4XSerializator).
|
||||||
|
q = ExecuteQuery2(dbKey, con, in, resp)
|
||||||
|
'#if VERSION1
|
||||||
|
Else if method = "query" Then
|
||||||
|
' Protocolo antiguo: descomprime el stream y ejecuta la consulta.
|
||||||
|
in = cs.WrapInputStream(in, "gzip")
|
||||||
|
q = ExecuteQuery(dbKey, con, in, resp)
|
||||||
|
Else if method = "batch" Then
|
||||||
|
' Protocolo antiguo: descomprime el stream y ejecuta un lote de comandos.
|
||||||
|
in = cs.WrapInputStream(in, "gzip")
|
||||||
|
q = ExecuteBatch(dbKey, con, in, resp)
|
||||||
|
'#end if
|
||||||
|
Else if method = "batch2" Then
|
||||||
|
' Ejecuta un lote de comandos usando el protocolo más nuevo.
|
||||||
|
q = ExecuteBatch2(dbKey, con, in, resp)
|
||||||
|
Else
|
||||||
|
' Si el método es desconocido, lo registra y envía un error.
|
||||||
|
Log("Unknown method: " & method)
|
||||||
|
SendPlainTextError(resp, 500, "unknown method")
|
||||||
|
End If
|
||||||
|
Catch
|
||||||
|
' Si ocurre cualquier error en el bloque Try, lo captura.
|
||||||
|
Log(LastException)
|
||||||
|
' Envía un error 500 (Internal Server Error) al cliente con el mensaje de la excepción.
|
||||||
|
SendPlainTextError(resp, 500, LastException.Message)
|
||||||
|
End Try
|
||||||
|
' Asegura que la conexión a la BD se cierre y se devuelva al pool.
|
||||||
|
If con <> Null And con.IsInitialized Then con.Close
|
||||||
|
' Registra en el log el comando ejecutado, cuánto tiempo tardó y la IP del cliente.
|
||||||
|
Log($"Command: ${q}, took: ${DateTime.Now - start}ms, client=${req.RemoteAddress}"$)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Ejecuta una consulta única usando el protocolo V2 (B4XSerializator).
|
||||||
|
Private Sub ExecuteQuery2 (DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
|
' Objeto para deserializar los datos enviados desde el cliente.
|
||||||
|
Dim ser As B4XSerializator
|
||||||
|
' Convierte el stream de entrada a un array de bytes y luego a un objeto Mapa.
|
||||||
|
Dim m As Map = ser.ConvertBytesToObject(Bit.InputStreamToBytes(in))
|
||||||
|
' Extrae el objeto DBCommand del mapa.
|
||||||
|
Dim cmd As DBCommand = m.Get("command")
|
||||||
|
' Extrae el límite de filas a devolver.
|
||||||
|
Dim limit As Int = m.Get("limit")
|
||||||
|
|
||||||
|
' Obtiene la sentencia SQL correspondiente al nombre del comando desde config.properties.
|
||||||
|
Dim sqlCommand As String = Connector.GetCommand(DB, cmd.Name)
|
||||||
|
|
||||||
|
' <<< INICIO NUEVA VALIDACIÓN: VERIFICAR SI EL COMANDO EXISTE >>>
|
||||||
|
' Comprueba si el comando no fue encontrado en el archivo de configuración.
|
||||||
|
If sqlCommand = Null Or sqlCommand = "null" Or sqlCommand.Trim = "" Then
|
||||||
|
Dim errorMessage As String = $"El comando '${cmd.Name}' no fue encontrado en el config.properties de '${DB}'."$
|
||||||
|
Log(errorMessage)
|
||||||
|
' Envía un error 400 (Bad Request) al cliente informando del problema.
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error" ' Retorna un texto para el log.
|
||||||
|
End If
|
||||||
|
' <<< FIN NUEVA VALIDACIÓN >>>
|
||||||
|
|
||||||
|
' --- INICIO VALIDACIÓN DE PARÁMETROS ---
|
||||||
|
' Comprueba si el SQL espera parámetros o si se recibieron parámetros.
|
||||||
|
If sqlCommand.Contains("?") Or (cmd.Parameters <> Null And cmd.Parameters.Length > 0) Then
|
||||||
|
' Cuenta cuántos '?' hay en la sentencia SQL para saber cuántos parámetros se esperan.
|
||||||
|
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
||||||
|
' Cuenta cuántos parámetros se recibieron.
|
||||||
|
Dim receivedParams As Int
|
||||||
|
If cmd.Parameters = Null Then receivedParams = 0 Else receivedParams = cmd.Parameters.Length
|
||||||
|
|
||||||
|
' Compara el número de parámetros esperados con los recibidos.
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
Dim errorMessage As String = $"Número de parametros equivocado para "${cmd.Name}". Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$
|
||||||
|
Log(errorMessage)
|
||||||
|
' Si no coinciden, envía un error 400 al cliente.
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
End If
|
||||||
|
' --- FIN VALIDACIÓN ---
|
||||||
|
|
||||||
|
' Ejecuta la consulta SQL con los parámetros proporcionados.
|
||||||
|
Dim rs As ResultSet = con.ExecQuery2(sqlCommand, cmd.Parameters)
|
||||||
|
' Si el límite es 0 o negativo, lo establece a un valor muy alto (máximo entero).
|
||||||
|
If limit <= 0 Then limit = 0x7fffffff 'max int
|
||||||
|
' Obtiene el objeto Java subyacente del ResultSet para acceder a métodos adicionales.
|
||||||
|
Dim jrs As JavaObject = rs
|
||||||
|
' Obtiene los metadatos del ResultSet (información sobre las columnas).
|
||||||
|
Dim rsmd As JavaObject = jrs.RunMethod("getMetaData", Null)
|
||||||
|
' Obtiene el número de columnas del resultado.
|
||||||
|
Dim cols As Int = rs.ColumnCount
|
||||||
|
' Crea un objeto DBResult para empaquetar la respuesta.
|
||||||
|
Dim res As DBResult
|
||||||
|
res.Initialize
|
||||||
|
res.columns.Initialize
|
||||||
|
res.Tag = Null
|
||||||
|
' Llena el mapa de columnas con el nombre de cada columna y su índice.
|
||||||
|
For i = 0 To cols - 1
|
||||||
|
res.columns.Put(rs.GetColumnName(i), i)
|
||||||
|
Next
|
||||||
|
' Inicializa la lista de filas.
|
||||||
|
res.Rows.Initialize
|
||||||
|
' Itera sobre cada fila del ResultSet, hasta llegar al límite.
|
||||||
|
Do While rs.NextRow And limit > 0
|
||||||
|
Dim row(cols) As Object
|
||||||
|
' Itera sobre cada columna de la fila actual.
|
||||||
|
For i = 0 To cols - 1
|
||||||
|
' Obtiene el tipo de dato de la columna según JDBC.
|
||||||
|
Dim ct As Int = rsmd.RunMethod("getColumnType", Array(i + 1))
|
||||||
|
' Maneja diferentes tipos de datos para leerlos de la forma correcta.
|
||||||
|
If ct = -2 Or ct = 2004 Or ct = -3 Or ct = -4 Then ' Tipos BLOB/binarios
|
||||||
|
row(i) = rs.GetBlob2(i)
|
||||||
|
Else If ct = 2005 Then ' Tipo CLOB (texto largo)
|
||||||
|
row(i) = rs.GetString2(i)
|
||||||
|
Else if ct = 2 Or ct = 3 Then ' Tipos numéricos que pueden tener decimales
|
||||||
|
row(i) = rs.GetDouble2(i)
|
||||||
|
Else If DateTimeMethods.ContainsKey(ct) Then ' Tipos de Fecha/Hora
|
||||||
|
' Obtiene el objeto de tiempo/fecha de Java.
|
||||||
|
Dim SQLTime As JavaObject = jrs.RunMethodJO(DateTimeMethods.Get(ct), Array(i + 1))
|
||||||
|
If SQLTime.IsInitialized Then
|
||||||
|
' Lo convierte a milisegundos (Long) para B4X.
|
||||||
|
row(i) = SQLTime.RunMethod("getTime", Null)
|
||||||
|
Else
|
||||||
|
row(i) = Null
|
||||||
|
End If
|
||||||
|
Else ' Para todos los demás tipos de datos
|
||||||
|
' Usa getObject que funciona para la mayoría de los tipos estándar.
|
||||||
|
row(i) = jrs.RunMethod("getObject", Array(i + 1))
|
||||||
|
End If
|
||||||
|
Next
|
||||||
|
' Añade la fila completa a la lista de resultados.
|
||||||
|
res.Rows.Add(row)
|
||||||
|
limit = limit - 1
|
||||||
|
Loop
|
||||||
|
' Cierra el ResultSet para liberar recursos.
|
||||||
|
rs.Close
|
||||||
|
' Serializa el objeto DBResult completo a un array de bytes.
|
||||||
|
Dim data() As Byte = ser.ConvertObjectToBytes(res)
|
||||||
|
' Escribe los datos serializados en el stream de respuesta.
|
||||||
|
resp.OutputStream.WriteBytes(data, 0, data.Length)
|
||||||
|
' Devuelve el nombre del comando para el log.
|
||||||
|
Return "query: " & cmd.Name
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Ejecuta un lote de comandos (INSERT, UPDATE, DELETE) usando el protocolo V2.
|
||||||
|
Private Sub ExecuteBatch2(DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
|
Dim ser As B4XSerializator
|
||||||
|
' Deserializa el mapa que contiene la lista de comandos.
|
||||||
|
Dim m As Map = ser.ConvertBytesToObject(Bit.InputStreamToBytes(in))
|
||||||
|
' Obtiene la lista de objetos DBCommand.
|
||||||
|
Dim commands As List = m.Get("commands")
|
||||||
|
' Prepara un objeto DBResult para la respuesta (aunque para batch no devuelve datos, solo confirmación).
|
||||||
|
Dim res As DBResult
|
||||||
|
res.Initialize
|
||||||
|
res.columns = CreateMap("AffectedRows (N/A)": 0)
|
||||||
|
res.Rows.Initialize
|
||||||
|
res.Tag = Null
|
||||||
|
Try
|
||||||
|
' Inicia una transacción. Todos los comandos del lote se ejecutarán como una unidad.
|
||||||
|
con.BeginTransaction
|
||||||
|
' Itera sobre cada comando en la lista.
|
||||||
|
For Each cmd As DBCommand In commands
|
||||||
|
' Obtiene la sentencia SQL para el comando actual.
|
||||||
|
Dim sqlCommand As String = Connector.GetCommand(DB, cmd.Name)
|
||||||
|
|
||||||
|
' <<< INICIO NUEVA VALIDACIÓN: VERIFICAR SI EL COMANDO EXISTE DENTRO DEL BATCH >>>
|
||||||
|
If sqlCommand = Null Or sqlCommand = "null" Or sqlCommand.Trim = "" Then
|
||||||
|
con.Rollback ' Deshace la transacción si un comando es inválido.
|
||||||
|
Dim errorMessage As String = $"El comando '${cmd.Name}' no fue encontrado en el config.properties de '${DB}'."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
' <<< FIN NUEVA VALIDACIÓN >>>
|
||||||
|
|
||||||
|
' --- INICIO VALIDACIÓN DE PARÁMETROS DENTRO DEL BATCH ---
|
||||||
|
If sqlCommand.Contains("?") Or (cmd.Parameters <> Null And cmd.Parameters.Length > 0) Then
|
||||||
|
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
||||||
|
Dim receivedParams As Int
|
||||||
|
If cmd.Parameters = Null Then receivedParams = 0 Else receivedParams = cmd.Parameters.Length
|
||||||
|
|
||||||
|
' Si el número de parámetros no coincide, deshace la transacción y envía error.
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
con.Rollback
|
||||||
|
Dim errorMessage As String = $"Número de parametros equivocado para "${cmd.Name}". Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
End If
|
||||||
|
' --- FIN VALIDACIÓN ---
|
||||||
|
|
||||||
|
' Ejecuta el comando (no es una consulta, no devuelve filas).
|
||||||
|
con.ExecNonQuery2(sqlCommand, cmd.Parameters)
|
||||||
|
Next
|
||||||
|
' Añade una fila simbólica al resultado para indicar éxito.
|
||||||
|
res.Rows.Add(Array As Object(0))
|
||||||
|
' Si todos los comandos se ejecutaron sin error, confirma la transacción.
|
||||||
|
con.TransactionSuccessful
|
||||||
|
Catch
|
||||||
|
' Si cualquier comando falla, se captura el error.
|
||||||
|
con.Rollback ' Se deshacen todos los cambios hechos en la transacción.
|
||||||
|
Log(LastException)
|
||||||
|
SendPlainTextError(resp, 500, LastException.Message)
|
||||||
|
End Try
|
||||||
|
' Serializa y envía la respuesta al cliente.
|
||||||
|
Dim data() As Byte = ser.ConvertObjectToBytes(res)
|
||||||
|
resp.OutputStream.WriteBytes(data, 0, data.Length)
|
||||||
|
' Devuelve un resumen para el log.
|
||||||
|
Return $"batch (size=${commands.Size})"$
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Código compilado condicionalmente para el protocolo antiguo (V1).
|
||||||
|
'#if VERSION1
|
||||||
|
|
||||||
|
' Ejecuta un lote de comandos usando el protocolo V1.
|
||||||
|
Private Sub ExecuteBatch(DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
|
' Lee y descarta la versión del cliente.
|
||||||
|
Dim clientVersion As Float = ReadObject(in) 'ignore
|
||||||
|
' Lee cuántos comandos vienen en el lote.
|
||||||
|
Dim numberOfStatements As Int = ReadInt(in)
|
||||||
|
Dim res(numberOfStatements) As Int ' Array para resultados (aunque no se usa).
|
||||||
|
Try
|
||||||
|
con.BeginTransaction
|
||||||
|
' Itera para procesar cada comando del lote.
|
||||||
|
For i = 0 To numberOfStatements - 1
|
||||||
|
' Lee el nombre del comando y la lista de parámetros usando el deserializador V1.
|
||||||
|
Dim queryName As String = ReadObject(in)
|
||||||
|
Dim params As List = ReadList(in)
|
||||||
|
|
||||||
|
Dim sqlCommand As String = Connector.GetCommand(DB, queryName)
|
||||||
|
|
||||||
|
' <<< INICIO NUEVA VALIDACIÓN: VERIFICAR SI EL COMANDO EXISTE (V1) >>>
|
||||||
|
If sqlCommand = Null Or sqlCommand = "null" Or sqlCommand.Trim = "" Then
|
||||||
|
con.Rollback
|
||||||
|
Dim errorMessage As String = $"El comando '${queryName}' no fue encontrado en el config.properties de '${DB}'."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
' <<< FIN NUEVA VALIDACIÓN >>>
|
||||||
|
|
||||||
|
' --- INICIO VALIDACIÓN DE PARÁMETROS DENTRO DEL BATCH (V1) ---
|
||||||
|
If sqlCommand.Contains("?") Or (params <> Null And params.Size > 0) Then
|
||||||
|
Dim expectedParams As Int = sqlCommand.Length - sqlCommand.Replace("?", "").Length
|
||||||
|
Dim receivedParams As Int
|
||||||
|
If params = Null Then receivedParams = 0 Else receivedParams = params.Size
|
||||||
|
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
con.Rollback
|
||||||
|
Dim errorMessage As String = $"Número de parametros equivocado para "${queryName}". Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
End If
|
||||||
|
' --- FIN VALIDACIÓN ---
|
||||||
|
|
||||||
|
' Ejecuta el comando.
|
||||||
|
con.ExecNonQuery2(sqlCommand, params)
|
||||||
|
Next
|
||||||
|
' Confirma la transacción.
|
||||||
|
con.TransactionSuccessful
|
||||||
|
|
||||||
|
' Comprime la salida antes de enviarla.
|
||||||
|
Dim out As OutputStream = cs.WrapOutputStream(resp.OutputStream, "gzip")
|
||||||
|
' Escribe la respuesta usando el serializador V1.
|
||||||
|
WriteObject(Main.VERSION, out)
|
||||||
|
WriteObject("batch", out)
|
||||||
|
WriteInt(res.Length, out)
|
||||||
|
For Each r As Int In res
|
||||||
|
WriteInt(r, out)
|
||||||
|
Next
|
||||||
|
out.Close
|
||||||
|
Catch
|
||||||
|
con.Rollback
|
||||||
|
Log(LastException)
|
||||||
|
SendPlainTextError(resp, 500, LastException.Message)
|
||||||
|
End Try
|
||||||
|
Return $"batch (size=${numberOfStatements})"$
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Ejecuta una consulta única usando el protocolo V1.
|
||||||
|
Private Sub ExecuteQuery(DB As String, con As SQL, in As InputStream, resp As ServletResponse) As String
|
||||||
|
Log("====================== ExecuteQuery =====================")
|
||||||
|
' Deserializa los datos de la petición usando el protocolo V1.
|
||||||
|
Dim clientVersion As Float = ReadObject(in) 'ignore
|
||||||
|
Dim queryName As String = ReadObject(in)
|
||||||
|
Dim limit As Int = ReadInt(in)
|
||||||
|
Dim params As List = ReadList(in)
|
||||||
|
' Obtiene la sentencia SQL.
|
||||||
|
Dim theSql As String = Connector.GetCommand(DB, queryName)
|
||||||
|
Log(444 & "|" & theSql)
|
||||||
|
|
||||||
|
' <<< INICIO NUEVA VALIDACIÓN: VERIFICAR SI EL COMANDO EXISTE (V1) >>>
|
||||||
|
If theSql = Null Or theSql ="null" Or theSql.Trim = "" Then
|
||||||
|
Dim errorMessage As String = $"El comando '${queryName}' no fue encontrado en el config.properties de '${DB}'."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
' <<< FIN NUEVA VALIDACIÓN >>>
|
||||||
|
|
||||||
|
' --- INICIO VALIDACIÓN DE PARÁMETROS (V1) ---
|
||||||
|
If theSql.Contains("?") Or (params <> Null And params.Size > 0) Then
|
||||||
|
Dim expectedParams As Int = theSql.Length - theSql.Replace("?", "").Length
|
||||||
|
Dim receivedParams As Int
|
||||||
|
If params = Null Then receivedParams = 0 Else receivedParams = params.Size
|
||||||
|
|
||||||
|
If expectedParams <> receivedParams Then
|
||||||
|
Dim errorMessage As String = $"Número de parametros equivocado para "${queryName}". Se esperaban ${expectedParams} y se recibieron ${receivedParams}."$
|
||||||
|
Log(errorMessage)
|
||||||
|
SendPlainTextError(resp, 400, errorMessage)
|
||||||
|
Return "error"
|
||||||
|
End If
|
||||||
|
End If
|
||||||
|
' --- FIN VALIDACIÓN ---
|
||||||
|
|
||||||
|
' Ejecuta la consulta.
|
||||||
|
Dim rs As ResultSet = con.ExecQuery2(theSql, params)
|
||||||
|
If limit <= 0 Then limit = 0x7fffffff 'max int
|
||||||
|
Dim jrs As JavaObject = rs
|
||||||
|
Dim rsmd As JavaObject = jrs.RunMethod("getMetaData", Null)
|
||||||
|
Dim cols As Int = rs.ColumnCount
|
||||||
|
' Comprime el stream de salida.
|
||||||
|
Dim out As OutputStream = cs.WrapOutputStream(resp.OutputStream, "gzip")
|
||||||
|
' Escribe la cabecera de la respuesta V1.
|
||||||
|
WriteObject(Main.VERSION, out)
|
||||||
|
WriteObject("query", out)
|
||||||
|
WriteInt(rs.ColumnCount, out)
|
||||||
|
' Escribe los nombres de las columnas.
|
||||||
|
For i = 0 To cols - 1
|
||||||
|
WriteObject(rs.GetColumnName(i), out)
|
||||||
|
Next
|
||||||
|
|
||||||
|
' Itera sobre las filas del resultado.
|
||||||
|
Do While rs.NextRow And limit > 0
|
||||||
|
' Escribe un byte '1' para indicar que viene una fila.
|
||||||
|
WriteByte(1, out)
|
||||||
|
' Itera sobre las columnas de la fila.
|
||||||
|
For i = 0 To cols - 1
|
||||||
|
Dim ct As Int = rsmd.RunMethod("getColumnType", Array(i + 1))
|
||||||
|
' Maneja los tipos de datos binarios de forma especial.
|
||||||
|
If ct = -2 Or ct = 2004 Or ct = -3 Or ct = -4 Then
|
||||||
|
WriteObject(rs.GetBlob2(i), out)
|
||||||
|
Else
|
||||||
|
' Escribe el valor de la columna.
|
||||||
|
WriteObject(jrs.RunMethod("getObject", Array(i + 1)), out)
|
||||||
|
End If
|
||||||
|
Next
|
||||||
|
limit = limit - 1
|
||||||
|
Loop
|
||||||
|
' Escribe un byte '0' para indicar el fin de las filas.
|
||||||
|
WriteByte(0, out)
|
||||||
|
out.Close
|
||||||
|
rs.Close
|
||||||
|
|
||||||
|
Return "query: " & queryName
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Escribe un único byte en el stream de salida.
|
||||||
|
Private Sub WriteByte(value As Byte, out As OutputStream)
|
||||||
|
out.WriteBytes(Array As Byte(value), 0, 1)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Serializador principal para el protocolo V1. Escribe un objeto al stream.
|
||||||
|
Private Sub WriteObject(o As Object, out As OutputStream)
|
||||||
|
Dim data() As Byte
|
||||||
|
' Escribe un byte de tipo seguido de los datos.
|
||||||
|
If o = Null Then
|
||||||
|
out.WriteBytes(Array As Byte(T_NULL), 0, 1)
|
||||||
|
Else If o Is Short Then
|
||||||
|
out.WriteBytes(Array As Byte(T_SHORT), 0, 1)
|
||||||
|
data = bc.ShortsToBytes(Array As Short(o))
|
||||||
|
Else If o Is Int Then
|
||||||
|
out.WriteBytes(Array As Byte(T_INT), 0, 1)
|
||||||
|
data = bc.IntsToBytes(Array As Int(o))
|
||||||
|
Else If o Is Float Then
|
||||||
|
out.WriteBytes(Array As Byte(T_FLOAT), 0, 1)
|
||||||
|
data = bc.FloatsToBytes(Array As Float(o))
|
||||||
|
Else If o Is Double Then
|
||||||
|
out.WriteBytes(Array As Byte(T_DOUBLE), 0, 1)
|
||||||
|
data = bc.DoublesToBytes(Array As Double(o))
|
||||||
|
Else If o Is Long Then
|
||||||
|
out.WriteBytes(Array As Byte(T_LONG), 0, 1)
|
||||||
|
data = bc.LongsToBytes(Array As Long(o))
|
||||||
|
Else If o Is Boolean Then
|
||||||
|
out.WriteBytes(Array As Byte(T_BOOLEAN), 0, 1)
|
||||||
|
Dim b As Boolean = o
|
||||||
|
Dim data(1) As Byte
|
||||||
|
If b Then data(0) = 1 Else data(0) = 0
|
||||||
|
Else If GetType(o) = "[B" Then ' Si el objeto es un array de bytes (BLOB)
|
||||||
|
data = o
|
||||||
|
out.WriteBytes(Array As Byte(T_BLOB), 0, 1)
|
||||||
|
' Escribe la longitud de los datos antes de los datos mismos.
|
||||||
|
WriteInt(data.Length, out)
|
||||||
|
Else ' Trata todo lo demás como un String
|
||||||
|
out.WriteBytes(Array As Byte(T_STRING), 0, 1)
|
||||||
|
data = bc.StringToBytes(o, "UTF8")
|
||||||
|
' Escribe la longitud del string antes del string.
|
||||||
|
WriteInt(data.Length, out)
|
||||||
|
End If
|
||||||
|
' Escribe los bytes del dato.
|
||||||
|
If data.Length > 0 Then out.WriteBytes(data, 0, data.Length)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Deserializador principal para el protocolo V1. Lee un objeto del stream.
|
||||||
|
Private Sub ReadObject(In As InputStream) As Object
|
||||||
|
' Lee el primer byte para determinar el tipo de dato.
|
||||||
|
Dim data(1) As Byte
|
||||||
|
In.ReadBytes(data, 0, 1)
|
||||||
|
Select data(0)
|
||||||
|
Case T_NULL
|
||||||
|
Return Null
|
||||||
|
Case T_SHORT
|
||||||
|
Dim data(2) As Byte
|
||||||
|
Return bc.ShortsFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
Case T_INT
|
||||||
|
Dim data(4) As Byte
|
||||||
|
Return bc.IntsFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
Case T_LONG
|
||||||
|
Dim data(8) As Byte
|
||||||
|
Return bc.LongsFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
Case T_FLOAT
|
||||||
|
Dim data(4) As Byte
|
||||||
|
Return bc.FloatsFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
Case T_DOUBLE
|
||||||
|
Dim data(8) As Byte
|
||||||
|
Return bc.DoublesFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
Case T_BOOLEAN
|
||||||
|
Dim b As Byte = ReadByte(In)
|
||||||
|
Return b = 1
|
||||||
|
Case T_BLOB
|
||||||
|
' Lee la longitud, luego lee esa cantidad de bytes.
|
||||||
|
Dim len As Int = ReadInt(In)
|
||||||
|
Dim data(len) As Byte
|
||||||
|
Return ReadBytesFully(In, data, data.Length)
|
||||||
|
Case Else ' T_STRING
|
||||||
|
' Lee la longitud, luego lee esa cantidad de bytes y los convierte a string.
|
||||||
|
Dim len As Int = ReadInt(In)
|
||||||
|
Dim data(len) As Byte
|
||||||
|
ReadBytesFully(In, data, data.Length)
|
||||||
|
Return BytesToString(data, 0, data.Length, "UTF8")
|
||||||
|
End Select
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Se asegura de leer exactamente la cantidad de bytes solicitada del stream.
|
||||||
|
Private Sub ReadBytesFully(In As InputStream, Data() As Byte, Len As Int) As Byte()
|
||||||
|
Dim count = 0, Read As Int
|
||||||
|
' Sigue leyendo en un bucle hasta llenar el buffer, por si los datos llegan en partes.
|
||||||
|
Do While count < Len And Read > -1
|
||||||
|
Read = In.ReadBytes(Data, count, Len - count)
|
||||||
|
count = count + Read
|
||||||
|
Loop
|
||||||
|
Return Data
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Escribe un entero (4 bytes) en el stream.
|
||||||
|
Private Sub WriteInt(i As Int, out As OutputStream)
|
||||||
|
Dim data() As Byte
|
||||||
|
data = bc.IntsToBytes(Array As Int(i))
|
||||||
|
out.WriteBytes(data, 0, data.Length)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Lee un entero (4 bytes) del stream.
|
||||||
|
Private Sub ReadInt(In As InputStream) As Int
|
||||||
|
Dim data(4) As Byte
|
||||||
|
Return bc.IntsFromBytes(ReadBytesFully(In, data, data.Length))(0)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Lee un solo byte del stream.
|
||||||
|
Private Sub ReadByte(In As InputStream) As Byte
|
||||||
|
Dim data(1) As Byte
|
||||||
|
In.ReadBytes(data, 0, 1)
|
||||||
|
Return data(0)
|
||||||
|
End Sub
|
||||||
|
|
||||||
|
' Lee una lista de objetos del stream (protocolo V1).
|
||||||
|
Private Sub ReadList(in As InputStream) As List
|
||||||
|
' Primero lee la cantidad de elementos en la lista.
|
||||||
|
Dim len As Int = ReadInt(in)
|
||||||
|
Dim l1 As List
|
||||||
|
l1.Initialize
|
||||||
|
' Luego lee cada objeto uno por uno y lo añade a la lista.
|
||||||
|
For i = 0 To len - 1
|
||||||
|
l1.Add(ReadObject(in))
|
||||||
|
Next
|
||||||
|
Return l1
|
||||||
|
End Sub
|
||||||
|
'#end If
|
||||||
|
|
||||||
|
' Envía una respuesta de error en formato de texto plano.
|
||||||
|
' Esto evita la página de error HTML por defecto que genera resp.SendError.
|
||||||
|
' resp: El objeto ServletResponse para enviar la respuesta.
|
||||||
|
' statusCode: El código de estado HTTP (ej. 400 para Bad Request, 500 para Internal Server Error).
|
||||||
|
' errorMessage: El mensaje de error que se enviará al cliente.
|
||||||
|
Private Sub SendPlainTextError(resp As ServletResponse, statusCode As Int, errorMessage As String)
|
||||||
|
Try
|
||||||
|
' Establece el código de estado HTTP (ej. 400, 500).
|
||||||
|
resp.Status = statusCode
|
||||||
|
|
||||||
|
' Define el tipo de contenido como texto plano, con codificación UTF-8 para soportar acentos.
|
||||||
|
resp.ContentType = "text/plain; charset=utf-8"
|
||||||
|
|
||||||
|
' Obtiene el OutputStream de la respuesta para escribir los datos directamente.
|
||||||
|
Dim out As OutputStream = resp.OutputStream
|
||||||
|
|
||||||
|
' Convierte el mensaje de error a un array de bytes usando UTF-8.
|
||||||
|
Dim data() As Byte = errorMessage.GetBytes("UTF8")
|
||||||
|
|
||||||
|
' Escribe los bytes en el stream de salida.
|
||||||
|
out.WriteBytes(data, 0, data.Length)
|
||||||
|
|
||||||
|
' Cierra el stream para asegurar que todos los datos se envíen correctamente.
|
||||||
|
out.Close
|
||||||
|
Catch
|
||||||
|
' Si algo falla al intentar enviar la respuesta de error, lo registra en el log
|
||||||
|
' para que no se pierda la causa original del problema.
|
||||||
|
Log("Error sending plain text error response: " & LastException)
|
||||||
|
End Try
|
||||||
|
End Sub
|
||||||
15
Manager.bas
15
Manager.bas
@@ -22,7 +22,7 @@ Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|||||||
' rdcc.Initialize
|
' rdcc.Initialize
|
||||||
Private estaDB As String = ""
|
Private estaDB As String = ""
|
||||||
' Log(Main.listaDeCP)
|
' Log(Main.listaDeCP)
|
||||||
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <a href="/manager?command=rpm2">Reiniciar</a> | <a href="/manager?command=reviveBow">Revive Bow</a> | </br></br>"$)
|
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <br/>"$)
|
||||||
For i = 0 To Main.listaDeCP.Size - 1
|
For i = 0 To Main.listaDeCP.Size - 1
|
||||||
Main.Connectors.Get(Main.listaDeCP.get(i)).As(RDCConnector).Initialize(Main.listaDeCP.get(i))
|
Main.Connectors.Get(Main.listaDeCP.get(i)).As(RDCConnector).Initialize(Main.listaDeCP.get(i))
|
||||||
If Main.listaDeCP.get(i) <> "DB1" Then estaDB = "." & Main.listaDeCP.get(i) Else estaDB = ""
|
If Main.listaDeCP.get(i) <> "DB1" Then estaDB = "." & Main.listaDeCP.get(i) Else estaDB = ""
|
||||||
@@ -42,7 +42,7 @@ Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|||||||
' shl.WorkingDirectory = GlobalParameters.WorkingDirectory
|
' shl.WorkingDirectory = GlobalParameters.WorkingDirectory
|
||||||
' shl.Run(-1)
|
' shl.Run(-1)
|
||||||
else If Command = "rsx" Then 'Reiniciamos el servidor DBReq
|
else If Command = "rsx" Then 'Reiniciamos el servidor DBReq
|
||||||
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <a href="/manager?command=rpm2">Reiniciar</a> | <a href="/manager?command=reviveBow">Revive Bow</a> | </br></br>"$)
|
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <br/>"$)
|
||||||
Log($"Ejecutamos ${File.DirApp}\start.bat"$)
|
Log($"Ejecutamos ${File.DirApp}\start.bat"$)
|
||||||
resp.Write($"Ejecutamos ${File.DirApp}\start.bat"$)
|
resp.Write($"Ejecutamos ${File.DirApp}\start.bat"$)
|
||||||
Public shl As Shell
|
Public shl As Shell
|
||||||
@@ -50,22 +50,13 @@ Sub Handle(req As ServletRequest, resp As ServletResponse)
|
|||||||
shl.WorkingDirectory = File.DirApp
|
shl.WorkingDirectory = File.DirApp
|
||||||
shl.Run(-1)
|
shl.Run(-1)
|
||||||
else If Command = "rpm2" Then 'Reiniciamos el proceso DBReq en PM2
|
else If Command = "rpm2" Then 'Reiniciamos el proceso DBReq en PM2
|
||||||
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <a href="/manager?command=rpm2">Reiniciar</a> | <a href="/manager?command=reviveBow">Revive Bow</a> | </br></br>"$)
|
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <br/>"$)
|
||||||
Log($"Ejecutamos ${File.DirApp}\reiniciaProcesoPM2.bat"$)
|
Log($"Ejecutamos ${File.DirApp}\reiniciaProcesoPM2.bat"$)
|
||||||
resp.Write($"Ejecutamos ${File.DirApp}\reiniciaProcesoPM2.bat"$)
|
resp.Write($"Ejecutamos ${File.DirApp}\reiniciaProcesoPM2.bat"$)
|
||||||
Public shl As Shell
|
Public shl As Shell
|
||||||
shl.Initialize("shl","cmd",Array("/c",File.DirApp & "\reiniciaProcesoPM2.bat " & Main.srvr.Port))
|
shl.Initialize("shl","cmd",Array("/c",File.DirApp & "\reiniciaProcesoPM2.bat " & Main.srvr.Port))
|
||||||
shl.WorkingDirectory = File.DirApp
|
shl.WorkingDirectory = File.DirApp
|
||||||
shl.Run(-1)
|
shl.Run(-1)
|
||||||
else If Command = "reviveBow" Then 'Reiniciamos el proceso DBReq en PM2
|
|
||||||
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <a href="/manager?command=rpm2">Reiniciar</a> | <a href="/manager?command=reviveBow">Revive Bow</a> | </br></br>"$)
|
|
||||||
Log($"Ejecutamos ${File.DirApp}\reiniciaProcesoBow.bat"$)
|
|
||||||
resp.Write($"Ejecutamos ${File.DirApp}\reiniciaProcesoBow.bat<br><br>"$)
|
|
||||||
resp.Write($"!!!BOW REINICIANDO!!!"$)
|
|
||||||
Public shl As Shell
|
|
||||||
shl.Initialize("shl","cmd",Array("/c",File.DirApp & "\reiniciaProcesoBow.bat " & Main.srvr.Port))
|
|
||||||
shl.WorkingDirectory = File.DirApp
|
|
||||||
shl.Run(-1)
|
|
||||||
else If Command = "paused" Then
|
else If Command = "paused" Then
|
||||||
GlobalParameters.IsPaused = 1
|
GlobalParameters.IsPaused = 1
|
||||||
else If Command = "continue" Then
|
else If Command = "continue" Then
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ Public Sub Initialize(DB As String)
|
|||||||
' Log("RDCConnector Initialize")
|
' Log("RDCConnector Initialize")
|
||||||
If DB.EqualsIgnoreCase("DB1") Then DB = "" 'Esto para el config.properties por default
|
If DB.EqualsIgnoreCase("DB1") Then DB = "" 'Esto para el config.properties por default
|
||||||
Dim config As Map = LoadConfigMap(DB)
|
Dim config As Map = LoadConfigMap(DB)
|
||||||
Log($"Inicializamos ${DB}, usuario: ${config.Get("User")} - Puerto: ${config.Get("ServerPort")}"$)
|
Log($"Inicializamos ${DB}, usuario: ${config.Get("User")}"$)
|
||||||
pool.Initialize(config.Get("DriverClass"), config.Get("JdbcUrl"), config.Get("User"), config.Get("Password"))
|
pool.Initialize(config.Get("DriverClass"), config.Get("JdbcUrl"), config.Get("User"), config.Get("Password"))
|
||||||
Dim jo As JavaObject = pool
|
Dim jo As JavaObject = pool
|
||||||
jo.RunMethod("setMaxPoolSize", Array(5)) 'number of concurrent connections
|
jo.RunMethod("setMaxPoolSize", Array(5)) 'number of concurrent connections
|
||||||
@@ -72,7 +72,7 @@ Public Sub Initialize(DB As String)
|
|||||||
' Dim jo2 As JavaObject = pool
|
' Dim jo2 As JavaObject = pool
|
||||||
' Log(jo2.GetField("END_TO_END_CLIENTID_INDEX"))
|
' Log(jo2.GetField("END_TO_END_CLIENTID_INDEX"))
|
||||||
|
|
||||||
' jo.RunMethod("setPreferredTestQuery", Array("BEGIN DBMS_SESSION.SET_IDENTIFIER('jRDC_Multi'); END;"))
|
' jo.RunMethod("setPreferredTestQuery", Array("BEGIN DBMS_SESSION.SET_IDENTIFIER('whatever'); END;"))
|
||||||
' jo.RunMethod("setPreferredTestQuery", Array("alter session set current_schema=MYSCHEMA"))
|
' jo.RunMethod("setPreferredTestQuery", Array("alter session set current_schema=MYSCHEMA"))
|
||||||
' jo2.RunMethod("setClientIdentifier",Array( "MAX")) ' Tiempo máximo de inactividad antes de cerrar una conexión
|
' jo2.RunMethod("setClientIdentifier",Array( "MAX")) ' Tiempo máximo de inactividad antes de cerrar una conexión
|
||||||
#if DEBUG
|
#if DEBUG
|
||||||
@@ -88,32 +88,33 @@ End Sub
|
|||||||
Private Sub LoadConfigMap(DB As String) As Map
|
Private Sub LoadConfigMap(DB As String) As Map
|
||||||
Private DBX As String = ""
|
Private DBX As String = ""
|
||||||
If DB <> "" Then DBX = "." & DB
|
If DB <> "" Then DBX = "." & DB
|
||||||
Log("============= LoadConfigMap =============")
|
Log("===========================================")
|
||||||
Log($""========= Leemos el config${DBX}.properties ========="$)
|
Log($"Leemos el config${DBX}.properties"$)
|
||||||
Return File.ReadMap("./", "config" & DBX & ".properties")
|
Return File.ReadMap("./", "config" & DBX & ".properties")
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Public Sub GetCommand(DB As String, Key As String) As String
|
Public Sub GetCommand(DB As String, Key As String) As String
|
||||||
' Log("==== GetCommand ====")
|
Log("==== GetCommand ====")
|
||||||
' Log("|" & Key & "|")
|
' Log("|" & DB & "|" & Key & "|")
|
||||||
commands = Main.commandsMap.get(DB).As(Map)
|
commands = Main.commandsMap.get(DB).As(Map)
|
||||||
If commands.ContainsKey("sql." & Key) = False Then
|
If commands.ContainsKey("sql." & Key) = False Then
|
||||||
Log("*** Command not found: " & Key)
|
Log("*** Command not found: " & Key)
|
||||||
End If
|
End If
|
||||||
|
' Log(commands.ContainsKey("sql." & Key))
|
||||||
Log("========= Traemos """ & Key & """ ==========")
|
Log("========= Traemos """ & Key & """ ==========")
|
||||||
Log(">>>>>> " & commands.Get("sql." & Key) & " <<<<<<")
|
Log(">>>>>> " & commands.Get("sql." & Key) & " <<<<<<")
|
||||||
Return commands.Get("sql." & Key)
|
Return commands.Get("sql." & Key)
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Public Sub GetConnection(DB As String) As SQL
|
Public Sub GetConnection(DB As String) As SQL
|
||||||
Log("============= GetConnection ============= ")
|
Log("==== GetConnection ==== ")
|
||||||
If DB.EqualsIgnoreCase("DB1") Then DB = "" 'Esto para el config.properties or default
|
If DB.EqualsIgnoreCase("DB1") Then DB = "" 'Esto para el config.properties or default
|
||||||
If DebugQueries Then LoadSQLCommands(LoadConfigMap(DB), DB)
|
If DebugQueries Then LoadSQLCommands(LoadConfigMap(DB), DB)
|
||||||
' Log("regresamos 0")
|
|
||||||
Return pool.GetConnection
|
Return pool.GetConnection
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Private Sub LoadSQLCommands(config2 As Map, DB As String)
|
Private Sub LoadSQLCommands(config2 As Map, DB As String)
|
||||||
|
Log("==== LoadSQLCommands ==== ")
|
||||||
Log($"Cargamos los comandos desde el config.${DB}.properties"$)
|
Log($"Cargamos los comandos desde el config.${DB}.properties"$)
|
||||||
Dim newCommands As Map
|
Dim newCommands As Map
|
||||||
newCommands.Initialize
|
newCommands.Initialize
|
||||||
@@ -123,7 +124,6 @@ Private Sub LoadSQLCommands(config2 As Map, DB As String)
|
|||||||
End If
|
End If
|
||||||
Next
|
Next
|
||||||
commands = newCommands
|
commands = newCommands
|
||||||
' Log(commands)
|
|
||||||
' Log($"Inicializado: ${DB} "$ & Main.commandsMap.IsInitialized)
|
' Log($"Inicializado: ${DB} "$ & Main.commandsMap.IsInitialized)
|
||||||
Main.commandsMap.Put(DB, commands)
|
Main.commandsMap.Put(DB, commands)
|
||||||
End Sub
|
End Sub
|
||||||
|
|||||||
59
README.md
59
README.md
@@ -1,48 +1,41 @@
|
|||||||
# jRDC-Multi (B4J)
|
# Servidor jRDC2-Multi Modificado (B4J)
|
||||||
Servidor de DBRequest que puede cargar hasta 4 archivos de config.properties al mismo tiempo.
|
|
||||||
|
|
||||||
Los archivos se deben de llamar:
|
## 1. Introducción
|
||||||
|
|
||||||
- config.propierties
|
Este proyecto es una versión modificada del servidor [jRDC2 original](https://www.b4x.com/android/forum/threads/b4x-jrdc2-b4j-implementation-of-rdc-remote-database-connector.61801/#content), diseñada para actuar como un backend robusto y flexible. Su función principal es recibir peticiones HTTP, ejecutar comandos SQL predefinidos contra una base de datos y devolver los resultados en un formato estructurado.
|
||||||
- config.DB2.properties
|
|
||||||
- config.DB3.properties
|
|
||||||
- config.DB4.properties
|
|
||||||
|
|
||||||
No es necesario que sean 4 archivos, solo toma en cuenta los archivos existentes en el directorio.
|
Ha sido adaptado para servir tanto a clientes nativos (B4A/B4i) como a clientes web modernos (JavaScript, a través de frameworks como React, Vue, Angular, etc.).
|
||||||
|
|
||||||
En la aplicacion movil, al URL del servidor se le agrega al final /DB2, /DB3 o /DB4. (Puerto de ejemplo: 1781)
|
## 2. Características Principales
|
||||||
|
|
||||||
- Para usar el config.properties => http://keymon.lat:1781
|
* **Soporte para Múltiples Bases de Datos**: Puede cargar y gestionar hasta 4 archivos de configuración (`config.properties`) simultáneamente.
|
||||||
- Para usar el config.DB2.properties => http://keymon.lat:1781/DB2
|
* **Comandos SQL Externalizados**: Las sentencias SQL se definen en los archivos de configuración, permitiendo modificarlas sin recompilar el servidor.
|
||||||
- Para usar el config.DB3.properties => http://keymon.lat:1781/DB3
|
* **Doble Handler de Peticiones**: Incluye un handler clásico para clientes B4X y un handler JSON para clientes web.
|
||||||
- Para usar el config.DB4.properties => http://keymon.lat:1781/DB4
|
* **Validaciones de Seguridad**: Verifica la existencia de comandos y la correspondencia en el número de parámetros.
|
||||||
|
* **Administración Remota**: Permite verificar el estado, recargar la configuración y reiniciar el servidor a través de URLs específicas.
|
||||||
|
|
||||||
El puerto es el mismo para todos los archivos, **sin importar** que diga en cada archivo, solo toma el puerto especificado en el **primer** config.properties.
|
## 3. Configuración
|
||||||
|
|
||||||
El usuario, contraseña y JdbcUrl, **si** los toma del archivo correspondiente.
|
### 3.1. Archivos de Configuración
|
||||||
|
|
||||||
Se puede revisar el **estatus** del servidor en el URL:
|
El sistema está preparado para manejar hasta **cuatro configuraciones de bases de datos** (de `DB1` a `DB4`). No es necesario tener los cuatro archivos; el servidor cargará únicamente los que encuentre.
|
||||||
|
|
||||||
- http://keymon.lat:1781/test
|
La nomenclatura de los archivos es fundamental:
|
||||||
|
|
||||||
Se puede forzar al servidor (**sin reiniciarlo**) a que **recargue** los archivos config.properties en el URL:
|
* `config.properties` (para `DB1`)
|
||||||
|
* `config.DB2.properties`
|
||||||
|
* `config.DB3.properties`
|
||||||
|
* `config.DB4.properties`
|
||||||
|
|
||||||
- http://keymon.lat:1781/manager?command=reload
|
**Notas importantes:**
|
||||||
|
|
||||||
Se puede reiniciar el servidor con el URL:
|
* El **puerto** del servidor se toma **únicamente** del archivo principal `config.properties`, sin importar lo que digan los demás.
|
||||||
|
* Los datos de conexión (`JdbcUrl`, usuario, contraseña) sí se toman del archivo correspondiente a cada base de datos.
|
||||||
|
|
||||||
- http://keymon.lat:1781/manager?command=rsx
|
### 3.2. Añadir Drivers de Bases de Datos Adicionales
|
||||||
- Este comando utiliza los archivos start.bat, start2.bat y stop.bat
|
|
||||||
|
|
||||||
Si se esta corriendo el servidor con PM2, se puede reinciar con el URL:
|
Si necesitas conectarte a otros tipos de bases de datos (ej. Oracle), debes agregar el archivo del controlador `.jar` al proyecto antes de compilar. En el módulo `Main`, añade una línea como la siguiente:
|
||||||
|
|
||||||
- http://keymon.lat:1781/manager?command=rpm2
|
```b4x
|
||||||
- Este comando ejecuta el archivo reiniciaProcesoPM2.bat, y **asume** que el nombre del proceso es "RDC-Multi", si no es asi, hay que **modificar** el archivo .bat
|
' Este es el nombre del archivo .jar, en este caso "C:\Ruta\Adicional\ojdbc11.jar"
|
||||||
|
#AdditionalJar: ojdbc11
|
||||||
## Agregar drivers de mas bases de datos
|
|
||||||
|
|
||||||
Si se necesitan agregar mas controladores para conectarse a otras bases de datos, hay que agregar una linea a "Main":
|
|
||||||
|
|
||||||
- #AdditionalJar: ojdbc11 <= este es el nombre del archivo .jar, en este caso "C:\Android\AdditionalLibs\B4J\ojdbc11.jar"
|
|
||||||
|
|
||||||
- Al compilar la aplicación, el archivo del controlador se incluye en el archivo .jar del servidor (jRDC-Multi.jar) y no es necesario copiarlo o agregarlo al directorio del servidor en producción.
|
|
||||||
48
README0.md
Normal file
48
README0.md
Normal file
@@ -0,0 +1,48 @@
|
|||||||
|
# jRDC-Multi (B4J)
|
||||||
|
Servidor de DBRequest que puede cargar hasta 4 archivos de config.properties al mismo tiempo.
|
||||||
|
|
||||||
|
Los archivos se deben de llamar:
|
||||||
|
|
||||||
|
- config.propierties
|
||||||
|
- config.DB2.properties
|
||||||
|
- config.DB3.properties
|
||||||
|
- config.DB4.properties
|
||||||
|
|
||||||
|
No es necesario que sean 4 archivos, solo toma en cuenta los archivos existentes en el directorio.
|
||||||
|
|
||||||
|
En la aplicacion movil, al URL del servidor se le agrega al final /DB2, /DB3 o /DB4. (Puerto de ejemplo: 1781)
|
||||||
|
|
||||||
|
- Para usar el config.properties => http://keymon.lat:1781
|
||||||
|
- Para usar el config.DB2.properties => http://keymon.lat:1781/DB2
|
||||||
|
- Para usar el config.DB3.properties => http://keymon.lat:1781/DB3
|
||||||
|
- Para usar el config.DB4.properties => http://keymon.lat:1781/DB4
|
||||||
|
|
||||||
|
El puerto es el mismo para todos los archivos, **sin importar** que diga en cada archivo, solo toma el puerto especificado en el **primer** config.properties.
|
||||||
|
|
||||||
|
El usuario, contraseña y JdbcUrl, **si** los toma del archivo correspondiente.
|
||||||
|
|
||||||
|
Se puede revisar el **estatus** del servidor en el URL:
|
||||||
|
|
||||||
|
- http://keymon.lat:1781/test
|
||||||
|
|
||||||
|
Se puede forzar al servidor (**sin reiniciarlo**) a que **recargue** los archivos config.properties en el URL:
|
||||||
|
|
||||||
|
- http://keymon.lat:1781/manager?command=reload
|
||||||
|
|
||||||
|
Se puede reiniciar el servidor con el URL:
|
||||||
|
|
||||||
|
- http://keymon.lat:1781/manager?command=rsx
|
||||||
|
- Este comando utiliza los archivos start.bat, start2.bat y stop.bat
|
||||||
|
|
||||||
|
Si se esta corriendo el servidor con PM2, se puede reinciar con el URL:
|
||||||
|
|
||||||
|
- http://keymon.lat:1781/manager?command=rpm2
|
||||||
|
- Este comando ejecuta el archivo reiniciaProcesoPM2.bat, y **asume** que el nombre del proceso es "RDC-Multi", si no es asi, hay que **modificar** el archivo .bat
|
||||||
|
|
||||||
|
## Agregar drivers de mas bases de datos
|
||||||
|
|
||||||
|
Si se necesitan agregar mas controladores para conectarse a otras bases de datos, hay que agregar una linea a "Main":
|
||||||
|
|
||||||
|
- #AdditionalJar: ojdbc11 <= este es el nombre del archivo .jar, en este caso "C:\Android\AdditionalLibs\B4J\ojdbc11.jar"
|
||||||
|
|
||||||
|
- Al compilar la aplicación, el archivo del controlador se incluye en el archivo .jar del servidor (jRDC-Multi.jar) y no es necesario copiarlo o agregarlo al directorio del servidor en producción.
|
||||||
@@ -16,7 +16,7 @@ End Sub
|
|||||||
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
Sub Handle(req As ServletRequest, resp As ServletResponse)
|
||||||
Log("TEST")
|
Log("TEST")
|
||||||
resp.ContentType = "text/html"
|
resp.ContentType = "text/html"
|
||||||
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <a href="/manager?command=rpm2">Reiniciar</a> | <a href="/manager?command=reviveBow">Revive Bow</a> | </br></br>"$)
|
resp.Write($"<a href="/test">Test</a> | <a href="/manager?command=reload">Reload</a> | <br/>"$)
|
||||||
resp.Write($"RemoteServer is running on port <strong>${Main.srvr.Port}</strong> ($DateTime{DateTime.Now})<br/>"$)
|
resp.Write($"RemoteServer is running on port <strong>${Main.srvr.Port}</strong> ($DateTime{DateTime.Now})<br/>"$)
|
||||||
Try
|
Try
|
||||||
' Dim con As SQL = Main.rdcConnectorDB1.GetConnection("")
|
' Dim con As SQL = Main.rdcConnectorDB1.GetConnection("")
|
||||||
|
|||||||
@@ -1,77 +0,0 @@
|
|||||||
#Lines starting with '#' are comments.
|
|
||||||
#Backslash character at the end of line means that the command continues in the next line.
|
|
||||||
|
|
||||||
DriverClass=oracle.jdbc.driver.OracleDriver
|
|
||||||
#JdbcUrl=jdbc:mysql://localhost/test?characterEncoding=utf8
|
|
||||||
|
|
||||||
#SQL Server
|
|
||||||
#DriverClass=net.sourceforge.jtds.jdbc.Driver
|
|
||||||
|
|
||||||
# este para produccion GHAN JdbcUrl=jdbc:oracle:thin:@//192.168.15.53:1521/DBKMT
|
|
||||||
#GOHAN ---> server
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.205:1521/DBKMT
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.236:1521/DBKMT
|
|
||||||
JdbcUrl=jdbc:oracle:thin:@//192.168.101.13:1521/DBKMT
|
|
||||||
|
|
||||||
# SVR-KEYMON-PRODUCCION--> Usuario
|
|
||||||
User=SALMA
|
|
||||||
Password=SALMAD2016M
|
|
||||||
|
|
||||||
#User=TORRADOCONAUTO
|
|
||||||
#Password=TORRADOCONAUTOD2016M
|
|
||||||
|
|
||||||
|
|
||||||
#--> Puertos
|
|
||||||
#SAC - DFR - MDA / GOHAN -->COBRANZA
|
|
||||||
#ServerPort=1783
|
|
||||||
#GUNA - SALMA - DURAKELO - DBC / SVR-KEYMON-PRODUCCION --> DISTRIBUIDORAS
|
|
||||||
ServerPort=9010
|
|
||||||
#CMG - TORRADO / TRUNKS -->COBRANZA/ GM
|
|
||||||
#ServerPort=1781
|
|
||||||
|
|
||||||
#If Debug is true then this file will be reloaded on every query.
|
|
||||||
#This is useful if you need to modify the queries.
|
|
||||||
Debug=true
|
|
||||||
|
|
||||||
#SQL COMMANDS
|
|
||||||
|
|
||||||
##################
|
|
||||||
#################
|
|
||||||
################ S O P O R T E
|
|
||||||
#################
|
|
||||||
##################
|
|
||||||
|
|
||||||
sql.traeConexion=select 'DB2' as conexion from dual
|
|
||||||
sql.select_soporte=select * from GUNA.soporte
|
|
||||||
sql.select_conexion=SELECT 'OK' AS VALOR FROM DUAL
|
|
||||||
|
|
||||||
sql.select_almacenes_KELL=select CAT_AG_ID, CAT_AG_NOMBRE from KELLOGGS.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_GUNA=select CAT_AG_ID, CAT_AG_NOMBRE from GUNA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_SALMA=select CAT_AG_ID, CAT_AG_NOMBRE from SALMA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_DANVIT=select CAT_AG_ID, CAT_AG_NOMBRE from DANVIT.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
|
|
||||||
sql.proc_QUITAR_VENTA_KELL=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_VENTA_X_TIPO( '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_GUNA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN GUNA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS, '''||(?)||'''); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_SALMA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN SALMA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_DANVIT=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN DANVIT.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_PAGOPAGARE_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_ELIMINAS_PAGOS_PAGARES_REP( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_FACTURACION_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LIBERA_FACTURACION(Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_CARGAFORANEA_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LLENAR_FILTROS ( '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
|
|
||||||
sql.proc_QUITAR_TICKET_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_TICKET( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
sql.revisa_liquidada_Guna=SELECT COUNT(*) as liquidada FROM GUNA.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) AND (HVD_DESCUENTO != 0 or HVD_FECHA_AVION IS NOT NULL)
|
|
||||||
sql.revisa_liquidada_Kell=SELECT COUNT(*) as liquidada FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) and HVD_TIPOVENTA = (?) AND HVD_ESTATUS = 'Liquidado'
|
|
||||||
|
|
||||||
sql.select_todos_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosGUNA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id left join cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosKELLOGGS_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from KELLOGGS.cat_logins left join KELLOGGS.cat_agencias on cat_lo_agencia = cat_ag_id left join KELLOGGS.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosSALMA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta as cat_ru_ruta from SALMA.cat_logins left join SALMA.cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosDANVIT_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from DANVIT.cat_logins left join DANVIT.cat_agencias on cat_lo_agencia = cat_ag_id left join DANVIT.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_ventaXrutaGuna_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaKelloggs_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from KELLOGGS.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) and hvd_tipoventa=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaSalma_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from SALMA.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaDanvit_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from DANVIT.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_prodsTicket_Kelloggs=SELECT HVD_CLIENTE CLIENTE, HVD_PROID PRODUCTO_ID, HVD_PRONOMBRE NOMBRE_PRODUCTO, HVD_CANT CANTIDAD, HVD_COSTO_TOT COSTO_TOTAL, HVD_RUTA RUTA, HVD_CODPROMO CODPROMO,NVL(HVD_TIPOVENTA,' ') TIPOVENTA, NVL(HVD_ESTATUS,' ') ESTATUS, hvd_cedis FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE TRUNC(HVD_FECHA) = TRUNC(SYSDATE) AND HVD_ALMACEN = (?) AND HVD_CLIENTE = (?) and hvd_rechazo is null ORDER BY HVD_CODPROMO, HVD_PRONOMBRE
|
|
||||||
|
|
||||||
@@ -1,76 +0,0 @@
|
|||||||
#Lines starting with '#' are comments.
|
|
||||||
#Backslash character at the end of line means that the command continues in the next line.
|
|
||||||
|
|
||||||
DriverClass=oracle.jdbc.driver.OracleDriver
|
|
||||||
#JdbcUrl=jdbc:mysql://localhost/test?characterEncoding=utf8
|
|
||||||
|
|
||||||
#SQL Server
|
|
||||||
#DriverClass=net.sourceforge.jtds.jdbc.Driver
|
|
||||||
|
|
||||||
# este para produccion GHAN JdbcUrl=jdbc:oracle:thin:@//192.168.15.53:1521/DBKMT
|
|
||||||
#GOHAN ---> server
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.205:1521/DBKMT
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.236:1521/DBKMT
|
|
||||||
JdbcUrl=jdbc:oracle:thin:@//192.168.101.12:1521/DBKMT
|
|
||||||
|
|
||||||
|
|
||||||
# SVR-KEYMON-PRODUCCION--> Usuario
|
|
||||||
#User=GUNA
|
|
||||||
#Password=GUNAD2015M
|
|
||||||
|
|
||||||
User=TORRADOCONAUTO
|
|
||||||
Password=TORRADOCONAUTOD2016M
|
|
||||||
|
|
||||||
#--> Puertos
|
|
||||||
#SAC - DFR - MDA / GOHAN -->COBRANZA
|
|
||||||
#ServerPort=1783
|
|
||||||
#GUNA - SALMA - DURAKELO - DBC / SVR-KEYMON-PRODUCCION --> DISTRIBUIDORAS
|
|
||||||
ServerPort=9010
|
|
||||||
#CMG - TORRADO / TRUNKS -->COBRANZA/ GM
|
|
||||||
#ServerPort=1781
|
|
||||||
|
|
||||||
#If Debug is true then this file will be reloaded on every query.
|
|
||||||
#This is useful if you need to modify the queries.
|
|
||||||
Debug=true
|
|
||||||
|
|
||||||
#SQL COMMANDS
|
|
||||||
|
|
||||||
##################
|
|
||||||
#################
|
|
||||||
################ S O P O R T E
|
|
||||||
#################
|
|
||||||
##################
|
|
||||||
|
|
||||||
sql.traeConexion=select 'DB3' as conexion from dual
|
|
||||||
sql.select_soporte=select * from GUNA.soporte
|
|
||||||
|
|
||||||
sql.select_almacenes_KELL=select CAT_AG_ID, CAT_AG_NOMBRE from KELLOGGS.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_GUNA=select CAT_AG_ID, CAT_AG_NOMBRE from GUNA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_SALMA=select CAT_AG_ID, CAT_AG_NOMBRE from SALMA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_DANVIT=select CAT_AG_ID, CAT_AG_NOMBRE from DANVIT.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
|
|
||||||
sql.proc_QUITAR_VENTA_KELL=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_VENTA_X_TIPO( '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_GUNA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN GUNA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS, '''||(?)||'''); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_SALMA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN SALMA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_DANVIT=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN DANVIT.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_PAGOPAGARE_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_ELIMINAS_PAGOS_PAGARES_REP( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_FACTURACION_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LIBERA_FACTURACION(Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_CARGAFORANEA_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LLENAR_FILTROS ( '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
|
|
||||||
sql.proc_QUITAR_TICKET_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_TICKET( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
sql.revisa_liquidada_Guna=SELECT COUNT(*) as liquidada FROM GUNA.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) AND (HVD_DESCUENTO != 0 or HVD_FECHA_AVION IS NOT NULL)
|
|
||||||
sql.revisa_liquidada_Kell=SELECT COUNT(*) as liquidada FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) and HVD_TIPOVENTA = (?) AND HVD_ESTATUS = 'Liquidado'
|
|
||||||
|
|
||||||
sql.select_todos_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosGUNA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id left join cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosKELLOGGS_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from KELLOGGS.cat_logins left join KELLOGGS.cat_agencias on cat_lo_agencia = cat_ag_id left join KELLOGGS.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosSALMA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta as cat_ru_ruta from SALMA.cat_logins left join SALMA.cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosDANVIT_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from DANVIT.cat_logins left join DANVIT.cat_agencias on cat_lo_agencia = cat_ag_id left join DANVIT.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_ventaXrutaGuna_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaKelloggs_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from KELLOGGS.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) and hvd_tipoventa=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaSalma_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from SALMA.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaDanvit_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from DANVIT.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_prodsTicket_Kelloggs=SELECT HVD_CLIENTE CLIENTE, HVD_PROID PRODUCTO_ID, HVD_PRONOMBRE NOMBRE_PRODUCTO, HVD_CANT CANTIDAD, HVD_COSTO_TOT COSTO_TOTAL, HVD_RUTA RUTA, HVD_CODPROMO CODPROMO,NVL(HVD_TIPOVENTA,' ') TIPOVENTA, NVL(HVD_ESTATUS,' ') ESTATUS, hvd_cedis FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE TRUNC(HVD_FECHA) = TRUNC(SYSDATE) AND HVD_ALMACEN = (?) AND HVD_CLIENTE = (?) and hvd_rechazo is null ORDER BY HVD_CODPROMO, HVD_PRONOMBRE
|
|
||||||
|
|
||||||
@@ -1,77 +0,0 @@
|
|||||||
#Lines starting with '#' are comments.
|
|
||||||
#Backslash character at the end of line means that the command continues in the next line.
|
|
||||||
|
|
||||||
DriverClass=oracle.jdbc.driver.OracleDriver
|
|
||||||
#JdbcUrl=jdbc:mysql://localhost/test?characterEncoding=utf8
|
|
||||||
|
|
||||||
#SQL Server
|
|
||||||
#DriverClass=net.sourceforge.jtds.jdbc.Driver
|
|
||||||
|
|
||||||
# este para produccion GHAN JdbcUrl=jdbc:oracle:thin:@//192.168.15.53:1521/DBKMT
|
|
||||||
#GOHAN ---> server
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.205:1521/DBKMT
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.236:1521/DBKMT
|
|
||||||
JdbcUrl=jdbc:oracle:thin:@//192.168.101.13:1521/DBKMT
|
|
||||||
|
|
||||||
# SVR-KEYMON-PRODUCCION--> Usuario
|
|
||||||
User=SALMA
|
|
||||||
Password=SALMAD2016M
|
|
||||||
|
|
||||||
#User=TORRADOCONAUTO
|
|
||||||
#Password=TORRADOCONAUTOD2016M
|
|
||||||
|
|
||||||
|
|
||||||
#--> Puertos
|
|
||||||
#SAC - DFR - MDA / GOHAN -->COBRANZA
|
|
||||||
#ServerPort=1783
|
|
||||||
#GUNA - SALMA - DURAKELO - DBC / SVR-KEYMON-PRODUCCION --> DISTRIBUIDORAS
|
|
||||||
ServerPort=9000
|
|
||||||
#CMG - TORRADO / TRUNKS -->COBRANZA/ GM
|
|
||||||
#ServerPort=1781
|
|
||||||
|
|
||||||
#If Debug is true then this file will be reloaded on every query.
|
|
||||||
#This is useful if you need to modify the queries.
|
|
||||||
Debug=true
|
|
||||||
|
|
||||||
#SQL COMMANDS
|
|
||||||
|
|
||||||
##################
|
|
||||||
#################
|
|
||||||
################ S O P O R T E
|
|
||||||
#################
|
|
||||||
##################
|
|
||||||
|
|
||||||
sql.traeConexion=select 'DB4' as conexion from dual
|
|
||||||
sql.select_soporte=select * from GUNA.soporte
|
|
||||||
sql.select_conexion=SELECT 'OK' AS VALOR FROM DUAL
|
|
||||||
|
|
||||||
sql.select_almacenes_KELL=select CAT_AG_ID, CAT_AG_NOMBRE from KELLOGGS.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_GUNA=select CAT_AG_ID, CAT_AG_NOMBRE from GUNA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_SALMA=select CAT_AG_ID, CAT_AG_NOMBRE from SALMA.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
sql.select_almacenes_DANVIT=select CAT_AG_ID, CAT_AG_NOMBRE from DANVIT.cat_agencias order by CAT_AG_NOMBRE
|
|
||||||
|
|
||||||
sql.proc_QUITAR_VENTA_KELL=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_VENTA_X_TIPO( '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_GUNA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN GUNA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS, '''||(?)||'''); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_SALMA=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN SALMA.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_VENTA_DANVIT=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN DANVIT.SP_QUITAR_VENTA( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_QUITAR_PAGOPAGARE_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_ELIMINAS_PAGOS_PAGARES_REP( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_FACTURACION_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LIBERA_FACTURACION(Cursor_SYS); end;'); END;
|
|
||||||
sql.proc_LIBERA_BANDERA_CARGAFORANEA_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_LLENAR_FILTROS ( '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
|
|
||||||
sql.proc_QUITAR_TICKET_KELLOGGS=BEGIN EXECUTE IMMEDIATE ('DECLARE Cursor_SYS Sys_Refcursor; BEGIN KELLOGGS.SP_QUITAR_TICKET( '''||(?)||''', '''||(?)||''', '''||(?)||''', Cursor_SYS); end;'); END;
|
|
||||||
|
|
||||||
sql.revisa_liquidada_Guna=SELECT COUNT(*) as liquidada FROM GUNA.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) AND (HVD_DESCUENTO != 0 or HVD_FECHA_AVION IS NOT NULL)
|
|
||||||
sql.revisa_liquidada_Kell=SELECT COUNT(*) as liquidada FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE trunc(HVD_DTESYNC) = trunc(sysdate) and hvd_almacen = (?) and hvd_ruta = (?) and HVD_TIPOVENTA = (?) AND HVD_ESTATUS = 'Liquidado'
|
|
||||||
|
|
||||||
sql.select_todos_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosGUNA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from cat_logins left join cat_agencias on cat_lo_agencia = cat_ag_id left join cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosKELLOGGS_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from KELLOGGS.cat_logins left join KELLOGGS.cat_agencias on cat_lo_agencia = cat_ag_id left join KELLOGGS.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosSALMA_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_lo_ruta as cat_ru_ruta from SALMA.cat_logins left join SALMA.cat_agencias on cat_lo_agencia = cat_ag_id where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_lo_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_todosDANVIT_soporte=select cat_lo_usuario, cat_lo_estatus, cat_lo_nombre, cat_lo_contrasena, cat_lo_agencia, cat_agencias.cat_ag_nombre, cat_ru_ruta from DANVIT.cat_logins left join DANVIT.cat_agencias on cat_lo_agencia = cat_ag_id left join DANVIT.cat_rutas on cat_lo_usuario = cat_ru_vendedor where (cat_lo_usuario LIKE ('%'||(?)||'%') or cat_lo_nombre LIKE ('%'||(?)||'%')) and cat_ag_nombre LIKE ('%'||(?)||'%') and cat_ru_ruta LIKE ('%'||(?)||'%') and rownum <= 20
|
|
||||||
sql.select_ventaXrutaGuna_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaKelloggs_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from KELLOGGS.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) and hvd_tipoventa=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaSalma_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from SALMA.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_ventaXrutaDanvit_soporte=select hvd_ruta, sum(hvd_costo_tot) as monto, hvd_tipoventa from DANVIT.hist_ventas_detalle where trunc(hvd_fecha)=trunc(sysdate) and hvd_ruta=(?) and hvd_almacen=(?) AND hvd_codpromo <> 'BASICA' group by hvd_ruta, hvd_tipoventa
|
|
||||||
sql.select_prodsTicket_Kelloggs=SELECT HVD_CLIENTE CLIENTE, HVD_PROID PRODUCTO_ID, HVD_PRONOMBRE NOMBRE_PRODUCTO, HVD_CANT CANTIDAD, HVD_COSTO_TOT COSTO_TOTAL, HVD_RUTA RUTA, HVD_CODPROMO CODPROMO,NVL(HVD_TIPOVENTA,' ') TIPOVENTA, NVL(HVD_ESTATUS,' ') ESTATUS, hvd_cedis FROM KELLOGGS.HIST_VENTAS_DETALLE WHERE TRUNC(HVD_FECHA) = TRUNC(SYSDATE) AND HVD_ALMACEN = (?) AND HVD_CLIENTE = (?) and hvd_rechazo is null ORDER BY HVD_CODPROMO, HVD_PRONOMBRE
|
|
||||||
|
|
||||||
@@ -1,49 +0,0 @@
|
|||||||
#Lines starting with '#' are comments.
|
|
||||||
#Backslash character at the end of line means that the command continues in the next line.
|
|
||||||
|
|
||||||
DriverClass=oracle.jdbc.driver.OracleDriver
|
|
||||||
#JdbcUrl=jdbc:mysql://localhost/test?characterEncoding=utf8
|
|
||||||
|
|
||||||
#SQL Server
|
|
||||||
#DriverClass=net.sourceforge.jtds.jdbc.Driver
|
|
||||||
|
|
||||||
# este para produccion GHAN JdbcUrl=jdbc:oracle:thin:@//192.168.15.53:1521/DBKMT
|
|
||||||
#GOHAN ---> server
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.205:1521/DBKMT
|
|
||||||
#JdbcUrl=jdbc:oracle:thin:@//10.0.0.236:1521/DBKMT
|
|
||||||
JdbcUrl=jdbc:oracle:thin:@//192.168.101.10:1521/DBKMT?oracle.jdbc.defaultClientIdentifier=jRDC_Multi
|
|
||||||
|
|
||||||
|
|
||||||
# SVR-KEYMON-PRODUCCION--> Usuario
|
|
||||||
User=GUNA
|
|
||||||
Password=GUNAD2015M
|
|
||||||
|
|
||||||
#User=TORRADOCONAUTO
|
|
||||||
#Password=TORRADOCONAUTOD2016M
|
|
||||||
|
|
||||||
|
|
||||||
#--> Puertos
|
|
||||||
#SAC - DFR - MDA / GOHAN -->COBRANZA
|
|
||||||
#ServerPort=1783
|
|
||||||
#GUNA - SALMA - DURAKELO - DBC / SVR-KEYMON-PRODUCCION --> DISTRIBUIDORAS
|
|
||||||
ServerPort=9010
|
|
||||||
#CMG - TORRADO / TRUNKS -->COBRANZA/ GM
|
|
||||||
#ServerPort=1781
|
|
||||||
|
|
||||||
#If Debug is true then this file will be reloaded on every query.
|
|
||||||
#This is useful if you need to modify the queries.
|
|
||||||
Debug=true
|
|
||||||
|
|
||||||
#SQL COMMANDS
|
|
||||||
|
|
||||||
##################
|
|
||||||
#################
|
|
||||||
################ S O P O R T E
|
|
||||||
#################
|
|
||||||
##################
|
|
||||||
|
|
||||||
sql.select_revisaClienteCredito_GUNA2=select (select count(CAT_CL_CODIGO) from GUNA.CAT_CLIENTES where CAT_CL_CODIGO = ? and CAT_CL_IDALMACEN <> '100') as cuantos, (select count(ID_CLIENTE) from GUNA.CAT_CLIENTES_CREDITO where ID_CLIENTE = ?) as cuantosCredito from DUAL
|
|
||||||
|
|
||||||
sql.traeConexion=select 'DB1' as conexion from dual
|
|
||||||
sql.select_soporte=select * from GUNA.soporte
|
|
||||||
sql.select_conexion=SELECT 'OK' AS VALOR FROM DUAL
|
|
||||||
@@ -3,22 +3,22 @@ Build1=Default,b4j.JRDCMulti
|
|||||||
File1=config.properties
|
File1=config.properties
|
||||||
FileGroup1=Default Group
|
FileGroup1=Default Group
|
||||||
Group=Default Group
|
Group=Default Group
|
||||||
Library1=byteconverter
|
Library1=javaobject
|
||||||
Library2=javaobject
|
Library2=jcore
|
||||||
Library3=jcore
|
Library3=jrandomaccessfile
|
||||||
Library4=jrandomaccessfile
|
Library4=jserver
|
||||||
Library5=jserver
|
Library5=jshell
|
||||||
Library6=jshell
|
Library6=json
|
||||||
Library7=json
|
Library7=jsql
|
||||||
Library8=jsql
|
Library8=byteconverter
|
||||||
Module1=DB1Handler
|
Module1=DB1Handler
|
||||||
Module10=RDCConnector
|
Module10=RDCConnector
|
||||||
Module11=TestHandler
|
Module11=TestHandler
|
||||||
Module2=DB1JsonHandler
|
Module2=DB1JsonHandler
|
||||||
Module3=DB2Handler
|
Module3=DB2Handler
|
||||||
Module4=DB2JsonHandler
|
Module4=DB3Handler
|
||||||
Module5=DB3Handler
|
Module5=DB4Handler
|
||||||
Module6=DB4Handler
|
Module6=DBHandlerGenerico
|
||||||
Module7=GlobalParameters
|
Module7=GlobalParameters
|
||||||
Module8=Manager
|
Module8=Manager
|
||||||
Module9=ping
|
Module9=ping
|
||||||
@@ -31,7 +31,7 @@ Version=10.3
|
|||||||
#Region Project Attributes
|
#Region Project Attributes
|
||||||
#CommandLineArgs:
|
#CommandLineArgs:
|
||||||
#MergeLibraries: True
|
#MergeLibraries: True
|
||||||
' VERSION 5.08.02
|
' VERSION 5.08.30
|
||||||
'###########################################################################################################
|
'###########################################################################################################
|
||||||
'###################### PULL #############################################################
|
'###################### PULL #############################################################
|
||||||
'Ctrl + click ide://run?file=%WINDIR%\System32\cmd.exe&Args=/c&Args=git&Args=pull
|
'Ctrl + click ide://run?file=%WINDIR%\System32\cmd.exe&Args=/c&Args=git&Args=pull
|
||||||
@@ -51,13 +51,12 @@ Version=10.3
|
|||||||
|
|
||||||
Sub Process_Globals
|
Sub Process_Globals
|
||||||
Public srvr As Server
|
Public srvr As Server
|
||||||
Public const VERSION As String = "5.08.12"
|
Public const VERSION As Float = 2.23
|
||||||
Type DBCommand (Name As String, Parameters() As Object)
|
Type DBCommand (Name As String, Parameters() As Object)
|
||||||
Type DBResult (Tag As Object, Columns As Map, Rows As List)
|
Type DBResult (Tag As Object, Columns As Map, Rows As List)
|
||||||
Dim listaDeCP As List
|
Dim listaDeCP As List
|
||||||
Dim cpFiles As List
|
Dim cpFiles As List
|
||||||
Public Connectors, commandsMap As Map
|
Public Connectors, commandsMap As Map
|
||||||
Dim onPing As Boolean = False
|
|
||||||
End Sub
|
End Sub
|
||||||
|
|
||||||
Sub AppStart (Args() As String)
|
Sub AppStart (Args() As String)
|
||||||
@@ -96,20 +95,23 @@ Sub AppStart (Args() As String)
|
|||||||
srvr.AddHandler("/ping", "ping", False) ' Agrega un manejador a la ruta "/test", asignando las solicitudes a la clase TestHandler, el último parámetro indica si el manejador debe ejecutar en un nuevo hilo (False en este caso)
|
srvr.AddHandler("/ping", "ping", False) ' Agrega un manejador a la ruta "/test", asignando las solicitudes a la clase TestHandler, el último parámetro indica si el manejador debe ejecutar en un nuevo hilo (False en este caso)
|
||||||
srvr.AddHandler("/test", "TestHandler", False) ' Agrega un manejador a la ruta "/test", asignando las solicitudes a la clase TestHandler, el último parámetro indica si el manejador debe ejecutar en un nuevo hilo (False en este caso)
|
srvr.AddHandler("/test", "TestHandler", False) ' Agrega un manejador a la ruta "/test", asignando las solicitudes a la clase TestHandler, el último parámetro indica si el manejador debe ejecutar en un nuevo hilo (False en este caso)
|
||||||
srvr.AddHandler("/manager", "Manager", False)
|
srvr.AddHandler("/manager", "Manager", False)
|
||||||
srvr.AddHandler("/db1", "DB1Handler", False)
|
' srvr.AddHandler("/db1", "DB1Handler", False)
|
||||||
srvr.AddHandler("/DB1", "DB1Handler", False)
|
' srvr.AddHandler("/DB1", "DB1Handler", False)
|
||||||
srvr.AddHandler("/db2", "DB2Handler", False)
|
' srvr.AddHandler("/db2", "DB2Handler", False)
|
||||||
srvr.AddHandler("/DB2", "DB2Handler", False)
|
' srvr.AddHandler("/DB2", "DB2Handler", False)
|
||||||
srvr.AddHandler("/db3", "DB3Handler", False)
|
' srvr.AddHandler("/db3", "DB3Handler", False)
|
||||||
srvr.AddHandler("/DB3", "DB3Handler", False)
|
' srvr.AddHandler("/DB3", "DB3Handler", False)
|
||||||
srvr.AddHandler("/db4", "DB4Handler", False)
|
' srvr.AddHandler("/db4", "DB4Handler", False)
|
||||||
srvr.AddHandler("/DB4", "DB4Handler", False)
|
' srvr.AddHandler("/DB4", "DB4Handler", False)
|
||||||
srvr.AddHandler("/DBJ", "DB1JsonHandler", False)
|
srvr.AddHandler("/DBJ", "DB1JsonHandler", False)
|
||||||
srvr.AddHandler("/dbrquery", "DB1JsonHandler", False)
|
srvr.AddHandler("/dbrquery", "DB1JsonHandler", False)
|
||||||
srvr.AddHandler("/*", "DB1Handler", False) ' Si no se especifica una base de datos, entonces asignamos la solicitud a la DB1.
|
' srvr.AddHandler("/*", "DB1Handler", False) ' Si no se especifica una base de datos, entonces asignamos la solicitud a la DB1.
|
||||||
|
|
||||||
|
srvr.AddHandler("/*", "DBHandlerGenerico", False)
|
||||||
|
|
||||||
srvr.Start
|
srvr.Start
|
||||||
Log("===========================================================")
|
Log("===========================================================")
|
||||||
Log($"-======== jRDC is running on port: ${srvr.port} (Version: ${VERSION}) ========-"$)
|
Log($"-=== jRDC is running on port: ${srvr.port} (version = $1.2{VERSION}) ===-"$)
|
||||||
Log("===========================================================")
|
Log("===========================================================")
|
||||||
StartMessageLoop
|
StartMessageLoop
|
||||||
End Sub
|
End Sub
|
||||||
@@ -23,17 +23,17 @@ ModuleBreakpoints7=
|
|||||||
ModuleBreakpoints8=
|
ModuleBreakpoints8=
|
||||||
ModuleBreakpoints9=
|
ModuleBreakpoints9=
|
||||||
ModuleClosedNodes0=
|
ModuleClosedNodes0=
|
||||||
ModuleClosedNodes1=7,10
|
ModuleClosedNodes1=
|
||||||
ModuleClosedNodes10=
|
ModuleClosedNodes10=
|
||||||
ModuleClosedNodes11=
|
ModuleClosedNodes11=
|
||||||
ModuleClosedNodes2=
|
ModuleClosedNodes2=
|
||||||
ModuleClosedNodes3=
|
ModuleClosedNodes3=4,5,6
|
||||||
ModuleClosedNodes4=
|
ModuleClosedNodes4=
|
||||||
ModuleClosedNodes5=
|
ModuleClosedNodes5=
|
||||||
ModuleClosedNodes6=
|
ModuleClosedNodes6=
|
||||||
ModuleClosedNodes7=
|
ModuleClosedNodes7=
|
||||||
ModuleClosedNodes8=
|
ModuleClosedNodes8=
|
||||||
ModuleClosedNodes9=
|
ModuleClosedNodes9=
|
||||||
NavigationStack=ping,SendSuccessResponse,39,0,RDCConnector,GetConnection,102,0,RDCConnector,Initialize,11,0,RDCConnector,Class_Globals,9,0,Main,AppStart,65,6,Main,Process_Globals,30,5,ping,Initialize,9,0,ping,Handle,10,6,DB1Handler,Initialize,15,0,DB1Handler,Handle,48,6,Manager,Handle,16,5
|
NavigationStack=DBHandlerGenerico,SendPlainTextError,603,0,DBHandlerGenerico,Initialize,27,0,DB1JsonHandler,Class_Globals,6,0,DB1JsonHandler,Initialize,13,0,DBHandlerGenerico,Class_Globals,15,0,DB1JsonHandler,Handle,197,6,DB1JsonHandler,SendSuccessResponse,238,0,DB1JsonHandler,SendErrorResponse,255,0,Main,AppStart,76,0
|
||||||
SelectedBuild=0
|
SelectedBuild=0
|
||||||
VisibleModules=1,2,10,8,11,9
|
VisibleModules=6,2,10
|
||||||
|
|||||||
@@ -1,11 +0,0 @@
|
|||||||
module.exports = {
|
|
||||||
"apps":[
|
|
||||||
{
|
|
||||||
"name":"jRDC-Multi",
|
|
||||||
"cwd":"C:/jRDC-Multi",
|
|
||||||
"script":"C:/java/jdk-14.0.1/bin/JAVA.EXE",
|
|
||||||
"args":"-jar C:/jRDC-Multi/jRDC_Multi.jar",
|
|
||||||
"exec_interpreter":""
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
|
||||||
@@ -1,9 +0,0 @@
|
|||||||
@rem Este script reinicia el proceso en PM2 del servidor de jRDC2
|
|
||||||
|
|
||||||
@rem estas lineas sirven para que el archivo bat corra en modo administrador.
|
|
||||||
set "params=%*"
|
|
||||||
cd /d "%~dp0" && ( if exist "%temp%\getadmin.vbs" del "%temp%\getadmin.vbs" ) && fsutil dirty query %systemdrive% 1>nul 2>nul || ( echo Set UAC = CreateObject^("Shell.Application"^) : UAC.ShellExecute "cmd.exe", "/k cd ""%~sdp0"" && ""%~s0"" %params%", "", "runas", 1 >> "%temp%\getadmin.vbs" && "%temp%\getadmin.vbs" && exit /B )
|
|
||||||
|
|
||||||
pm2 restart BotSoporte_4.0
|
|
||||||
|
|
||||||
exit
|
|
||||||
@@ -4,6 +4,6 @@
|
|||||||
set "params=%*"
|
set "params=%*"
|
||||||
cd /d "%~dp0" && ( if exist "%temp%\getadmin.vbs" del "%temp%\getadmin.vbs" ) && fsutil dirty query %systemdrive% 1>nul 2>nul || ( echo Set UAC = CreateObject^("Shell.Application"^) : UAC.ShellExecute "cmd.exe", "/k cd ""%~sdp0"" && ""%~s0"" %params%", "", "runas", 1 >> "%temp%\getadmin.vbs" && "%temp%\getadmin.vbs" && exit /B )
|
cd /d "%~dp0" && ( if exist "%temp%\getadmin.vbs" del "%temp%\getadmin.vbs" ) && fsutil dirty query %systemdrive% 1>nul 2>nul || ( echo Set UAC = CreateObject^("Shell.Application"^) : UAC.ShellExecute "cmd.exe", "/k cd ""%~sdp0"" && ""%~s0"" %params%", "", "runas", 1 >> "%temp%\getadmin.vbs" && "%temp%\getadmin.vbs" && exit /B )
|
||||||
|
|
||||||
pm2 restart jRDC-Multi
|
pm2 start RDC-Multi
|
||||||
|
|
||||||
exit
|
exit
|
||||||
Reference in New Issue
Block a user