开发者

How can I design my Java / C# library so it stays binary compatible in case of future changes?

Task: I am designing a library which will be used by developers.

Objective: I need to make sure that changes in future versions will not impact existing developers.

Example:

Situation during first release:

There is one class

public class ClassSample

{

String methodSample(String para1,String Para2, int Para3, String Para4);

}

Situation during second release:

Requirements:

Response of methodSample can return multiple values.

More parameters are needed in methodSample method.

Solution: One way could be just add another overloaded method which will have new parameters and return object rather than built-in data type.

But problem with above solution is, it will have too many overloaded methods in future, too many parameters will be overkill.

Modified Solution 1:

void methodSample(Request request, Response response)

In each release(obviously if required), I will modify Request & Response classes to have new additional methods to get/set values. There will be a problem in this case as inside the method, I won't be able to differentiate whether caller is of Version10 or Version20.

Modified Solution 2:

void methodSample(AbsractRequest request, AbstractResponse response)

In each release we can extend derived class like Request200 extends Request100 extends AbstractRequest, similarly for response classes. In this case I can check inside method whether caller is of Version10 or Version20 by checking instance typing.

In summary Modified Solution 2 looks good to me, what about your thoughts开发者_如何学Python ?


I would go for Modified Solution 1, but with the addition of a get/set Version method in the class.

Your library can the use getVersion find out which behaviour the user program is expecting


I realise this might be a bit late but thought might be useful to you or someone else.

I've created an SDK in the past that required versioning and did something very similar to what I posted below and it worked a treat.

The idea being that all messages derive from an abstracted class as you suggested, but there is a static that is set in the calling application right at the start. All requests then simply set a Version property equal to that of the static. This way its only specified once in the whole application.

When you add new versions, just add to the enum. I actually used an integer in mine and incremented it but I think an Enum is always more maintainable.

Enjoy!

namespace SilverlightClassLibrary1
{
    public enum SDKVersions
    {
        NonSpecific = 0,
        Version100,
        Version200,
    }

    public abstract class RequestBase
    {
        public static SDKVersions SystemSDKVersion { get; set; }

        public SDKVersions RequestSDKVersion { get; set; }

        protected RequestBase()
        {
            this.RequestSDKVersion = RequestBase.SystemSDKVersion;
        }
    }

    public class SimpleDataRequest : RequestBase
    {
        public String Data { get; set; }
    }

    public class SimpleDataResponse
    {
        public String Response { get; set; }
    }

    public class SomeSDKFunctionality
    {
        public static void RandomSDKFunction(SimpleDataRequest request, out SimpleDataResponse response)
        {
            switch (request.RequestSDKVersion)
            {
                case SDKVersions.Version100:
                    //Legacy response
                    response = new SimpleDataResponse()
                               {
                                   Response = "Helo " + request.Data,
                               };
                    break;

                default:
                    //Fixed / Updated Response
                    response = new SimpleDataResponse()
                               {
                                   Response = "Hello " + request.Data + "!",
                               };
                    break;
            }
        }
    }
}

namespace MyExternalApplication
{
    public class Main
    {
        public void ApplicationEntryPoint()
        {
            //Specify a specific version you intend to use
            RequestBase.SystemSDKVersion = SDKVersions.Version100;

        }

        public void ButtonClickExample()
        {
            SimpleDataResponse response;
            SomeSDKFunctionality.RandomSDKFunction(new SimpleDataRequest()
                                                   {
                                                       Data = "James",
                                                   }, out response);
        }
    }
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