~ubuntu-branches/ubuntu/hardy/gnue-common/hardy

« back to all changes in this revision

Viewing changes to setupext/install_data.py

  • Committer: Bazaar Package Importer
  • Author(s): Andrew Mitchell
  • Date: 2005-03-09 11:06:31 UTC
  • Revision ID: james.westby@ubuntu.com-20050309110631-8gvvn39q7tjz1kj6
Tags: upstream-0.5.14
Import upstream version 0.5.14

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
"""install_data.py
 
2
 
 
3
Provides a more sophisticated facility to install data files
 
4
than distutils' install_data does.
 
5
You can specify your files as a template like in MANIFEST.in
 
6
and you have more control over the copy process. 
 
7
 
 
8
Copyright 2000 by Rene Liebscher, Germany.
 
9
 
 
10
Permission is hereby granted, free of charge, to any person obtaining
 
11
a copy of this software and associated documentation files (the
 
12
"Software"), to deal in the Software without restriction, including
 
13
without limitation the rights to use, copy, modify, merge, publish,
 
14
distribute, sublicense, and/or sell copies of the Software, and to
 
15
permit persons to whom the Software is furnished to do so, subject to
 
16
the following conditions:
 
17
 
 
18
The above copyright notice and this permission notice shall be included
 
19
in all copies or substantial portions of the Software.
 
20
 
 
21
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 
22
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 
23
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 
24
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
 
25
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
 
26
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
 
27
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
28
 
 
29
"""
 
30
 
 
31
# created 2000/08/01, Rene Liebscher <R.Liebscher@gmx.de>
 
32
# modified 2000/12/18, Martin v. Löwis <loewis@informatik.hu-berlin.de>
 
33
 
 
34
###########################################################################
 
35
# import some modules we need 
 
36
 
 
37
import os,sys,string
 
38
from types import StringType,TupleType,ListType
 
39
from distutils.util import change_root
 
40
from distutils.filelist import FileList
 
41
from distutils.command.install_data import install_data
 
42
 
 
43
###########################################################################
 
44
# a container class for our more sophisticated install mechanism
 
45
 
 
46
class Data_Files:
 
47
    """ container for list of data files.
 
48
        supports alternate base_dirs e.g. 'install_lib','install_header',...
 
49
        supports a directory where to copy files
 
50
        supports templates as in MANIFEST.in
 
51
        supports preserving of paths in filenames 
 
52
            eg. foo/xyz is copied to base_dir/foo/xyz
 
53
        supports stripping of leading dirs of source paths 
 
54
            eg. foo/bar1/xyz, foo/bar2/abc can be copied to bar1/xyz, bar2/abc 
 
55
    """
 
56
 
 
57
    def __init__(self,base_dir=None,files=None,copy_to=None,template=None,preserve_path=0,strip_dirs=0):
 
58
        self.base_dir = base_dir
 
59
        self.files = files
 
60
        self.copy_to = copy_to
 
61
        if template is not None:
 
62
            t = []
 
63
            for item in template:
 
64
                item = string.strip(item)
 
65
                if not item:continue
 
66
                t.append(item)
 
67
            template = t
 
68
        self.template = template
 
69
        self.preserve_path = preserve_path
 
70
        self.strip_dirs = strip_dirs
 
71
        self.finalized = 0
 
72
 
 
73
    def warn (self, msg):
 
74
        sys.stderr.write ("warning: %s: %s\n" %
 
75
                          ("install_data", msg))
 
76
        
 
77
    def debug_print (self, msg):
 
78
        """Print 'msg' to stdout if the global DEBUG (taken from the
 
79
        DISTUTILS_DEBUG environment variable) flag is true.
 
80
        """
 
81
        from distutils.core import DEBUG
 
82
        if DEBUG:
 
83
            print msg
 
84
 
 
85
        
 
86
    def finalize(self):
 
87
        """ complete the files list by processing the given template """
 
88
        if self.finalized: 
 
89
            return
 
90
        if self.files == None:
 
91
            self.files = []
 
92
        if self.template != None:
 
93
            if type(self.template) == StringType:
 
94
                self.template = string.split(self.template,";")
 
