comparison hgext3rd/fastimport/vendor/python_fastimport/processor.py @ 86:28704a2a7461 vendor/python-fastimport

Import python-fastimport-0.9.8
author Roy Marples <roy@marples.name>
date Tue, 19 Jan 2021 22:56:34 +0000
parents
children 2fc99e3479d9
comparison
equal deleted inserted replaced
85:1f5544a8870b 86:28704a2a7461
1 # Copyright (C) 2008 Canonical Ltd
2 #
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.
7 #
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.
12 #
13 # You should have received a copy of the GNU General Public License
14 # along with this program. If not, see <http://www.gnu.org/licenses/>.
15
16 """Processor for fast-import commands.
17
18 This module provides the skeleton of a fast-import backend.
19 To import from a fast-import stream to your version-control system:
20
21 - derive a class from the abstract ImportProcessor class and
22 implement the *_helper methods.
23
24 - parse a fast-import stream into a sequence of commands, for example
25 using the helpers from the parser module.
26
27 - pass that command sequence to the process method of your processor.
28
29 See git-fast-import.1 for the meaning of each command and the
30 processors package for examples.
31 """
32 import sys
33 import time
34
35 from fastimport import errors
36 from fastimport.helpers import newobject as object
37
38
39 class ImportProcessor(object):
40 """Base class for fast-import stream processors.
41
42 Subclasses should override the pre_*, post_* and *_handler
43 methods as appropriate.
44 """
45
46 known_params = []
47
48 def __init__(self, params=None, verbose=False, outf=None):
49 if outf is None:
50 self.outf = sys.stdout
51 else:
52 self.outf = outf
53 self.verbose = verbose
54 if params is None:
55 self.params = {}
56 else:
57 self.params = params
58 self.validate_parameters()
59
60 # Handlers can set this to request exiting cleanly without
61 # iterating through the remaining commands
62 self.finished = False
63
64 def validate_parameters(self):
65 """Validate that the parameters are correctly specified."""
66 for p in self.params:
67 if p not in self.known_params:
68 raise errors.UnknownParameter(p, self.known_params)
69
70 def process(self, command_iter):
71 """Import data into Bazaar by processing a stream of commands.
72
73 :param command_iter: an iterator providing commands
74 """
75 self._process(command_iter)
76
77 def _process(self, command_iter):
78 self.pre_process()
79 for cmd in command_iter():
80 try:
81 name = (cmd.name + b'_handler').decode('utf8')
82 handler = getattr(self.__class__, name)
83 except KeyError:
84 raise errors.MissingHandler(cmd.name)
85 else:
86 self.pre_handler(cmd)
87 handler(self, cmd)
88 self.post_handler(cmd)
89 if self.finished:
90 break
91 self.post_process()
92
93 def warning(self, msg, *args):
94 """Output a warning but timestamp it."""
95 pass
96
97 def debug(self, mgs, *args):
98 """Output a debug message."""
99 pass
100
101 def _time_of_day(self):
102 """Time of day as a string."""
103 # Note: this is a separate method so tests can patch in a fixed value
104 return time.strftime("%H:%M:%S")
105
106 def pre_process(self):
107 """Hook for logic at start of processing."""
108 pass
109
110 def post_process(self):
111 """Hook for logic at end of processing."""
112 pass
113
114 def pre_handler(self, cmd):
115 """Hook for logic before each handler starts."""
116 pass
117
118 def post_handler(self, cmd):
119 """Hook for logic after each handler finishes."""
120 pass
121
122 def progress_handler(self, cmd):
123 """Process a ProgressCommand."""
124 raise NotImplementedError(self.progress_handler)
125
126 def blob_handler(self, cmd):
127 """Process a BlobCommand."""
128 raise NotImplementedError(self.blob_handler)
129
130 def checkpoint_handler(self, cmd):
131 """Process a CheckpointCommand."""
132 raise NotImplementedError(self.checkpoint_handler)
133
134 def commit_handler(self, cmd):
135 """Process a CommitCommand."""
136 raise NotImplementedError(self.commit_handler)
137
138 def reset_handler(self, cmd):
139 """Process a ResetCommand."""
140 raise NotImplementedError(self.reset_handler)
141
142 def tag_handler(self, cmd):
143 """Process a TagCommand."""
144 raise NotImplementedError(self.tag_handler)
145
146 def feature_handler(self, cmd):
147 """Process a FeatureCommand."""
148 raise NotImplementedError(self.feature_handler)
149
150
151 class CommitHandler(object):
152 """Base class for commit handling.
153
154 Subclasses should override the pre_*, post_* and *_handler
155 methods as appropriate.
156 """
157
158 def __init__(self, command):
159 self.command = command
160
161 def process(self):
162 self.pre_process_files()
163 for fc in self.command.iter_files():
164 try:
165 name = (fc.name[4:] + b'_handler').decode('utf8')
166 handler = getattr(self.__class__, name)
167 except KeyError:
168 raise errors.MissingHandler(fc.name)
169 else:
170 handler(self, fc)
171 self.post_process_files()
172
173 def warning(self, msg, *args):
174 """Output a warning but add context."""
175 pass
176
177 def pre_process_files(self):
178 """Prepare for committing."""
179 pass
180
181 def post_process_files(self):
182 """Save the revision."""
183 pass
184
185 def modify_handler(self, filecmd):
186 """Handle a filemodify command."""
187 raise NotImplementedError(self.modify_handler)
188
189 def delete_handler(self, filecmd):
190 """Handle a filedelete command."""
191 raise NotImplementedError(self.delete_handler)
192
193 def copy_handler(self, filecmd):
194 """Handle a filecopy command."""
195 raise NotImplementedError(self.copy_handler)
196
197 def rename_handler(self, filecmd):
198 """Handle a filerename command."""
199 raise NotImplementedError(self.rename_handler)
200
201 def deleteall_handler(self, filecmd):
202 """Handle a filedeleteall command."""
203 raise NotImplementedError(self.deleteall_handler)