def initialize(): global TheFileSystemManager TheFileSystemManager = FileSystemManager() # Load available backends FileSystemBackendManager.scanFileSystemBackends() # Mount everything according to the configuration file, if any FileSystemBackendManager.mountAll()
def rmdir(self, path, recursive = False, notify = True): """ Removes a directory. vpath is NOT supported. If recursive is set to True, which is DANGEROUS, will remove all existing files and directories before deleting the directory. TODO: define a strategy to follow mount points or not... For now, we do not follow them and only deletes entities in the same backend as the deleted dir. @rtype: bool @returns: True if the directory was removed or was already removed (i.e. deleted). False otherwise. """ (adjusted, backend) = FileSystemBackendManager.getBackend(path) if not backend: raise Exception('No backend available to manipulate %s' % path) if backend.isfile(adjusted): raise Exception("Attempting to delete directory '%s', which is a file" % path) if not backend.isdir(adjusted): return True # already removed if not recursive: ret = backend.rmdir(adjusted) else: getLogger().info("Deleting directory '%s' recursively, adjusted to '%s' for backend '%s'" % (path, adjusted, backend)) ret = self._rmdir(adjusted, backend, notify = True) if ret and notify: self._notifyDirDeleted(path) return ret
def rename(self, source, newName): """ FIXME: support for vpath (to rename a profile) Constraints on name: only [a-zA-Z0-9_.\(\)\[\]#-] @type source: string @param source: docroot-path of the object to rename @type newName: string @param newName: the new (base)name of the object in its current directory. @rtype: bool @returns: True if renamed, False otherwise (typically because the destination already exists) """ (adjusted, backend) = FileSystemBackendManager.getBackend(source) if not backend: raise Exception('No backend available to manipulate %s' % source) destination = '%s/%s' % (os.path.split(source)[0], newName) if self.exists(destination): return False else: if self.isdir(source): ret = backend.renamedir(adjusted, newName) else: ret = backend.rename(adjusted, newName) if ret: self._notifyFileRenamed(source, newName) return ret
def _writeFile(self, filename, content, reason, notify, username): path = os.path.split(filename)[0] res = self.mkdir(path, notify = notify) if not res: raise Exception('Unable to create directory %s to write %s' % (path, filename)) (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) newfile = False if not self.isfile(filename): newfile = True try: backend.write(adjusted, content, baseRevision = None, reason = reason, username = username) except Exception as e: getLogger().error("Unable to write %s: %s" % (filename, str(e))) return False if notify: if newfile: self._notifyFileCreated(filename) else: self._notifyFileChanged(filename) # Well, could be a new revision, too. return True
def mkdir(self, path, notify = True): """ Automatically creates all the directories to create this one. vpath is NOT supported. @rtype: bool @returns: True if the directory was created or was already created (i.e. available). False otherwise. """ paths = os.path.normpath(path).split('/') previousPath = '' for p in paths: if p: p = '%s/%s' % (previousPath, p) previousPath = p (adjusted, backend) = FileSystemBackendManager.getBackend(p) if not backend: raise Exception('No backend available to manipulate %s (creating %s)' % (path, p)) if backend.isfile(adjusted): return False # Cannot create elif backend.isdir(adjusted): # nothing to do at this level continue else: res = backend.mkdir(adjusted) if not res: return False if notify: self._notifyDirCreated(p) return True
def revisions(self, filename): (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) return backend.revisions( adjusted, baseRevision=None, scope=FileSystemBackend.FileSystemBackend.SCOPE_LOCAL)
def isfile(self, path): """ FIXME: A profile is currently not a file... """ (adjusted, backend) = FileSystemBackendManager.getBackend(path) if not backend: raise Exception('No backend available to manipulate %s' % path) return backend.isfile(adjusted)
def getdir(self, path): """ Lists the contents of a directory. vpath is supported to list the profiles virtual folder. """ # Analyse the vpath: could be a virtual folder such as # associated profiles or associated executions vpath = VirtualPath(path) baseObject = vpath.getBaseValue() (adjusted, backend) = FileSystemBackendManager.getBackend(baseObject) if not backend: raise Exception('No backend available to manipulate %s' % baseObject) # Extended dir contents if vpath.isRevisionRelated(): dircontents = backend.revisions( adjusted, baseRevision=None, scope=FileSystemBackend.FileSystemBackend.SCOPE_LOCAL) if dircontents is not None: res = [] for entry in dircontents: name = entry['id'] applicationType = self.getApplicationType( baseObject, path, 'file') if applicationType: res.append({ 'name': name, 'type': applicationType, 'revision': entry }) return res else: return None # Standard dir contents elif vpath.isProfileRelated(): dircontents = backend.getprofiles(adjusted) else: dircontents = backend.getdir(adjusted) if dircontents is None: return None # Now converts the backend-level object type to application-level type res = [] for entry in dircontents: name = entry['name'] applicationType = self.getApplicationType(name, path, entry['type']) if applicationType: res.append({'name': name, 'type': applicationType}) return res
def attributes(self, filename): """ Get the attributes of a file. vpath is supported. """ vpath = VirtualPath(filename) baseObject = vpath.getBaseValue() (adjusted, backend) = FileSystemBackendManager.getBackend(baseObject) if not backend: raise Exception('No backend available to manipulate %s' % baseObject) if vpath.isProfileRelated(): return backend.profileattributes(adjusted, vpath.getVirtualValue()) else: return backend.attributes(adjusted, revision = None)
def getdir(self, path): """ Lists the contents of a directory. vpath is supported to list the profiles virtual folder. """ # Analyse the vpath: could be a virtual folder such as # associated profiles or associated executions vpath = VirtualPath(path) baseObject = vpath.getBaseValue() (adjusted, backend) = FileSystemBackendManager.getBackend(baseObject) if not backend: raise Exception('No backend available to manipulate %s' % baseObject) # Extended dir contents if vpath.isRevisionRelated(): dircontents = backend.revisions(adjusted, baseRevision = None, scope = FileSystemBackend.FileSystemBackend.SCOPE_LOCAL) if dircontents is not None: res = [] for entry in dircontents: name = entry['id'] applicationType = self.getApplicationType(baseObject, path, 'file') if applicationType: res.append({'name': name, 'type': applicationType, 'revision': entry}) return res else: return None # Standard dir contents elif vpath.isProfileRelated(): dircontents = backend.getprofiles(adjusted) else: dircontents = backend.getdir(adjusted) if dircontents is None: return None # Now converts the backend-level object type to application-level type res = [] for entry in dircontents: name = entry['name'] applicationType = self.getApplicationType(name, path, entry['type']) if applicationType: res.append({'name': name, 'type': applicationType}) return res
def _writeProfile(self, filename, profilename, content, notify, username): resourcepath = '%s/profiles/%s' % (filename, profilename) (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) newfile = False if not self.attributes(resourcepath): newfile = True print "DEBUG: new profile (%s): %s" % (resourcepath, newfile) try: backend.writeprofile(adjusted, profilename, content, username = username) except Exception, e: getLogger().error("Unable to profile %s for %s: %s" % (profilename, filename, str(e))) return False
def _writeFile(self, filename, content, reason, notify, username): path = os.path.split(filename)[0] res = self.mkdir(path, notify = notify) if not res: raise Exception('Unable to create directory %s to write %s' % (path, filename)) (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) newfile = False if not self.isfile(filename): newfile = True try: backend.write(adjusted, content, baseRevision = None, reason = reason, username = username) except Exception, e: getLogger().error("Unable to write %s: %s" % (filename, str(e))) return False
def unlink(self, filename, reason = None, notify = True, username = None): """ Removes a file. vpath is supported to remove a profile. """ vpath = VirtualPath(filename) baseObject = vpath.getBaseValue() (adjusted, backend) = FileSystemBackendManager.getBackend(baseObject) if not backend: raise Exception('No backend available to manipulate %s' % filename) if vpath.isProfileRelated(): ret = backend.unlinkprofile(adjusted, vpath.getVirtualValue(), username = username) else: ret = backend.unlink(adjusted, reason, username = username) if ret and notify: self._notifyFileDeleted(filename) return ret
def read(self, filename): """ Returns the content of a file. vpath is supported. """ # Analyse the vpath: could be a virtual folder such as # associated profiles or associated executions vpath = VirtualPath(filename) baseObject = vpath.getBaseValue() (adjusted, backend) = FileSystemBackendManager.getBackend(baseObject) if not backend: raise Exception('No backend available to manipulate %s' % baseObject) if vpath.isProfileRelated(): return backend.readprofile(adjusted, vpath.getVirtualValue()) elif vpath.isRevisionRelated(): return backend.read(adjusted, revision = vpath.getVirtualValue()) else: return backend.read(adjusted, revision = None)
def _writeProfile(self, filename, profilename, content, notify, username): resourcepath = '%s/profiles/%s' % (filename, profilename) (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) newfile = False if not self.attributes(resourcepath): newfile = True print "DEBUG: new profile (%s): %s" % (resourcepath, newfile) try: backend.writeprofile(adjusted, profilename, content, username=username) except Exception, e: getLogger().error("Unable to profile %s for %s: %s" % (profilename, filename, str(e))) return False
(profilefilename, str(e))) return False self._repo.stage([profilelocalname]) ret = self._repo.do_commit( message="Removed profile %s for %s" % (profilename, localname), committer=(username and username or self._defaultCommitter)) getLogger().info("New revision created: %s" % ret) return True def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("git", GitBackend)
profilefilename = "%s.profiles/%s" % (filename, profilename) c = pysvn.Client() try: c.remove(profilefilename) except Exception, e: getLogger().warning("Unable to unlink %s: %s" % (profilefilename, str(e))) return False rev = c.checkin([profilefilename], log_message = "Removed profile %s for %s" % (profilename, localname)) getLogger().info("New revision created: %s" % rev.number) return True def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("svn", SvnBackend)
def revisions(self, filename): (adjusted, backend) = FileSystemBackendManager.getBackend(filename) if not backend: raise Exception('No backend available to manipulate %s' % filename) return backend.revisions(adjusted, baseRevision = None, scope = FileSystemBackend.FileSystemBackend.SCOPE_LOCAL)
def isdir(self, path): (adjusted, backend) = FileSystemBackendManager.getBackend(path) if not backend: raise Exception('No backend available to manipulate %s' % path) return backend.isdir(adjusted)
profilefilename = "%s.profiles/%s" % (filename, profilename) try: os.remove(profilefilename) return True except Exception, e: getLogger().warning("Unable to unlink %s: %s" % (profilefilename, str(e))) return False def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("local", LocalBackend)
return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: os.remove(profilefilename) return True except Exception, e: getLogger().warning("Unable to unlink %s: %s" % (profilefilename, str(e))) return False def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("local", LocalBackend)
except Exception, e: getLogger().warning("Unable to unlink %s: %s" % (profilefilename, str(e))) return False rev = c.checkin([profilefilename], log_message="Removed profile %s for %s" % (profilename, localname)) getLogger().info("New revision created: %s" % rev.number) return True def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("svn", SvnBackend)
try: os.remove(profilefilename) except Exception, e: getLogger().warning("Unable to unlink %s: %s" % (profilefilename, str(e))) return False self._repo.stage([profilelocalname]) ret = self._repo.do_commit(message = "Removed profile %s for %s" % (profilename, localname), committer = (username and username or self._defaultCommitter)) getLogger().info("New revision created: %s" % ret) return True def profileattributes(self, filename, profilename): filename = self._realpath(filename) if not filename: return None profilefilename = "%s.profiles/%s" % (filename, profilename) try: s = os.stat(profilefilename) a = FileSystemBackend.Attributes() a.mtime = s.st_ctime a.size = s.st_size return a except Exception, e: getLogger().warning("Unable to get file attributes for %s: %s" % (profilefilename, str(e))) return None FileSystemBackendManager.registerFileSystemBackendClass("git", GitBackend)