사용자 정의 직렬화 / Deserialization을 사용한 유닛 테스트 서비스 서비스

StackOverflow https://stackoverflow.com//questions/9671493

  •  12-12-2019
  •  | 
  •  

문제

나는 자체 DE / 직렬화 메커니즘이 제공된 웹 서비스를 테스트하는 데 문제가 있습니다.

Task에서 사용중인 샘플 TaskService 클래스 :

public class Task
{
    public string TaskName { get; set; }
    public string AuxData { get; set; }

    public static void RegisterCustomSerialization(IAppHost appHost)
    {
        appHost.ContentTypeFilters.Register("application/xml", SerializeTaskToStream, DeserializeTaskFromStream);
    }

    public static void SerializeTaskToStream(IRequestContext requestContext, object response, Stream stream)
    {
        var tasks = response as List<Task>;
        if (tasks != null)
        {
            using (var sw = new StreamWriter(stream))
            {
                if (tasks.Count == 0)
                {
                    sw.WriteLine("<Tasks/>");
                    return;
                }

                sw.WriteLine("<Tasks>");
                foreach (Task task in tasks)
                {
                    if (task != null)
                    {
                        sw.WriteLine("  <Task type=\"new serializer\">");
                        sw.Write("    <TaskName>");
                        sw.Write(task.TaskName);
                        sw.WriteLine("</TaskName>");
                        sw.Write("    <AuxData>");
                        sw.Write(task.AuxData);
                        sw.WriteLine("</AuxData>");
                        sw.WriteLine("  </Task>");
                    }
                }
                sw.WriteLine("</Tasks>");
            }
        }
        else
        {
            var task = response as Task;
            using (var sw = new StreamWriter(stream))
            {
                if (task != null)
                {
                    sw.WriteLine("  <Task type=\"new serializer\">");
                    sw.Write("    <TaskName>");
                    sw.Write(task.TaskName);
                    sw.WriteLine("</TaskName>");
                    sw.Write("    <AuxData>");
                    sw.Write(task.AuxData);
                    sw.WriteLine("</AuxData>");
                    sw.WriteLine("  </Task>");
                }
            }
        }
    }

    public static object DeserializeTaskFromStream(Type type, Stream stream)
    {
        if (stream == null || stream.Length == 0)
            return null; // should throw exception?
        XDocument xdoc = XDocument.Load(stream);
        XElement auxData = xdoc.Root.Element("AuxData");

        return new Task() { AuxData = auxData.Value };
    }


    public override bool Equals(object obj)
    {
        Task task = obj as Task;
        if (task == null)
            return false;
        return TaskName.Equals(task.TaskName);
    }

    public override int GetHashCode()
    {
        return TaskName.GetHashCode();
    }
}
.

I : http : // www. servicestack.net/servicestack.northwind/vcard-format.htm https://github.com/servicestack/servicestack.examples/blob/master/src/servicestack.northwind/servicestack.northwind.serviceintface/vcardformat.cs

내 기본 테스트 클래스는 다음과 같습니다.

public class SimpleRestTestBase : AppHostBase
{
    public SimpleRestTestBase() : base( "SimpleRestTestBase", typeof(TaskService).Assembly)
    {
        Instance = null;
        Init();
    }

    public override void Configure(Funq.Container container)
    {
        SetConfig(new EndpointHostConfig
        {
            DefaultContentType = ContentType.Xml
        }
        );

        Task.RegisterCustomSerialization(this);

        Routes
          .Add<Task>("/tasks/{TaskName}")
          .Add<List<Task>>("/tasks");

        container.Register(new List<Task>());
    }
}
.

및 실패한 단위 테스트 :

[TestFixture]
public class SimpleTest : SimpleRestTestBase
{
    [Test]
    public void TestMetodRequiringServer()
    {
        var client = (IRestClient)new XmlServiceClient("http://localhost:53967");
        var data = client.Get<List<Task>>("/api/tasks");
    }
}
.

NUNIT 테스트 러너를 사용할 때 얻는 예외는 다음과 같습니다.

Testing.SimpleTest.TestMetodRequiringServer: System.Runtime.Serialization.SerializationException : Error in line 1 position 9. Expecting element 'ArrayOfTask' from namespace 'http://schemas.datacontract.org/2004/07/ServiceStackMVC'.. Encountered 'Element' with name 'Tasks', namespace ''.

사용자 정의 직렬화 / 음성화 코드에 대한 정보를 XmlServiceClient에 어떻게 전달합니까?

도움이 되었습니까?

해결책

일반 XML 직렬화 형식 (Application / XML)을 Welly-Couply 1 웹 서비스 출력 만 처리 할 수있는 사용자 지정 버전으로 무시합니다. 이것은 매우 드뭅니다 (즉, 휴식을 취할 수 있습니다). XML을 반환하는 다른 서비스. 사용자 정의 XML을 반환하려면 XML 문자열을 대신 반환하여 필요한 서비스로 제한하십시오.

XMLServiceClient의 구현은 XML 직렬화 / servicestack이 사용하는 XML 직렬화 / deserialization에 크게 결합 될 때 변경할 수 없습니다. 원하는 XML 페이로드를 보내려면 원시 HTTP 클라이언트를 사용해야합니다. 다음은 .NET의 웹 요청으로 원시 XML을 보내는 예입니다. https://stackoverflow.com/a/8046734/85785

사용자 정의 XML을 반환하고 보내는 이래 웹 서비스에 대한 사용자 정의 요청 바인더를 무시할 수 있으므로 원하는 방식의 요청을 수행 할 수있는 기회가 있습니다.

이를 수행하는 방법에 대한 몇 가지 예제는 다음과 같은 Wiki 페이지를 참조하십시오.

https://github.com/servicestack/servicestack/wiki/serialization-deserialization.

참고 : 사용자 정의 XML을 반환하는 것은 서비스가 강한 타이핑되고 지능형이며 의견이있는 자연의 많은 이점을 지나치게합니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top