웹 서비스를 통해 복잡한 데이터를 전송할 때 선호하는 방법은 무엇입니까?

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

  •  08-06-2019
  •  | 
  •  

문제

2008년인데 아직도 이 일이 생각나네요.그래서 저는 복잡한 유형을 전달하고 반환해야 하는 웹 메서드를 개발 중입니다.제가 고려하고 있는 두 가지 옵션은 다음과 같습니다.

  1. 패스하고 돌아오세요 실제 데이터와 동작을 모두 포함하는 비즈니스 개체입니다.wsdl.exe가 실행되면 데이터 부분만 포함하는 프록시 클래스가 자동으로 생성되며, 이러한 클래스는 서버 측의 실제 비즈니스 개체와 자동으로 변환됩니다.클라이언트 측에서는 멍청한 프록시 유형만 사용할 수 있으며 적절하다고 판단되는 실제 비즈니스 개체에 매핑해야 합니다.여기서 큰 단점은 서버측과 클라이언트측을 모두 "소유"하고 동일한 실제 비즈니스 개체 세트를 사용하려는 경우 이름 충돌 등으로 인해 특정 문제에 직면할 수 있다는 것입니다.(실제 객체와 프록시의 이름이 동일하기 때문입니다.)

  2. "실제" 비즈니스 개체를 전달하는 것을 잊어버리세요.대신, 실제 비즈니스 객체에 수동으로 매핑할 간단한 DataTransfer 객체를 생성하세요.어쨌든 wsdl.exe에 의해 새 프록시 개체에 복사되지만 적어도 웹 서비스가 기본적으로 비즈니스 논리가 포함된 개체를 처리할 수 있다고 생각하도록 속이지는 않습니다.

그런데 - wsdl.exe에 어떻게 지시하는지 아는 사람 있나요? ~ 아니다 객체의 복사본을 만드시겠습니까?그냥 '야, 여기 기존 유형을 써라.복사하지 마세요!"

어쨌든, 나는 지금은 2번에 어느 정도 자리를 잡았는데, 여러분은 어떻게 생각하시는지 궁금합니다.느낌이 있어 거기에 있어요 방법 일반적으로 이 작업을 수행하는 더 나은 방법이 있으며 내 모든 요점이 완전히 정확하지 않을 수도 있으므로 귀하의 경험이 무엇인지 알려주십시오.

업데이트:방금 VS 2008에는 프록시 파일에 완전히 새로운 동일한 유형을 생성하는 대신 "서비스 참조"를 추가할 때 기존 유형을 재사용할 수 있는 옵션이 있다는 것을 알았습니다.달콤한.

도움이 되었습니까?

해결책

계층을 분리해야 한다는 주장도 있습니다. 웹 서비스와 주고받는 일련의 직렬화 가능한 개체가 있고, 해당 집합과 비즈니스 개체 사이를 매핑하고 변환하는 변환기가 있어야 합니다(이는 전달에 적합하지 않은 속성을 가질 수 있음). 철사)

웹 서비스 소프트웨어 공장에서 선호하는 접근 방식입니다. 서비스 공장 이는 웹 서비스 인터페이스/계약을 위반하지 않고 비즈니스 개체를 변경할 수 있음을 의미합니다.

다른 팁

나는 하이브리드를 할 것이다.나는 이런 객체를 사용할 것이다

public class TransferObject
{
    public string Type { get; set; }
    public byte[] Data { get; set; }
}

그런 다음 개체를 직렬화한 다음 압축하는 멋진 작은 유틸리티가 있습니다.

public static class CompressedSerializer
{
    /// <summary>
    /// Decompresses the specified compressed data.
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="compressedData">The compressed data.</param>
    /// <returns></returns>
    public static T Decompress<T>(byte[] compressedData) where T : class
    {
        T result = null;
        using (MemoryStream memory = new MemoryStream())
        {
            memory.Write(compressedData, 0, compressedData.Length);
            memory.Position = 0L;

            using (GZipStream zip= new GZipStream(memory, CompressionMode.Decompress, true))
            {
                zip.Flush();
                var formatter = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
                result = formatter.Deserialize(zip) as T;
            }
        }

        return result;
    }

    /// <summary>
    /// Compresses the specified data.
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="data">The data.</param>
    /// <returns></returns>
    public static byte[] Compress<T>(T data)
    {
        byte[] result = null;
        using (MemoryStream memory = new MemoryStream())
        {
            using (GZipStream zip= new GZipStream(memory, CompressionMode.Compress, true))
            {
                var formatter = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
                formatter.Serialize(zip, data);
            }

            result = memory.ToArray();
        }

        return result;
    }
}

그런 다음 유형 이름이 있는 전송 객체를 전달하면 됩니다.그래서 당신은 이런 일을 할 수 있습니다

[WebMethod]
public void ReceiveData(TransferObject data)
{
    Type originType = Type.GetType(data.Type);
    object item = CompressedSerializer.Decompress<object>(data.Data);
}

현재 압축된 직렬 변환기는 제네릭을 사용하여 강력한 형식을 지정하지만 위의 OriginType을 사용하여 역직렬화하기 위해 Type 개체를 쉽게 가져오는 메서드를 만들 수 있습니다. 모두 구현에 따라 다릅니다.

이것이 당신에게 몇 가지 아이디어를 제공하기를 바랍니다.아, 그리고 다른 질문에 대답하자면, wsdl.exe는 유형 재사용을 지원하지 않지만 WCF는 지원합니다.

대런 썼다:나는 하이브리드를 할 것이다.이런 객체를 사용하겠습니다 ...

흥미로운 아이디어...(wsdl-ed) 객체 자체 대신 객체의 직렬화된 버전을 전달합니다.어떤 면에서는 그 우아함이 마음에 들지만 다른 면에서는 귀하의 웹 서비스를 잠재적인 제3자나 파트너 등에 노출하려는 목적을 무너뜨리는 것 같습니다.무엇을 통과해야 할지 어떻게 알 수 있을까요?순전히 문서에만 의존해야 합니까?또한 직렬화가 매우 .Net에 특정하기 때문에 "이기종 클라이언트" 측면 중 일부가 손실됩니다.비판하려는 의도는 아니지만, 귀하가 제안하는 내용이 이러한 유형의 사용 사례에도 적용되는지 궁금합니다.하지만 폐쇄된 환경에서 사용해도 아무런 문제가 없습니다.

WCF를 살펴봐야 하는데...그동안 피하고 있었는데 이제 때가 된 것 같습니다.

아, 물론이죠. 제가 웹 서비스의 소비자이거나 개체를 요청하는 일종의 컨트롤러가 있는 경우에만 이 작업을 수행합니다. 그런 다음 웹 서비스를 직접 소비하는 대신 직렬화 및 전송을 처리합니다.그러나 실제로 웹 서비스를 직접 사용하는 경우에는 처음에 해당 유형을 포함하는 어셈블리가 필요하지 않거나 반드시 있어야 하며 wsdl이 생성하는 개체를 사용해야 합니다.

그리고 그렇습니다. 제가 제시하는 내용은 매우 .NET에만 국한됩니다. 왜냐하면 저는 다른 것을 사용하는 것을 좋아하지 않기 때문입니다..net 외부에서 웹 서비스를 소비하는 유일한 때는 javascript였지만 지금은 xml 웹 서비스 응답 대신 json 응답만 사용합니다. :)

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