|
Size: 1818
Comment:
|
← Revision 6 as of 2009-04-22 03:53:19 ⇥
Size: 2131
Comment: fix broken example
|
| Deletions are marked like this. | Additions are marked like this. |
| Line 1: | Line 1: |
| ## page was renamed from DistutilsAutoDataDiscovery | |
| Line 11: | Line 12: |
| def npFilesFor( dirname ): """Return all non-python-file filenames in dir""" |
import imp def non_python_files(path): """ Return all non-python-file filenames in path """ |
| Line 14: | Line 17: |
| allResults = [] for name in os.listdir(dirname): path = os.path.join( dirname, name ) |
all_results = [] module_suffixes = [info[0] for info in imp.get_suffixes()] ignore_dirs = ['cvs'] for item in os.listdir(path): name = os.path.join(path, item) |
| Line 18: | Line 23: |
| os.path.isfile( path) and os.path.splitext( name )[1] not in ('.py','.pyc','.pyo') ): result.append( path ) elif os.path.isdir( path ) and name.lower() !='cvs': allResults.extend( npFilesFor(path)) |
os.path.isfile(name) and os.path.splitext(item)[1] not in module_suffixes ): result.append(name) elif os.path.isdir(name) and item.lower() not in ignore_dirs: all_results.extend(non_python_files(name)) |
| Line 26: | Line 30: |
| allResults.append( (dirname, result)) return allResults |
all_results.append((path, result)) return all_results |
| Line 33: | Line 37: |
| dataFiles = ( npFilesFor( 'pytable') + npFilesFor( os.path.join('pytable','doc')) ) |
data_files = ( non_python_files('pytable') + non_python_files(os.path.join('pytable', 'doc')) ) |
| Line 45: | Line 49: |
| data_files = dataFiles, | data_files = data_files, |
| Line 47: | Line 51: |
| **extraArguments ) |
**extra_arguments ) |
| Line 52: | Line 56: |
You can see a real-world usage example in the [[http://cvs.sourceforge.net/viewcvs.py/pytable/table/setup.py?view=markup|PyTable setup script]] |
Problem
Distutils requires that you manually specify each directory and data-file to be included in the distribution. For packages with large and deep sub-package hierarchies it can be a pain to keep this list in sync with the code, particularly as forgetting an entry is not noticable until a user happens to report that a resource is missing.
Solution
Use an automatic scanning mechanism to generate the data_files parameter for setup:
import os
import imp
def non_python_files(path):
""" Return all non-python-file filenames in path """
result = []
all_results = []
module_suffixes = [info[0] for info in imp.get_suffixes()]
ignore_dirs = ['cvs']
for item in os.listdir(path):
name = os.path.join(path, item)
if (
os.path.isfile(name) and
os.path.splitext(item)[1] not in module_suffixes
):
result.append(name)
elif os.path.isdir(name) and item.lower() not in ignore_dirs:
all_results.extend(non_python_files(name))
if result:
all_results.append((path, result))
return all_resultsThen call it for the directories which contain data-files you want to include.
data_files = (
non_python_files('pytable') +
non_python_files(os.path.join('pytable', 'doc'))
)and pass the result to setup:
setup (
name = "pytable",
version = "0.7.7a",
data_files = data_files,
cmdclass = {'install_data':smart_install_data},
**extra_arguments
)(See DistutilsInstallDataScattered for the smart_install_data command.)
You can see a real-world usage example in the PyTable setup script
Discussion
Again, there should be some way to do this with a distutils template processing call or something, but this direct processing approach works well enough. This approach is very similar to DistutilsAutoPackageDiscovery.
