Cleanup tree_status and use -z
[stgit] / stgit / commands / refresh.py
CommitLineData
fcee87cf
CM
1
2__copyright__ = """
3Copyright (C) 2005, Catalin Marinas <catalin.marinas@gmail.com>
4
5This program is free software; you can redistribute it and/or modify
6it under the terms of the GNU General Public License version 2 as
7published by the Free Software Foundation.
8
9This program is distributed in the hope that it will be useful,
10but WITHOUT ANY WARRANTY; without even the implied warranty of
11MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12GNU General Public License for more details.
13
14You should have received a copy of the GNU General Public License
15along with this program; if not, write to the Free Software
16Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17"""
18
19import sys, os
20from optparse import OptionParser, make_option
21
22from stgit.commands.common import *
23from stgit.utils import *
5e888f30 24from stgit.out import *
fcee87cf
CM
25from stgit import stack, git
26from stgit.config import config
27
28
29help = 'generate a new commit for the current patch'
026c0689 30usage = """%prog [options] [<files...>]
26aab5b0
CM
31
32Include the latest tree changes in the current patch. This command
33generates a new GIT commit object with the patch details, the previous
34one no longer being visible. The patch attributes like author,
35committer and description can be changed with the command line
36options. The '--force' option is useful when a commit object was
37created with a different tool but the changes need to be included in
38the current patch."""
fcee87cf
CM
39
40options = [make_option('-f', '--force',
41 help = 'force the refresh even if HEAD and '\
42 'top differ',
43 action = 'store_true'),
44 make_option('-e', '--edit',
45 help = 'invoke an editor for the patch '\
46 'description',
47 action = 'store_true'),
6ad48e48
PBG
48 make_option('-s', '--showpatch',
49 help = 'show the patch content in the editor buffer',
50 action = 'store_true'),
6ee70d6b
CM
51 make_option('--update',
52 help = 'only update the current patch files',
53 action = 'store_true'),
f80bef49
CM
54 make_option('--undo',
55 help = 'revert the commit generated by the last refresh',
56 action = 'store_true'),
fcee87cf
CM
57 make_option('-m', '--message',
58 help = 'use MESSAGE as the patch ' \
59 'description'),
eff17c6b
CM
60 make_option('-a', '--annotate', metavar = 'NOTE',
61 help = 'annotate the patch log entry'),
62 make_option('--author', metavar = '"NAME <EMAIL>"',
19cd0a8f 63 help = 'use "NAME <EMAIL>" as the author details'),
fcee87cf
CM
64 make_option('--authname',
65 help = 'use AUTHNAME as the author name'),
66 make_option('--authemail',
67 help = 'use AUTHEMAIL as the author e-mail'),
68 make_option('--authdate',
69 help = 'use AUTHDATE as the author date'),
70 make_option('--commname',
71 help = 'use COMMNAME as the committer name'),
72 make_option('--commemail',
73 help = 'use COMMEMAIL as the committer ' \
c40c3500 74 'e-mail'),
42fc7623
YD
75 make_option('-p', '--patch',
76 help = 'refresh (applied) PATCH instead of the top one'),
c40c3500
CM
77 make_option('--sign',
78 help = 'add Signed-off-by line',
79 action = 'store_true'),
80 make_option('--ack',
81 help = 'add Acked-by line',
82 action = 'store_true')]
fcee87cf
CM
83
84
85def func(parser, options, args):
c73e63b7 86 autoresolved = config.get('stgit.autoresolved')
fcee87cf
CM
87
88 if autoresolved != 'yes':
89 check_conflicts()
90
42fc7623 91 if options.patch:
6ee70d6b 92 if args or options.update:
42fc7623
YD
93 raise CmdException, \
94 'Only full refresh is available with the --patch option'
95 patch = options.patch
96 if not crt_series.patch_applied(patch):
97 raise CmdException, 'Patches "%s" not applied' % patch
98 else:
99 patch = crt_series.get_current()
100 if not patch:
101 raise CmdException, 'No patches applied'
fcee87cf
CM
102
103 if not options.force:
104 check_head_top_equal()
105
f80bef49 106 if options.undo:
27ac2b7e 107 out.start('Undoing the refresh of "%s"' % patch)
f80bef49 108 crt_series.undo_refresh()
27ac2b7e 109 out.done()
f80bef49
CM
110 return
111
19cd0a8f
CM
112 if options.author:
113 options.authname, options.authemail = name_email(options.author)
114
c40c3500
CM
115 if options.sign:
116 sign_str = 'Signed-off-by'
bc7ba6e9
YD
117 if options.ack:
118 raise CmdException, '--ack and --sign were both specified'
c40c3500
CM
119 elif options.ack:
120 sign_str = 'Acked-by'
121 else:
122 sign_str = None
123
14c88aa0 124 files = [path for (stat,path) in git.tree_status(verbose = True)]
6ee70d6b
CM
125 if args:
126 files = [f for f in files if f in args]
127
128 if files or not crt_series.head_top_equal() \
fcee87cf
CM
129 or options.edit or options.message \
130 or options.authname or options.authemail or options.authdate \
c40c3500 131 or options.commname or options.commemail \
ea7634bb 132 or options.sign or options.ack:
42fc7623
YD
133
134 if options.patch:
135 applied = crt_series.get_applied()
136 between = applied[:applied.index(patch):-1]
137 pop_patches(between, keep = True)
6ee70d6b
CM
138 elif options.update:
139 rev1 = git_id('//bottom')
140 rev2 = git_id('//top')
141 patch_files = git.barefiles(rev1, rev2).split('\n')
142 files = [f for f in files if f in patch_files]
143 if not files:
144 out.info('No modified files for updating patch "%s"' % patch)
145 return
42fc7623 146
27ac2b7e 147 out.start('Refreshing patch "%s"' % patch)
fcee87cf
CM
148
149 if autoresolved == 'yes':
150 resolved_all()
6ee70d6b 151 crt_series.refresh_patch(files = files,
026c0689 152 message = options.message,
fcee87cf 153 edit = options.edit,
6ad48e48 154 show_patch = options.showpatch,
fcee87cf
CM
155 author_name = options.authname,
156 author_email = options.authemail,
157 author_date = options.authdate,
158 committer_name = options.commname,
f80bef49 159 committer_email = options.commemail,
eff17c6b
CM
160 backup = True, sign_str = sign_str,
161 notes = options.annotate)
fcee87cf 162
dc4e5946 163 if crt_series.empty_patch(patch):
27ac2b7e 164 out.done('empty patch')
dc4e5946 165 else:
27ac2b7e 166 out.done()
7c53fcf5 167
42fc7623
YD
168 if options.patch:
169 between.reverse()
170 push_patches(between)
ea7634bb
CM
171 elif options.annotate:
172 # only annotate the top log entry as there is no need to
173 # refresh the patch and generate a full commit
174 crt_series.log_patch(crt_series.get_patch(patch), None,
175 notes = options.annotate)
fcee87cf 176 else:
27ac2b7e 177 out.info('Patch "%s" is already up to date' % patch)