Mercurial > hg > hg-fastimport
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) |
