Beispiel #1
0
class PoppyAnonymousShell(ftp.FTPShell):
    """The 'command' interface for sessions.

    Roughly equivalent to the SFTPServer in the sftp side of things.
    """
    def __init__(self, fsroot):
        self._fs_root = fsroot
        self.uploadfilesystem = UploadFileSystem(tempfile.mkdtemp())
        self._current_upload = self.uploadfilesystem.rootpath
        os.chmod(self._current_upload, 0770)
        self._log = logging.getLogger("poppy-sftp")
        self.hook = Hooks(self._fs_root,
                          self._log,
                          "ubuntu",
                          perms='g+rws',
                          prefix='-ftp')
        self.hook.new_client_hook(self._current_upload, 0, 0)
        self.hook.auth_verify_hook(self._current_upload, None, None)
        super(PoppyAnonymousShell,
              self).__init__(filepath.FilePath(self._current_upload))

    def openForWriting(self, file_segments):
        """Write the uploaded file to disk, safely.

        :param file_segments: A list containing string items, one for each
            path component of the file being uploaded.  The file referenced
            is relative to the temporary root for this session.

        If the file path contains directories, we create them.
        """
        filename = os.sep.join(file_segments)
        self._create_missing_directories(filename)
        return super(PoppyAnonymousShell, self).openForWriting(file_segments)

    def makeDirectory(self, path):
        """Make a directory using the secure `UploadFileSystem`."""
        path = os.sep.join(path)
        return defer.maybeDeferred(self.uploadfilesystem.mkdir, path)

    def access(self, segments):
        """Permissive CWD that auto-creates target directories."""
        if segments:
            path = self._path(segments)
            path.makedirs()
        return super(PoppyAnonymousShell, self).access(segments)

    def logout(self):
        """Called when the client disconnects.

        We need to post-process the upload.
        """
        self.hook.client_done_hook(self._current_upload, 0, 0)

    def _create_missing_directories(self, filename):
        # Same as SFTPServer
        new_dir, new_file = os.path.split(
            self.uploadfilesystem._sanitize(filename))
        if new_dir != '':
            if not os.path.exists(os.path.join(self._current_upload, new_dir)):
                self.uploadfilesystem.mkdir(new_dir)

    def list(self, path_segments, attrs):
        return defer.fail(ftp.CmdNotImplementedError("LIST"))
Beispiel #2
0
class SFTPServer:
    """An implementation of `ISFTPServer` that backs onto a Poppy filesystem.
    """

    implements(ISFTPServer)

    def __init__(self, avatar, fsroot):
        provideHandler(self.connectionClosed)
        self._avatar = avatar
        self._fs_root = fsroot
        self.uploadfilesystem = UploadFileSystem(tempfile.mkdtemp())
        self._current_upload = self.uploadfilesystem.rootpath
        os.chmod(self._current_upload, 0770)
        self._log = logging.getLogger("poppy-sftp")
        self.hook = Hooks(self._fs_root,
                          self._log,
                          "ubuntu",
                          perms='g+rws',
                          prefix='-sftp')
        self.hook.new_client_hook(self._current_upload, 0, 0)
        self.hook.auth_verify_hook(self._current_upload, None, None)

    def gotVersion(self, other_version, ext_data):
        return {}

    def openFile(self, filename, flags, attrs):
        self._create_missing_directories(filename)
        absfile = self._translate_path(filename)
        return SFTPFile(absfile)

    def removeFile(self, filename):
        pass

    def renameFile(self, old_path, new_path):
        abs_old = self._translate_path(old_path)
        abs_new = self._translate_path(new_path)
        os.rename(abs_old, abs_new)

    def makeDirectory(self, path, attrs):
        # XXX: We ignore attrs here
        self.uploadfilesystem.mkdir(path)

    def removeDirectory(self, path):
        self.uploadfilesystem.rmdir(path)

    def openDirectory(self, path):
        pass

    def getAttrs(self, path, follow_links):
        pass

    def setAttrs(self, path, attrs):
        pass

    def readLink(self, path):
        pass

    def makeLink(self, link_path, target_path):
        pass

    def realPath(self, path):
        return path

    def extendedRequest(self, extended_name, extended_data):
        pass

    def _create_missing_directories(self, filename):
        new_dir, new_file = os.path.split(
            self.uploadfilesystem._sanitize(filename))
        if new_dir != '':
            if not os.path.exists(os.path.join(self._current_upload, new_dir)):
                self.uploadfilesystem.mkdir(new_dir)

    def _translate_path(self, filename):
        return self.uploadfilesystem._full(
            self.uploadfilesystem._sanitize(filename))

    @adapter(SFTPClosed)
    def connectionClosed(self, event):
        if event.avatar is not self._avatar:
            return
        self.hook.client_done_hook(self._current_upload, 0, 0)
