Esempio n. 1
0
    def child(self, path):
        """
        Create and return a new L{FilePath} representing a path contained by
        C{self}.

        @param path: The base name of the new L{FilePath}.  If this contains
            directory separators or parent references it will be rejected.
        @type path: L{bytes}

        @raise InsecurePath: If the result of combining this path with C{path}
            would result in a path which is not a direct child of this path.

        @return: The child path.
        @rtype: L{FilePath}
        """
        if platform.isWindows() and path.count(b":"):
            # Catch paths like C:blah that don't have a slash
            raise InsecurePath("%r contains a colon." % (path,))
        norm = normpath(path)
        if self.sep in norm:
            raise InsecurePath("%r contains one or more directory separators" % (path,))
        newpath = abspath(joinpath(self.path, norm))
        if not newpath.startswith(self.path):
            raise InsecurePath("%r is not a child of %s" % (newpath, self.path))
        return self.clonePath(newpath)
Esempio n. 2
0
    def child(self, path):
        """
        Create and return a new L{FilePath} representing a path contained by
        C{self}.

        @param path: The base name of the new L{FilePath}.  If this contains
            directory separators or parent references it will be rejected.
        @type path: L{bytes}

        @raise InsecurePath: If the result of combining this path with C{path}
            would result in a path which is not a direct child of this path.

        @return: The child path.
        @rtype: L{FilePath}
        """
        if platform.isWindows() and path.count(b":"):
            # Catch paths like C:blah that don't have a slash
            raise InsecurePath("%r contains a colon." % (path, ))
        norm = normpath(path)
        if self.sep in norm:
            raise InsecurePath("%r contains one or more directory separators" %
                               (path, ))
        newpath = abspath(joinpath(self.path, norm))
        if not newpath.startswith(self.path):
            raise InsecurePath("%r is not a child of %s" %
                               (newpath, self.path))
        return self.clonePath(newpath)
Esempio n. 3
0
    def setContent(self, content, ext=b'.new'):
        """
        Replace the file at this path with a new file that contains the given
        bytes, trying to avoid data-loss in the meanwhile.

        On UNIX-like platforms, this method does its best to ensure that by the
        time this method returns, either the old contents I{or} the new contents
        of the file will be present at this path for subsequent readers
        regardless of premature device removal, program crash, or power loss,
        making the following assumptions:

            - your filesystem is journaled (i.e. your filesystem will not
              I{itself} lose data due to power loss)

            - your filesystem's C{rename()} is atomic

            - your filesystem will not discard new data while preserving new
              metadata (see U{http://mjg59.livejournal.com/108257.html} for more
              detail)

        On most versions of Windows there is no atomic C{rename()} (see
        U{http://bit.ly/win32-overwrite} for more information), so this method
        is slightly less helpful.  There is a small window where the file at
        this path may be deleted before the new file is moved to replace it:
        however, the new file will be fully written and flushed beforehand so in
        the unlikely event that there is a crash at that point, it should be
        possible for the user to manually recover the new version of their data.
        In the future, Twisted will support atomic file moves on those versions
        of Windows which I{do} support them: see U{Twisted ticket
        3004<http://twistedmatrix.com/trac/ticket/3004>}.

        This method should be safe for use by multiple concurrent processes, but
        note that it is not easy to predict which process's contents will
        ultimately end up on disk if they invoke this method at close to the
        same time.

        @param content: The desired contents of the file at this path.
        @type content: L{bytes}

        @param ext: An extension to append to the temporary filename used to
            store the bytes while they are being written.  This can be used to
            make sure that temporary files can be identified by their suffix,
            for cleanup in case of crashes.

        @type ext: L{bytes}
        """
        sib = self.temporarySibling(ext)
        f = sib.open('w')
        try:
            f.write(content)
        finally:
            f.close()
        if platform.isWindows() and exists(self.path):
            os.unlink(self.path)
        os.rename(sib.path, self.path)
Esempio n. 4
0
    def setContent(self, content, ext=b'.new'):
        """
        Replace the file at this path with a new file that contains the given
        bytes, trying to avoid data-loss in the meanwhile.

        On UNIX-like platforms, this method does its best to ensure that by the
        time this method returns, either the old contents I{or} the new contents
        of the file will be present at this path for subsequent readers
        regardless of premature device removal, program crash, or power loss,
        making the following assumptions:

            - your filesystem is journaled (i.e. your filesystem will not
              I{itself} lose data due to power loss)

            - your filesystem's C{rename()} is atomic

            - your filesystem will not discard new data while preserving new
              metadata (see U{http://mjg59.livejournal.com/108257.html} for more
              detail)

        On most versions of Windows there is no atomic C{rename()} (see
        U{http://bit.ly/win32-overwrite} for more information), so this method
        is slightly less helpful.  There is a small window where the file at
        this path may be deleted before the new file is moved to replace it:
        however, the new file will be fully written and flushed beforehand so in
        the unlikely event that there is a crash at that point, it should be
        possible for the user to manually recover the new version of their data.
        In the future, Twisted will support atomic file moves on those versions
        of Windows which I{do} support them: see U{Twisted ticket
        3004<http://twistedmatrix.com/trac/ticket/3004>}.

        This method should be safe for use by multiple concurrent processes, but
        note that it is not easy to predict which process's contents will
        ultimately end up on disk if they invoke this method at close to the
        same time.

        @param content: The desired contents of the file at this path.
        @type content: L{bytes}

        @param ext: An extension to append to the temporary filename used to
            store the bytes while they are being written.  This can be used to
            make sure that temporary files can be identified by their suffix,
            for cleanup in case of crashes.

        @type ext: L{bytes}
        """
        sib = self.temporarySibling(ext)
        f = sib.open('w')
        try:
            f.write(content)
        finally:
            f.close()
        if platform.isWindows() and exists(self.path):
            os.unlink(self.path)
        os.rename(sib.path, self.path)
