开发者

Creating versioned libraries in python

开发者 https://www.devze.com 2023-04-01 17:13 出处:网络
We\'re setting up new branches at work which all will share the same libraries. The problem with this is if we update one library you might break all apps that aren\'t updated.

We're setting up new branches at work which all will share the same libraries.

The problem with this is if we update one library you might break all apps that aren't updated.

Therefore we would like to version our libraries.

The way I was planning on doing this is either like this

loader.load(name='mylib', version='1.0')

or maybe like this:

import mylib
mylib.load(version='1.0')

The question is how this loader would work.

The naive approach is to have each version in their own folder, the problem with this however is that if there is a common bug in all versions every version needs to be fixed separately.

A slightly better approach (for maintainability) is to have all versions of a library in the same file and call some load function which creates links to functions. I don't know how pretty this will be (we might end up with monster file of several thousand lines, we could of course remove old, unused versions).

To help with keeping the number of versions down I'm开发者_高级运维 planning on only incrementing the version number when I break compatibility, not when bug fixing or adding new stuff.

Is there anything like this built into python or any other approach that would work?

Does anyone have experience of this sort of stuff?


I can add that things that are using the libs are test cases, we just want the tester to cd into the branch and run ./testit.py, nothing else.


Solution

The solution is based on Gringo Suave's suggestion.

class MyClass_1_0:
    def func1(self):
        return 'Baz'

    def func2(self):
        return 'Bar'

class MyClass_1_1(MyClass_1_0):
    # Overwriting a function:
    def func1(self):
        return 'Foo'

    # Definining a new function which uses a function
    # from a previous version:
    def func3(self):
        print("{} {}".format(self.func1(), self.func2()))

# Change this to the latest version for stuff that always wants the latest
class MyClass(MyClass_1_1): pass

Example usage:

>>> from my.module import MyClass_1_1 as MyClass
>>> m = MyClass()
>>> m.func3()
Foo Bar


Typically the way this is done is by incrementing the module name. You could design a more robust method, but this is the easiest to understand/implement.

import package.modv2
import package.modv3

Create a new module version each time the API has changed.

It could also be done at the function level to minimize the number of files:

from package.module import functionv2
from package.module import functionv3


I believe this is what virtualenv was designed to do. From the virtualenv website:

virtualenv is a tool to create isolated Python environments.

The basic problem being addressed is one of dependencies and versions, and indirectly permissions. Imagine you have an application that needs version 1 of LibFoo, but another application requires version 2. How can you use both these applications?

In [this case], virtualenv can help you. It creates an environment that has its own installation directories, that doesn't share libraries with other virtualenv environments (and optionally doesn't access the globally installed libraries either).


I know setuptools used to have something like this. I can't find it right now but that doesn't mean it's gone. You might want to look into it.

0

精彩评论

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