class SFTPServer:
    """An implementation of `ISFTPServer` that backs onto a Poppy filesystem.
    """

    implements(ISFTPServer)

    def __init__(self, avatar, fsroot):
        provideHandler(self.connectionClosed)
        self._avatar = avatar
        self._fs_root = fsroot
        self.uploadfilesystem = UploadFileSystem(tempfile.mkdtemp())
        self._current_upload = self.uploadfilesystem.rootpath
        os.chmod(self._current_upload, 0770)
        self._log = logging.getLogger("poppy-sftp")
        self.hook = Hooks(
            self._fs_root, self._log, "ubuntu", perms='g+rws', prefix='-sftp')
        self.hook.new_client_hook(self._current_upload, 0, 0)
        self.hook.auth_verify_hook(self._current_upload, None, None)

    def gotVersion(self, other_version, ext_data):
        return {}

    def openFile(self, filename, flags, attrs):
        self._create_missing_directories(filename)
        absfile = self._translate_path(filename)
        return SFTPFile(absfile)

    def removeFile(self, filename):
        pass

    def renameFile(self, old_path, new_path):
        abs_old = self._translate_path(old_path)
        abs_new = self._translate_path(new_path)
        os.rename(abs_old, abs_new)

    def makeDirectory(self, path, attrs):
        # XXX: We ignore attrs here
        self.uploadfilesystem.mkdir(path)

    def removeDirectory(self, path):
        self.uploadfilesystem.rmdir(path)

    def openDirectory(self, path):
        pass

    def getAttrs(self, path, follow_links):
        pass

    def setAttrs(self, path, attrs):
        pass

    def readLink(self, path):
        pass

    def makeLink(self, link_path, target_path):
        pass

    def realPath(self, path):
        return path

    def extendedRequest(self, extended_name, extended_data):
        pass

    def _create_missing_directories(self, filename):
        new_dir, new_file = os.path.split(
            self.uploadfilesystem._sanitize(filename))
        if new_dir != '':
            if not os.path.exists(
                os.path.join(self._current_upload, new_dir)):
                self.uploadfilesystem.mkdir(new_dir)

    def _translate_path(self, filename):
        return self.uploadfilesystem._full(
            self.uploadfilesystem._sanitize(filename))

    @adapter(SFTPClosed)
    def connectionClosed(self, event):
        if event.avatar is not self._avatar:
            return
        self.hook.client_done_hook(self._current_upload, 0, 0)
class PoppyAnonymousShell(ftp.FTPShell):
    """The 'command' interface for sessions.

    Roughly equivalent to the SFTPServer in the sftp side of things.
    """

    def __init__(self, fsroot):
        self._fs_root = fsroot
        self.uploadfilesystem = UploadFileSystem(tempfile.mkdtemp())
        self._current_upload = self.uploadfilesystem.rootpath
        os.chmod(self._current_upload, 0770)
        self._log = logging.getLogger("poppy-sftp")
        self.hook = Hooks(
            self._fs_root, self._log, "ubuntu", perms='g+rws',
            prefix='-ftp')
        self.hook.new_client_hook(self._current_upload, 0, 0)
        self.hook.auth_verify_hook(self._current_upload, None, None)
        super(PoppyAnonymousShell, self).__init__(
            filepath.FilePath(self._current_upload))

    def openForWriting(self, file_segments):
        """Write the uploaded file to disk, safely.

        :param file_segments: A list containing string items, one for each
            path component of the file being uploaded.  The file referenced
            is relative to the temporary root for this session.

        If the file path contains directories, we create them.
        """
        filename = os.sep.join(file_segments)
        self._create_missing_directories(filename)
        return super(PoppyAnonymousShell, self).openForWriting(file_segments)

    def makeDirectory(self, path):
        """Make a directory using the secure `UploadFileSystem`."""
        path = os.sep.join(path)
        return defer.maybeDeferred(self.uploadfilesystem.mkdir, path)

    def access(self, segments):
        """Permissive CWD that auto-creates target directories."""
        if segments:
            path = self._path(segments)
            path.makedirs()
        return super(PoppyAnonymousShell, self).access(segments)

    def logout(self):
        """Called when the client disconnects.

        We need to post-process the upload.
        """
        self.hook.client_done_hook(self._current_upload, 0, 0)

    def _create_missing_directories(self, filename):
        # Same as SFTPServer
        new_dir, new_file = os.path.split(
            self.uploadfilesystem._sanitize(filename))
        if new_dir != '':
            if not os.path.exists(
                os.path.join(self._current_upload, new_dir)):
                self.uploadfilesystem.mkdir(new_dir)

    def list(self, path_segments, attrs):
        return defer.fail(ftp.CmdNotImplementedError("LIST"))