Added fix for TeX includes with same name as subdirs.
[scons.git] / test / Copy-Action.py
1 #!/usr/bin/env python
2 #
3 # __COPYRIGHT__
4 #
5 # Permission is hereby granted, free of charge, to any person obtaining
6 # a copy of this software and associated documentation files (the
7 # "Software"), to deal in the Software without restriction, including
8 # without limitation the rights to use, copy, modify, merge, publish,
9 # distribute, sublicense, and/or sell copies of the Software, and to
10 # permit persons to whom the Software is furnished to do so, subject to
11 # the following conditions:
12 #
13 # The above copyright notice and this permission notice shall be included
14 # in all copies or substantial portions of the Software.
15 #
16 # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY
17 # KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
18 # WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19 # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20 # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21 # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22 # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 #
24
25 __revision__ = "__FILE__ __REVISION__ __DATE__ __DEVELOPER__"
26
27 """
28 Verify that the Copy() Action works, and preserves file modification
29 times and modes.
30 """
31
32 import os
33 import stat
34 import sys
35
36 import TestSCons
37
38 test = TestSCons.TestSCons()
39
40 test.write('SConstruct', """
41 Execute(Copy('f1.out', 'f1.in'))
42 Execute(Copy(File('d2.out'), 'd2.in'))
43 Execute(Copy('d3.out', File('f3.in')))
44 def cat(env, source, target):
45     target = str(target[0])
46     f = open(target, "wb")
47     for src in source:
48         f.write(open(str(src), "rb").read())
49     f.close()
50 Cat = Action(cat)
51 env = Environment()
52 env.Command('bar.out', 'bar.in', [Cat,
53                                   Copy("f4.out", "f4.in"),
54                                   Copy("d5.out", "d5.in"),
55                                   Copy("d6.out", "f6.in")])
56 env = Environment(OUTPUT = 'f7.out', INPUT = 'f7.in')
57 env.Command('f8.out', 'f8.in', [Copy('$OUTPUT', '$INPUT'), Cat])
58 env.Command('f9.out', 'f9.in', [Cat, Copy('${TARGET}-Copy', '$SOURCE')])
59
60 env.CopyTo( 'd4', 'f10.in' )
61 env.CopyAs( 'd4/f11.out', 'f11.in')
62 env.CopyAs( 'd4/f12.out', 'd5/f12.in')
63
64 env.Command('f   13.out', 'f   13.in', Copy('$TARGET', '$SOURCE'))
65 """)
66
67 test.write('f1.in', "f1.in\n")
68 test.subdir('d2.in')
69 test.write(['d2.in', 'file'], "d2.in/file\n")
70 test.write('f3.in', "f3.in\n")
71 test.subdir('d3.out')
72 test.write('bar.in', "bar.in\n")
73 test.write('f4.in', "f4.in\n")
74 test.subdir('d5.in')
75 test.write(['d5.in', 'file'], "d5.in/file\n")
76 test.write('f6.in', "f6.in\n")
77 test.subdir('d6.out')
78 test.write('f7.in', "f7.in\n")
79 test.write('f8.in', "f8.in\n")
80 test.write('f9.in', "f9.in\n")
81 test.write('f10.in', "f10.in\n")
82 test.write('f11.in', "f11.in\n")
83 test.subdir('d5')
84 test.write(['d5', 'f12.in'], "f12.in\n")
85 test.write('f   13.in', "f   13.in\n")
86
87 os.chmod('f1.in', 0646)
88 os.chmod('f4.in', 0644)
89
90 test.sleep()
91
92 d4_f10_in   = os.path.join('d4', 'f10.in')
93 d4_f11_out  = os.path.join('d4', 'f11.out')
94 d4_f12_out  = os.path.join('d4', 'f12.out')
95 d5_f12_in   = os.path.join('d5', 'f12.in')
96
97 expect = test.wrap_stdout(read_str = """\
98 Copy("f1.out", "f1.in")
99 Copy("d2.out", "d2.in")
100 Copy("d3.out", "f3.in")
101 """,
102                           build_str = """\
103 cat(["bar.out"], ["bar.in"])
104 Copy("f4.out", "f4.in")
105 Copy("d5.out", "d5.in")
106 Copy("d6.out", "f6.in")
107 Copy file(s): "f10.in" to "%(d4_f10_in)s"
108 Copy file(s): "f11.in" to "%(d4_f11_out)s"
109 Copy file(s): "%(d5_f12_in)s" to "%(d4_f12_out)s"
110 Copy("f   13.out", "f   13.in")
111 Copy("f7.out", "f7.in")
112 cat(["f8.out"], ["f8.in"])
113 cat(["f9.out"], ["f9.in"])
114 Copy("f9.out-Copy", "f9.in")
115 """ % locals())
116
117 test.run(options = '-n', arguments = '.', stdout = expect)
118
119 test.must_not_exist('f1.out')
120 test.must_not_exist('d2.out')
121 test.must_not_exist(os.path.join('d3.out', 'f3.in'))
122 test.must_not_exist('f4.out')
123 test.must_not_exist('d5.out')
124 test.must_not_exist(os.path.join('d6.out', 'f6.in'))
125 test.must_not_exist('f7.out')
126 test.must_not_exist('f8.out')
127 test.must_not_exist('f9.out')
128 test.must_not_exist('f9.out-Copy')
129 test.must_not_exist('d4/f10.in')
130 test.must_not_exist('d4/f11.out')
131 test.must_not_exist('d4/f12.out')
132 test.must_not_exist('f 13.out')
133 test.must_not_exist('f    13.out')
134
135 test.run()
136
137 test.must_match('f1.out', "f1.in\n")
138 test.must_match(['d2.out', 'file'], "d2.in/file\n")
139 test.must_match(['d3.out', 'f3.in'], "f3.in\n")
140 test.must_match('f4.out', "f4.in\n")
141 test.must_match(['d5.out', 'file'], "d5.in/file\n")
142 test.must_match(['d6.out', 'f6.in'], "f6.in\n")
143 test.must_match('f7.out', "f7.in\n")
144 test.must_match('f8.out', "f8.in\n")
145 test.must_match('f9.out', "f9.in\n")
146 test.must_match('f9.out-Copy', "f9.in\n")
147 test.must_match('d4/f10.in', 'f10.in\n')
148 test.must_match('d4/f11.out', 'f11.in\n')
149 test.must_match('d4/f12.out', 'f12.in\n')
150 test.must_match('f   13.out', 'f   13.in\n')
151
152 errors = 0
153
154 def must_be_same(f1, f2):
155     global errors
156     if isinstance(f1, list):
157         f1 = os.path.join(*f1)
158     if isinstance(f2, list):
159         f2 = os.path.join(*f2)
160     s1 = os.stat(f1)
161     s2 = os.stat(f2)
162     for value in ['ST_MODE', 'ST_MTIME']:
163         v = getattr(stat, value)
164         if s1[v] != s2[v]:
165             msg = '%s[%s] %s != %s[%s] %s\n' % \
166                   (repr(f1), value, s1[v],
167                    repr(f2), value, s2[v],)
168             sys.stderr.write(msg)
169             errors = errors + 1
170
171 must_be_same('f1.out',                  'f1.in')
172 must_be_same(['d2.out', 'file'],        ['d2.in', 'file'])
173 must_be_same(['d3.out', 'f3.in'],       'f3.in')
174 must_be_same('f4.out',                  'f4.in')
175 must_be_same(['d5.out', 'file'],        ['d5.in', 'file'])
176 must_be_same(['d6.out', 'f6.in'],       'f6.in')
177 must_be_same('f7.out',                  'f7.in')
178 must_be_same(['d4', 'f10.in'],          'f10.in')
179 must_be_same(['d4', 'f11.out'],         'f11.in')
180 must_be_same(['d4', 'f12.out'],         ['d5', 'f12.in'])
181 must_be_same('f   13.out',              'f   13.in')
182
183 if errors:
184     test.fail_test()
185
186 test.pass_test()
187
188 # Local Variables:
189 # tab-width:4
190 # indent-tabs-mode:nil
191 # End:
192 # vim: set expandtab tabstop=4 shiftwidth=4: