System.InvalidOperationException: The store type 'decimal(18,4)' could not be found in the SqlServer provider manifest - ef-code-first

I am constructing my connection string the following way (with appropriate values for connection parameters).
var builder = new SqlConnectionStringBuilder
{
PersistSecurityInfo = false,
InitialCatalog = "mydatabase",
UserID = "myuser",
Password = "mydatabase",
DataSource = "myserver"
};
var connectionString = builder.ConnectionString;
using (var db = Helper.MakeContext(connectionString)) {
var carrier = db.Carriers.FirstOrDefault(); // fails here with error
Console.WriteLine(carrier.Carrier);
}
Helper is in a different project
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using System.Data.SqlClient;
using ApiForVivtrack3.Entities;
public static class Helper
{
//public string ConnectionString { get; set; }
public static ApiDbContext MakeContext(string connectionString)
{
var db = new ApiDbContext(connectionString);
return db;
}
}
The EF 6.2 DbContext is set up as follows
using System.Data.Entity.ModelConfiguration.Conventions;
using System.Data.Entity;
namespace ApiForVivtrack3.Entities
{
public partial class ApiDbContext : DbContext
{
public ApiDbContext(string efConnectString)
: base(efConnectString)
{
}
// DbSet declarations
}
}
The call stack is
Test method UnitTestProject1.UnitTest1.TestMethod1 threw exception:
System.InvalidOperationException: The store type 'decimal(18,4)' could not be found in the SqlServer provider manifest
at System.Data.Entity.Utilities.DbProviderManifestExtensions.GetStoreTypeFromName(DbProviderManifest providerManifest, String name)
at System.Data.Entity.ModelConfiguration.Configuration.Properties.Primitive.PrimitivePropertyConfiguration.ConfigureColumn(EdmProperty column, EntityType table, DbProviderManifest providerManifest)
at System.Data.Entity.ModelConfiguration.Configuration.Properties.Primitive.PrimitivePropertyConfiguration.Configure(EdmProperty column, EntityType table, DbProviderManifest providerManifest, Boolean allowOverride, Boolean fillFromExistingConfiguration)
at System.Data.Entity.ModelConfiguration.Configuration.Properties.Primitive.PrimitivePropertyConfiguration.<>c__DisplayClass4.<Configure>b__3(Tuple`2 pm)
at System.Data.Entity.Utilities.IEnumerableExtensions.Each[T](IEnumerable`1 ts, Action`1 action)
at System.Data.Entity.ModelConfiguration.Configuration.Properties.Primitive.PrimitivePropertyConfiguration.Configure(IEnumerable`1 propertyMappings, DbProviderManifest providerManifest, Boolean allowOverride, Boolean fillFromExistingConfiguration)
at System.Data.Entity.ModelConfiguration.Configuration.Types.StructuralTypeConfiguration.ConfigurePropertyMappings(IList`1 propertyMappings, DbProviderManifest providerManifest, Boolean allowOverride)
at System.Data.Entity.ModelConfiguration.Configuration.Types.EntityTypeConfiguration.ConfigurePropertyMappings(DbDatabaseMapping databaseMapping, EntityType entityType, DbProviderManifest providerManifest, Boolean allowOverride)
at System.Data.Entity.ModelConfiguration.Configuration.Types.EntityTypeConfiguration.Configure(EntityType entityType, DbDatabaseMapping databaseMapping, DbProviderManifest providerManifest)
at System.Data.Entity.ModelConfiguration.Configuration.ModelConfiguration.ConfigureEntityTypes(DbDatabaseMapping databaseMapping, ICollection`1 entitySets, DbProviderManifest providerManifest)
at System.Data.Entity.ModelConfiguration.Configuration.ModelConfiguration.Configure(DbDatabaseMapping databaseMapping, DbProviderManifest providerManifest)
at System.Data.Entity.DbModelBuilder.Build(DbProviderManifest providerManifest, DbProviderInfo providerInfo)
at System.Data.Entity.DbModelBuilder.Build(DbConnection providerConnection)
at System.Data.Entity.Internal.LazyInternalContext.CreateModel(LazyInternalContext internalContext)
at System.Data.Entity.Internal.RetryLazy`2.GetValue(TInput input)
at System.Data.Entity.Internal.LazyInternalContext.InitializeContext()
at System.Data.Entity.Internal.InternalContext.Initialize()
at System.Data.Entity.Internal.InternalContext.GetEntitySetAndBaseTypeForType(Type entityType)
at System.Data.Entity.Internal.Linq.InternalSet`1.Initialize()
at System.Data.Entity.Internal.Linq.InternalSet`1.get_InternalContext()
at System.Data.Entity.Infrastructure.DbQuery`1.System.Linq.IQueryable.get_Provider()
at System.Linq.Queryable.FirstOrDefault[TSource](IQueryable`1 source)
at UnitTestProject1.UnitTest1.TestMethod1() in D:\devnet10\SBD.Common\UnitTestProject2\UnitTest1.cs:line 39
I have done a text search for Decimal(18, but nothing comes up.

I understand this is an OQ. Seeing as it is unanswered, I'll share what I had to do.
Do a Find (ctrl F) for (18, 4) or what ever the values are in the error message. Most likely you will find the text strings show up in the Fluent API section of your solution.
In my case, I copied Fluent API code from a CORE application into my EF 6 application. Core used "HasColumnType()" which is not compatible with EF 6 that uses "HasPrecision()".
Replace "HasColumnType(" with "HasPrecision(" and run the code again...

As pointed out by another answer, this error can be thrown by Entity Framework 6 if you attempt to configure a decimal column using syntax taken from Entity Framework Core configuration. HasColumnType("decimal(18,4)") needs replacing with HasPrecision(18,4).
This is some regex which can be used to replace all instances of this within your code (regexr demo). Replace this:
\.HasColumnType\("decimal\((\d+),(\d+)\)"\)
with this:
.HasPrecision($1, $2)
I have tested this regex in JetBrains Rider, but be aware that other IDEs may use different regex flavours. Hopefully this should get you started even if you need to modify it.

Related

Issue running EF6 "SqlQuery<T>()" in the context of .NET Core 3.x

I have a .NET Framework 4.x class library that leverages Entity Framework 6. Up until recently it has been leveraged in another 4.x based application but more recently it's been used in a .NET Core 3.x Azure function. Nothing has been changed in the class library and most aspects seem to work as expected with the exception of methods that accept SqlParameters, in particular DbContext.Database.SqlQuery<T>().
The problem that I'm running into seems to be very similar to what happens when using EF Core with .NET Core 3.x without updating from System.Data.SqlClient to Microsoft.Data.SqlClient, except it flips the problem on its head. The exception message is:
The SqlParameterCollection only accepts non-null SqlParameter type objects, not SqlParameter objects.
However, all documentation that I've come across states that EF 6 is compatible with .NET Core 3.x but is not compatible with Microsoft.Data.SqlClient. I'm most certainly using System.Data.SqlClient.SqlParameter and I can't see anywhere where the app is dipping into Microsoft.Data.SqlClient, as illustrated by this partial stack trace:
at System.Data.SqlClient.SqlParameterCollection.ValidateType(Object value)
at System.Data.SqlClient.SqlParameterCollection.AddRange(Array values)
at System.Data.Entity.Core.Objects.ObjectContext.CreateStoreCommand(String commandText, Object[] parameters)
at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQueryInternal[TElement](String commandText, String entitySetName, ExecutionOptions executionOptions, Object[] parameters)
at System.Data.Entity.Core.Objects.ObjectContext.<>c__DisplayClass186_0`1.<ExecuteStoreQueryReliably>b__1()
at System.Data.Entity.Core.Objects.ObjectContext.ExecuteInTransaction[T](Func`1 func, IDbExecutionStrategy executionStrategy, Boolean startLocalTransaction, Boolean releaseConnectionOnSuccess)
at System.Data.Entity.Core.Objects.ObjectContext.<>c__DisplayClass186_0`1.<ExecuteStoreQueryReliably>b__0()
at System.Data.Entity.SqlServer.DefaultSqlExecutionStrategy.Execute[TResult](Func`1 operation)
at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQueryReliably[TElement](String commandText, String entitySetName, ExecutionOptions executionOptions, Object[] parameters)
at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQuery[TElement](String commandText, ExecutionOptions executionOptions, Object[] parameters)
at System.Data.Entity.Internal.InternalContext.<>c__DisplayClass111_0`1.<ExecuteSqlQuery>b__0()
at System.Data.Entity.Internal.LazyEnumerator`1.MoveNext()
at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
<<a bunch of our custom stuff>>
at Microsoft.Azure.WebJobs.Host.Executors.VoidMethodInvoker`2.InvokeAsync(TReflected instance, Object[] arguments) in C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Host\Executors\VoidMethodInvoker.cs:line 21
at Microsoft.Azure.WebJobs.Host.Executors.FunctionInvoker`2.<InvokeAsync>d__10.MoveNext() in C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Host\Executors\FunctionInvoker.cs:line 52
EDIT: Here's the pared down code from the solution...
In the .NetCore 3.1 Function (v3):
using Microsoft.Azure.ServiceBus;
using Microsoft.Azure.WebJobs;
using Microsoft.Extensions.Logging;
using MyProject.Services;
namespace MyProject.Functions
{
public class MyFunction
{
private readonly MyDbContext _ctx;
public MyFunction(MyDbContext ctx)
{
_ctx = ctx;
}
[FunctionName("MyFunction")]
public override void Run([ServiceBusTrigger("%QueueName%", Connection = "%ConnectionString%")]
Message msg,
ILogger log)
{
var service = new MyService();
service.DoStuff();
}
}
}
In the .NET 4.8 class library:
using System.Collections.Generic;
using System.Data.SqlClient;
using System.Linq;
namespace MyProject.Services
{
public class MyService
{
private readonly MyDbContext _context;
public MyService(MyDbContext ctx)
{
_context = ctx;
}
public void DoStuff()
{
//this works
var lineItems1 = _context.LineItems.Where(li => li.Description == "something arbitrary").ToList();
//this gives the exception and stack trace from the original post
var lineItems2 = _context.Database.SqlQuery<LineItem>(
"SELECT * FROM LineItems WHERE Description = #Description",
new[] { new SqlParameter("#Description", "something arbitrary") }).ToList();
}
}
}

Xamarin: A public field without getXXX()/setXXX() lost its generic when binding a jar lib

In jar:
public List<CloudPoiInfo> poiList;
but Xamarin generated the code as System.Collections.IList poiList
which System.Collections.Generic.IList<Com.Baidu.Mapapi.Cloud.CloudPoiInfo> myClassList is right.
I've tried
<attr path="/api/package[#name='com.baidu.mapapi.cloud']/class/field[#type-generic-aware='java.util.List<com.baidu.mapapi.cloud.CloudPoiInfo>']" name="type">System.Collections.Generic.IList<Com.Baidu.Mapapi.Cloud.CloudPoiInfo></attr>
I've fixed it:
Metadata.xml
<remove-node path="/api/package[#name='com.baidu.mapapi.cloud']/class[#name='CloudSearchResult']/field[#name='poiList']"/>
{project}/Additions/CloudSearchResult.cs
using Android.Runtime;
using System;
using System.Collections;
using System.Collections.Generic;
namespace Com.Baidu.Mapapi.Cloud
{
public partial class CloudSearchResult : BaseSearchResult
{
static IntPtr poiList_jfieldId;
// Metadata.xml XPath field reference: path="/api/package[#name='com.baidu.mapapi.cloud']/class[#name='CloudSearchResult']/field[#name='poiList']"
[Register("poiList")]
public global::System.Collections.Generic.IList<CloudPoiInfo> PoiListX
{
get
{
if (poiList_jfieldId == IntPtr.Zero)
poiList_jfieldId = JNIEnv.GetFieldID(class_ref_2, "poiList", "Ljava/util/List;");
IntPtr __ret = JNIEnv.GetObjectField(Handle, poiList_jfieldId);
return global::Android.Runtime.JavaList<CloudPoiInfo>.FromJniHandle(__ret, JniHandleOwnership.TransferLocalRef);
}
set
{
if (poiList_jfieldId == IntPtr.Zero)
poiList_jfieldId = JNIEnv.GetFieldID(class_ref_2, "poiList", "Ljava/util/List;");
IntPtr native_value = global::Android.Runtime.JavaList<CloudPoiInfo>.ToLocalJniHandle(value);
JNIEnv.SetField(Handle, poiList_jfieldId, native_value);
JNIEnv.DeleteLocalRef(native_value);
}
}
internal static new IntPtr java_class_handle_2;
internal static new IntPtr class_ref_2
{
get
{
return JNIEnv.FindClass("com/baidu/mapapi/cloud/CloudSearchResult", ref java_class_handle_2);
}
}
}
public abstract partial class BaseSearchResult : Java.Lang.Object
{
}
public partial class CloudPoiInfo : Java.Lang.Object
{
}
}
Generics in Java and C# are very different so the IList without generics is actually correct. This is due to type erasure on Java side.
http://en.wikipedia.org/wiki/Generics_in_Java
Generics are checked at compile-time for type-correctness. The generic
type information is then removed in a process called type erasure. For
example, List will be converted to the non-generic type List,
which ordinarily contains arbitrary objects. The compile-time check
guarantees that the resulting code is type-correct.
Consequent to type erasure, type parameters cannot be determined at
run-time. For example, when an ArrayList is examined at runtime, there
is no general way to determine whether, before type erasure, it was an
ArrayList or an ArrayList.

An item with the same key has already been added

I am getting this error randomly at the production server here is the stack trace of the error. I am using linq to sql and .net 4.0
System.ArgumentException: An item with the same key has already been added.
at System.ThrowHelper.ThrowArgumentException(ExceptionResource resource)
at System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add)
at System.Data.Linq.DataContext.GetTable(MetaTable metaTable)
at System.Data.Linq.DataContext.GetTable[TEntity]()
at UserManagement.Models.EvoletDataContext.get_sysModules() in D:\MyProj\Models\datamdl.designer.cs:line 1294
at UserManagement.Models.FilterRepository.GetModuleHead(String actionName) in D:\MyProj\Models\FilterRepository.cs:line 14
at UserManagement.Models.DummyAttrib.OnAuthorization(AuthorizationContext filterContext) in D:\MyProj\Models\Filters.cs:line 44
at Glimpse.Net.Plumbing.GlimpseAuthorizationFilter.OnAuthorization(AuthorizationContext filterContext)
at System.Web.Mvc.ControllerActionInvoker.InvokeAuthorizationFilters(ControllerContext controllerContext, IList`1 filters, ActionDescriptor actionDescriptor)
at System.Web.Mvc.ControllerActionInvoker.InvokeAction(ControllerContext controllerContext, String actionName)
at System.Web.Mvc.Controller.ExecuteCore()
at System.Web.Mvc.ControllerBase.Execute(RequestContext requestContext)
at System.Web.Mvc.ControllerBase.System.Web.Mvc.IController.Execute(RequestContext requestContext)
at System.Web.Mvc.MvcHandler.<>c__DisplayClass6.<>c__DisplayClassb.<BeginProcessRequest>b__5()
at System.Web.Mvc.Async.AsyncResultWrapper.<>c__DisplayClass1.<MakeVoidDelegate>b__0()
at System.Web.Mvc.Async.AsyncResultWrapper.<>c__DisplayClass8`1.<BeginSynchronous>b__7(IAsyncResult _)
at System.Web.Mvc.Async.AsyncResultWrapper.WrappedAsyncResult`1.End()
at System.Web.Mvc.MvcHandler.<>c__DisplayClasse.<EndProcessRequest>b__d()
at System.Web.Mvc.SecurityUtil.<GetCallInAppTrustThunk>b__0(Action f)
at System.Web.Mvc.SecurityUtil.ProcessInApplicationTrust(Action action)
at System.Web.Mvc.MvcHandler.EndProcessRequest(IAsyncResult asyncResult)
at System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.EndProcessRequest(IAsyncResult result)
at System.Web.HttpApplication.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute()
at System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously)
Code at line 14 is below. I have also included the datacontext
private EvoletDataContext db = new EvoletDataContext();
public sysModule GetModuleHead(string actionName)
{
var val = (from mod in db.sysModules
where
mod.ModuleActionResult.ToLower().Equals(actionName.ToLowerInvariant())
select mod).SingleOrDefault();
return val;
}
Code at line 44 is
public class DummyAttrib:FilterAttribute,IAuthorizationFilter
{
private readonly FilterRepository _filterRepository = new FilterRepository();
public void OnAuthorization(AuthorizationContext filterContext)
{
if (!filterContext.Controller.ControllerContext.IsChildAction && !filterContext.HttpContext.Request.IsAjaxRequest())
{
var cont = (ApplicationController)filterContext.Controller;
var modhead = _filterRepository.GetModuleHead(filterContext.RouteData.Values["action"].ToString());
if (cont.DocumentID != 0 && modhead !=null)
{
if (_filterRepository.hasRightonModuleChildren(modhead.ModuleID, cont.RoleID))
return;
}
if (cont.DocumentID == 0 && !filterContext.RouteData.Values["action"].ToString().ToLowerInvariant().Equals("index"))
{
filterContext.Result = new RedirectResult("/account.mvc/AccessDenied");
return;
}
if (!_filterRepository.hasRighton(cont.DocumentID, cont.RoleID))
{
filterContext.Result = new RedirectResult("/account.mvc/AccessDenied");
return;
}
}
}
}
LINQ maintains a 'cache' of sorts of tables you have already used, to prevent having to look them up multiple times.
at System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add)
at System.Data.Linq.DataContext.GetTable(MetaTable metaTable)
at System.Data.Linq.DataContext.GetTable[TEntity]()
The table you're trying to use hasn't been used within the data context before, so it's being added to the 'cache'. One of the ways this could fail is if you're calling GetTable() from multiple threads simultaneously, which suggests you're using a single data context for the entire application, which is not a good idea. Also, don't use the same data context if you're executing tasks in parallel.
I have a same problem. I've solved it.
Actually I have a duplicate property with the same name in my ViewModel.
One Property was in BaseViewModel and another is in derived Model.
For Example
public class BaseviewModel{
public int UserId { get; set; }
}
public class Model : BaseViewModel
{
public int UserId { get; set; }
}
I have changed them as
public class BaseviewModel{
public int UserId { get; set; }
}
public class Model : BaseViewModel
{
public int User_Id { get; set; }
}
Now it is working fine.
It looks like a bug - but MS have fixed it for .NET 4
http://connect.microsoft.com/VisualStudio/feedback/details/496178/linq-to-sql-projection-throws-argumentexception-an-item-with-the-same-key-has-already-been-added
Are you overriding any properties in your model classes?
Hope this helps,
Matt
I had the same error but the cause was one of my many-to-one relationships being defined with the wrong ends as the primary and secondary keys in the relationship.
Using the SQL Server Management Studio designer it was too easy to drag-drop from the child table to the parent table and miss the difference in the created relationship.
Check that all your relationships are correctly defined.
We have had similar problems after couple of months of deployment in production server. After doing some research I found out that sometimes there is a problem with LINQ closing connection automatically. Now we are specifically closing all the LINQ TO SQL connection via static extension method. Sample code:
public static void extClose(this System.Data.Linq.DataContext dataContext, bool submitChanges)
{
if (null != dataContext && System.Data.ConnectionState.Closed != dataContext.Connection.State)
{
if (true == submitChanges)
{
dataContext.SubmitChanges();
}
dataContext.Connection.Close();
}
}
I got the same issue in EF 4.1. with an existing application.
What happened? The EF 4.1 requires the .net framework 4.0. Windows update replaced the .net framework 4.0 with 4.5 and I got the same error you got.
The solution was to uninstall .net 4.5 and install .net 4.0.
On the production machine you should set the windows to skip the update to 4.5.

