4
\$\begingroup\$

Recently I asked this question: Generic methods for serializing and deserialzing xml files using streams

However it has come to my attention that this gives me an (harmless) exception when trying to deserialize.

System.IO.FileNotFoundException occurred
 Message="Could not load file or assembly '[Containing Assembly of MyType].XmlSerializers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' or one of its dependencies. The system cannot find the file specified."
 Source="mscorlib"
 FileName="[Containing Assembly of MyType].XmlSerializers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"
 FusionLog=""
 StackTrace:
 at System.Reflection.Assembly._nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, Assembly locationHint, StackCrawlMark& stackMark, Boolean throwOnFileNotFound, Boolean forIntrospection)
 at System.Reflection.Assembly.nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, Assembly locationHint, StackCrawlMark& stackMark, Boolean throwOnFileNotFound, Boolean forIntrospection)

It is a well known problem and most people would fix it by adding this to their csproj:

<Target Name="AfterBuild" DependsOnTargets="AssignTargetPaths;Compile;ResolveKeySource" Inputs="$(MSBuildAllProjects);@(IntermediateAssembly)" Outputs="$(OutputPath)$(_SGenDllName)">
 <!-- Delete the file because I can't figure out how to force the SGen task. -->
 <Delete
 Files="$(TargetDir)$(TargetName).XmlSerializers.dll"
 ContinueOnError="true" />
 <SGen
 BuildAssemblyName="$(TargetFileName)"
 BuildAssemblyPath="$(OutputPath)"
 References="@(ReferencePath)"
 ShouldGenerateSerializer="true"
 UseProxyTypes="false"
 KeyContainer="$(KeyContainerName)"
 KeyFile="$(KeyOriginatorFile)"
 DelaySign="$(DelaySign)"
 ToolPath="$(TargetFrameworkSDKToolsDirectory)"
 Platform="$(Platform)">
 <Output
 TaskParameter="SerializationAssembly"
 ItemName="SerializationAssembly" />
 </SGen>
</Target>

However I've tried something different namely:

public static T DeserializeObject<T>(this Stream stream) where T : IXmlSerializable
{
 Parameters.RequireNotNull(stream, "stream");
 using (var xmlTextReader = XmlReader.Create(stream))
 {
 var importer = new XmlReflectionImporter()
 var mapping = importer.ImportTypeMapping(typeof(T));
 var serializer = new XmlSerializer(mapping);
 T result = (T)serializer.Deserialize(xmlTextReader);
 stream.Close();
 return result;
 }
}

So my question, is this good code? is this a proper work around?

asked Nov 10, 2015 at 8:40
\$\endgroup\$

1 Answer 1

2
\$\begingroup\$

So my question, is this good code? is this a proper work around?

I would ask different questions:

  • Does the code work?
  • Could you avoid editing the csproj file?

If both answers are yes, the I'd say it's a good workaround... but not a perfect one.

stream.Close();

This line shouldn't be there. The caller should take care of disposing the stream. Every method should keep track only of its own resources. The ones that come from the outside world should be taken care of by their respective owner.

I'd be really surprised if I called this method and wanted to work with the stream later but get an exception that it has already been closed.

answered Nov 3, 2016 at 10:51
\$\endgroup\$

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.