# Copyright (c) 2014 Dark Secret Software Inc. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or # implied. # See the License for the specific language governing permissions and # limitations under the License. import os import os.path import shutil import pyrax import simport class MissingArgument(Exception): pass class ArchiveCallback(object): def __init__(self, **kwargs): pass def on_open(self, filename): """Called when an Archive is opened.""" pass def on_close(self, filename): """Called when an Archive is closed. If you move/change the file/name return the new location so subsequent callbacks will have the right location. """ return filename class CallbackList(ArchiveCallback): def __init__(self, **kwargs): super(CallbackList, self).__init__(**kwargs) self.callbacks = [] self.config = kwargs callback_str = self.config.get('callback_list', "") callback_str_list = [x.strip() for x in callback_str.split(",")] self.callbacks = [simport.load(c)(**self.config) for c in callback_str_list] # TODO(Sandy): Need some exception handling around these. # The failure of one shouldn't stop processing. def on_open(self, filename): for c in self.callbacks: c.on_open(filename) def on_close(self, filename): for c in self.callbacks: filename = c.on_close(filename) class ChangeExtensionCallback(ArchiveCallback): """filename.dat becomes filename.dat.done""" def __init__(self, **kwargs): super(ChangeExtensionCallback, self).__init__(**kwargs) self.new_extension = kwargs.get('new_extension', '.done') def on_close(self, filename): new = "%s.%s" % (filename, self.new_extension) os.rename(filename, new) return new class MoveFileCallback(ArchiveCallback): def __init__(self, **kwargs): super(MoveFileCallback, self).__init__(**kwargs) self.destination_folder = kwargs.get('destination_folder', '.') def on_close(self, filename): """Move this file to destination folder.""" shutil.move(filename, self.destination_folder) path, fn = os.path.split(filename) return os.path.join(self.destination_folder, fn) class DeleteFileCallback(ArchiveCallback): def on_close(self, filename): """Delete this file.""" os.remove(filename) return None class SwiftUploadCallback(ArchiveCallback): def __init__(self, **kwargs): super(SwiftUploadCallback, self).__init__(**kwargs) self.credentials_file = kwargs.get('credentials_file') if not self.credentials_file: raise MissingArgument("No credentials_file defined.") self.container = kwargs.get('container', 'shoebox') self.auth_method = kwargs.get('auth_method', 'rackspace') self.region = kwargs.get('region', 'DFW') pyrax.set_setting('identity_type', self.auth_method) pyrax.set_setting("region", self.region) pyrax.set_credential_file(self.credentials_file) self.cloud_files = pyrax.cloudfiles self.cloud_files.create_container(self.container) def on_close(self, filename): checksum = pyrax.utils.get_checksum(filename) # Blocking call ... obj = self.cloud_files.upload_file(self.container, filename, etag=checksum) return filename