##// END OF EJS Templates
added menu for changeset raw diff and download diff...
marcink -
r468:9dd372c7 default
parent child Browse files
Show More
@@ -1,136 +1,138 b''
1 #!/usr/bin/env python
1 #!/usr/bin/env python
2 # encoding: utf-8
2 # encoding: utf-8
3 # changeset controller for pylons
3 # changeset controller for pylons
4 # Copyright (C) 2009-2010 Marcin Kuzminski <marcin@python-works.com>
4 # Copyright (C) 2009-2010 Marcin Kuzminski <marcin@python-works.com>
5 # This program is free software; you can redistribute it and/or
5 # This program is free software; you can redistribute it and/or
6 # modify it under the terms of the GNU General Public License
6 # modify it under the terms of the GNU General Public License
7 # as published by the Free Software Foundation; version 2
7 # as published by the Free Software Foundation; version 2
8 # of the License or (at your opinion) any later version of the license.
8 # of the License or (at your opinion) any later version of the license.
9 #
9 #
10 # This program is distributed in the hope that it will be useful,
10 # This program is distributed in the hope that it will be useful,
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # GNU General Public License for more details.
13 # GNU General Public License for more details.
14 #
14 #
15 # You should have received a copy of the GNU General Public License
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
17 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
18 # MA 02110-1301, USA.
18 # MA 02110-1301, USA.
19 """
19 """
20 Created on April 25, 2010
20 Created on April 25, 2010
21 changeset controller for pylons
21 changeset controller for pylons
22 @author: marcink
22 @author: marcink
23 """
23 """
24 from pylons import tmpl_context as c, url, request, response
24 from pylons import tmpl_context as c, url, request, response
25 from pylons.controllers.util import redirect
25 from pylons.controllers.util import redirect
26 from pylons_app.lib.auth import LoginRequired, HasRepoPermissionAnyDecorator
26 from pylons_app.lib.auth import LoginRequired, HasRepoPermissionAnyDecorator
27 from pylons_app.lib.base import BaseController, render
27 from pylons_app.lib.base import BaseController, render
28 from pylons_app.model.hg_model import HgModel
28 from pylons_app.model.hg_model import HgModel
29 from vcs.exceptions import RepositoryError
29 from vcs.exceptions import RepositoryError
30 from vcs.nodes import FileNode
30 from vcs.nodes import FileNode
31 from vcs.utils import diffs as differ
31 from vcs.utils import diffs as differ
32 import logging
32 import logging
33 import traceback
33 import traceback
34
34
35 log = logging.getLogger(__name__)
35 log = logging.getLogger(__name__)
36
36
37 class ChangesetController(BaseController):
37 class ChangesetController(BaseController):
38
38
39 @LoginRequired()
39 @LoginRequired()
40 @HasRepoPermissionAnyDecorator('repository.read', 'repository.write',
40 @HasRepoPermissionAnyDecorator('repository.read', 'repository.write',
41 'repository.admin')
41 'repository.admin')
42 def __before__(self):
42 def __before__(self):
43 super(ChangesetController, self).__before__()
43 super(ChangesetController, self).__before__()
44
44
45 def index(self, revision):
45 def index(self, revision):
46 hg_model = HgModel()
46 hg_model = HgModel()
47 try:
47 try:
48 c.changeset = hg_model.get_repo(c.repo_name).get_changeset(revision)
48 c.changeset = hg_model.get_repo(c.repo_name).get_changeset(revision)
49 except RepositoryError:
49 except RepositoryError:
50 log.error(traceback.format_exc())
50 log.error(traceback.format_exc())
51 return redirect(url('hg_home'))
51 return redirect(url('hg_home'))
52 else:
52 else:
53 try:
53 try:
54 c.changeset_old = c.changeset.parents[0]
54 c.changeset_old = c.changeset.parents[0]
55 except IndexError:
55 except IndexError:
56 c.changeset_old = None
56 c.changeset_old = None
57 c.changes = []
57 c.changes = []
58
58
59 for node in c.changeset.added:
59 for node in c.changeset.added:
60 filenode_old = FileNode(node.path, '')
60 filenode_old = FileNode(node.path, '')
61 if filenode_old.is_binary or node.is_binary:
61 if filenode_old.is_binary or node.is_binary:
62 diff = 'binary file'
62 diff = 'binary file'
63 else:
63 else:
64 f_udiff = differ.get_udiff(filenode_old, node)
64 f_udiff = differ.get_udiff(filenode_old, node)
65 diff = differ.DiffProcessor(f_udiff).as_html()
65 diff = differ.DiffProcessor(f_udiff).as_html()
66
66
67 cs1 = None
67 cs1 = None
68 cs2 = node.last_changeset.raw_id
68 cs2 = node.last_changeset.raw_id
69 c.changes.append(('added', node, diff, cs1, cs2))
69 c.changes.append(('added', node, diff, cs1, cs2))
70
70
71 for node in c.changeset.changed:
71 for node in c.changeset.changed:
72 filenode_old = c.changeset_old.get_node(node.path)
72 filenode_old = c.changeset_old.get_node(node.path)
73 if filenode_old.is_binary or node.is_binary:
73 if filenode_old.is_binary or node.is_binary:
74 diff = 'binary file'
74 diff = 'binary file'
75 else:
75 else:
76 f_udiff = differ.get_udiff(filenode_old, node)
76 f_udiff = differ.get_udiff(filenode_old, node)
77 diff = differ.DiffProcessor(f_udiff).as_html()
77 diff = differ.DiffProcessor(f_udiff).as_html()
78
78
79 cs1 = filenode_old.last_changeset.raw_id
79 cs1 = filenode_old.last_changeset.raw_id
80 cs2 = node.last_changeset.raw_id
80 cs2 = node.last_changeset.raw_id
81 c.changes.append(('changed', node, diff, cs1, cs2))
81 c.changes.append(('changed', node, diff, cs1, cs2))
82
82
83 for node in c.changeset.removed:
83 for node in c.changeset.removed:
84 c.changes.append(('removed', node, None, None, None))
84 c.changes.append(('removed', node, None, None, None))
85
85
86 return render('changeset/changeset.html')
86 return render('changeset/changeset.html')
87
87
88 def raw_changeset(self,revision):
88 def raw_changeset(self,revision):
89
89
90 hg_model = HgModel()
90 hg_model = HgModel()
91 method = request.GET.get('diff','show')
91 try:
92 try:
92 c.changeset = hg_model.get_repo(c.repo_name).get_changeset(revision)
93 c.changeset = hg_model.get_repo(c.repo_name).get_changeset(revision)
93 except RepositoryError:
94 except RepositoryError:
94 log.error(traceback.format_exc())
95 log.error(traceback.format_exc())
95 return redirect(url('hg_home'))
96 return redirect(url('hg_home'))
96 else:
97 else:
97 try:
98 try:
98 c.changeset_old = c.changeset.parents[0]
99 c.changeset_old = c.changeset.parents[0]
99 except IndexError:
100 except IndexError:
100 c.changeset_old = None
101 c.changeset_old = None
101 c.changes = []
102 c.changes = []
102
103
103 for node in c.changeset.added:
104 for node in c.changeset.added:
104 filenode_old = FileNode(node.path, '')
105 filenode_old = FileNode(node.path, '')
105 if filenode_old.is_binary or node.is_binary:
106 if filenode_old.is_binary or node.is_binary:
106 diff = 'binary file'
107 diff = 'binary file'
107 else:
108 else:
108 f_udiff = differ.get_udiff(filenode_old, node)
109 f_udiff = differ.get_udiff(filenode_old, node)
109 diff = differ.DiffProcessor(f_udiff).raw_diff()
110 diff = differ.DiffProcessor(f_udiff).raw_diff()
110
111
111 cs1 = None
112 cs1 = None
112 cs2 = node.last_changeset.raw_id
113 cs2 = node.last_changeset.raw_id
113 c.changes.append(('added', node, diff, cs1, cs2))
114 c.changes.append(('added', node, diff, cs1, cs2))
114
115
115 for node in c.changeset.changed:
116 for node in c.changeset.changed:
116 filenode_old = c.changeset_old.get_node(node.path)
117 filenode_old = c.changeset_old.get_node(node.path)
117 if filenode_old.is_binary or node.is_binary:
118 if filenode_old.is_binary or node.is_binary:
118 diff = 'binary file'
119 diff = 'binary file'
119 else:
120 else:
120 f_udiff = differ.get_udiff(filenode_old, node)
121 f_udiff = differ.get_udiff(filenode_old, node)
121 diff = differ.DiffProcessor(f_udiff).raw_diff()
122 diff = differ.DiffProcessor(f_udiff).raw_diff()
122
123
123 cs1 = filenode_old.last_changeset.raw_id
124 cs1 = filenode_old.last_changeset.raw_id
124 cs2 = node.last_changeset.raw_id
125 cs2 = node.last_changeset.raw_id
125 c.changes.append(('changed', node, diff, cs1, cs2))
126 c.changes.append(('changed', node, diff, cs1, cs2))
126
127
127 response.content_type = 'text/plain'
128 response.content_type = 'text/plain'
128
129 if method == 'download':
130 response.content_disposition = 'attachment; filename=%s.patch' % revision
129 parent = True if len(c.changeset.parents) > 0 else False
131 parent = True if len(c.changeset.parents) > 0 else False
130 c.parent_tmpl = 'Parent %s' % c.changeset.parents[0]._hex if parent else ''
132 c.parent_tmpl = 'Parent %s' % c.changeset.parents[0]._hex if parent else ''
131
133
132 c.diffs = ''
134 c.diffs = ''
133 for x in c.changes:
135 for x in c.changes:
134 c.diffs += x[2]
136 c.diffs += x[2]
135
137
136 return render('changeset/raw_changeset.html')
138 return render('changeset/raw_changeset.html')
@@ -1,94 +1,106 b''
1 <%inherit file="/base/base.html"/>
1 <%inherit file="/base/base.html"/>
2
2
3 <%def name="title()">
3 <%def name="title()">
4 ${_('Changeset')}
4 ${_('Changeset')}
5 </%def>
5 </%def>
6
6
7 <%def name="breadcrumbs_links()">
7 <%def name="breadcrumbs_links()">
8 ${h.link_to(u'Home',h.url('/'))}
8 ${h.link_to(u'Home',h.url('/'))}
9 &raquo;
9 &raquo;
10 ${h.link_to(c.repo_name,h.url('summary_home',repo_name=c.repo_name))}
10 ${h.link_to(c.repo_name,h.url('summary_home',repo_name=c.repo_name))}
11 &raquo;
11 &raquo;
12 ${_('Changeset')} - r${c.changeset.revision}:${c.changeset.raw_id}
12 ${_('Changeset')} - r${c.changeset.revision}:${c.changeset.raw_id}
13 </%def>
13 </%def>
14
14
15 <%def name="page_nav()">
15 <%def name="page_nav()">
16 ${self.menu('changelog')}
16 ${self.menu('changelog')}
17 </%def>
17 </%def>
18
18
19 <%def name="main()">
19 <%def name="main()">
20 <div class="box">
20 <div class="box">
21 <!-- box / title -->
21 <!-- box / title -->
22 <div class="title">
22 <div class="title">
23 ${self.breadcrumbs()}
23 ${self.breadcrumbs()}
24 </div>
24 </div>
25 <div class="table">
25 <div class="table">
26 <div id="body" class="diffblock">
27 <div class="code-header">
28 <div>
29 ${_('Changeset')} - r${c.changeset.revision}:${c.changeset.raw_id}
30 &raquo; <span>${h.link_to(_('raw diff'),
31 h.url('raw_changeset_home',repo_name=c.repo_name,revision=c.changeset.raw_id,diff='show'))}</span>
32 &raquo; <span>${h.link_to(_('download diff'),
33 h.url('raw_changeset_home',repo_name=c.repo_name,revision=c.changeset.raw_id,diff='download'))}</span>
34 </div>
35 </div>
36 </div>
37
26 <div id="changeset_content">
38 <div id="changeset_content">
27 <div class="container">
39 <div class="container">
28 <div class="left">
40 <div class="left">
29 <div class="date">${_('Date')}: ${c.changeset.date}</div>
41 <div class="date">${_('Date')}: ${c.changeset.date}</div>
30 <div class="author">${_('Author')}: ${c.changeset.author}</div>
42 <div class="author">${_('Author')}: ${c.changeset.author}</div>
31 <div class="message">${h.wrap_paragraphs(c.changeset.message)}</div>
43 <div class="message">${h.wrap_paragraphs(c.changeset.message)}</div>
32 </div>
44 </div>
33 <div class="right">
45 <div class="right">
34 <span class="logtags">
46 <span class="logtags">
35 <span class="branchtag">${c.changeset.branch}</span>
47 <span class="branchtag">${c.changeset.branch}</span>
36 %for tag in c.changeset.tags:
48 %for tag in c.changeset.tags:
37 <span class="tagtag">${tag}</span>
49 <span class="tagtag">${tag}</span>
38 %endfor
50 %endfor
39 </span>
51 </span>
40 %if len(c.changeset.parents)>1:
52 %if len(c.changeset.parents)>1:
41 <div class="merge">
53 <div class="merge">
42 ${_('merge')}
54 ${_('merge')}
43 <img alt="merge" src="/images/icons/arrow_join.png">
55 <img alt="merge" src="/images/icons/arrow_join.png">
44 </div>
56 </div>
45 %endif
57 %endif
46 %for p_cs in reversed(c.changeset.parents):
58 %for p_cs in reversed(c.changeset.parents):
47 <div class="parent">${_('Parent')} ${p_cs.revision}: ${h.link_to(p_cs.raw_id,
59 <div class="parent">${_('Parent')} ${p_cs.revision}: ${h.link_to(p_cs.raw_id,
48 h.url('changeset_home',repo_name=c.repo_name,revision=p_cs.raw_id),title=p_cs.message)}
60 h.url('changeset_home',repo_name=c.repo_name,revision=p_cs.raw_id),title=p_cs.message)}
49 </div>
61 </div>
50 %endfor
62 %endfor
51 </div>
63 </div>
52 </div>
64 </div>
53 <span style="font-size:1.1em;font-weight: bold">${_('Files affected')}</span>
65 <span style="font-size:1.1em;font-weight: bold">${_('Files affected')}</span>
54 <div class="cs_files">
66 <div class="cs_files">
55 %for change,filenode,diff,cs1,cs2 in c.changes:
67 %for change,filenode,diff,cs1,cs2 in c.changes:
56 <div class="cs_${change}">${h.link_to(filenode.path,h.url.current(anchor='CHANGE-%s'%filenode.path))}</div>
68 <div class="cs_${change}">${h.link_to(filenode.path,h.url.current(anchor='CHANGE-%s'%filenode.path))}</div>
57 %endfor
69 %endfor
58 </div>
70 </div>
59 </div>
71 </div>
60
72
61 %for change,filenode,diff,cs1,cs2 in c.changes:
73 %for change,filenode,diff,cs1,cs2 in c.changes:
62 %if change !='removed':
74 %if change !='removed':
63 <div style="clear:both;height:10px"></div>
75 <div style="clear:both;height:10px"></div>
64 <div id="body" class="diffblock">
76 <div id="body" class="diffblock">
65 <div id="${'CHANGE-%s'%filenode.path}" class="code-header">
77 <div id="${'CHANGE-%s'%filenode.path}" class="code-header">
66 <div>
78 <div>
67 <span>
79 <span>
68 ${h.link_to_if(change!='removed',filenode.path,h.url('files_home',repo_name=c.repo_name,
80 ${h.link_to_if(change!='removed',filenode.path,h.url('files_home',repo_name=c.repo_name,
69 revision=filenode.changeset.raw_id,f_path=filenode.path))}
81 revision=filenode.changeset.raw_id,f_path=filenode.path))}
70 </span>
82 </span>
71 %if 1:
83 %if 1:
72 &raquo; <span>${h.link_to(_('diff'),
84 &raquo; <span>${h.link_to(_('diff'),
73 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='diff'))}</span>
85 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='diff'))}</span>
74 &raquo; <span>${h.link_to(_('raw diff'),
86 &raquo; <span>${h.link_to(_('raw diff'),
75 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='raw'))}</span>
87 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='raw'))}</span>
76 &raquo; <span>${h.link_to(_('download diff'),
88 &raquo; <span>${h.link_to(_('download diff'),
77 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='download'))}</span>
89 h.url('files_diff_home',repo_name=c.repo_name,f_path=filenode.path,diff2=cs2,diff1=cs1,diff='download'))}</span>
78 %endif
90 %endif
79 </div>
91 </div>
80 </div>
92 </div>
81 <div class="code-body">
93 <div class="code-body">
82 %if diff:
94 %if diff:
83 ${diff|n}
95 ${diff|n}
84 %else:
96 %else:
85 ${_('No changes in this file')}
97 ${_('No changes in this file')}
86 %endif
98 %endif
87 </div>
99 </div>
88 </div>
100 </div>
89 %endif
101 %endif
90 %endfor
102 %endfor
91 </div>
103 </div>
92 </div>
104 </div>
93
105
94 </%def> No newline at end of file
106 </%def>
@@ -1,8 +1,8 b''
1 # HG changeset patch
1 # HG changeset patch
2 # User ${c.changeset.author}
2 # User ${c.changeset.author|n}
3 # Date ${"%d %d" % c.changeset._ctx.date()}
3 # Date ${"%d %d" % c.changeset._ctx.date()}
4 # Node ID ${c.changeset._hex}
4 # Node ID ${c.changeset._hex}
5 # ${c.parent_tmpl}
5 # ${c.parent_tmpl}
6 ${c.changeset.message}
6 ${c.changeset.message}
7
7
8 ${c.diffs|n} No newline at end of file
8 ${c.diffs|n}
General Comments 0
You need to be logged in to leave comments. Login now