Dos cuestiones acerca de ejecutar sentecias sql sobre SQL Server

09/09/2006 - 16:55 por [Juanjo] | Informe spam
Buenas grupo:

Tengo un par de dudas acerca de ejecutar sentencias en SQL SERVER.

Tengo una aplicacion C# 2005 y una base de datos sql server 2005, y la
forma de ejecutar las sentencias
sql es construyendo la sentecia a "mano" y luego ejecutando (no uso
procedimientos almacenados):
1. PREGUNTA:
Para sentencias de insercion o modificacion, si todo los datos de un cuadro
de texto, p.e., como
puedo proteger estas cadenas, porque si meten una comilla ( ' ), da un error
porque considera esta
comilla como parte de la sentencia y no de la cadena.
2. PREGUNTA:
Cuando hago un select para recoger datos y mostrarlo por ejemplo en un
combo, si el campo quiero
mostrar de la base de datos es una cadena de 50 caracteres, en el combo
muestra cadenas de 50
caracteres, aunque no ocupen esos 50 caracteres. se que esto se puede
solucionar con la funcion
Trim() de la clase String o cuando construyo la sentencia con las funciones
sql ltrim o rtrim. Pero hay alguna
forma de configurar el sql server, o la clase DataTable para que
"automaticamente" haga esto?.


Muchas gracias.

Un saludo

Preguntas similare

Leer las respuestas

#1 Octavio Hernandez
11/09/2006 - 17:11 | Informe spam
Juanjo,

Construir la sentencia SQL "a mano" (formalmente, a eso se le dice "SQL
dinámico") está cayendo en franco desuso
desde que se conoce su vulnerabilidad ante los ataques conocidos como
"inyección de SQL". Te recomiendo cambiar
ese SQL dinámico por SQL parametrizado, que es mucho más seguro además de
más eficiente.

La idea es en lugar de construir la sentencia así:

"INSERT INTO Clientes(Nombre, Apellidos) VALUES('" + txt1.Text + "','" +
txt2.Text + "')"

Tenerla ya compilada de antemano así:

"INSERT INTO Clientes(Nombre, Apellidos) VALUES(@P1, @P2)"

(@P1 y @P2 son parámetros)

Antes de ejecutarla, asignas los valores de los TextBox a los dos
parámetros:

sqlCommand1.Parameters["@P1"].Value = txt1.Text;
sqlCommand1.Parameters["@P2"].Value = txt2.Text;

Con este enfoque desaparecería el problema del apóstrofe dentro de las
cadenas, y evitarías la inyección de SQL.

Slds - Octavio


"[Juanjo]" escribió en el mensaje
news:
Buenas grupo:

Tengo un par de dudas acerca de ejecutar sentencias en SQL SERVER.

Tengo una aplicacion C# 2005 y una base de datos sql server 2005, y la
forma de ejecutar las sentencias
sql es construyendo la sentecia a "mano" y luego ejecutando (no uso
procedimientos almacenados):
1. PREGUNTA:
Para sentencias de insercion o modificacion, si todo los datos de un
cuadro de texto, p.e., como
puedo proteger estas cadenas, porque si meten una comilla ( ' ), da un
error porque considera esta
comilla como parte de la sentencia y no de la cadena.
2. PREGUNTA:
Cuando hago un select para recoger datos y mostrarlo por ejemplo en un
combo, si el campo quiero
mostrar de la base de datos es una cadena de 50 caracteres, en el combo
muestra cadenas de 50
caracteres, aunque no ocupen esos 50 caracteres. se que esto se puede
solucionar con la funcion
Trim() de la clase String o cuando construyo la sentencia con las
funciones sql ltrim o rtrim. Pero hay alguna
forma de configurar el sql server, o la clase DataTable para que
"automaticamente" haga esto?.


Muchas gracias.

Un saludo



Respuesta Responder a este mensaje
#2 [Juanjo]
11/09/2006 - 17:29 | Informe spam
Gracias por constestar antetodo, pero esa solucion no me vale.

El problema es que estoy haciendo una libreria "generica" de modo yo le paso
directamente la sentencia
sql, si importar la tabla, por lo que no puedo tener la sentencia
precompilada.

Yo se que en php hay una funcion que te devuelve la misma cadena pero
protegiendo los caracteres
especiales, pero con C# no doy con ella.

gracias de todas las formas.



"Octavio Hernandez" escribió en el mensaje
news:
Juanjo,

Construir la sentencia SQL "a mano" (formalmente, a eso se le dice "SQL
dinámico") está cayendo en franco desuso
desde que se conoce su vulnerabilidad ante los ataques conocidos como
"inyección de SQL". Te recomiendo cambiar
ese SQL dinámico por SQL parametrizado, que es mucho más seguro además de
más eficiente.

La idea es en lugar de construir la sentencia así:

"INSERT INTO Clientes(Nombre, Apellidos) VALUES('" + txt1.Text + "','"
+ txt2.Text + "')"

Tenerla ya compilada de antemano así:

"INSERT INTO Clientes(Nombre, Apellidos) VALUES(@P1, @P2)"

(@P1 y @P2 son parámetros)

Antes de ejecutarla, asignas los valores de los TextBox a los dos
parámetros:

sqlCommand1.Parameters["@P1"].Value = txt1.Text;
sqlCommand1.Parameters["@P2"].Value = txt2.Text;

Con este enfoque desaparecería el problema del apóstrofe dentro de las
cadenas, y evitarías la inyección de SQL.

Slds - Octavio


"[Juanjo]" escribió en el mensaje
news:
Buenas grupo:

Tengo un par de dudas acerca de ejecutar sentencias en SQL SERVER.

Tengo una aplicacion C# 2005 y una base de datos sql server 2005, y la
forma de ejecutar las sentencias
sql es construyendo la sentecia a "mano" y luego ejecutando (no uso
procedimientos almacenados):
1. PREGUNTA:
Para sentencias de insercion o modificacion, si todo los datos de un
cuadro de texto, p.e., como
puedo proteger estas cadenas, porque si meten una comilla ( ' ), da un
error porque considera esta
comilla como parte de la sentencia y no de la cadena.
2. PREGUNTA:
Cuando hago un select para recoger datos y mostrarlo por ejemplo en un
combo, si el campo quiero
mostrar de la base de datos es una cadena de 50 caracteres, en el combo
muestra cadenas de 50
caracteres, aunque no ocupen esos 50 caracteres. se que esto se puede
solucionar con la funcion
Trim() de la clase String o cuando construyo la sentencia con las
funciones sql ltrim o rtrim. Pero hay alguna
forma de configurar el sql server, o la clase DataTable para que
"automaticamente" haga esto?.


Muchas gracias.

Un saludo







Respuesta Responder a este mensaje
#3 Eduardo A. Morcillo [MS MVP VB]
11/09/2006 - 19:10 | Informe spam
El problema es que estoy haciendo una libreria "generica" de modo yo
le paso directamente la sentencia
sql, si importar la tabla, por lo que no puedo tener la sentencia
precompilada.



Que sea una libreria generica no implica que no se pueda. Yo tengo hecha una
y usa parametros. Tienes tambien el Data Access Application Block de
Microsoft que tambien usa parametros. Pero si quieres seguir con la otra
forma (que no es recomendable) simplemente tienes que duplicar los ' que
esten dentro de los strings. No se de ninguna funcion que lo haga con una
sentencia sql completa pero puedes usar Replace para cada string que
concatenas en la sentencia.

En cuanto a la segunda pregunta, es por el tipo de datos. Si usas varchar en
lugar de char el campo ocupara solo el tamaño de la data sin completar con
espacios hasta llegar al tamaño del campo.

Eduardo A. Morcillo [MS MVP VB]
http://www.mvps.org/emorcillo
http://mvp.support.microsoft.com/pr...4EF5A4191C
Respuesta Responder a este mensaje
#4 [Juanjo]
11/09/2006 - 19:50 | Informe spam
gracias por las respuestas.

Solo una duda. Tengo una funcion de la forma:

bool insertaRegistro(string sql)
{
abreConexion();
ejecuta(sql);
cierraConexion();
}

mas o menos no?Esto me vale para cualquier consulta sql, de insercion sobre
cualquier tabla no?

Tu dices que con parametros se puede hacer algo parecido? puedes escribir
"algo" en pseudocodigo
de como seria?

Muchas gracias.



"Eduardo A. Morcillo [MS MVP VB]" <emorcillo .AT. mvps.org> escribió en el
mensaje news:%
El problema es que estoy haciendo una libreria "generica" de modo yo
le paso directamente la sentencia
sql, si importar la tabla, por lo que no puedo tener la sentencia
precompilada.



Que sea una libreria generica no implica que no se pueda. Yo tengo hecha
una y usa parametros. Tienes tambien el Data Access Application Block de
Microsoft que tambien usa parametros. Pero si quieres seguir con la otra
forma (que no es recomendable) simplemente tienes que duplicar los ' que
esten dentro de los strings. No se de ninguna funcion que lo haga con una
sentencia sql completa pero puedes usar Replace para cada string que
concatenas en la sentencia.

En cuanto a la segunda pregunta, es por el tipo de datos. Si usas varchar
en lugar de char el campo ocupara solo el tamaño de la data sin completar
con espacios hasta llegar al tamaño del campo.

Eduardo A. Morcillo [MS MVP VB]
http://www.mvps.org/emorcillo
http://mvp.support.microsoft.com/pr...4EF5A4191C

Respuesta Responder a este mensaje
#5 Eduardo A. Morcillo [MS MVP VB]
11/09/2006 - 20:45 | Informe spam
Puede ser algo mas o menos asi:

static int EjecutaComando(string sql, params SqlParameter[] parametros) {

using (SqlConnection conexion = new SqlConnection(connectionString)) {

using (SqlCommand comando = new SqlCommand(sql, conexion)) {

comando.Parameters.AddRange(parametros);

return comando.ExecuteNonQuery();

}
}

}

Y lo usarias asi:

EjecutaComando(
"INSERT INTO Tabla (C1, C2) VALUES(@C1, @C2)",
new SqlParameter("@C1", "Hola"),
new SqlParameter("@C2", DateTime.Today));

EjecutaComando(
"DELETE FROM OtraTabla WHERE Codigo = @CODIGO",
new SqlParameter("@CODIGO", "ABC123"));

Eduardo A. Morcillo [MS MVP VB]
http://www.mvps.org/emorcillo
http://mvp.support.microsoft.com/pr...4EF5A4191C
Respuesta Responder a este mensaje
Ads by Google
Help Hacer una preguntaSiguiente Respuesta Tengo una respuesta
Search Busqueda sugerida