.net 1.1 웹 응용 프로그램에서 연결 개체가 열려 있거나 제대로 처리되지 않았을 때 "내부 연결 치명적인 오류"예외가있는 것으로 보이는 문제를 조사하고 있습니다. 웹 서버는로드가 많은 경우 결국 충돌합니다. 코드를 확인한 후 try catch의 모든 위치에서 실제로 sqlconnection.close()를 호출합니다.메모리 누출/잘못 작성된 코드 또는 둘 다 - sqlconnection을 올바르게 처리 하시겠습니까?
프로젝트는 다음 패턴을 구현합니다. 누군가가 이것이 메모리 누수의 원인이 될 수 있다고 생각되면 저에게 말해 줄 수 있습니까?
영문 웹 페이지는 개인 서브에 다음 호출이
여기Public Class dbDictionary
Inherits DBInteractionBase
Public Function GetTag(ByVal tagId)
'uses the _connection connection object and Executes sql which sometimes throws a sql exception, but closes the connection in finally
GetDictConnectionString()
'new sqlconnection object for another sqlcommand
Dim dictConnection As New SqlConnection
dictConnection = _connection 'At this point the _connection is closed.
'I think the dictConnection is a reference to _connection
Dim cmdToExecute As SqlCommand = New SqlCommand
' // Use base class' connection object
cmdToExecute.Connection = dictConnection
Try
' // Open connection.
dictConnection.Open()
' // Execute query.
adapter.Fill(toReturn)
Catch ex As Exception
Throw New Exception("Error occured.", ex)
Finally
' // Close connection.
dictConnection.Close()
cmdToExecute.Dispose()
adapter.Dispose()
End Try
End Function
Private Function GetDictConnectionString()
' initialize SqlCommand... Use base class _connection object
cmdToExecute.Connection = _connection
Try
_connection.Open()
adapter.Fill(toReturn)
Catch ex As Exception
Return "Error" ' Could this be the issue? The original exception isn't released?
Finally
_connection.Close()
cmdToExecute.Dispose()
adapter.Dispose()
End Try
End Class
가 상속하는 DBInteractionBase입니다 dbDictionary는 DB에서 SQL 테이블을 얻기 위해 사용된다
Dim oDictionary As New dbDictionary
tagVal = oDictionary.GetTag(41)
을하여 Page_Load하게
Public MustInherit Class DBInteractionBase
Inherits System.Web.UI.Page
Protected _connection As SqlConnection
Public Sub New()
_connection = New SqlConnection
_connection.ConnectionString = "some conn string"
End Sub
Public Overloads Sub Dispose()
Dispose(True)
GC.SuppressFinalize(Me)
End Sub
Protected Overridable Overloads Sub Dispose(ByVal isDisposing As Boolean)
' // Check to see if Dispose has already been called.
If Not _isDisposed Then
If isDisposing Then
' // Dispose managed resources.
_connection.Dispose()
_connection = Nothing
End If
End If
_isDisposed = True
End Sub
이제 코드가 실행될 때 Dispose never call gets gets 호출 웹 페이지에 의해 편집 됨. 처분 코드가 GC에 의해 실행되면 궁금한 점은 무엇입니까? 내가 볼 수있는 또 다른 문제는 GetDictConnectionString에 예외가있는 경우 원래 SQL 예외를 다시 발생시키지 않는다는 것입니다. 어떻게 든 SQL 객체를 메모리에 남겨 두겠습니까? 이것은 .NET 1.1 응용 프로그램이고 (.NET 1의 GC는 매우 효율적이지 않습니다.)
또한 perfmon을 사용하여 웹 서버에서 메모리 누수를 모니터링 할 수 있는지 궁금합니다. 나는이 코드를 수정할 계획이며 문제가 해결되었다는 표시를 원합니다. SqlClient : Current # 연결 풀의 트렌드를 볼 수 있습니다. 세션 수가 줄어들면 계속 낮추어야하는지 궁금해지기 때문에 매일 1000 번씩 꾸준히 증가하고 있습니다. 나는 (\ ASP.NET Apps v1.1.4322 (합계) \ Sessions Active)에서 서버 부하가 어떻게되는지를보고있다.
dictConnection을 새로운 SqlConnction으로 선언 한 다음이를 기존 _connection에 다시 지정하는 이유는 무엇입니까? 나는 또한 당신이 정말로 SqlConnections를 처분하고 싶지 않다는 것을 지적해야한다. Close를 실행하면 연결 풀로 반환됩니다. 동일한 연결 문자열을 계속 사용하면 자동으로 다시 사용됩니다. – tomasmcguinness
왜 내가 새 sqlconnection 객체를 선언했는지 모르겠지만 리팩토링하는 사람은 내 목록에 있습니다. 나는 그것이 우리가 가지고있는 문제들에 어떤 함의가 있는지를 알고 싶다. SqlConnection 개체를 올바르게 처리하지 않으면 메모리에 남아있을 가능성이 있습니까? – kiev
SqlConnections는 기본적으로 유지되지만 성능면에서 일반적으로 좋은 점이 있으며 풀링 된 개체 수가 설정된 크기로만 증가해야합니다. – tomasmcguinness