I am designing a (SOAP-like) inter-process communication protocol for making function calls over a network. I want to make sure an older client can talk to a newer server. After thinking over it for a while, it seems like the only thing I can do are:
我正在设计一个(类似SOAP的)进程间通信协议,用于通过网络进行函数调用。我想确保较旧的客户端可以与较新的服务器通信。经过一段时间的思考,似乎我唯一能做的就是:
- avoiding API changes
- make it possible to add functions
- make it possible to add function parameters
避免API更改
可以添加功能
可以添加功能参数
However, when the server's functionality thoroughly changes, this isn't enough. For example:
但是,当服务器的功能彻底改变时,这还不够。例如:
- a parameter that has to be moved from one function call to another.
- a parameter type that changes, for example from an integer to a string.
必须从一个函数调用移动到另一个函数调用的参数。
一个参数类型,例如从整数变为字符串。
My question is: can this kind of changes be made while staying backward compatible, or is the only option simply not to make them?
我的问题是:可以在保持向后兼容的同时做出这种改变,还是只是不做它们的唯一选择?
Note: I know, I am suffering from the not invented here syndrome, but in my opinion that doesn't invalidate this question.
注意:我知道,我患有这里没有发明的综合症,但在我看来,这并没有使这个问题无效。
1 个解决方案
#1
You haven't said exactly how you are implementing the IPC, so I might be making some poor assumptions here. Anyway, off the top of my head, there are a couple approaches to an issue like this.
你还没有确切地说明你是如何实现IPC的,所以我可能会在这里做一些不好的假设。无论如何,在我的脑海中,有一些方法可以解决这个问题。
First, regarding the point of parameter order/type changing, you can use a dynamic language like Python to get around this.
首先,关于参数顺序/类型更改的要点,您可以使用像Python这样的动态语言来解决这个问题。
>>> def discriminant(a,b,c):
... return b*b - 4*a*c
>>> discriminant(1,8,2)
56
>>>
>>> discriminant (c=2, a=1, b=8)
56
Python allows you to use named parameters so that you can name variables in any order you like, and all variables are dynamically typed.
Python允许您使用命名参数,以便您可以按您喜欢的任何顺序命名变量,并且所有变量都是动态类型的。
A less efficient approach to the ordering issue might be to pass all arguments in as a dictionary (written in Python, but can be adapted for whichever language):
排序问题的一种效率较低的方法可能是将所有参数作为字典传递(用Python编写,但可以适用于任何语言):
>>> def disc2(in_dict):
... return in_dict['b']*in_dict['b'] - 4 * in_dict['a'] * in_dict['c']
...
>>> d = dict(a=1, b=8, c=2)
>>> d
{'a': 1, 'c': 2, 'b': 8}
>>> disc2(d)
56
To expand upon this idea, you could also contain a "version" field in your dictionary (or arguments, whatever) to allow the server to adjust accordingly to the incoming arguments. It doesn't have to be a dictionary, you could put a version field in the packet containing the IPC message as well. This might be a contrived example, but you could account for missing fields this way as well.
为了扩展这个想法,您还可以在字典中包含“version”字段(或参数,无论如何),以允许服务器根据传入的参数进行相应调整。它不必是字典,您也可以在包含IPC消息的数据包中放置一个版本字段。这可能是一个人为的例子,但你也可以通过这种方式解释缺失的字段。
>>> def disc3(d):
... if d['version'] == 1: # original spec
... return d['b'] * d['b'] - 4 * d['a'] * d['c']
... else: # newer clients returning smaller values of c
... return d['b'] * d['b'] - 4 * d['a'] * (2*d['c'])
...
>>> d['version'] = 1
>>> disc3(d)
56
>>> d['version'] = 2
>>> disc3(d)
48
#1
You haven't said exactly how you are implementing the IPC, so I might be making some poor assumptions here. Anyway, off the top of my head, there are a couple approaches to an issue like this.
你还没有确切地说明你是如何实现IPC的,所以我可能会在这里做一些不好的假设。无论如何,在我的脑海中,有一些方法可以解决这个问题。
First, regarding the point of parameter order/type changing, you can use a dynamic language like Python to get around this.
首先,关于参数顺序/类型更改的要点,您可以使用像Python这样的动态语言来解决这个问题。
>>> def discriminant(a,b,c):
... return b*b - 4*a*c
>>> discriminant(1,8,2)
56
>>>
>>> discriminant (c=2, a=1, b=8)
56
Python allows you to use named parameters so that you can name variables in any order you like, and all variables are dynamically typed.
Python允许您使用命名参数,以便您可以按您喜欢的任何顺序命名变量,并且所有变量都是动态类型的。
A less efficient approach to the ordering issue might be to pass all arguments in as a dictionary (written in Python, but can be adapted for whichever language):
排序问题的一种效率较低的方法可能是将所有参数作为字典传递(用Python编写,但可以适用于任何语言):
>>> def disc2(in_dict):
... return in_dict['b']*in_dict['b'] - 4 * in_dict['a'] * in_dict['c']
...
>>> d = dict(a=1, b=8, c=2)
>>> d
{'a': 1, 'c': 2, 'b': 8}
>>> disc2(d)
56
To expand upon this idea, you could also contain a "version" field in your dictionary (or arguments, whatever) to allow the server to adjust accordingly to the incoming arguments. It doesn't have to be a dictionary, you could put a version field in the packet containing the IPC message as well. This might be a contrived example, but you could account for missing fields this way as well.
为了扩展这个想法,您还可以在字典中包含“version”字段(或参数,无论如何),以允许服务器根据传入的参数进行相应调整。它不必是字典,您也可以在包含IPC消息的数据包中放置一个版本字段。这可能是一个人为的例子,但你也可以通过这种方式解释缺失的字段。
>>> def disc3(d):
... if d['version'] == 1: # original spec
... return d['b'] * d['b'] - 4 * d['a'] * d['c']
... else: # newer clients returning smaller values of c
... return d['b'] * d['b'] - 4 * d['a'] * (2*d['c'])
...
>>> d['version'] = 1
>>> disc3(d)
56
>>> d['version'] = 2
>>> disc3(d)
48