none
Agregar lineas de productos RRS feed

  • Pregunta

  • Hola, buenas tardes.

    Tengo una gran duda respecto a un proyecto que estoy realizando. Estoy realizando un sistema de stock, compras y ventas. Programado en lenguaje C# y utilizando arquitectura en Capas, mediante procedimientos almacenados en SQL SERVER.

    Mi gran duda llega en el momento de realizar una venta (en compras sería exactamente lo mismo). Tengo la tabla VENTAS (Cabecera) y la tabla DETALLE_VENTA (Cuerpo). En la tabla DETALLE_VENTA tengo una columna llamada ID_ARTICULO, que se relaciona con tabla PRODUCTOS. Estoy tratando de generar una venta cargando varios artículos mediante un GridView, una vez realizado y generado la venta, la cual se genera correctamente, me dirijo a la base de datos y me encuentro, consultando la tabla DETALLE_VENTA, que sólo carga el primer artículo que ingresé a la grilla y el resto de los artículos no. Lo cuál es lógico y no puedo encontrarle solución.
    Alguien me podría ayudar con eso. Será un problema en el procedimiento almacenado?

    Aguardo respuestas.
    Saludos.

    P.D.: Si sirve como ayuda, aquí dejo mi procedimiento almacenado del registro de DETALLE_VENTA

    ALTER Proc [dbo].[RegistrarDetalleVenta]

    @id_articulo Int,
    @id_venta Int,
    @cantidad Int,
    @precio_unidad Decimal(6,2),
    @iva Money,
    @sub_total Money,
    @Mensaje Varchar(100) Out
    As Begin
    Declare @Stock As Int
    Set @Stock=(Select stock From Articulos Where id_articulo=@id_articulo)
    Begin
    Insert DetalleVenta Values(@id_articulo,@id_venta,@cantidad,@precio_unidad,@iva,@sub_total)
    Set @Mensaje='Registrado Correctamente.'
    End
    Update Articulos Set stock=@Stock-@cantidad Where id_articulo=@id_articulo
    End

    martes, 1 de septiembre de 2020 19:06

Todas las respuestas

  • Hola EmiSavoretti:

    No es el procedimiento almacenado.

    Dentro del código c# tienes algo que hace que la grilla solo registre la primera linea. 

    En el mismo tienes varias cosas que puedes mejorar pero que no son el motivo de la pregunta.

    Si dos detalleVenta acceden al mismo tiempo a modificar el stock del mismo producto el resultado podría ser que se modificaría el stock de una manera errónea. Los dos leen el stock en la query del procedimiento almacenado para el idArticulo=1 y el motor les devuelve 10 unidades. Uno de los procedimientos modifica el stock restando 5 unidades, y el otro también. Como los dos han leído 10 el resultado es que el stock es de 5, cuando debiera de ser de 0.

    Una solución a este problema, puede ser manejar el nivel de aislamiento de la operación en el procedure.

    ALTER Proc [dbo].[RegistrarDetalleVenta] (
       @id_articulo Int,
       @id_venta Int,
       @cantidad Int,
       @precio_unidad Decimal(6,2),
       @iva Money,
       @sub_total Money,
       @Mensaje Varchar(100) Out
    )
    As 
    Begin
    Set transaction isolation level serializable
    begin tran
    begin try
    	
    	Begin
    		Insert DetalleVenta Values(@id_articulo,@id_venta,@cantidad,@precio_unidad,@iva,@sub_total);
    		Set @Mensaje='Registrado Correctamente.';
    	End
    
    	Declare @Stock As Int;
    	Set @Stock=(Select stock From Articulos Where id_articulo=@id_articulo);
    
    	Update Articulos Set stock=@Stock-@cantidad Where id_articulo=@id_articulo;
    	commit tran;
    end try
    begin catch
    	if @@TRANCOUNT>0
    		rollback tran;
    	Set @Mensaje = 'Error';
    
    	DECLARE @ErrorMsg NVARCHAR(4000);  
        DECLARE @ErrorSvr INT;  
        DECLARE @ErrorStS INT;  
       
        SELECT  
            @ErrorMsg = ERROR_MESSAGE(),  
            @ErrorSvr = ERROR_SEVERITY(),  
            @ErrorStS = ERROR_STATE();  
     
        RAISERROR (@ErrorMsg,   
                   @ErrorSvr,
                   @ErrorStS 
                   );  
    
    end catch
    End

    miércoles, 2 de septiembre de 2020 3:36
  • Perfecto Javi Fernández. La verdad es que me estoy poniendo un poco mal porque no puedo encontrarle la solución.  He revisado el código y no encuentro. No sé por donde buscar. Por ejemplo, me parece lógico que registre la primera línea porque en la tabla DETALLE_VENTA solo hay 1 ID_ARTICULO. Por ende, para ese ID_ARTICULO solo puede asignarse un articulo.
    Me explico?


    jueves, 3 de septiembre de 2020 21:21
  • Hola EmiSavoretti: 

    Tendrás que poner un punto de interrupción donde se produce la llamada al procedure, y donde realices la iteración para la llamada al procedure, en vez de pasar la row correspondiente, estarás pasando la row 0 siempre, o algo del estilo.

    Puedes postear esa parte del código en el foro MSDN de c# y ahí seguro que te pueden ayudar.

    MSDN C#

    viernes, 4 de septiembre de 2020 4:14