我有一个使用 Linq2Sql 将记录插入数据库的 Web 服务。
Web服务方法如下:
public class WS_StreamCrossing : IStreamCrossing
{
public string SendStreamCrossingSurveys(List<Survey> mySurveyList)
{
if (mySurveyList == null)
{
throw new ArgumentNullException("mySurveyList");
}
string result = "Failed";
using (StreamCrossingDataContext myObjectContext = GetDBContext())
{
foreach (Survey myPassedSurvey in mySurveyList)
{
// Check for existing Survey with matching data (PRNo, MP, FWVersion, CulvertID, SurveyDate)
Survey myMatchingSurvey = myObjectContext.Surveys.FirstOrDefault(x => x.PRNo == myPassedSurvey.PRNo && x.MP == myPassedSurvey.MP && x.FWVersion == myPassedSurvey.FWVersion && x.CulvertID == myPassedSurvey.CulvertID && x.SurveyDate == myPassedSurvey.SurveyDate);
if (myMatchingSurvey != null)
{
myMatchingSurvey.AdjacentLandowner = myPassedSurvey.AdjacentLandowner;
myMatchingSurvey.ApproachLengthLeft = myPassedSurvey.ApproachLengthLeft;
myMatchingSurvey.ApproachLengthRight = myPassedSurvey.ApproachLengthRight;
myMatchingSurvey.ApproachSlopeLeft = myPassedSurvey.ApproachSlopeLeft;
myMatchingSurvey.ApproachSlopeRight = myPassedSurvey.ApproachSlopeRight;
myMatchingSurvey.BackwaterComments = myPassedSurvey.BackwaterComments;
myMatchingSurvey.CalculatedPassability = myPassedSurvey.CalculatedPassability;
myMatchingSurvey.County = myPassedSurvey.County;
myMatchingSurvey.CrossingType = myPassedSurvey.CrossingType;
myMatchingSurvey.CrushedLocation = myPassedSurvey.CrushedLocation;
myMatchingSurvey.CrushedPercent = myPassedSurvey.CrushedPercent;
//myMatchingSurvey.CulvertID = myPassedSurvey.CulvertID;
myMatchingSurvey.DefinedPassability = myPassedSurvey.DefinedPassability;
myMatchingSurvey.ErosionExtent = myPassedSurvey.ErosionExtent;
myMatchingSurvey.ErosionNotes = myPassedSurvey.ErosionNotes;
myMatchingSurvey.FillDepthDownStream = myPassedSurvey.FillDepthDownStream;
myMatchingSurvey.FillDepthUpStream = myPassedSurvey.FillDepthUpStream;
myMatchingSurvey.FutureComments = myPassedSurvey.FutureComments;
myMatchingSurvey.FutureVisit = myPassedSurvey.FutureVisit;
//myMatchingSurvey.FWVersion = myPassedSurvey.FWVersion;
myMatchingSurvey.GeneralCondition = myPassedSurvey.GeneralCondition;
myMatchingSurvey.HeadChangeComments = myPassedSurvey.HeadChangeComments;
myMatchingSurvey.InletStructure = myPassedSurvey.InletStructure;
myMatchingSurvey.IsBackwatered = myPassedSurvey.IsBackwatered;
myMatchingSurvey.IsErosionCorrectable = myPassedSurvey.IsErosionCorrectable;
myMatchingSurvey.IsErosionPresent = myPassedSurvey.IsErosionPresent;
myMatchingSurvey.IsHeadChanged = myPassedSurvey.IsHeadChanged;
myMatchingSurvey.IsOvertopping = myPassedSurvey.IsOvertopping;
myMatchingSurvey.IsPerched = myPassedSurvey.IsPerched;
myMatchingSurvey.IsPrioritySite = myPassedSurvey.IsPrioritySite;
myMatchingSurvey.IsRustedThrough = myPassedSurvey.IsRustedThrough;
myMatchingSurvey.IsScourPoolPresent = myPassedSurvey.IsScourPoolPresent;
myMatchingSurvey.IsSubstrateEntireLength = myPassedSurvey.IsSubstrateEntireLength;
myMatchingSurvey.IsUpstreamPondPresent = myPassedSurvey.IsUpstreamPondPresent;
myMatchingSurvey.Latitude = myPassedSurvey.Latitude;
myMatchingSurvey.LocationComments = myPassedSurvey.LocationComments;
myMatchingSurvey.LocationOfLowPoint = myPassedSurvey.LocationOfLowPoint;
myMatchingSurvey.Longitude = myPassedSurvey.Longitude;
//myMatchingSurvey.MP = myPassedSurvey.MP;
myMatchingSurvey.NonNativeInvasiveSpecies = myPassedSurvey.NonNativeInvasiveSpecies;
myMatchingSurvey.Observers = myPassedSurvey.Observers;
myMatchingSurvey.OutletStructure = myPassedSurvey.OutletStructure;
myMatchingSurvey.OutletType = myPassedSurvey.OutletType;
myMatchingSurvey.OvertoppingComments = myPassedSurvey.OvertoppingComments;
myMatchingSurvey.PassabilityComments = myPassedSurvey.PassabilityComments;
myMatchingSurvey.PerchHeight = myPassedSurvey.PerchHeight;
myMatchingSurvey.PhotoDownstream = myPassedSurvey.PhotoDownstream;
myMatchingSurvey.PhotoInlet = myPassedSurvey.PhotoInlet;
myMatchingSurvey.PhotoOutlet = myPassedSurvey.PhotoOutlet;
myMatchingSurvey.PhotoRoadApproachLeft = myPassedSurvey.PhotoRoadApproachLeft;
myMatchingSurvey.PhotoRoadApproachRight = myPassedSurvey.PhotoRoadApproachRight;
myMatchingSurvey.PhotoUpstream = myPassedSurvey.PhotoUpstream;
myMatchingSurvey.PluggedLocation = myPassedSurvey.PluggedLocation;
myMatchingSurvey.PluggedPercent = myPassedSurvey.PluggedPercent;
myMatchingSurvey.PriorityComments = myPassedSurvey.PriorityComments;
myMatchingSurvey.PriorityReason = myPassedSurvey.PriorityReason;
//myMatchingSurvey.PRNo = myPassedSurvey.PRNo;
myMatchingSurvey.PtID = myPassedSurvey.PtID;
myMatchingSurvey.RefMiles = myPassedSurvey.RefMiles;
myMatchingSurvey.RiffleBankfullWidth = myPassedSurvey.RiffleBankfullWidth;
myMatchingSurvey.RiffleMeasuredWith = myPassedSurvey.RiffleMeasuredWith;
myMatchingSurvey.RiffleSubstrate = myPassedSurvey.RiffleSubstrate;
myMatchingSurvey.RiffleWaterDepth = myPassedSurvey.RiffleWaterDepth;
myMatchingSurvey.RiffleWaterVelocity = myPassedSurvey.RiffleWaterVelocity;
myMatchingSurvey.RiffleWettedWidth = myPassedSurvey.RiffleWettedWidth;
myMatchingSurvey.RoadCondition = myPassedSurvey.RoadCondition;
myMatchingSurvey.RoadName = myPassedSurvey.RoadName;
myMatchingSurvey.RoadSurface = myPassedSurvey.RoadSurface;
myMatchingSurvey.RoadWidth = myPassedSurvey.RoadWidth;
myMatchingSurvey.RunOffPath = myPassedSurvey.RunOffPath;
myMatchingSurvey.ScourPoolDepth = myPassedSurvey.ScourPoolDepth;
myMatchingSurvey.ScourPoolLength = myPassedSurvey.ScourPoolLength;
myMatchingSurvey.ScourPoolWidth = myPassedSurvey.ScourPoolWidth;
myMatchingSurvey.SiteID = myPassedSurvey.SiteID;
myMatchingSurvey.SlopeDownStream = myPassedSurvey.SlopeDownStream;
myMatchingSurvey.SlopeUpStream = myPassedSurvey.SlopeUpStream;
myMatchingSurvey.SpeciesObserved = myPassedSurvey.SpeciesObserved;
myMatchingSurvey.StreamFlow = myPassedSurvey.StreamFlow;
myMatchingSurvey.StructureEmbeddedDepthInlet = myPassedSurvey.StructureEmbeddedDepthInlet;
myMatchingSurvey.StructureEmbeddedDepthOutlet = myPassedSurvey.StructureEmbeddedDepthOutlet;
myMatchingSurvey.StructureInterior = myPassedSurvey.StructureInterior;
myMatchingSurvey.StructureShape = myPassedSurvey.StructureShape;
myMatchingSurvey.StructureWaterDepthInlet = myPassedSurvey.StructureWaterDepthInlet;
myMatchingSurvey.StructureWaterDepthOutlet = myPassedSurvey.StructureWaterDepthOutlet;
myMatchingSurvey.StructureWaterVelocityInlet = myPassedSurvey.StructureWaterVelocityInlet;
myMatchingSurvey.StructureWaterVelocityMeasured = myPassedSurvey.StructureWaterVelocityMeasured;
myMatchingSurvey.StructureWaterVelocityMeasuredWith = myPassedSurvey.StructureWaterVelocityMeasuredWith;
myMatchingSurvey.StructureWaterVelocityOutlet = myPassedSurvey.StructureWaterVelocityOutlet;
myMatchingSurvey.SubstrateInStructure = myPassedSurvey.SubstrateInStructure;
//myMatchingSurvey.SurveyDate = myPassedSurvey.SurveyDate;
myMatchingSurvey.UpstreamPondLength = myPassedSurvey.UpstreamPondLength;
myMatchingSurvey.UpstreamPondWidth = myPassedSurvey.UpstreamPondWidth;
myMatchingSurvey.VegetationDitchLeft = myPassedSurvey.VegetationDitchLeft;
myMatchingSurvey.VegetationDitchRight = myPassedSurvey.VegetationDitchRight;
myMatchingSurvey.Waterway = myPassedSurvey.Waterway;
// Delete all Erosions
myObjectContext.Erosions.DeleteAllOnSubmit(myMatchingSurvey.Erosions);
// Assign new Erosions
myMatchingSurvey.Erosions = myPassedSurvey.Erosions;
// Delete all Spans
myObjectContext.Spans.DeleteAllOnSubmit(myMatchingSurvey.Spans);
// Assign new Spans
myMatchingSurvey.Spans = myPassedSurvey.Spans;
}
else
{
myObjectContext.Surveys.InsertOnSubmit(myPassedSurvey);
}
}
myObjectContext.SubmitChanges();
result = "Success";
}
return result;
}
当我通过 Web 服务发送基本测试以添加新记录时,它会在以下位置生成错误myObjectContext.SubmitChanges()
:
System.NullReferenceException 未被用户代码处理 Message=Object 引用未设置为对象的实例。Source=System.Data.Linq StackTrace:在 System.Data.Linq.Binary.ToArray() 在 System.Data.Linq.DBConvert.ChangeType(Object value, Type type) 在 System.Data.Linq.SqlClient.SqlTypeSystem.ProviderBase System.Data.Linq.SqlClient.SqlProvider.AssignParameters 处 System.Data.Linq.SqlClient.SqlTypeSystem.ProviderBase.InitializeParameter(ProviderType 类型,DbParameter 参数,对象值) 处的 .GetParameterValue(SqlType 类型,对象值)(DbCommand cmd,ReadOnlyCollection
1 parms, Object[] userArguments, Object lastResult) at System.Data.Linq.SqlClient.SqlProvider.Execute(Expression query, QueryInfo queryInfo, IObjectReaderFactory factory, Object[] parentArgs, Object[] userArgs, ICompiledSubQuery[] subQueries, Object lastResult) at System.Data.Linq.SqlClient.SqlProvider.ExecuteAll(Expression query, QueryInfo[] queryInfos, IObjectReaderFactory factory, Object[] userArguments, ICompiledSubQuery[] subQueries) at System.Data.Linq.SqlClient.SqlProvider.System.Data.Linq.Provider.IProvider.Execute(Expression query) at System.Data.Linq.ChangeDirector.StandardChangeDirector.DynamicInsert(TrackedObject item) at System.Data.Linq.ChangeDirector.StandardChangeDirector.Insert(TrackedObject item) at System.Data.Linq.ChangeProcessor.SubmitChanges(ConflictMode failureMode) at System.Data.Linq.DataContext.SubmitChanges(ConflictMode failureMode) at System.Data.Linq.DataContext.SubmitChanges() at DNR.CulvertInventory.SERVICE.WS_StreamCrossing.SendStreamCrossingSurveys(List
C:\TFS Projects\DNR.CulvertInventory\Main\Src\Code\DNR.CulvertInventory\DNR.CulvertInventory.SERVICE\WS_StreamCrossing.svc.cs 中的 1 mySurveyList):DNR.CulvertInventory.SERVICE.WS_StreamCrossing.SendStreamCrossingSurvey(Survey)的第 255 行mySurvey) 在 C:\TFS Projects\DNR.CulvertInventory\Main\Src\Code\DNR.CulvertInventory\DNR.CulvertInventory.SERVICE\WS_StreamCrossing.svc.cs: SyncInvokeSendStreamCrossingSurvey (Object , Object[] , Object[] ) 的第 273 行在 System.ServiceModel.Dispatcher.DispatchOperationRuntime.InvokeBegin(MessageRpc& rpc) InnerException:
问题是,当我使用 Visual Studio 测试项目对服务运行测试时,不会发生此错误。这是一个示例测试,它正在尝试同样的事情并且工作得很好:
[TestMethod]
[HostType("ASP.NET")]
[AspNetDevelopmentServerHost(testDirectory)]
[UrlToTest(testURL)]
public void CanCreateNewSurveyWithErosionsAndSpans()
{
string expected = "Success";
SERVICE.Survey mySurvey = CreateBaseSurveyObject();
SERVICE.Erosion myFirstErosion = CreateErosionObject(2);
mySurvey.Erosions.Add(myFirstErosion);
SERVICE.Erosion mySecondErosion = CreateErosionObject(2);
mySurvey.Erosions.Add(mySecondErosion);
SERVICE.Span myFirstSpan = CreateSpanObject(2);
mySurvey.Spans.Add(myFirstSpan);
SERVICE.Span mySecondSpan = CreateSpanObject(2);
mySurvey.Spans.Add(mySecondSpan);
string actual = target.SendStreamCrossingSurvey(mySurvey);
Assert.AreEqual(expected, actual);
}
有任何想法吗?
为了回答问题,这里有更多数据。
这是GetDBContext()
方法:
private StreamCrossingDataContext GetDBContext()
{
SERVICE.StreamCrossingDataContext db = new SERVICE.StreamCrossingDataContext();
DataLoadOptions options = new DataLoadOptions();
options.LoadWith<SERVICE.Survey>(x => x.Erosions);
options.LoadWith<SERVICE.Survey>(x => x.Spans);
db.LoadOptions = options;
return db;
}