开发者

Python: Best practice for including a version number in an app?

开发者 https://www.devze.com 2023-02-01 01:27 出处:网络
I have a PyQt application that reads and writes data files. I am including a \'version number\' in each file written.This is a simple number similar to: 1.2or something (major and minor versions).

I have a PyQt application that reads and writes data files. I am including a 'version number' in each file written. This is a simple number similar to: 1.2 or something (major and minor versions).

I am doing this so that I can change the format of these data files in future versions and then still correctly parse them simply by checking to see what the version is inside the file.

My question is what is the best practice for keeping this number stored inside the app itself. I.e. do I 开发者_开发百科just hard-code the app version number into the class that is responsible for reading and writing files? Or should I have some sort of object/variable stored at the top-level of the app and somehow access it from the class responsible for reading and writing these files. If the latter, how do I store it and how do I access it?

Thanks.


First, version the data format separately from the app, if not already doing so. Second, have separate classes for newer versions of the format. If the format is completely backwards compatible, you can drop the classes for older versions. As for the file structure, you could have something like:

  • DF
    • __init__.py
    • dfbase.py
    • v1_1
      • __init__.py
      • format.py
    • v2_0
      • __init__.py
      • format.py

where "df" stands for the data format name. The package initialization files import the appropriate packages and define a structure or function to make them accessible. The top-level __init__.py should also define a factory function to create data format objects, so you don't have to.

DF/__init__.py:

from df.dfbase import DFBase
from v1_1 import DF as DF1
from v2_0 import DF as DF2
versions = {
  '1.0': DF1, # let's say minor versions are fully backwards compatible
  '1.1': DF1, 
  '2.0': DF2
}
def create(file):
    """Factory function. Loads data from 'file', returns a DF of the appropriate 
    version.
    """
    ...

DF/v1_1/__init__.py:

__version__ = '1.1'
# previous versions that this one is backwards compatible with
previous = ['1.0']
from format import DF

DF/v1_1/format.py:

from df import DFBase

class DF(DFBase):
    ...

DF/v2_0/__init__.py:

__version__ = '2.0'
from format import DF

With a little more coding in DF/__init__.py, you could automate the import and registration of format versions.

import glob, sys
from ndf.ndfbase import NDFBase

formats={}

for ver in glob.iglob('v*_*'):
    pkg = '{0}.{1}'.format(__package__, ver)
    __import__(pkg)
    formats[sys.modules[pkg].__version__] = sys.modules[pkg]
    if hasattr(sys.modules[pkg], 'previous'):
        for prev in sys.modules[pkg].previous:
            formats[prev] = sys.modules[pkg]

def create(file):
    """Factory function. Loads data from 'file', returns a DF of the appropriate 
    version.
    """
    ...


Many open source projects (e.g. numpy, fabric) have a module called "version", which contains version information in top-level variables. See e.g. fabric's version file.


Personally, I wouldn't do it manually this way. I'd save my code in Subversion and let it maintain the revision numbers for me.

0

精彩评论

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