WCF Error in deserializing body of request message for operation

I have a asp.net client web application and a WCF web service which was developed from schema xsd. When calling the service i get an error in deserializing body of request. I tried updating service reference but that did not help.
This is my code:
OSEOP.HMA_OrderingBindingClient client = new OSEOP.HMA_OrderingBindingClient();
OSEOP.GetCapabilitiesRequest request = new OSEOP.GetCapabilitiesRequest();
request.GetCapabilities = new OSEOP.GetCapabilities();
request.GetCapabilities.service = "OS";
string[] arrAcceptedVersions = { "1.0.0", "2.0.0" };
request.GetCapabilities.AcceptVersions = arrAcceptedVersions;
OSEOP.Capabilities capabilities = client.GetCapabilities(request.GetCapabilities);
txtGetCapabilitiesResponse.Text = capabilities.Contents.ToString();
client.Close();
and this is the error:
System.ServiceModel.FaultException`1 was unhandled by user code
Message=Error in deserializing body of request message for operation 'GetCapabilities'.
Source=mscorlib
StackTrace:
Server stack trace:
at System.ServiceModel.Channels.ServiceChannel.ThrowIfFaultUnderstood(Message reply, MessageFault fault, String action, MessageVersion version, FaultConverter faultConverter)
at System.ServiceModel.Channels.ServiceChannel.HandleReply(ProxyOperationRuntime operation, ProxyRpc& rpc)
at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout)
at System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation)
at System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)
Exception rethrown at [0]:
at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
at OSEOP.HMA_OrderingBinding.GetCapabilities(GetCapabilitiesRequest request)
at OSEOP.HMA_OrderingBindingClient.OSEOP.HMA_OrderingBinding.GetCapabilities(GetCapabilitiesRequest request) in c:\Windows\Microsoft.NET\Framework64\v4.0.30319\Temporary ASP.NET Files\oseop_testclient\023fa9f5\ea876945\App_WebReferences.k9c5tqe1.0.cs:line 44135
at OSEOP.HMA_OrderingBindingClient.GetCapabilities(GetCapabilities GetCapabilities1) in c:\Windows\Microsoft.NET\Framework64\v4.0.30319\Temporary ASP.NET Files\oseop_testclient\023fa9f5\ea876945\App_WebReferences.k9c5tqe1.0.cs:line 44141
at _Default.cmdGetCapabilities_Click(Object sender, EventArgs e) in d:\Documents\DEV\SARPilot\SVN_repository\Services\OrderingServices\TestClient\Default.aspx.cs:line 30
at System.Web.UI.WebControls.Button.RaisePostBackEvent(String eventArgument)
at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
InnerException:
as you can see, the error happens at the client and never gets sent out to the WCF service. For this reason i'm not getting anything in my MessageLogging. That's why i thought it would have something to do with the service reference.
Can anyone help?
EDIT #1:
What i don't understand is the GetCapabilities takes a GetCapabilitiesRequest parameter but when i'm implementing the client, my intellisense asks for a OSEOP.GetCapabilities object.
OSEOP is what i named the web reference.
public class OrderingService : HMA_OrderingBinding
{
public GetCapabilitiesResponse GetCapabilities(GetCapabilitiesRequest request)
{
throw new NotImplementedException();
}
}
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
[System.ServiceModel.ServiceContractAttribute(Namespace = "http://www.opengis.net/oseop/1.0", ConfigurationName = "HMA_OrderingBinding")]
public interface HMA_OrderingBinding
{
[OperationContract]
[XmlSerializerFormatAttribute]
GetCapabilitiesResponse GetCapabilities(GetCapabilitiesRequest request);
}
/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("svcutil", "3.0.4506.2152")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true, Namespace = "http://www.opengis.net/oseop/1.0")]
public partial class Capabilities : CapabilitiesBaseType
{
private OrderingServiceContentsType contentsField;
private NotificationProducerMetadataPropertyType notificationsField;
/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute(Order = 0)]
public OrderingServiceContentsType Contents
{
get
{
return this.contentsField;
}
set
{
this.contentsField = value;
}
}
/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute(Order = 1)]
public NotificationProducerMetadataPropertyType Notifications
{
get
{
return this.notificationsField;
}
set
{
this.notificationsField = value;
}
}
}
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
[System.ServiceModel.MessageContractAttribute(IsWrapped = false)]
public partial class GetCapabilitiesRequest
{
[System.ServiceModel.MessageBodyMemberAttribute(Namespace = "http://www.opengis.net/oseop/1.0", Order = 0)]
public GetCapabilities GetCapabilities;
public GetCapabilitiesRequest()
{
}
public GetCapabilitiesRequest(GetCapabilities GetCapabilities)
{
this.GetCapabilities = GetCapabilities;
}
}
EDIT #2 #Marc:
Marc, your answer was very helpful. But you see how the server side is something like this:
GetCapabilitiesResponse GetCapabilities(GetCapabilitiesRequest request)
Yet my intellisense thinks it's something like this:
Capabilities GetCapabilities(GetCapabilities GetCapabilities1)
And I've found a snippet of code within the IOrder.cs file (47,256 lines of code generated from schema) that I'm sure is causing the problem but I tried commenting out the trouble function, updating service reference, and my intellisense still wants GetCapabilities GetCapabilities1
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
public partial class HMA_OrderingBindingClient : System.ServiceModel.ClientBase<HMA_OrderingBinding>, HMA_OrderingBinding
{
public HMA_OrderingBindingClient()
{
}
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
GetCapabilitiesResponse HMA_OrderingBinding.GetCapabilities(GetCapabilitiesRequest request)
{
return base.Channel.GetCapabilities(request);
}
public Capabilities GetCapabilities(GetCapabilities GetCapabilities1)
{
GetCapabilitiesRequest inValue = new GetCapabilitiesRequest();
inValue.GetCapabilities = GetCapabilities1;
GetCapabilitiesResponse retVal = ((HMA_OrderingBinding)(this)).GetCapabilities(inValue);
return retVal.Capabilities;
}
}
Two questions:
Why do you create a GetCapabilitiesRequest object which contains a subobject GetCapabilities, and then in your method call, you only use the contained suboject GetCapabilities??
So why not just create the GetCapabilities in the first place and forget about the wrapping object??
Also, can you please show us the GetCapabilitiesRequest and GetCapabilities and the return class Capabilities, too? If you have a deserialization error, most likely something with those classes isn't right...
Update: thanks for the update to your question....
hmm... can't seem to find anything obviously wrong at first glance....
About your question:
What I don't understand is the
GetCapabilities takes a
GetCapabilitiesRequest parameter but
when I'm implementing the client, my
intellisense asks for a
OSEOP.GetCapabilities object.
Yes, that's clear - your service-side uses its set of classes - GetCapabilitiesRequest and so forth.
When you do an Add Service Reference in Visual Studio, what VS does is
interrogate the server to find out about the service - what methods it has and what parameters it needs
it creates a set of copies of your classes for the client-side proxy - in that namespace that you define on the Add Service Reference dialog box. Those are classes that look exactly the same as your server side classes - but they are not the same classes - they just serialize to XML (and deserialize from XML) the same way as those on the server. That's why your client-side proxy has different classes in a different namespace. That's standard WCF behavior - nothing to be alarmed about...
Update no. 2: Carlos, the schema you sent me seems to be incomplete or has errors. Try to use OGC project on CodePlex as a base and build in your code manually or wait until the schema gets ‘officially’ published.

Resolving HttpRequestScoped services in ASMX with Autofac 2.1.12

The Description I had a legacy type that is HttpRequestScoped and a legacy web service consuming that service. To resolve services in legacy concerns, I have a global resolver. This was all working well in 1.4, and now that I'm using 2.1.12 I'm experiencing DependencyResolutionException.
The Code In 2.1.12, my Global.asax.cs:
builder.Register(c => new SomeLegacyType(HttpContext.Current)) // note: it relies on HttpContext.Current
.As<SomeLegacyType>()
.HttpRequestScoped();
_containerProvider = new ContainerProvider(builder.Build()); // this is my app's IContainerProvider
Setup.Resolver = new AutofacResolver(_containerProvider.ApplicationContainer);
Setup.Resolver is a singleton, and it is being set to AutofacResolver which looks something like this:
public class AutofacResolver : IResolver
{
private readonly IContainer _container;
public AutofacResolver(IContainer container)
{
_container = container;
}
public TService Get<TService>()
{
return _container.Resolve<TService>();
}
}
The web service looks like this:
[WebService]
public LegacyWebService : WebService
{
[WebMethod(EnableSession=true)]
public String SomeMethod()
{
var legacyType = Setup.Resolver.Get<SomeLegacyType>();
}
}
The Exception The following exception when Setup.Resolver.Get<SomeLegacyType>() is called:
Autofac.Core.DependencyResolutionException: No scope matching the expression 'value(Autofac.Builder.RegistrationBuilder`3+<>c__DisplayClass0[SomeAssembly.SomeLegacyType,Autofac.Builder.SimpleActivatorData,Autofac.Builder.SingleRegistrationStyle]).lifetimeScopeTag.Equals(scope.Tag)' is visible from the scope in which the instance was requested.
at Autofac.Core.Lifetime.MatchingScopeLifetime.FindScope(ISharingLifetimeScope mostNestedVisibleScope)
at Autofac.Core.Resolving.ComponentActivation..ctor(IComponentRegistration registration, IResolveOperation context, ISharingLifetimeScope mostNestedVisibleScope)
at Autofac.Core.Resolving.ResolveOperation.Resolve(ISharingLifetimeScope activationScope, IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Lifetime.LifetimeScope.Resolve(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Container.Resolve(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.TryResolve(IComponentContext context, Service service, IEnumerable`1 parameters, Object& instance)
at Autofac.ResolutionExtensions.Resolve(IComponentContext context, Service service, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.Resolve[TService](IComponentContext context, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.Resolve[TService](IComponentContext context)
Side Question Is there a better way to have properties injected in ASMX, the same way my ASPX pages are injected (rather than use Setup.Resolver)? I use the AttributedInjectionModule because of legacy concerns. It doesn't appear that the module works on ASMX.
If you configure your 'resolver' to use the RequestLifetime rather than ApplicationContainer all should work as expected.
This means your IContainer parameter will have to change to ILifetimeScope.
I'm not sure about a better way to inject ASMX dependencies, there may be one but I don't think Autofac supports it.

Resources