/b-gtk/fix-viz

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/b-gtk/fix-viz
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
1
# Copyright (C) 2006 by Szilveszter Farkas (Phanatic) <szilveszter.farkas@gmail.com>
0.8.46 by Szilveszter Farkas (Phanatic)
Modified OliveDialog class interface; huge cleanups.
2
#
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
3
# This program is free software; you can redistribute it and/or modify
4
# it under the terms of the GNU General Public License as published by
5
# the Free Software Foundation; either version 2 of the License, or
6
# (at your option) any later version.
0.8.46 by Szilveszter Farkas (Phanatic)
Modified OliveDialog class interface; huge cleanups.
7
#
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
8
# This program is distributed in the hope that it will be useful,
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
# GNU General Public License for more details.
0.8.46 by Szilveszter Farkas (Phanatic)
Modified OliveDialog class interface; huge cleanups.
12
#
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
13
# You should have received a copy of the GNU General Public License
14
# along with this program; if not, write to the Free Software
15
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
16
17
try:
18
    import pygtk
19
    pygtk.require("2.0")
20
except:
21
    pass
0.13.13 by Jelmer Vernooij
Update TODO
22
    
0.13.10 by Jelmer Vernooij
Don't pass around gladefile all the time.
23
import gtk
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
24
25
from errors import show_bzr_error
26
27
from bzrlib.config import LocationConfig
0.11.1 by Jelmer Vernooij
Eliminate olive.backend.errors.
28
import bzrlib.errors as errors
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
29
153 by Jelmer Vernooij
Fix references to dialog.
30
from dialog import error_dialog, info_dialog, question_dialog
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
31
154 by Jelmer Vernooij
Add trivial generic class for storing URL history.
32
from history import UrlHistory
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
33
34
class PushDialog(gtk.Dialog):
35
    """ New implementation of the Push dialog. """
36
    def __init__(self, branch, parent=None):
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
37
        """ Initialize the Push dialog. """
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
38
        gtk.Dialog.__init__(self, title="Push - Olive",
39
                                  parent=parent,
40
                                  flags=0,
41
                                  buttons=(gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL))
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
42
        
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
43
        # Get arguments
0.13.13 by Jelmer Vernooij
Update TODO
44
        self.branch = branch
0.8.19 by Szilveszter Farkas (Phanatic)
2006-07-21 Szilveszter Farkas <Szilveszter.Farkas@gmail.com>
45
        
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
46
        # Create the widgets
47
        self._label_location = gtk.Label(_("Location:"))
48
        self._label_test = gtk.Label(_("(click the Test button to check write access)"))
49
        self._check_remember = gtk.CheckButton(_("_Remember as default location"),
50
                                               use_underline=True)
51
        self._check_prefix = gtk.CheckButton(_("Create the path _leading up to the location"),
52
                                             use_underline=True)
53
        self._check_overwrite = gtk.CheckButton(_("_Overwrite target if diverged"),
54
                                                use_underline=True)
55
        self._combo = gtk.ComboBoxEntry()
56
        self._button_test = gtk.Button(_("_Test"), use_underline=True)
57
        self._button_push = gtk.Button(_("_Push"), use_underline=True)
58
        self._hbox_location = gtk.HBox()
59
        self._hbox_test = gtk.HBox()
60
        self._image_test = gtk.Image()
61
        
62
        # Set callbacks
63
        self._button_test.connect('clicked', self._on_test_clicked)
64
        self._button_push.connect('clicked', self._on_push_clicked)
65
        
66
        # Set properties
67
        self._image_test.set_from_stock(gtk.STOCK_DIALOG_INFO, gtk.ICON_SIZE_BUTTON)
68
        self._label_location.set_alignment(0, 0.5)
69
        self._label_test.set_alignment(0, 0.5)
70
        self._hbox_location.set_spacing(3)
71
        self._hbox_test.set_spacing(3)
72
        self.vbox.set_spacing(3)
73
        
74
        # Pack widgets
75
        self._hbox_location.pack_start(self._label_location, False, False)
76
        self._hbox_location.pack_start(self._combo, True, True)
77
        self._hbox_test.pack_start(self._image_test, False, False)