Esempio n. 5
0
def getProgramsMenuPath():
    """
    Get the path to the Programs menu.

    Probably will break on non-US Windows.

    @return: the filesystem location of the common Start Menu->Programs.
    @rtype: L{str}
    """
    if not platform.isWindows():
        return "C:\\Windows\\Start Menu\\Programs"
    keyname = 'SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders'
    hShellFolders = win32api.RegOpenKeyEx(win32con.HKEY_LOCAL_MACHINE,
                                          keyname, 0, win32con.KEY_READ)
    return win32api.RegQueryValueEx(hShellFolders, 'Common Programs')[0]
Esempio n. 6
0
def getProgramsMenuPath():
    """
    Get the path to the Programs menu.

    Probably will break on non-US Windows.

    @return: the filesystem location of the common Start Menu->Programs.
    @rtype: L{str}
    """
    if not platform.isWindows():
        return "C:\\Windows\\Start Menu\\Programs"
    keyname = 'SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders'
    hShellFolders = win32api.RegOpenKeyEx(win32con.HKEY_LOCAL_MACHINE, keyname,
                                          0, win32con.KEY_READ)
    return win32api.RegQueryValueEx(hShellFolders, 'Common Programs')[0]
Esempio n. 7
0
    def getUserID(self):
        """
        Returns the user ID of the file's owner.

        @raise NotImplementedError: if the platform is Windows, since the UID
            is always 0 on Windows
        @return: the user ID of the file's owner
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_uid
Esempio n. 8
0
    def getGroupID(self):
        """
        Returns the group ID of the file.

        @raise NotImplementedError: if the platform is Windows, since the GID
            is always 0 on windows
        @return: the group ID of the file
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_gid
Esempio n. 9
0
    def getGroupID(self):
        """
        Returns the group ID of the file.

        @raise NotImplementedError: if the platform is Windows, since the GID
            is always 0 on windows
        @return: the group ID of the file
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_gid
Esempio n. 10
0
    def getUserID(self):
        """
        Returns the user ID of the file's owner.

        @raise NotImplementedError: if the platform is Windows, since the UID
            is always 0 on Windows
        @return: the user ID of the file's owner
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_uid
Esempio n. 11
0
    def getInodeNumber(self):
        """
        Retrieve the file serial number, also called inode number, which
        distinguishes this file from all other files on the same device.

        @raise NotImplementedError: if the platform is Windows, since the
            inode number would be a dummy value for all files in Windows
        @return: a number representing the file serial number
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_ino
Esempio n. 12
0
    def getInodeNumber(self):
        """
        Retrieve the file serial number, also called inode number, which
        distinguishes this file from all other files on the same device.

        @raise NotImplementedError: if the platform is Windows, since the
            inode number would be a dummy value for all files in Windows
        @return: a number representing the file serial number
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_ino
Esempio n. 13
0
    def getDevice(self):
        """
        Retrieves the device containing the file.  The inode number and device
        number together uniquely identify the file, but the device number is
        not necessarily consistent across reboots or system crashes.

        @raise NotImplementedError: if the platform is Windows, since the device
            number would be 0 for all partitions on a Windows platform
        @return: a number representing the device
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_dev
Esempio n. 14
0
    def getDevice(self):
        """
        Retrieves the device containing the file.  The inode number and device
        number together uniquely identify the file, but the device number is
        not necessarily consistent across reboots or system crashes.

        @raise NotImplementedError: if the platform is Windows, since the device
            number would be 0 for all partitions on a Windows platform
        @return: a number representing the device
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_dev
Esempio n. 15
0
    def getNumberOfHardLinks(self):
        """
        Retrieves the number of hard links to the file.

        This count keeps track of how many directories have entries for this
        file. If the count is ever decremented to zero then the file itself is
        discarded as soon as no process still holds it open.  Symbolic links
        are not counted in the total.

        @raise NotImplementedError: if the platform is Windows, since Windows
            doesn't maintain a link count for directories, and L{os.stat} does
            not set C{st_nlink} on Windows anyway.
        @return: the number of hard links to the file
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_nlink
Esempio n. 16
0
    def getNumberOfHardLinks(self):
        """
        Retrieves the number of hard links to the file.

        This count keeps track of how many directories have entries for this
        file. If the count is ever decremented to zero then the file itself is
        discarded as soon as no process still holds it open.  Symbolic links
        are not counted in the total.

        @raise NotImplementedError: if the platform is Windows, since Windows
            doesn't maintain a link count for directories, and L{os.stat} does
            not set C{st_nlink} on Windows anyway.
        @return: the number of hard links to the file
        @rtype: L{int}
        @since: 11.0
        """
        if platform.isWindows():
            raise NotImplementedError

        st = self.statinfo
        if not st:
            self.restat()
            st = self.statinfo
        return st.st_nlink