50

app.config ファイルをプログラムで変更して、使用するサービス ファイル エンドポイントを設定したいと考えています。実行時にこれを行う最良の方法は何ですか? 参考のため:

<endpoint address="http://mydomain/MyService.svc"
    binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_IASRService"
    contract="ASRService.IASRService" name="WSHttpBinding_IASRService">
    <identity>
        <dns value="localhost" />
    </identity>
</endpoint>
4

11 に答える 11

97

これはクライアント側のものですか??

その場合は、WsHttpBinding のインスタンスと EndpointAddress を作成し、これら 2 つをパラメーターとして受け取るプロキシ クライアント コンストラクターに渡す必要があります。

// using System.ServiceModel;
WSHttpBinding binding = new WSHttpBinding();
EndpointAddress endpoint = new EndpointAddress(new Uri("http://localhost:9000/MyService"));

MyServiceClient client = new MyServiceClient(binding, endpoint);

サーバー側にある場合は、ServiceHost の独自のインスタンスをプログラムで作成し、それに適切なサービス エンドポイントを追加する必要があります。

ServiceHost svcHost = new ServiceHost(typeof(MyService), null);

svcHost.AddServiceEndpoint(typeof(IMyService), 
                           new WSHttpBinding(), 
                           "http://localhost:9000/MyService");

もちろん、これらのサービス エンドポイントを複数、サービス ホストに追加することもできます。完了したら、.Open() メソッドを呼び出してサービス ホストを開く必要があります。

動的に (実行時に) 使用する構成を選択できるようにする場合は、それぞれに一意の名前を付けて複数の構成を定義し、その構成を使用して (サービス ホストまたはプロキシ クライアントの) 適切なコンストラクターを呼び出すことができます。使用したい名前。

たとえば、次のように簡単に設定できます。

<endpoint address="http://mydomain/MyService.svc"
        binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_IASRService"
        contract="ASRService.IASRService" 
        name="WSHttpBinding_IASRService">
        <identity>
            <dns value="localhost" />
        </identity>
</endpoint>

<endpoint address="https://mydomain/MyService2.svc"
        binding="wsHttpBinding" bindingConfiguration="SecureHttpBinding_IASRService"
        contract="ASRService.IASRService" 
        name="SecureWSHttpBinding_IASRService">
        <identity>
            <dns value="localhost" />
        </identity>
</endpoint>

<endpoint address="net.tcp://mydomain/MyService3.svc"
        binding="netTcpBinding" bindingConfiguration="NetTcpBinding_IASRService"
        contract="ASRService.IASRService" 
        name="NetTcpBinding_IASRService">
        <identity>
            <dns value="localhost" />
        </identity>
</endpoint>

(3 つの異なる名前、異なる bindingConfigurations を指定することによる異なるパラメーター) を選択し、適切なものを選択してサーバー (またはクライアント プロキシ) をインスタンス化します。

ただし、サーバーとクライアントのどちらの場合でも、実際にサービス ホストまたはプロキシ クライアントを作成する前に選択する必要があります。いったん作成されると、これらは不変です。起動して実行すると、微調整することはできません。

マルク

于 2009-06-08T18:49:47.500 に答える
26

次のコードを使用して、App.Config ファイルのエンドポイント アドレスを変更します。使用する前に名前空間を変更または削除することをお勧めします。

using System;
using System.Xml;
using System.Configuration;
using System.Reflection;
//...

namespace Glenlough.Generations.SupervisorII
{
    public class ConfigSettings
    {

        private static string NodePath = "//system.serviceModel//client//endpoint";
        private ConfigSettings() { }

        public static string GetEndpointAddress()
        {
            return ConfigSettings.loadConfigDocument().SelectSingleNode(NodePath).Attributes["address"].Value;
        }

        public static void SaveEndpointAddress(string endpointAddress)
        {
            // load config document for current assembly
            XmlDocument doc = loadConfigDocument();

            // retrieve appSettings node
            XmlNode node = doc.SelectSingleNode(NodePath);

            if (node == null)
                throw new InvalidOperationException("Error. Could not find endpoint node in config file.");

            try
            {
                // select the 'add' element that contains the key
                //XmlElement elem = (XmlElement)node.SelectSingleNode(string.Format("//add[@key='{0}']", key));
                node.Attributes["address"].Value = endpointAddress;

                doc.Save(getConfigFilePath());
            }
            catch( Exception e )
            {
                throw e;
            }
        }

        public static XmlDocument loadConfigDocument()
        {
            XmlDocument doc = null;
            try
            {
                doc = new XmlDocument();
                doc.Load(getConfigFilePath());
                return doc;
            }
            catch (System.IO.FileNotFoundException e)
            {
                throw new Exception("No configuration file found.", e);
            }
        }

        private static string getConfigFilePath()
        {
            return Assembly.GetExecutingAssembly().Location + ".config";
        }
    }
}
于 2010-01-14T22:37:59.293 に答える
12
SomeServiceClient client = new SomeServiceClient();

var endpointAddress = client.Endpoint.Address; //gets the default endpoint address

EndpointAddressBuilder newEndpointAddress = new EndpointAddressBuilder(endpointAddress);
                newEndpointAddress.Uri = new Uri("net.tcp://serverName:8000/SomeServiceName/");
                client = new SomeServiceClient("EndpointConfigurationName", newEndpointAddress.ToEndpointAddress());

私はこのようにしました。良いことは、構成から残りのエンドポイント バインディング設定を引き続き取得し、 URI を置き換えるだけであることです。

于 2012-02-20T11:50:15.400 に答える
6

この短いコードは私のために働いた:

Configuration wConfig = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
ServiceModelSectionGroup wServiceSection = ServiceModelSectionGroup.GetSectionGroup(wConfig);

ClientSection wClientSection = wServiceSection.Client;
wClientSection.Endpoints[0].Address = <your address>;
wConfig.Save();

もちろん、構成が変更された後に ServiceClient プロキシを作成する必要があります。これを機能させるには、 System.ConfigurationアセンブリとSystem.ServiceModelアセンブリも参照する必要があります。

乾杯

于 2014-04-08T09:19:32.613 に答える
3

これは、構成セクションが定義されていない場合でも、アプリの構成ファイルを更新するために使用できる最短のコードです。

void UpdateAppConfig(string param)
{
   var doc = new XmlDocument();
   doc.Load("YourExeName.exe.config");
   XmlNodeList endpoints = doc.GetElementsByTagName("endpoint");
   foreach (XmlNode item in endpoints)
   {
       var adressAttribute = item.Attributes["address"];
       if (!ReferenceEquals(null, adressAttribute))
       {
           adressAttribute.Value = string.Format("http://mydomain/{0}", param);
       }
   }
   doc.Save("YourExeName.exe.config");
}
于 2012-12-20T08:38:48.283 に答える
2

Malcolm Swaine のコードを変更および拡張して、特定のノードを名前属性で変更し、外部構成ファイルも変更しました。それが役に立てば幸い。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Reflection;

namespace LobbyGuard.UI.Registration
{
public class ConfigSettings
{

    private static string NodePath = "//system.serviceModel//client//endpoint";

    private ConfigSettings() { }

    public static string GetEndpointAddress()
    {
        return ConfigSettings.loadConfigDocument().SelectSingleNode(NodePath).Attributes["address"].Value;
    }

    public static void SaveEndpointAddress(string endpointAddress)
    {
        // load config document for current assembly
        XmlDocument doc = loadConfigDocument();

        // retrieve appSettings node
        XmlNodeList nodes = doc.SelectNodes(NodePath);

        foreach (XmlNode node in nodes)
        {
            if (node == null)
                throw new InvalidOperationException("Error. Could not find endpoint node in config file.");

            //If this isnt the node I want to change, look at the next one
            //Change this string to the name attribute of the node you want to change
            if (node.Attributes["name"].Value != "DataLocal_Endpoint1")
            {
                continue;
            }

            try
            {
                // select the 'add' element that contains the key
                //XmlElement elem = (XmlElement)node.SelectSingleNode(string.Format("//add[@key='{0}']", key));
                node.Attributes["address"].Value = endpointAddress;

                doc.Save(getConfigFilePath());

                break;
            }
            catch (Exception e)
            {
                throw e;
            }
        }
    }