78
        self._hbox_test.pack_start(self._label_test, True, True)
79
        self.vbox.pack_start(self._hbox_location)
80
        self.vbox.pack_start(self._check_remember)
81
        self.vbox.pack_start(self._check_prefix)
82
        self.vbox.pack_start(self._check_overwrite)
83
        self.vbox.pack_start(self._hbox_test)
84
        self.action_area.pack_start(self._button_test)
85
        self.action_area.pack_end(self._button_push)
86
        
87
        # Show the dialog
88
        self.vbox.show_all()
89
        
90
        # Build location history
154 by Jelmer Vernooij
Add trivial generic class for storing URL history.
91
        self._history = UrlHistory(self.branch.get_config(), 'push_history')
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
92
        self._build_history()
93
        
94
    def _build_history(self):
95
        """ Build up the location history. """
154 by Jelmer Vernooij
Add trivial generic class for storing URL history.
96
        self._combo_model = gtk.ListStore(str)
97
        for item in self._history.get_entries():
98
            self._combo_model.append([ item ])
99
        self._combo.set_model(self._combo_model)
100
        self._combo.set_text_column(0)
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
101
        
102
        location = self.branch.get_push_location()
103
        if location:
104
            self._combo.get_child().set_text(location)
105
    
106
    def _on_test_clicked(self, widget):
107
        """ Test button clicked handler. """
0.8.58 by Szilveszter Farkas (Phanatic)
Added Test write access functionality to the Push dialog.
108
        import re
109
        _urlRE = re.compile(r'^(?P<proto>[^:/\\]+)://(?P<path>.*)$')
110
        
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
111
        url = self._combo.get_child().get_text()
0.8.58 by Szilveszter Farkas (Phanatic)
Added Test write access functionality to the Push dialog.
112
        
113
        m = _urlRE.match(url)
114
        if m:
115
            proto = m.groupdict()['proto']
222 by Jelmer Vernooij
Fix whitespace, add comment.
116
            # FIXME: This should ask the transport or branch rather than 
117
            # guessing using regular expressions. JRV 20070714
118
            if proto in ('sftp', 'file', 'ftp'):
119
                # have write access (most probably)
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
120
                self._image_test.set_from_stock(gtk.STOCK_YES, 4)
121
                self._label_test.set_markup(_('<b>Write access is probably available</b>'))
0.8.58 by Szilveszter Farkas (Phanatic)
Added Test write access functionality to the Push dialog.
122
            else:
123
                # no write access
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
124
                self._image_test.set_from_stock(gtk.STOCK_NO, 4)
125
                self._label_test.set_markup(_('<b>No write access</b>'))
0.8.58 by Szilveszter Farkas (Phanatic)
Added Test write access functionality to the Push dialog.
126
        else:
127
            # couldn't determine
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
128
            self._image_test.set_from_stock(gtk.STOCK_DIALOG_QUESTION, 4)
129
            self._label_test.set_markup(_('<b>Could not determine</b>'))
0.8.58 by Szilveszter Farkas (Phanatic)
Added Test write access functionality to the Push dialog.
130
    
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
131
    @show_bzr_error
132
    def _on_push_clicked(self, widget):
133
        """ Push button clicked handler. """
134
        location = self._combo.get_child().get_text()
135
        revs = 0
136
        try:
137
            revs = do_push(self.branch,
138
                           location=location,
139
                           overwrite=self._check_overwrite.get_active(),
140
                           remember=self._check_remember.get_active(),
141
                           create_prefix=self._check_prefix.get_active())
142
        except errors.DivergedBranches:
143
            response = question_dialog(_('Branches have been diverged'),
144
                                       _('You cannot push if branches have diverged.\nOverwrite?'))
145
            if response == gtk.RESPONSE_OK:
146
                revs = do_push(self.branch, overwrite=True)
147
            return
148
        
154 by Jelmer Vernooij
Add trivial generic class for storing URL history.
149
        self._history.add_entry(location)
126.1.19 by Szilveszter Farkas (Phanatic)
Refactored the Push dialog. Add 'gpush' command.
150
        info_dialog(_('Push successful'),
151
                    _("%d revision(s) pushed.") % revs)
