2009-06-25 4 views
0

J'essaye de construire un DAL pour Oracle en utilisant WCF.Mon L'application est sur intranet, donc je choisis d'aller pour la liaison de tcp qui est supposée être la plus rapide. Mon exigence est simple. Ma DAL expose une fonction qui renvoie un jeu de données basé sur query/sp. Au départ, nous utilisions le webservice et tout allait bien sauf les problèmes de timeout. Une partie de la requête SP prend plus de 2h pour terminer et WCF fonctionne en douceur ... pas de timeout si vous définissez le paramètre right :)WCF DAL pour ORACLE: 150+ utilisateurs

Problème est venu quand nous l'avons fait en direct et plus de 150 utilisateurs l'ont simultanément. J'ai étudié et trouvé que je ne fermais pas proxy.So j'ai fait cela et le scénario amélioré, mais la performance est toujours seulement 50% de webservice et à l'heure l'utilisateur n'est pas capable de se connecter du tout.

Maintenant beaucoup de l'article et beaucoup de suggestiions Je suis passé par et réponse le plus typique est cela dépend de vos requirments comment définir les paramètres (ils sont si nombreux ... :().

Quelqu'un pls me aider avec la suggestion étant donné mes requirments spécifiques appels longs ne sont que 10% (ceux qui consomment 2-3 heures)

Mon service est hébergé dans service.pls fenêtre voir ces lignes suivantes:..

espace de noms Phoenix { classe partielle PhoenixDataServiceHost: ServiceBase { public PhoenixDataServiceHost() { InitializeComponent(); }

internal static ServiceHost svh; 
    string IpPort = "8043"; 
    protected override void OnStart(string[] args) 
    { 
     NetTcpBinding ntcp = new NetTcpBinding(); 

     ntcp.Security.Mode = SecurityMode.None; 
     ntcp.MaxBufferPoolSize = 2147483647; 
     ntcp.MaxReceivedMessageSize = 2147483647; 
     ntcp.MaxBufferSize = 2147483647; 
     ntcp.ReaderQuotas.MaxStringContentLength = 2147483647; 
     ntcp.ReaderQuotas.MaxDepth = 2147483647; 
     ntcp.ReaderQuotas.MaxBytesPerRead = 2147483647; 
     ntcp.ReaderQuotas.MaxNameTableCharCount = 2147483647; 
     ntcp.ReaderQuotas.MaxArrayLength = 2147483647; 
     ntcp.SendTimeout = new TimeSpan(3, 0, 0); 
     ntcp.ReceiveTimeout = new TimeSpan(3, 0, 0); 
     ntcp.OpenTimeout = new TimeSpan(0, 10, 0); 
     ntcp.CloseTimeout = new TimeSpan(0, 10, 0); 
     ntcp.MaxConnections = 400; 
     ntcp.ListenBacklog = 500; 

     if (svh != null) 
     { 
      svh.Close(); 
     } 
     svh = new ServiceHost(typeof(PhoenixDataService)); 
     ((ServiceBehaviorAttribute)svh.Description.Behaviors[0]).MaxItemsInObjectGraph = 2147483647; 
     ((ServiceBehaviorAttribute)svh.Description.Behaviors[0]).IncludeExceptionDetailInFaults = true; 
     svh.AddServiceEndpoint(
      typeof(IPhoenixDataLayer), 
      ntcp, 
      "net.tcp://localhost:"+IpPort); 
     System.ServiceModel.Description.ServiceThrottlingBehavior throttlingBehavior = 
new System.ServiceModel.Description.ServiceThrottlingBehavior(); 
     throttlingBehavior.MaxConcurrentCalls = 400; 
     throttlingBehavior.MaxConcurrentInstances = Int32.MaxValue; 
     throttlingBehavior.MaxConcurrentSessions = 400; 
     svh.Description.Behaviors.Add(throttlingBehavior); 
     svh.Open(); 
    } 

    protected override void OnStop() 
    { 
     if (svh != null) 
     { 
      svh.Close(); 
     } 
    } 
} 

}

J'utilise usine sur le client de canal. Veuillez trouver le code ci-dessous:

using System; en utilisant System.Collections.Generic; en utilisant System.Linq; en utilisant System.Text; en utilisant Phoenix; en utilisant System.ServiceModel; en utilisant System.Data; en utilisant CustomEnum; namespace KIPLProject { Classe publique PhoenixDataServerProxy { static ChannelFactory scf; client IPhoenixDataLayer statique;

public void OpenChannel() 
    { 
     // client = new PhoenixDataService(); 
     // return; 

     //if (scf == null) 
     //{ 
      NetTcpBinding ntcp = new NetTcpBinding(); 

      ntcp.MaxBufferPoolSize = 2147483647; 
      ntcp.MaxReceivedMessageSize = 2147483647; 
      ntcp.MaxBufferSize = 2147483647; 
      ntcp.ReaderQuotas.MaxStringContentLength = 2147483647; 
      ntcp.ReaderQuotas.MaxDepth = 2147483647; 
      ntcp.ReaderQuotas.MaxBytesPerRead = 2147483647; 
      ntcp.ReaderQuotas.MaxNameTableCharCount = 2147483647; 
      ntcp.ReaderQuotas.MaxArrayLength = 2147483647; 
      ntcp.SendTimeout = new TimeSpan(3, 0, 0); 
      ntcp.ReceiveTimeout = new TimeSpan(3, 0, 0); 
      ntcp.OpenTimeout = new TimeSpan(0, 2, 0); 
      ntcp.CloseTimeout = new TimeSpan(0, 10, 0); 
      ntcp.Security.Mode = SecurityMode.None; 
      scf = new ChannelFactory<IPhoenixDataLayer>(ntcp, "net.tcp://"+Program.wcfPort); 

      client = scf.CreateChannel(); 

     // } 



    } 

    public PhoenixDataServerProxy(string Name, KIPLCommandType Type) 
    { 
     SPName = Name; 
     SPType = Type.ToString(); 
     Index = 0; 
    } 

    public PhoenixDataServerProxy() 
    { 
     Index = 0; 

    } 


    #region proxy for WCF Service Function 
    public DataSet GetDataSet(string[][] Param, string SpName, string Type, string constr, bool DebugMode) 
    { 
     try 
     { 
      OpenChannel(); 
      DataSet ds = client.GetDataSet(Param, SpName, Type, constr, DebugMode); 
      CloseChannel(); 
      return ds; 

     } 
     catch (Exception) 
     { 

      scf = null; 
      return null; 
     } 
    } 

}

maintenant Ma demande est déjà en ligne et l'arrêt du service est un gros problème, donc je suis restriced avec trop d'expériences. PLs suggèrent si j'ai besoin de définir les paramètres différemment

Répondre

0

Vous utilisez un seul client pour toutes les demandes. C'est peut-être ce qui vous cause des problèmes.

Ce que vous pouvez faire est de créer un nouveau proxy client pour chaque requête. Créez-le avec l'instruction "using" pour vous assurer qu'il est correctement nettoyé/éliminé.

Du côté client d'abord créer une classe proxy:

public class PhoenixDataLayerProxy : ClientBase<IPhoenixDataLayer>, IPhoenixDataLayer 
{ 
    public DataSet GetDataSet(string[][] Param, string SpName, string Type, string constr, bool DebugMode) 
    { 
     return base.Channel.GetDataSet(string[][] Param, string SpName, string Type, string constr, bool DebugMode); 
    } 

}

Utilisez ensuite le proxy dans une déclaration à l'aide:

using (PhoenixDataLayerProxy client = new PhoenixDataLayerProxy() 
{ 
    var result = client.GetDataSet ..... 
} 

Il se peut aussi que vous frappez la limite pour les connexions entrantes maximales. Voir:

http://blogs.msdn.com/drnick/archive/2006/03/10/547568.aspx

+0

Désolé, na pas faire passer votre message. Pouvez-vous indiquer dans mon code ce que vous vouliez dire !!!!! –

+0

En fait, dans les forums, j'ai eu le point que nous devrions cache objet proxy que la création de canal est coûteux.Mes clients de toute façon va créer une demande distincte comme son application wpf, donc ce changement fonctionnerait ?? Désolé de déranger, mais je dois être sûr avant de faire ce changement que le service est déjà en direct –

Questions connexes