    public static void SaveEndpointAddress(string endpointAddress, string ConfigPath, string endpointName)
    {
        // load config document for current assembly
        XmlDocument doc = loadConfigDocument(ConfigPath);

        // retrieve appSettings node
        XmlNodeList nodes = doc.SelectNodes(NodePath);

        foreach (XmlNode node in nodes)
        {
            if (node == null)
                throw new InvalidOperationException("Error. Could not find endpoint node in config file.");

            //If this isnt the node I want to change, look at the next one
            if (node.Attributes["name"].Value != endpointName)
            {
                continue;
            }

            try
            {
                // select the 'add' element that contains the key
                //XmlElement elem = (XmlElement)node.SelectSingleNode(string.Format("//add[@key='{0}']", key));
                node.Attributes["address"].Value = endpointAddress;

                doc.Save(ConfigPath);

                break;
            }
            catch (Exception e)
            {
                throw e;
            }
        }
    }

    public static XmlDocument loadConfigDocument()
    {
        XmlDocument doc = null;
        try
        {
            doc = new XmlDocument();
            doc.Load(getConfigFilePath());
            return doc;
        }
        catch (System.IO.FileNotFoundException e)
        {
            throw new Exception("No configuration file found.", e);
        }
    }

    public static XmlDocument loadConfigDocument(string Path)
    {
        XmlDocument doc = null;
        try
        {
            doc = new XmlDocument();
            doc.Load(Path);
            return doc;
        }
        catch (System.IO.FileNotFoundException e)
        {
            throw new Exception("No configuration file found.", e);
        }
    }

    private static string getConfigFilePath()
    {
        return Assembly.GetExecutingAssembly().Location + ".config";
    }
}

}

于 2012-09-10T19:33:52.530 に答える
2
MyServiceClient client = new MyServiceClient(binding, endpoint);
client.Endpoint.Address = new EndpointAddress("net.tcp://localhost/webSrvHost/service.svc");
client.Endpoint.Binding = new NetTcpBinding()
            {
                Name = "yourTcpBindConfig",
                ReaderQuotas = XmlDictionaryReaderQuotas.Max,
                ListenBacklog = 40 }

config の uri や config のバインディング情報を変更するのは非常に簡単です。これは、あなたの望むことですか?

于 2013-12-02T10:51:01.783 に答える
1

あなたが望むのは、実行時に構成ファイルのバージョンを交換することだと思います。その場合は、正しいアドレスを持つ構成ファイルのコピーを作成します(.Debugや.Releaseなどの関連する拡張子も付けます)(これにより、デバッグ バージョンとランタイム バージョン) を作成し、ビルド タイプに応じて正しいファイルをコピーするビルド後のステップを作成します。

これは、出力ファイルを正しいバージョン (デバッグ/ランタイム) でオーバーライドする、過去に使用したビルド後のイベントの例です。

copy "$(ProjectDir)ServiceReferences.ClientConfig.$(ConfigurationName)" "$(ProjectDir)ServiceReferences.ClientConfig" /Y

$(ProjectDir) は、構成ファイルが配置されているプロジェクト ディレクトリです。 $(ConfigurationName) は、アクティブな構成のビルド タイプです。

編集: プログラムでこれを行う方法の詳細な説明については、Marc の回答を参照してください。

于 2009-06-08T18:59:22.737 に答える
0

client セクションを正しい web.config ファイルに配置しているかどうかを確認してください。SharePoint には約 6 ~ 7 個の構成ファイルがあります。 http://msdn.microsoft.com/en-us/library/office/ms460914(v=office.14).aspx ( http://msdn.microsoft.com/en-us/library/office/ms460914%28v =office.14%29.aspx )

これを投稿して、簡単に試すことができます

ServiceClient client = new ServiceClient("ServiceSOAP");

于 2014-12-23T13:37:45.843 に答える