动态 AX 2012 DLL 配置文件未更新

本文关键字:更新 配置文件 DLL AX 2012 动态 | 更新日期: 2023-09-27 18:34:49

我们已将一个 C# 项目添加到 AX 环境中。 我们最近对 app.config 文件进行了修改,清理并重新生成了项目,并将其部署到 AOT。 如果我进入 SqlServer Management Studio 并查询 VSASSEMBLIES 表,我可以看到相应的 .dll 和 .dll.config 文件。 我转储了 .dll.config 的内容并将其转换回文本,以确保表中的版本是最新的,而且是最新的。

问题是,当AOS重新启动时,.dll.config文件永远不会写出到磁盘(C:''Program Files''Microsoft Dynamics AX''60''Server[Instance]''bin''VSAssemblies(。 .dll被写出来,但配置不会被写出来。 如果我清除整个目录并重新启动 AOS,则除了我们的配置文件之外,所有内容都会被写回去。

EInvoiceCFDI_MX.dll的配置文件被写出来了,所以我搜索了他们的项目文件和配置,无法提出他们设置的任何我们没有的东西。

我在 AOT 中看到的唯一内容是 EInvoiceCFDI_MX 项目在项目输出下显示 .dll.config 文件,而我们的项目没有。 我检查了默认构建脚本引用的中间目标,它清楚地表明 app.config 应该复制到项目输出中,但由于某种原因它没有。

我错过了什么?


简,谢谢你的帖子。

我们正在按照您引用的方式构建/配置服务:

CLRObject clientType = CLRInterop::getType("OurService");
OurService client = AifUtil::createServiceClient(clientType); 

createServiceClient(( 抛出异常:

System.Reflection.TargetInvocationException: Exception has been thrown by the 
target of an invocation. ---> System.InvalidOperationException: Unable to find 
the application configuaration file C:'Users'<user>'AppData'Local'Microsoft'
Dynamics Ax'VSAssemblies'OurService.dll.config.

OurService.dll.config 文件位于 AOT 中,但在服务器或客户端启动时不会写出到磁盘。

动态 AX 2012 DLL 配置文件未更新

在 Visual Studio 项目中,转到 app.config 文件的属性并设置以下属性:

  • 构建:内容
  • 复制到外文件夹:如果较新,则复制

(不确定属性的翻译是否正确,因为我有德语版本......

您是否更改了全局 app.config?不要!

而是使用AifUtil::CreateServiceClient使项目配置文件可用,如此处所述。

更改配置文件?这将起作用,但类库的 配置文件存储在模型存储中,并由 客户端/服务器。除非在 AOT 中更改,否则无法更改它, Visual Studio项目被重新生成,此时客户端/服务器 将从模型商店下载新版本。所以,你可以 将所有应用程序.config 设置复制/粘贴到 AX32(serv(.exe.config 中 文件并在那里更改它。然后,您将不需要使用 aifUtil::createserviceclient.无论如何,这是非常不切实际的, 特别是对于在客户端运行的服务!

来自 Technet 文章:以下示例代码演示如何构造和配置必应 Bing 服务的服务客户端对象。若要使用 Web 服务,必须在 Microsoft Dynamics AX 程序中使用此代码,以使服务引用能够构造和配置服务客户端的实例。

// Retrieve the X++ type for the Bing service client object. 
ClrObject clientType = CLRInterop::getType("BingSearch.ServiceReferences.BingV2ServiceReference.BingPortTypeClient");
// Use the AifUtil class to create an instance of the service client object.     
BingSearch.ServiceReferences.BingV2ServiceReference.BingPortTypeClient client = AifUtil::CreateServiceClient(clientType);

配置文件中包含哪些更改?

如果要修改地址,还可以消除对配置文件的需求,并根据存储在 Ax 环境中的参数自行配置绑定。

例如,当您创建了一个外部服务并且想要从 Ax 调用它时,但 DEV/TST/PRODUCTION 具有不同的 URL。您可以在创建客户端时指定这一点,而不是在配置文件中添加地址和绑定信息。

下面是一段代码,它手动更改端点并输入我们想要的值。(您可以将参数中的值放在偏离轨道之外,以便您可以为每个环境设置它。

static void Consume_GetZipCodePlaceNameWithEndPoint(Args _args)
{
    DynamicsAxServices.WebServices.ZipCode.USAZipCodeServiceRef.PostalCodeServiceClient postalServiceClient;
    DynamicsAxServices.WebServices.ZipCode.USAZipCodeServiceRef.PostalCodepostalCode;
    System.ServiceModel.Description.ServiceEndpoint endPoint;
    System.ServiceModel.EndpointAddress endPointAddress;
    System.Exception exception;
    System.Type type;
    ;
    try
    {
        // Get the .NET type of the client proxy
        type = CLRInterop::getType('DynamicsAxServices.WebServices.ZipCode.USAZipCodeServiceRef.PostalCodeServiceClient');
        // Let AifUtil create the proxy client because it uses the VSAssemblies path for the config file
        postalServiceClient = AifUtil::createServiceClient(type);
        // Create and endpoint address, This should be a parameter stored   in the system
        endPointAddress = new System.ServiceModel.EndpointAddress("http://www.restfulwebservices.net/wcf/USAZipCodeService.svc");
        // Get the WCF endpoint
        endPoint = postalServiceClient.get_Endpoint();
        // Set the endpoint address.
        endPoint.set_Address(endPointAddress);
        // Use the zipcode to find a place name
        postalCode = postalServiceClient.GetPostCodeDetailByPostCode("10001"); // 10001 is New York
        // Use the getAnyTypeForObject to marshal the System.String to an Ax anyType
        // so that it can be used with info()
        info(strFmt('%1', CLRInterop::getAnyTypeForObject(postalCode.get_PlaceName())));
    }
    catch(Exception::CLRError)
    {
        // Get the .NET Type Exception
        exception = CLRInterop::getLastException();
        // Go through the inner exceptions
        while(exception)
        {
            // Print the exception to the infolog
            info(CLRInterop::getAnyTypeForObject(exception.ToString()));
            // Get the inner exception for more details
            exception = exception.get_InnerException();
        }
    }
}