95
            filelist = FileList(self.warn,self.debug_print)
 
96
            for line in self.template:
 
97
                filelist.process_template_line(string.strip(line))
 
98
            filelist.sort()
 
99
            filelist.remove_duplicates()    
 
100
            self.files.extend(filelist.files)     
 
101
        self.finalized = 1
 
102
 
 
103
# end class Data_Files
 
104
 
 
105
###########################################################################
 
106
# a more sophisticated install routine than distutils install_data
 
107
 
 
108
class install_Data_Files (install_data):
 
109
    
 
110
    def check_data(self,d):
 
111
        """ check if data are in new format, if not create a suitable object.
 
112
            returns finalized data object
 
113
        """
 
114
        if not isinstance(d, Data_Files):
 
115
            self.warn(("old-style data files list found "
 
116
                        "-- please convert to Data_Files instance"))
 
117
            if type(d) is TupleType:
 
118
                if len(d) != 2 or  not (type(d[1]) is ListType):
 
119
                        raise DistutilsSetupError, \
 
120
                          ("each element of 'data_files' option must be an "
 
121
                            "Data File instance, a string or 2-tuple (string,[strings])")
 
122
                d = Data_Files(copy_to=d[0],files=d[1])
 
123
            else:
 
124
                if not (type(d) is StringType):
 
125
                        raise DistutilsSetupError, \
 
126
                          ("each element of 'data_files' option must be an "
 
127
                           "Data File instance, a string or 2-tuple (string,[strings])")
 
128
                d = Data_Files(files=[d])
 
129
        d.finalize()
 
130
        return d
 
131
     
 
132
    def run(self):
 
133
        self.outfiles = []
 
134
        install_cmd = self.get_finalized_command('install')
 
135
 
 
136
        for d in self.data_files:
 
137
            d = self.check_data(d)
 
138
 
 
139
            install_dir = self.install_dir
 
140
            # alternative base dir given => overwrite install_dir
 
141
            if d.base_dir != None:
 
142
                install_dir = getattr(install_cmd,d.base_dir)
 
143
     
 
144
            # copy to an other directory 
 
145
            if d.copy_to != None:
 
146
                if not os.path.isabs(d.copy_to):
 
147
                    # relatiev path to install_dir
 
148
                    dir = os.path.join(install_dir, d.copy_to)
 
149
                elif install_cmd.root:
 
150
                    # absolute path and alternative root set 
 
151
                    dir = change_root(self.root,d.copy_to)
 
152
                else:
 
153
                    # absolute path
 
154
                    dir = d.copy_to                  
 
155
            else:
 
156
                # simply copy to install_dir
 
157
                dir = install_dir
 
158
                # warn if necceassary  
 
159
                self.warn("setup script did not provide a directory to copy files to "
 
160
                          " -- installing right in '%s'" % install_dir)
 
161
 
 
162
            dir=os.path.normpath(dir)
 
163
            # create path
 
164
            self.mkpath(dir)
 
165
 
 
166
            # copy all files    
 
167
            for src in d.files:
 
168
                if d.strip_dirs > 0:
 
169
                    dst = string.join(string.split(os.path.normcase(src),os.sep)[d.strip_dirs:],os.sep)
 
170
                else:
 
171
                    dst = src
 
172
                if d.preserve_path:
 
173
                    # preserve path in filename
 
174
                    self.mkpath(os.path.dirname(os.path.join(dir,dst)))
 
175
                    out = self.copy_file(src, os.path.join(dir,dst))
 
176
                else:
 
177
                    out = self.copy_file(src, dir)
 
178
                if type(out) is TupleType:
 
179
                    out = out[0]
 
180
                self.outfiles.append(out)
 
181
 
 
182
        return self.outfiles
 
183
 
 
184
    def get_inputs (self):
 
185
        inputs = []
 
186
        for d in self.data_files:
 
187
            d = self.check_data(d)
 
188
            inputs.append(d.files)
 
189
        return inputs
 
190
  
 
191
    def get_outputs (self):
 
192
         return self.outfiles
 
193
 
 
194
 
 
195
###########################################################################
 
196