locked
Error handling RRS feed

  • Question

  • Hi,

    Maybe this silly question relative to OO programming or architecture, but could find a forum for this and I have serious doubts the must's-be, so please help me.

    I am developing a system which uses 3 layers: Presentation - > Logical -> Data

    So which way would it be the best practice to catch errors in the data layer?

    • Catch the error, show it directly from the data layer, inform logical layer and data layer performs the rollback
    • Catch the error, show it directly from the data layer, inform logical layer and logical layer performs the rollback
    • Catch the error, pass it to a global var, inform logical, show it in logical, perform rollback in logical

     

    Also, I have doubts where should the "try catch" should be located: presentation, logical or data?

    So I am a little confused about the "which one should do that"

    Thanks in advance.


    G.Waters


    Thursday, August 16, 2018 8:17 PM

Answers

  • One option is to have a exception class which a connection class inherits. From there in your data class(es) implement the connection class.

    Public Class DataOperations
        Inherits BaseSqlServerConnection

    Since the connection class inherits the exception class you could have a method (in this case in the DataOperations class) as shown below.

    Public Function GetFruitsWithImagesFromList() As List(Of Fruit)
        Dim fruitImage As Image = Nothing
        Dim fruitList As New List(Of Fruit)
    
        Using cn As New SqlConnection(ConnectionString)
            Using cmd As New SqlCommand("SELECT id ,[Description], Picture FROM dbo.Fruits", cn)
                Try
                    cn.Open()
                    Dim reader As SqlDataReader = cmd.ExecuteReader()
    
                    While reader.Read()
    
                        Dim imageData = CType(reader(2), Byte())
    
                        If imageData IsNot Nothing Then
    
                            Using ms As New MemoryStream(imageData, 0, imageData.Length)
                                ms.Write(imageData, 0, imageData.Length)
                                fruitImage = Image.FromStream(ms, True)
                            End Using
    
                        Else
                            fruitImage = InvalidImage
                        End If
    
                        fruitList.Add(New Fruit() With
                                    {
                                        .Id = reader.GetInt32(0),
                                        .Description = reader.GetString(1),
                                        .Picture = fruitImage
                                    })
                    End While
    
                Catch ex As Exception
                    mHasException = True
                    mLastException = ex
                End Try
            End Using
        End Using
    
        Return fruitList
    
    End Function

    Create an instance of DataOperations, call GetFruitsWithImagesList. Then check off the instance of DataOperations then property HasException, if true the Exception is in LastException property or if you simply want the Exception text use LastExceptionMessage. There is also in this case a property HasSqlException, if HasException is true then and HasSqlException is true you are a step closer to a specific issue.

    Of course you can also write to a log file, send an email are other ideas along with the above.

    Any ways that is one basic idea where you can capture an exception in the data layer and pass it back up to upper layers.


    Please remember to mark the replies as answers if they help and unmark them if they provide no help, this will help others who are looking for solutions to the same or similar problem. Contact via my Twitter (Karen Payne) or Facebook (Karen Payne) via my MSDN profile but will not answer coding question on either.
    VB Forums - moderator
    profile for Karen Payne on Stack Exchange, a network of free, community-driven Q&A sites

    • Marked as answer by George Waters Saturday, August 25, 2018 8:05 PM
    Thursday, August 16, 2018 9:00 PM

All replies

  • One option is to have a exception class which a connection class inherits. From there in your data class(es) implement the connection class.

    Public Class DataOperations
        Inherits BaseSqlServerConnection

    Since the connection class inherits the exception class you could have a method (in this case in the DataOperations class) as shown below.

    Public Function GetFruitsWithImagesFromList() As List(Of Fruit)
        Dim fruitImage As Image = Nothing
        Dim fruitList As New List(Of Fruit)
    
        Using cn As New SqlConnection(ConnectionString)
            Using cmd As New SqlCommand("SELECT id ,[Description], Picture FROM dbo.Fruits", cn)
                Try
                    cn.Open()
                    Dim reader As SqlDataReader = cmd.ExecuteReader()
    
                    While reader.Read()
    
                        Dim imageData = CType(reader(2), Byte())
    
                        If imageData IsNot Nothing Then
    
                            Using ms As New MemoryStream(imageData, 0, imageData.Length)
                                ms.Write(imageData, 0, imageData.Length)
                                fruitImage = Image.FromStream(ms, True)
                            End Using
    
                        Else
                            fruitImage = InvalidImage
                        End If
    
                        fruitList.Add(New Fruit() With
                                    {
                                        .Id = reader.GetInt32(0),
                                        .Description = reader.GetString(1),
                                        .Picture = fruitImage
                                    })
                    End While
    
                Catch ex As Exception
                    mHasException = True
                    mLastException = ex
                End Try
            End Using
        End Using
    
        Return fruitList
    
    End Function

    Create an instance of DataOperations, call GetFruitsWithImagesList. Then check off the instance of DataOperations then property HasException, if true the Exception is in LastException property or if you simply want the Exception text use LastExceptionMessage. There is also in this case a property HasSqlException, if HasException is true then and HasSqlException is true you are a step closer to a specific issue.

    Of course you can also write to a log file, send an email are other ideas along with the above.

    Any ways that is one basic idea where you can capture an exception in the data layer and pass it back up to upper layers.


    Please remember to mark the replies as answers if they help and unmark them if they provide no help, this will help others who are looking for solutions to the same or similar problem. Contact via my Twitter (Karen Payne) or Facebook (Karen Payne) via my MSDN profile but will not answer coding question on either.
    VB Forums - moderator
    profile for Karen Payne on Stack Exchange, a network of free, community-driven Q&A sites

    • Marked as answer by George Waters Saturday, August 25, 2018 8:05 PM
    Thursday, August 16, 2018 9:00 PM
  • The key here would be to have global exception handling implemented at the presentation layer project that would catch all unhandled exceptions. No code in the PL. BLL and DAL will be handled by a try/catch, which makes the thrown exception an unhandled exception. The unhandled exception from the PL, BLL or DAL will be caught by the unhandled exception event in the presentation layer project.

    I tested the code myself in the tutorial by creating a test VB.NET DAL classlib project that has a class method that just throws a new Exception() when the DAL class method was executed by the form's button-click event. The global unhandled exception event logic in the presentation layer project caught the unhandled exception that bubbled up to the presentation layer project from the DAL.

    Thanks for making me look for this, becuase I could easily do global exception handling in ASP.NET Web solutions like MVC and Web form, and now I have a solid global exception handling solution when I need it for a Layered or N-tier architectural style Windows form solution.

    Try it man there is VB and C# example code in the download.

    https://www.codeproject.com/Articles/43182/Centralised-Exception-Handling-in-C-Windows-Applic

    Thursday, August 16, 2018 10:46 PM
  • Hi,

    Do you resolve the issue? If you resolve the issue, could you please mark the helpful as answer. it will be beneficial to other community.

    Best Regards,

    Alex


    MSDN Community Support Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Wednesday, August 22, 2018 7:38 AM
  • I think that you should locate "try catch" in presentation layer, all you exception will be redirected to the presentation layer, even if you do not use "try catch", you don´t need to use "try catch" in logical or data layer, to perform your rollbacks you can use unit of work pattern.

    I hope that it help you.

    Wednesday, August 22, 2018 8:16 AM