152
        
153
        self.response(gtk.RESPONSE_OK)
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
154
155
def do_push(branch, location=None, remember=False, overwrite=False,
156
         create_prefix=False):
157
    """ Update a mirror of a branch.
158
    
159
    :param branch: the source branch
160
    
161
    :param location: the location of the branch that you'd like to update
162
    
163
    :param remember: if set, the location will be stored
164
    
165
    :param overwrite: overwrite target location if it diverged
166
    
167
    :param create_prefix: create the path leading up to the branch if it doesn't exist
168
    
169
    :return: number of revisions pushed
170
    """
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
171
    from bzrlib.bzrdir import BzrDir
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
172
    from bzrlib.transport import get_transport
173
        
99 by Szilveszter Farkas (Phanatic)
Fixed bug: #66656 (Push doesn't work).
174
    br_from = branch
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
175
    
176
    stored_loc = br_from.get_push_location()
177
    if location is None:
178
        if stored_loc is None:
0.13.6 by Jelmer Vernooij
Don't pass along dialog context everywhere.
179
            error_dialog(_('Push location is unknown'),
99 by Szilveszter Farkas (Phanatic)
Fixed bug: #66656 (Push doesn't work).
180
                         _('Please specify a location manually.'))
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
181
            return
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
182
        else:
183
            location = stored_loc
184
185
    transport = get_transport(location)
186
    location_url = transport.base
187
188
    if br_from.get_push_location() is None or remember:
189
        br_from.set_push_location(location_url)
190
191
    old_rh = []
192
193
    try:
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
194
        dir_to = BzrDir.open(location_url)
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
195
        br_to = dir_to.open_branch()
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
196
    except errors.NotBranchError:
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
197
        # create a branch.
198
        transport = transport.clone('..')
199
        if not create_prefix:
200
            try:
201
                relurl = transport.relpath(location_url)
202
                transport.mkdir(relurl)
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
203
            except errors.NoSuchFile:
0.13.6 by Jelmer Vernooij
Don't pass along dialog context everywhere.
204
                error_dialog(_('Non existing parent directory'),
0.8.98 by Szilveszter Farkas (Phanatic)
Loads of fixes. Pyflakes cleanup.
205
                             _("The parent directory (%s)\ndoesn't exist.") % location)
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
206
                return
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
207
        else:
208
            current = transport.base
209
            needed = [(transport, transport.relpath(location_url))]
210
            while needed:
211
                try:
212
                    transport, relpath = needed[-1]
213
                    transport.mkdir(relpath)
214
                    needed.pop()
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
215
                except errors.NoSuchFile:
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
216
                    new_transport = transport.clone('..')
217
                    needed.append((new_transport,
218
                                   new_transport.relpath(transport.base)))
219
                    if new_transport.base == transport.base:
0.13.6 by Jelmer Vernooij
Don't pass along dialog context everywhere.
220
                        error_dialog(_('Path prefix not created'),
0.8.98 by Szilveszter Farkas (Phanatic)
Loads of fixes. Pyflakes cleanup.
221
                                     _("The path leading up to the specified location couldn't\nbe created."))
0.8.85 by Szilveszter Farkas (Phanatic)
Fix Push functionality.
222
                        return
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
223
        dir_to = br_from.bzrdir.clone(location_url,
224
            revision_id=br_from.last_revision())
225
        br_to = dir_to.open_branch()
226
        count = len(br_to.revision_history())
227
    else:
228
        old_rh = br_to.revision_history()
229
        try:
0.13.13 by Jelmer Vernooij
Update TODO
230
            tree_to = dir_to.open_workingtree()
231
        except errors.NotLocalUrl:
232
            # FIXME - what to do here? how should we warn the user?
233
            #warning('This transport does not update the working '
234
            #        'tree of: %s' % (br_to.base,))
235
            count = br_to.pull(br_from, overwrite)
236
        except errors.NoWorkingTree:
237
            count = br_to.pull(br_from, overwrite)
238
        else:
239
            count = tree_to.pull(br_from, overwrite)
240
0.11.9 by Jelmer Vernooij
Remove last few bits from backend and integrate them where necessary.
241
    return count