2

以下のコードのように dbContext をグローバル変数として開いた場合、各関数で新しい datacontext を使用して using ブロックでラップする場合と比較して、接続プールの問題が発生する可能性はありますか?

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using LoopinDeals.Helper;

namespace LoopinDeals.Model
{
    public class DealUsersRepository
    {
        private DataClassesDataContext DbContext = new DataClassesDataContext();

        public void AddUser(string Email, string Password)
        {
            DealUser deal = new DealUser()
            {
                Email = Email,
                Password = Password,
                EmailVerified = true,
                LastLogin = DateTime.Now,
                AccountCreated = DateTime.Now,
                IsActive = true,
                RegistrationMethod = RegistrationType.Normal.ToString(),
                Subscribe = "true"
            };

            DbContext.DealUsers.InsertOnSubmit(deal);
            DbContext.SubmitChanges();
        }

        public void AddSignUpUser(string Email, string City)
        {
            try
            {
                DealUser UserData = new DealUser()
                    {
                        Email = Email,
                        City = City,
                        IsActive = false,
                        LastLogin = DateTime.Now
                    };
                DbContext.DealUsers.InsertOnSubmit(UserData);
            }
            catch (Exception ex)
            {               

            }
        }

        public void UpdateSignUpUser(string Email, string FirstName, string LastName, string Password, string Mobile, string City)
        {
            try
            {
                DealUser UserData = DbContext.DealUsers.Single(UD => UD.Email == Email);
                UserData.FirstName = FirstName;
                UserData.LastName = LastName;
                UserData.Password = Password;
                UserData.Mobile = Mobile;
                UserData.City = City;
                UserData.IsActive = true;
                UserData.LastLogin = DateTime.Now;
                DbContext.SubmitChanges();
            }
            catch (Exception ex)
            {

            }
        }


    }
}

説明

このコードは私が書いたものではなく、外部委託されたものであることに注意してください。次のエラー メッセージが表示されてクラッシュし、修正方法を見つけようとしています。

「/」アプリケーションでサーバー エラーが発生しました。タイムアウトになりました。プールから接続を取得する前に、タイムアウト期間が経過しました。これは、プールされたすべての接続が使用中で、最大プール サイズに達したために発生した可能性があります。説明: 現在の Web 要求の実行中に未処理の例外が発生しました。エラーの詳細とコード内のどこでエラーが発生したかについては、スタック トレースを確認してください。

例外の詳細: System.InvalidOperationException: タイムアウトが発生しました。プールから接続を取得する前に、タイムアウト期間が経過しました。これは、プールされたすべての接続が使用中で、最大プール サイズに達したために発生した可能性があります。

ソース エラー:

[該当するソース行はありません]

ソース ファイル: c:\Windows\Microsoft.NET\Framework64\v2.0.50727\Temporary ASP.NET Files\root\f44daa26\cce00cbd\App_Web_b21g2v5x.5.cs 行: 0

スタックトレース:

[InvalidOperationException: タイムアウトが発生しました。プールから接続を取得する前に、タイムアウト期間が経過しました。これは、プールされたすべての接続が使用中で、最大プール サイズに達したために発生した可能性があり ます

+6265031
System.Data.SqlClient.SqlConnection.Open() +258
System.Data.Linq.SqlClient.SqlConnectionManager.UseConnection(IConnectionUser ユーザー) +65 System.Data.Linq.SqlClient.SqlProvider.get_IsSqlCe() +33 System.Data .Linq.SqlClient.SqlProvider.InitializeProviderMode() +32
System.Data.Linq.SqlClient.SqlProvider.System.Data.Linq.Provider.IProvider.Execute(式クエリ) +63
System.Data.Linq.DataQuery`1.System.Collections.Generic.IEnumerable.GetEnumerator() +45 LoopinDeals.Model.SiteDetails..ctor() +253 LoopinDeals.Admin.Default..ctor() +76
c:\Windows\Microsoft.NET\Framework64\v2.0.50727\Temporary ASP の ASP.admin_default_aspx..ctor() .NET Files\root\f44daa26\cce00cbd\App_Web_b21g2v5x.5.cs:0
__ASP.FastObjectFactory_app_web_b21g2v5x.Create_ASP_admin_default_aspx() in c:\Windows\Microsoft.NET\Framework64\v2.0.50727\Temporary ASP.NET Files\root\f44daa26\ cce00cbd\App_Web_b21g2v5x.22.cs:0
System.Web.Compilation.BuildManager.CreateInstanceFromVirtualPath(VirtualPath virtualPath, Type requiredBaseType, HttpContext context, Boolean allowCrossApp, Boolean noAssert) +138
System.Web.UI.PageHandlerFactory.GetHandlerHelper(HttpContext context, String requestType, VirtualPath virtualPath, String physicalPath) + 50 System.Web.MaterializeHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +425 System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +263

ここに SiteDetailsConstructor を追加しましたが、これにより接続プールの問題が発生する可能性はありますか?

    public class SiteDetails
    {
        public DataClassesDataContext DbContext = new DataClassesDataContext();

        public SiteDetails()
        {
            var Details = from dtl in DbContext.SiteSettings
                          select dtl;

            foreach (var item in Details)
            {
                MetaIndexKeyword = item.MetaIndexKeyword;
                MetaIndexDesc = item.MetaIndexDesc;
                MetaIndexTitle = item.MetaIndexTitle;
                MetaGetPrefrenceKeyword = item.MetaGetPrefrenceKeyword;
                MetaGetPrefrenceDesc = item.MetaGetPrefrenceDesc;
                Logo = item.Logo;
                Favicon = item.Favicon;
                NoImage = item.NoImage;
                SiteName = item.SiteName;
                SiteTitle = item.SiteTitle;
                SiteUrl = item.SiteUrl;
                FbAndTwitterShareMessage = item.FbAndTwitterShareMessage;
                CharacterSet = item.CharacterSet;
                SiteMaintanance = item.SiteMaintanance;
                PasswordChar = item.PasswordChar;
                HtmlMetaKeyword = item.HtmlMetaKeyword;
                HtmlMetaDescription = item.HtmlMetaDescription;
                MetaDataGoogleSiteMap = item.MetaDataGoogleSiteMap;
                WebMasterEmail = item.WebMasterEmail;
                SupportEmail = item.SupportEmail;
                NoReplyName = item.NoReplyName;
                NoReplyEmail = item.NoReplyEmail;
                DeleteExpireDeals = item.DeleteExpireDeals;
                DealsPerPageBeforeLogin = item.DealsPerPageBeforeLogin;
                DealsPerPageAfterLogin = item.DealsPerPageAfterLogin;
                RecentViewDeals = item.RecentViewDeals;
                BoughtDeals = item.BoughtDeals;
                FbFanPage = item.FacebookFanPage;
                FbApplicationId = item.FbApplicationId;
                FbSecret = item.FbSecret;
                FbApiSharingDeals = item.FbApiSharingDeals;
                GoogleApiKey = item.GoogleApiKey;
                TwitterScreenName = item.TwitterScreenName;
                TwitterConsumerKey = item.TwitterConsumerKey;
                TwitterConsumerSecret = item.TwitterConsumerSecret;
                SharingAppId = item.SharingAppId;
                SharingAppSecret = item.SharingAppSecret;
                SharingCanvasURL = item.SharingCanvasURL;
                InviteMessage = item.InviteMessage;
                SharingMsgLink = item.SharingMsgLink;
                ShareMsgPicture = item.ShareMsgPicture;
                ShareMsgName = item.ShareMsgName;
                ShareMsgCaption = item.ShareMsgCaption;
                ShareMsgDesc = item.ShareMsgDesc;
            }

        }

        public static string MetaIndexKeyword { get; set; }
        public static string MetaIndexDesc { get; set; }
        public static string MetaIndexTitle { get; set; }
        public static string MetaGetPrefrenceKeyword { get; set; }
        public static string MetaGetPrefrenceDesc { get; set; }
        public static string Logo { get; set; }
        public static string Favicon { get; set; }
        public static string NoImage { get; set; }
        public static string SiteName { get; set; }
        public static string SiteTitle { get; set; }
        public static string SiteUrl { get; set; }
        public static string FbAndTwitterShareMessage { get; set; }
        public static string CharacterSet { get; set; }
        public static string SiteMaintanance { get; set; }
        public static string PasswordChar { get; set; }
        public static string HtmlMetaKeyword { get; set; }
        public static string HtmlMetaDescription { get; set; }
        public static string MetaDataGoogleSiteMap { get; set; }
        public static string WebMasterEmail { get; set; }
        public static string SupportEmail { get; set; }
        public static string NoReplyName { get; set; }
        public static string NoReplyEmail { get; set; }
        public static bool? DeleteExpireDeals { get; set; }
        public static int? DealsPerPageBeforeLogin { get; set; }
        public static int? DealsPerPageAfterLogin { get; set; }
        public static int? RecentViewDeals { get; set; }
        public static int? BoughtDeals { get; set; }
        public static string FbFanPage { get; set; }
        public static string FbApplicationId { get; set; }
        public static string FbSecret { get; set; }
        public static string FbApiSharingDeals { get; set; }
        public static string GoogleApiKey { get; set; }
        public static string TwitterScreenName { get; set; }
        public static string TwitterConsumerKey { get; set; }
        public static string TwitterConsumerSecret { get; set; }

        public static string SharingAppId { get; set; }
        public static string SharingAppSecret { get; set; }
        public static string SharingCanvasURL { get; set; }
        public static string InviteMessage { get; set; }
        public static string SharingMsgLink { get; set; }
        public static string ShareMsgPicture { get; set; }
        public static string ShareMsgName { get; set; }
        public static string ShareMsgCaption { get; set; }
        public static string ShareMsgDesc { get; set; }

    }
}
4

2 に答える 2

6

DB 接続は を呼び出したときにのみ開かれ、使用され、閉じられるため、接続プールの問題が発生することはありませんSubmitChanges

DBContext はスレッドセーフではないため、リポジトリ インスタンスが複数のスレッドで使用されている場合に問題が発生します。

もう 1 つの問題は、DBContext インスタンス内で EF によって行われるデータのキャッシュです。DBContext インスタンスを破棄しないと、このキャッシュされたデータが蓄積され、しばらくすると、メモリ プレッシャが発生するまで非常に大きくなる可能性があります。

これらの両方の理由から (そして、コンテキストを再作成するためのオーバーヘッドがあまりないため)、DBContext の使用を using ブロック内に保持することは、全体的にはより良い方法です。

于 2012-05-14T03:37:44.930 に答える
5

コンテキストをグローバルに管理しても、接続プールの問題は発生しません。ただし、コンテキストにはすべてのデータがアクセスされる DBSet が含まれているため、メモリが不足するまでコンテキストが大きくなります (DB が使用可能なメモリよりも大きいと仮定します)。

しかし、コンテキストは安価に作成できます。なぜグローバルに管理する必要があるのでしょうか?

-- 新しい情報への対応

あなたが示しているコードフラグメントが問題の背後にあるとはまったく思いません。むしろ、コード トレースを見ると、SiteDetails のコンストラクターで問題が発生しているように見えます。このコンストラクターは大量のデータをロードしていますか? os の場合、あまりにも多くのスレッドがあまりにも多くのデータをロードしようとしているため、単にデータベースを圧倒している可能性があります。

于 2012-05-14T03:39:14.620 に答える