mirror of
https://github.com/archlinuxarm/PKGBUILDs.git
synced 2024-11-18 22:54:00 +00:00
1417 lines
46 KiB
Diff
1417 lines
46 KiB
Diff
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/setup.py wxPython-src-2.8.10.1/wxPython/setup.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/setup.py 2009-06-06 14:43:00.000000000 -0400
|
|
+++ wxPython-src-2.8.10.1/wxPython/setup.py 2009-06-06 14:43:55.000000000 -0400
|
|
@@ -882,6 +882,7 @@
|
|
'wx.tools.Editra',
|
|
'wx.tools.Editra.src',
|
|
'wx.tools.Editra.src.autocomp',
|
|
+ 'wx.tools.Editra.src.ebmlib',
|
|
'wx.tools.Editra.src.eclib',
|
|
'wx.tools.Editra.src.extern',
|
|
'wx.tools.Editra.src.syntax',
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/__init__.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/__init__.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/__init__.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/__init__.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,33 @@
|
|
+###############################################################################
|
|
+# Name: __init__.py #
|
|
+# Purpose: Editra Buisness Model Library #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library:
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: __init__.py 60840 2009-05-31 16:00:50Z CJP $"
|
|
+__revision__ = "$Revision: 60840 $"
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+# Text Utils
|
|
+from searcheng import *
|
|
+from fchecker import *
|
|
+from fileutil import *
|
|
+from fileimpl import *
|
|
+
|
|
+from backupmgr import *
|
|
+
|
|
+# Storage Classes
|
|
+from histcache import *
|
|
+from clipboard import *
|
|
+
|
|
+# Misc
|
|
+from miscutil import *
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/backupmgr.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/backupmgr.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/backupmgr.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/backupmgr.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,160 @@
|
|
+###############################################################################
|
|
+# Name: backupmgr.py #
|
|
+# Purpose: File Backup Manager #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: FileBackupMgr
|
|
+
|
|
+Helper class for managing and creating backups of files.
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: backupmgr.py 60581 2009-05-10 02:56:00Z CJP $"
|
|
+__revision__ = "$Revision: 60581 $"
|
|
+
|
|
+__all__ = [ 'FileBackupMgr', ]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import os
|
|
+import shutil
|
|
+
|
|
+# Local Imports
|
|
+import fileutil
|
|
+import fchecker
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+class FileBackupMgr(object):
|
|
+ """File backup creator and manager"""
|
|
+ def __init__(self, header=None, template=u"%s~"):
|
|
+ """Create a BackupManager
|
|
+ @keyword header: header to id backups with (Text files only!!)
|
|
+ @keyword template: template string for naming backup file with
|
|
+
|
|
+ """
|
|
+ object.__init__(self)
|
|
+
|
|
+ # Attributes
|
|
+ self.checker = fchecker.FileTypeChecker()
|
|
+ self.header = header # Backup id header
|
|
+ self.template = template # Filename template
|
|
+
|
|
+ def _CheckHeader(self, fname):
|
|
+ """Check if the backup file has a header that matches the
|
|
+ header used to identify backup files.
|
|
+ @param fname: name of file to check
|
|
+ @return: bool (True if header is ok, False otherwise)
|
|
+
|
|
+ """
|
|
+ isok = False
|
|
+ try:
|
|
+ handle = open(fname)
|
|
+ line = handle.readline()
|
|
+ isok = line.startswith(self.header)
|
|
+ except:
|
|
+ isok = False
|
|
+ finally:
|
|
+ handle.close()
|
|
+ return isok
|
|
+
|
|
+ def GetBackupFilename(self, fname):
|
|
+ """Get the unique name for the files backup copy
|
|
+ @param fname: string (file path)
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ rname = self.template % fname
|
|
+ if self.header is not None and \
|
|
+ not self.checker.IsBinary(fname) and \
|
|
+ os.path.exists(rname):
|
|
+ # Make sure that the template backup name does not match
|
|
+ # an existing file that is not a backup file.
|
|
+ while not self._CheckHeader(rname):
|
|
+ rname = self.template % rname
|
|
+
|
|
+ return rname
|
|
+
|
|
+ def GetBackupWriter(self, fileobj):
|
|
+ """Create a backup filewriter method to backup a files contents
|
|
+ with.
|
|
+ @param fileobj: object implementing fileimpl.FileObjectImpl interface
|
|
+ @return: callable(text) to create backup with
|
|
+
|
|
+ """
|
|
+ nfile = fileobj.Clone()
|
|
+ fname = self.GetBackupFilename(nfile.GetPath())
|
|
+ nfile.SetPath(fname)
|
|
+ # Write the header if it is enabled
|
|
+ if self.header is not None and not self.checker.IsBinary(fname):
|
|
+ nfile.Write(self.header + os.linesep)
|
|
+ return nfile.Write
|
|
+
|
|
+ def HasBackup(self, fname):
|
|
+ """Check if a given file has a backup file available or not
|
|
+ @param fname: string (file path)
|
|
+
|
|
+ """
|
|
+ backup = self.GetBackupFilename(fname)
|
|
+ return os.path.exists(backup)
|
|
+
|
|
+ def IsBackupNewer(self, fname):
|
|
+ """Is the backup of this file newer than the saved version
|
|
+ of the file?
|
|
+ @param fname: string (file path)
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ backup = self.GetBackupFilename(fname)
|
|
+ if os.path.exists(fname) and os.path.exists(backup):
|
|
+ mod1 = fileutil.GetFileModTime(backup)
|
|
+ mod2 = fileutil.GetFileModTime(fname)
|
|
+ return mod1 > mod2
|
|
+ else:
|
|
+ return False
|
|
+
|
|
+ def MakeBackupCopy(self, fname):
|
|
+ """Create a backup copy of the given filename
|
|
+ @param fname: string (file path)
|
|
+ @return: bool (True == Success)
|
|
+
|
|
+ """
|
|
+ backup = self.GetBackupFilename(fname)
|
|
+ try:
|
|
+ if os.path.exists(backup):
|
|
+ os.remove(backup)
|
|
+
|
|
+ shutil.copy2(fname, backup)
|
|
+ except:
|
|
+ return False
|
|
+ else:
|
|
+ return True
|
|
+
|
|
+ def MakeBackupCopyAsync(self, fname):
|
|
+ """Do the backup asyncronously
|
|
+ @param fname: string (file path)
|
|
+ @todo: Not implemented yet
|
|
+
|
|
+ """
|
|
+ raise NotImplementedError("TODO: implement once threadpool is finished")
|
|
+
|
|
+ def SetBackupFileTemplate(self, tstr):
|
|
+ """Set the filename template for generating the backupfile name
|
|
+ @param tstr: template string i.e) %s~
|
|
+
|
|
+ """
|
|
+ assert tstr.count("%s") == 1, "Format statment must only have one arg"
|
|
+ self.template = tstr
|
|
+
|
|
+ def SetHeader(self, header):
|
|
+ """Set the header string for identifying a file as a backup
|
|
+ @param header: string (single line only)
|
|
+
|
|
+ """
|
|
+ assert '\n' not in header, "Header must only be a single line"
|
|
+ self.header = header
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/clipboard.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/clipboard.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/clipboard.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/clipboard.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,135 @@
|
|
+###############################################################################
|
|
+# Name: histcache.py #
|
|
+# Purpose: History Cache #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: Clipboard
|
|
+
|
|
+Clipboard helper class
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Hasan Aljudy"
|
|
+__cvsid__ = "$Id: clipboard.py 60681 2009-05-17 10:41:42Z CJP $"
|
|
+__revision__ = "$Revision: 60681 $"
|
|
+
|
|
+__all__ = [ 'Clipboard',]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import wx
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+class Clipboard(object):
|
|
+ """Multiple clipboards as named registers (as per vim)
|
|
+
|
|
+ " is an alias for system clipboard and is also the default clipboard.
|
|
+
|
|
+ @note: The only way to access multiple clipboards right now is through
|
|
+ Normal mode when Vi(m) emulation is enabled.
|
|
+
|
|
+ """
|
|
+ NAMES = list(u'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_')
|
|
+ registers = {}
|
|
+ current = u'"'
|
|
+
|
|
+ @classmethod
|
|
+ def Switch(cls, reg):
|
|
+ """Switch to register
|
|
+ @param reg: char
|
|
+
|
|
+ """
|
|
+ if reg in cls.NAMES or reg == u'"':
|
|
+ cls.current = reg
|
|
+ else:
|
|
+ raise Exception(u"Switched to invalid register name")
|
|
+
|
|
+ @classmethod
|
|
+ def NextFree(cls, reg):
|
|
+ """Switch to the next free register. If current register is free, no
|
|
+ switching happens.
|
|
+
|
|
+ A free register is one that's either unused or has no content
|
|
+
|
|
+ @param reg: char
|
|
+ @note: This is not used yet.
|
|
+
|
|
+ """
|
|
+ if cls.Get() == u'':
|
|
+ return
|
|
+
|
|
+ for name in cls.NAMES:
|
|
+ if cls.registers.get(name, u'') == u'':
|
|
+ cls.Switch(name)
|
|
+ break
|
|
+
|
|
+ @classmethod
|
|
+ def AllUsed(cls):
|
|
+ """Get a dictionary mapping all used clipboards (plus the system
|
|
+ clipboard) to their content.
|
|
+
|
|
+ @note: This is not used yet.
|
|
+
|
|
+ """
|
|
+ cmd_map = { u'"': cls.SystemGet() }
|
|
+ for name in cls.NAMES:
|
|
+ if cls.registers.get(name, u''):
|
|
+ cmd_map[name] = cls.registers[name]
|
|
+ return cmd_map
|
|
+
|
|
+ @classmethod
|
|
+ def Get(cls):
|
|
+ """Get the content of the current register. Used for pasting"""
|
|
+ if cls.current == u'"':
|
|
+ return cls.SystemGet()
|
|
+ else:
|
|
+ return cls.registers.get( cls.current, u'' )
|
|
+
|
|
+ @classmethod
|
|
+ def Set(cls, text):
|
|
+ """Set the content of the current register
|
|
+ @param text: string
|
|
+
|
|
+ """
|
|
+ if cls.current == u'"':
|
|
+ return cls.SystemSet(text)
|
|
+ else:
|
|
+ cls.registers[cls.current] = text
|
|
+
|
|
+ @classmethod
|
|
+ def SystemGet(cls):
|
|
+ """Get text from the system clipboard
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ text = None
|
|
+ if wx.TheClipboard.Open():
|
|
+ if wx.TheClipboard.IsSupported(wx.DataFormat(wx.DF_TEXT)):
|
|
+ text = wx.TextDataObject()
|
|
+ wx.TheClipboard.GetData(text)
|
|
+
|
|
+ wx.TheClipboard.Close()
|
|
+
|
|
+ if text is not None:
|
|
+ return text.GetText()
|
|
+ else:
|
|
+ return u''
|
|
+
|
|
+ @classmethod
|
|
+ def SystemSet(cls, text):
|
|
+ """Set text into the system clipboard
|
|
+ @param text: string
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ ok = False
|
|
+ if wx.TheClipboard.Open():
|
|
+ wx.TheClipboard.SetData(wx.TextDataObject(text))
|
|
+ wx.TheClipboard.Close()
|
|
+ ok = True
|
|
+ return ok
|
|
\ No newline at end of file
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fchecker.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fchecker.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fchecker.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fchecker.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,82 @@
|
|
+###############################################################################
|
|
+# Name: fchecker.py #
|
|
+# Purpose: Filetype checker object. #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: FileTypeChecker
|
|
+
|
|
+Helper class for checking what kind of a content a file contains.
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: fchecker.py 60505 2009-05-03 19:18:21Z CJP $"
|
|
+__revision__ = "$Revision: 60505 $"
|
|
+
|
|
+__all__ = [ 'FileTypeChecker', ]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import os
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+class FileTypeChecker(object):
|
|
+ """File type checker and recognizer"""
|
|
+ TXTCHARS = ''.join(map(chr, [7, 8, 9, 10, 12, 13, 27] + range(0x20, 0x100)))
|
|
+ ALLBYTES = ''.join(map(chr, range(256)))
|
|
+
|
|
+ def __init__(self, preread=4096):
|
|
+ """Create the FileTypeChecker
|
|
+ @keyword preread: number of bytes to read for checking file type
|
|
+
|
|
+ """
|
|
+ object.__init__(self)
|
|
+
|
|
+ # Attributes
|
|
+ self._preread = preread
|
|
+
|
|
+ @staticmethod
|
|
+ def _GetHandle(fname):
|
|
+ """Get a file handle for reading
|
|
+ @param fname: filename
|
|
+ @return: file object or None
|
|
+
|
|
+ """
|
|
+ try:
|
|
+ handle = open(fname, 'rb')
|
|
+ except:
|
|
+ handle = None
|
|
+ return handle
|
|
+
|
|
+ def IsBinary(self, fname):
|
|
+ """Is the file made up of binary data
|
|
+ @param fname: filename to check
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ handle = self._GetHandle(fname)
|
|
+ if handle is not None:
|
|
+ bytes = handle.read(self._preread)
|
|
+ handle.close()
|
|
+ nontext = bytes.translate(FileTypeChecker.ALLBYTES,
|
|
+ FileTypeChecker.TXTCHARS)
|
|
+ return bool(nontext)
|
|
+ else:
|
|
+ return False
|
|
+
|
|
+ def IsReadableText(self, fname):
|
|
+ """Is the given path readable as text. Will return True if the
|
|
+ file is accessable by current user and is plain text.
|
|
+ @param fname: filename
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ f_ok = False
|
|
+ if os.access(fname, os.R_OK):
|
|
+ f_ok = not self.IsBinary(fname)
|
|
+ return f_ok
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fileimpl.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fileimpl.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fileimpl.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fileimpl.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,215 @@
|
|
+###############################################################################
|
|
+# Name: Cody Precord #
|
|
+# Purpose: File Object Interface Implementation #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# License: wxWindows License #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: FileObjectImpl
|
|
+
|
|
+Implementation of a file object interface class. Objects and methods inside
|
|
+of this library expect a file object that derives from this interface.
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__svnid__ = "$Id: fileimpl.py 60582 2009-05-10 04:24:30Z CJP $"
|
|
+__revision__ = "$Revision: 60582 $"
|
|
+
|
|
+#--------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import os
|
|
+
|
|
+# Editra Buisness Model Imports
|
|
+import fileutil
|
|
+
|
|
+#--------------------------------------------------------------------------#
|
|
+
|
|
+class FileObjectImpl(object):
|
|
+ """File Object Interface implementation base class"""
|
|
+ def __init__(self, path=u'', modtime=0):
|
|
+ object.__init__(self)
|
|
+
|
|
+ # Attributes
|
|
+ self._path = path
|
|
+ self._modtime = modtime
|
|
+
|
|
+ self._handle = None
|
|
+ self.open = False
|
|
+
|
|
+ self.last_err = None
|
|
+
|
|
+ def ClearLastError(self):
|
|
+ """Reset the error marker on this file"""
|
|
+ del self.last_err
|
|
+ self.last_err = None
|
|
+
|
|
+ def Clone(self):
|
|
+ """Clone the file object
|
|
+ @return: FileObject
|
|
+
|
|
+ """
|
|
+ fileobj = FileObjectImpl(self._path, self._modtime)
|
|
+ fileobj.SetLastError(self.last_err)
|
|
+ return fileobj
|
|
+
|
|
+ def Close(self):
|
|
+ """Close the file handle
|
|
+ @note: this is normally done automatically after a read/write operation
|
|
+
|
|
+ """
|
|
+ try:
|
|
+ self._handle.close()
|
|
+ except:
|
|
+ pass
|
|
+
|
|
+ self.open = False
|
|
+
|
|
+ def DoOpen(self, mode):
|
|
+ """Opens and creates the internal file object
|
|
+ @param mode: mode to open file in
|
|
+ @return: True if opened, False if not
|
|
+ @postcondition: self._handle is set to the open handle
|
|
+
|
|
+ """
|
|
+ if not len(self._path):
|
|
+ return False
|
|
+
|
|
+ try:
|
|
+ file_h = open(self._path, mode)
|
|
+ except (IOError, OSError), msg:
|
|
+ self.last_err = msg
|
|
+ return False
|
|
+ else:
|
|
+ self._handle = file_h
|
|
+ self.open = True
|
|
+ return True
|
|
+
|
|
+ def GetExtension(self):
|
|
+ """Get the files extension if it has one else simply return the
|
|
+ filename minus the path.
|
|
+ @return: string file extension (no dot)
|
|
+
|
|
+ """
|
|
+ fname = os.path.split(self._path)
|
|
+ return fname[-1].split(os.extsep)[-1].lower()
|
|
+
|
|
+ def GetHandle(self):
|
|
+ """Get this files handle"""
|
|
+ return self._handle
|
|
+
|
|
+ def GetLastError(self):
|
|
+ """Return the last error that occured when using this file
|
|
+ @return: err traceback or None
|
|
+
|
|
+ """
|
|
+ return unicode(self.last_err).replace("u'", "'")
|
|
+
|
|
+ def GetModtime(self):
|
|
+ """Get the timestamp of this files last modification"""
|
|
+ return self._modtime
|
|
+
|
|
+ def GetPath(self):
|
|
+ """Get the path of the file
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ return self._path
|
|
+
|
|
+ def GetSize(self):
|
|
+ """Get the size of the file
|
|
+ @return: int
|
|
+
|
|
+ """
|
|
+ if self._path:
|
|
+ return fileutil.GetFileSize(self._path)
|
|
+ else:
|
|
+ return 0
|
|
+
|
|
+ @property
|
|
+ def Handle(self):
|
|
+ """Raw file handle property"""
|
|
+ return self._handle
|
|
+
|
|
+ def IsOpen(self):
|
|
+ """Check if file is open or not
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ return self.open
|
|
+
|
|
+ def IsReadOnly(self):
|
|
+ """Is the file Read Only
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ if os.path.exists(self._path):
|
|
+ return not os.access(self._path, os.R_OK|os.W_OK)
|
|
+ else:
|
|
+ return False
|
|
+
|
|
+ @property
|
|
+ def Modtime(self):
|
|
+ """File modification time propery"""
|
|
+ return self.GetModtime()
|
|
+
|
|
+ @property
|
|
+ def ReadOnly(self):
|
|
+ """Is the file read only?"""
|
|
+ return self.IsReadOnly()
|
|
+
|
|
+ def ResetAll(self):
|
|
+ """Reset all file attributes"""
|
|
+ self._handle = None
|
|
+ self.open = False
|
|
+ self._path = u''
|
|
+ self._modtime = 0
|
|
+ self.last_err = None
|
|
+
|
|
+ def SetLastError(self, err):
|
|
+ """Set the last error
|
|
+ @param err: exception object / msg
|
|
+
|
|
+ """
|
|
+ self.last_err = err
|
|
+
|
|
+ def SetPath(self, path):
|
|
+ """Set the path of the file
|
|
+ @param path: absolute path to file
|
|
+
|
|
+ """
|
|
+ self._path = path
|
|
+
|
|
+ def SetModTime(self, mtime):
|
|
+ """Set the modtime of this file
|
|
+ @param mtime: long int to set modtime to
|
|
+
|
|
+ """
|
|
+ self._modtime = mtime
|
|
+
|
|
+ #--- SHould be overridden by subclass ---#
|
|
+
|
|
+ def Read(self):
|
|
+ """Open/Read the file
|
|
+ @return: string (file contents)
|
|
+
|
|
+ """
|
|
+ txt = u''
|
|
+ if self.DoOpen('rb'):
|
|
+ try:
|
|
+ txt = self._handle.read()
|
|
+ except:
|
|
+ pass
|
|
+
|
|
+ return txt
|
|
+
|
|
+ def Write(self, value):
|
|
+ """Open/Write the value to disk
|
|
+ @param value: string
|
|
+
|
|
+ """
|
|
+ if self.DoOpen('wb'):
|
|
+ self._handle.write(value)
|
|
+ self._handle.close()
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fileutil.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fileutil.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/fileutil.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/fileutil.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,180 @@
|
|
+###############################################################################
|
|
+# Name: fileutil.py #
|
|
+# Purpose: File Management Utilities. #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: File Utilities
|
|
+
|
|
+Utility functions for managing and working with files.
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__svnid__ = "$Id: fileutil.py 60523 2009-05-05 18:49:31Z CJP $"
|
|
+__revision__ = "$Revision: 60523 $"
|
|
+
|
|
+__all__ = [ 'GetFileModTime', 'GetFileSize', 'GetUniqueName', 'MakeNewFile',
|
|
+ 'MakeNewFolder', 'GetFileExtension', 'GetFileName', 'GetPathName',
|
|
+ 'ResolveRealPath', 'IsLink' ]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import os
|
|
+import platform
|
|
+import stat
|
|
+
|
|
+UNIX = WIN = False
|
|
+if platform.system().lower() in ['windows', 'microsoft']:
|
|
+ WIN = True
|
|
+ try:
|
|
+ # Check for if win32 extensions are available
|
|
+ import win32com.client as win32client
|
|
+ except ImportError:
|
|
+ win32client = None
|
|
+else:
|
|
+ UNIX = True
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+def GetFileExtension(file_str):
|
|
+ """Gets last atom at end of string as extension if
|
|
+ no extension whole string is returned
|
|
+ @param file_str: path or file name to get extension from
|
|
+
|
|
+ """
|
|
+ return file_str.split('.')[-1]
|
|
+
|
|
+def GetFileModTime(file_name):
|
|
+ """Returns the time that the given file was last modified on
|
|
+ @param file_name: path of file to get mtime of
|
|
+
|
|
+ """
|
|
+ try:
|
|
+ mod_time = os.path.getmtime(file_name)
|
|
+ except (OSError, EnvironmentError):
|
|
+ mod_time = 0
|
|
+ return mod_time
|
|
+
|
|
+def GetFileName(path):
|
|
+ """Gets last atom on end of string as filename
|
|
+ @param path: full path to get filename from
|
|
+
|
|
+ """
|
|
+ return os.path.split(path)[-1]
|
|
+
|
|
+def GetFileSize(path):
|
|
+ """Get the size of the file at a given path
|
|
+ @param path: Path to file
|
|
+ @return: long
|
|
+
|
|
+ """
|
|
+ try:
|
|
+ return os.stat(path)[stat.ST_SIZE]
|
|
+ except:
|
|
+ return 0
|
|
+
|
|
+def GetPathName(path):
|
|
+ """Gets the path minus filename
|
|
+ @param path: full path to get base of
|
|
+
|
|
+ """
|
|
+ return os.path.split(path)[0]
|
|
+
|
|
+def IsLink(path):
|
|
+ """Is the file a link
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ if WIN:
|
|
+ return path.endswith(".lnk") or os.path.islink(path)
|
|
+ else:
|
|
+ return os.path.islink(path)
|
|
+
|
|
+def ResolveRealPath(link):
|
|
+ """Return the real path of the link file
|
|
+ @param link: path of link file
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ assert IsLink(link), "ResolveRealPath expects a link file!"
|
|
+ realpath = link
|
|
+ if WIN and win32client is not None:
|
|
+ shell = win32client.Dispatch("WScript.Shell")
|
|
+ shortcut = shell.CreateShortCut(link)
|
|
+ realpath = shortcut.Targetpath
|
|
+ else:
|
|
+ realpath = os.path.realpath(link)
|
|
+ return realpath
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+def GetUniqueName(path, name):
|
|
+ """Make a file name that will be unique in case a file of the
|
|
+ same name already exists at that path.
|
|
+ @param path: Root path to folder of files destination
|
|
+ @param name: desired file name base
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ tmpname = os.path.join(path, name)
|
|
+ if os.path.exists(tmpname):
|
|
+ if '.' not in name:
|
|
+ ext = ''
|
|
+ fbase = name
|
|
+ else:
|
|
+ ext = '.' + name.split('.')[-1]
|
|
+ fbase = name[:-1 * len(ext)]
|
|
+
|
|
+ inc = len([x for x in os.listdir(path) if x.startswith(fbase)])
|
|
+ tmpname = os.path.join(path, "%s-%d%s" % (fbase, inc, ext))
|
|
+ while os.path.exists(tmpname):
|
|
+ inc = inc + 1
|
|
+ tmpname = os.path.join(path, "%s-%d%s" % (fbase, inc, ext))
|
|
+
|
|
+ return tmpname
|
|
+
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+def MakeNewFile(path, name):
|
|
+ """Make a new file at the given path with the given name.
|
|
+ If the file already exists, the given name will be changed to
|
|
+ a unique name in the form of name + -NUMBER + .extension
|
|
+ @param path: path to directory to create file in
|
|
+ @param name: desired name of file
|
|
+ @return: Tuple of (success?, Path of new file OR Error message)
|
|
+
|
|
+ """
|
|
+ if not os.path.isdir(path):
|
|
+ path = os.path.dirname(path)
|
|
+ fname = GetUniqueName(path, name)
|
|
+
|
|
+ try:
|
|
+ open(fname, 'w').close()
|
|
+ except (IOError, OSError), msg:
|
|
+ return (False, str(msg))
|
|
+
|
|
+ return (True, fname)
|
|
+
|
|
+def MakeNewFolder(path, name):
|
|
+ """Make a new folder at the given path with the given name.
|
|
+ If the folder already exists, the given name will be changed to
|
|
+ a unique name in the form of name + -NUMBER.
|
|
+ @param path: path to create folder on
|
|
+ @param name: desired name for folder
|
|
+ @return: Tuple of (success?, new dirname OR Error message)
|
|
+
|
|
+ """
|
|
+ if not os.path.isdir(path):
|
|
+ path = os.path.dirname(path)
|
|
+ folder = GetUniqueName(path, name)
|
|
+ try:
|
|
+ os.mkdir(folder)
|
|
+ except (OSError, IOError), msg:
|
|
+ return (False, str(msg))
|
|
+
|
|
+ return (True, folder)
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/histcache.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/histcache.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/histcache.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/histcache.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,131 @@
|
|
+###############################################################################
|
|
+# Name: histcache.py #
|
|
+# Purpose: History Cache #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: HistoryCache
|
|
+
|
|
+History cache that acts as a stack for managing a history list o
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: histcache.py 60613 2009-05-13 02:27:21Z CJP $"
|
|
+__revision__ = "$Revision: 60613 $"
|
|
+
|
|
+__all__ = [ 'HistoryCache', 'HIST_CACHE_UNLIMITED']
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Globals
|
|
+HIST_CACHE_UNLIMITED = -1
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+class HistoryCache(object):
|
|
+ def __init__(self, max_size=HIST_CACHE_UNLIMITED):
|
|
+ object.__init__(self)
|
|
+
|
|
+ # Attributes
|
|
+ self._list = list()
|
|
+ self.cpos = -1
|
|
+ self.max_size = max_size
|
|
+
|
|
+ def _Resize(self):
|
|
+ """Adjust cache size based on max size setting"""
|
|
+ if self.max_size != HIST_CACHE_UNLIMITED:
|
|
+ lsize = len(self._list)
|
|
+ if lsize:
|
|
+ adj = self.max_size - lsize
|
|
+ if adj < 0:
|
|
+ self._list.pop(0)
|
|
+ self.cpos = len(self._list) - 1
|
|
+
|
|
+ def Clear(self):
|
|
+ """Clear the history cache"""
|
|
+ del self._list
|
|
+ self._list = list()
|
|
+ self.cpos = -1
|
|
+
|
|
+ def GetSize(self):
|
|
+ """Get the current size of the cache
|
|
+ @return: int (number of items in the cache)
|
|
+
|
|
+ """
|
|
+ return len(self._list)
|
|
+
|
|
+ def GetMaxSize(self):
|
|
+ """Get the max size of the cache
|
|
+ @return: int
|
|
+
|
|
+ """
|
|
+ return self.max_size
|
|
+
|
|
+ def GetNextItem(self):
|
|
+ """Get the next item in the history cache, moving the
|
|
+ current postion towards the end of the cache.
|
|
+ @return: object or None if at end of list
|
|
+
|
|
+ """
|
|
+ item = None
|
|
+ if self.cpos < len(self._list) - 1:
|
|
+ self.cpos += 1
|
|
+ item = self._list[self.cpos]
|
|
+ return item
|
|
+
|
|
+ def GetPreviousItem(self):
|
|
+ """Get the previous item in the history cache, moving the
|
|
+ current postion towards the begining of the cache.
|
|
+ @return: object or None if at start of list
|
|
+
|
|
+ """
|
|
+ item = None
|
|
+ if self.cpos >= 0:
|
|
+ item = self._list[self.cpos]
|
|
+ self.cpos -= 1
|
|
+ return item
|
|
+
|
|
+ def HasPrevious(self):
|
|
+ """Are there more items to the left of the current position
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ more = self.cpos >= 0
|
|
+ return more
|
|
+
|
|
+ def HasNext(self):
|
|
+ """Are there more items to the right of the current position
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ if self.cpos == -1 and len(self._list):
|
|
+ more = True
|
|
+ else:
|
|
+ more = self.cpos >= 0 and self.cpos < len(self._list)
|
|
+ return more
|
|
+
|
|
+ def PutItem(self, item):
|
|
+ """Put an item on the top of the cache
|
|
+ @param item: object
|
|
+
|
|
+ """
|
|
+ if self.cpos != len(self._list) - 1:
|
|
+ self._list = self._list[:self.cpos]
|
|
+ self._list.append(item)
|
|
+ self.cpos += 1
|
|
+ self._Resize()
|
|
+
|
|
+ def SetMaxSize(self, max_size):
|
|
+ """Set the maximum size of the cache
|
|
+ @param max_size: int (HIST_CACHE_UNLIMITED for unlimited size)
|
|
+
|
|
+ """
|
|
+ assert max_size > 0 or max_size == 1, "Invalid max size"
|
|
+ self.max_size = max_size
|
|
+ self._Resize()
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/miscutil.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/miscutil.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/miscutil.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/miscutil.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,33 @@
|
|
+###############################################################################
|
|
+# Name: miscutil.py #
|
|
+# Purpose: Various helper functions. #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: MiscUtil
|
|
+
|
|
+Various helper functions
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: miscutil.py 60840 2009-05-31 16:00:50Z CJP $"
|
|
+__revision__ = "$Revision: 60840 $"
|
|
+
|
|
+__all__ = [ 'MinMax', ]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+def MinMax(arg1, arg2):
|
|
+ """Return an ordered tuple of the minumum and maximum value
|
|
+ of the two args.
|
|
+ @return: tuple
|
|
+
|
|
+ """
|
|
+ return min(arg1, arg2), max(arg1, arg2)
|
|
diff -Naur wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/searcheng.py wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/searcheng.py
|
|
--- wxPython-src-2.8.10.1-orig/wxPython/wx/tools/Editra/src/ebmlib/searcheng.py 1969-12-31 19:00:00.000000000 -0500
|
|
+++ wxPython-src-2.8.10.1/wxPython/wx/tools/Editra/src/ebmlib/searcheng.py 2009-06-06 03:48:10.000000000 -0400
|
|
@@ -0,0 +1,400 @@
|
|
+###############################################################################
|
|
+# Name: searcheng.py #
|
|
+# Purpose: Text search engine and utilities #
|
|
+# Author: Cody Precord <cprecord@editra.org> #
|
|
+# Copyright: (c) 2009 Cody Precord <staff@editra.org> #
|
|
+# Licence: wxWindows Licence #
|
|
+###############################################################################
|
|
+
|
|
+"""
|
|
+Editra Buisness Model Library: SearchEngine
|
|
+
|
|
+Text Search Engine for finding text and grepping files
|
|
+
|
|
+"""
|
|
+
|
|
+__author__ = "Cody Precord <cprecord@editra.org>"
|
|
+__cvsid__ = "$Id: searcheng.py 60680 2009-05-17 20:31:58Z CJP $"
|
|
+__revision__ = "$Revision: 60680 $"
|
|
+
|
|
+__all__ = [ 'SearchEngine', ]
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+# Imports
|
|
+import os
|
|
+import re
|
|
+import fnmatch
|
|
+import types
|
|
+from StringIO import StringIO
|
|
+
|
|
+# Local imports
|
|
+import fchecker
|
|
+
|
|
+#-----------------------------------------------------------------------------#
|
|
+
|
|
+class SearchEngine(object):
|
|
+ """Text Search Engine
|
|
+ All Search* methods are iterable generators
|
|
+ All Find* methods do a complete search and return the match collection
|
|
+ @summary: Text Search Engine
|
|
+ @todo: Add file filter support
|
|
+
|
|
+ """
|
|
+ def __init__(self, query, regex=True, down=True,
|
|
+ matchcase=True, wholeword=False):
|
|
+ """Initialize a search engine object
|
|
+ @param query: search string
|
|
+ @keyword regex: Is a regex search
|
|
+ @keyword down: Search down or up
|
|
+ @keyword matchcase: Match case
|
|
+ @keyword wholeword: Match whole word
|
|
+
|
|
+ """
|
|
+ object.__init__(self)
|
|
+
|
|
+ # Attributes
|
|
+ self._isregex = regex
|
|
+ self._next = down
|
|
+ self._matchcase = matchcase
|
|
+ self._wholeword = wholeword
|
|
+ self._unicode = False
|
|
+ self._query = query
|
|
+ self._regex = u''
|
|
+ self._pool = u''
|
|
+ self._lmatch = None # Last match object
|
|
+ self._filters = None # File Filters
|
|
+ self._formatter = lambda f, l, m: u"%s %d: %s" % (f, l+1, m)
|
|
+ self._CompileRegex()
|
|
+
|
|
+ def _CompileRegex(self):
|
|
+ """Prepare and compile the regex object based on the current state
|
|
+ and settings of the engine.
|
|
+ @postcondition: the engines regular expression is created
|
|
+
|
|
+ """
|
|
+ tmp = self._query
|
|
+ if not self._isregex:
|
|
+ tmp = re.escape(tmp)
|
|
+
|
|
+ if self._wholeword:
|
|
+ tmp = "\\b%s\\b" % tmp
|
|
+
|
|
+ flags = re.MULTILINE
|
|
+
|
|
+ if not self._matchcase:
|
|
+ flags |= re.IGNORECASE
|
|
+
|
|
+ if self._unicode:
|
|
+ flags |= re.UNICODE
|
|
+
|
|
+ try:
|
|
+ self._regex = re.compile(tmp, flags)
|
|
+ except:
|
|
+ self._regex = None
|
|
+
|
|
+ def ClearPool(self):
|
|
+ """Clear the search pool"""
|
|
+ del self._pool
|
|
+ self._pool = u""
|
|
+
|
|
+ def Find(self, spos=0):
|
|
+ """Find the next match based on the state of the search engine
|
|
+ @keyword spos: search start position
|
|
+ @return: tuple (match start pos, match end pos) or None if no match
|
|
+ @note: L{SetSearchPool} has been called to set search string
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return None
|
|
+
|
|
+ if self._next:
|
|
+ return self.FindNext(spos)
|
|
+ else:
|
|
+ if spos == 0:
|
|
+ spos = -1
|
|
+ return self.FindPrev(spos)
|
|
+
|
|
+ def FindAll(self):
|
|
+ """Find all the matches in the current context
|
|
+ @return: list of tuples [(start1, end1), (start2, end2), ]
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return list()
|
|
+
|
|
+ matches = [match for match in self._regex.finditer(self._pool)]
|
|
+ return matches
|
|
+
|
|
+ def FindAllLines(self):
|
|
+ """Find all the matches in the current context
|
|
+ @return: list of strings
|
|
+
|
|
+ """
|
|
+ rlist = list()
|
|
+ if self._regex is None:
|
|
+ return rlist
|
|
+
|
|
+ for lnum, line in enumerate(StringIO(self._pool)):
|
|
+ if self._regex.search(line) is not None:
|
|
+ rlist.append(self._formatter(u"Untitled", lnum, line))
|
|
+
|
|
+ return rlist
|
|
+
|
|
+ def FindNext(self, spos=0):
|
|
+ """Find the next match of the query starting at spos
|
|
+ @keyword spos: search start position in string
|
|
+ @return: tuple (match start pos, match end pos) or None if no match
|
|
+ @note: L{SetSearchPool} has been called to set the string to search in.
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return None
|
|
+
|
|
+ if spos < len(self._pool):
|
|
+ match = self._regex.search(self._pool[spos:])
|
|
+ if match is not None:
|
|
+ self._lmatch = match
|
|
+ return match.span()
|
|
+ return None
|
|
+
|
|
+ def FindPrev(self, spos=-1):
|
|
+ """Find the previous match of the query starting at spos
|
|
+ @keyword spos: search start position in string
|
|
+ @return: tuple (match start pos, match end pos)
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return None
|
|
+
|
|
+ if spos+1 < len(self._pool):
|
|
+ matches = [match for match in
|
|
+ self._regex.finditer(self._pool[:spos])]
|
|
+ if len(matches):
|
|
+ lmatch = matches[-1]
|
|
+ self._lmatch = lmatch
|
|
+ return (lmatch.start(), lmatch.end())
|
|
+ return None
|
|
+
|
|
+ def GetLastMatch(self):
|
|
+ """Get the last found match object from the previous L{FindNext} or
|
|
+ L{FindPrev} action.
|
|
+ @return: match object or None
|
|
+
|
|
+ """
|
|
+ return self._lmatch
|
|
+
|
|
+ def GetOptionsString(self):
|
|
+ """Get a string describing the search engines options"""
|
|
+ rstring = u"\"%s\" [ " % self._query
|
|
+ for desc, attr in (("regex: %s", self._isregex),
|
|
+ ("match case: %s", self._matchcase),
|
|
+ ("whole word: %s", self._wholeword)):
|
|
+ if attr:
|
|
+ rstring += (desc % u"on; ")
|
|
+ else:
|
|
+ rstring += (desc % u"off; ")
|
|
+ rstring += u"]"
|
|
+
|
|
+ return rstring
|
|
+
|
|
+ def GetQuery(self):
|
|
+ """Get the raw query string used by the search engine
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ return self._query
|
|
+
|
|
+ def GetQueryObject(self):
|
|
+ """Get the regex object used for the search. Will return None if
|
|
+ there was an error in creating the object.
|
|
+ @return: pattern object
|
|
+
|
|
+ """
|
|
+ return self._regex
|
|
+
|
|
+ def GetSearchPool(self):
|
|
+ """Get the search pool string for this L{SearchEngine}.
|
|
+ @return: string
|
|
+
|
|
+ """
|
|
+ return self._pool
|
|
+
|
|
+ def IsMatchCase(self):
|
|
+ """Is the engine set to a case sensitive search
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ return self._matchcase
|
|
+
|
|
+ def IsRegEx(self):
|
|
+ """Is the engine searching with the query as a regular expression
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ return self._isregex
|
|
+
|
|
+ def IsWholeWord(self):
|
|
+ """Is the engine set to search for wholeword matches
|
|
+ @return: bool
|
|
+
|
|
+ """
|
|
+ return self._wholeword
|
|
+
|
|
+ def SearchInBuffer(self, sbuffer):
|
|
+ """Search in the buffer
|
|
+ @param sbuffer: buffer like object
|
|
+ @todo: implement
|
|
+
|
|
+ """
|
|
+ raise NotImplementedError
|
|
+
|
|
+ def SearchInDirectory(self, directory, recursive=True):
|
|
+ """Search in all the files found in the given directory
|
|
+ @param directory: directory path
|
|
+ @keyword recursive: search recursivly
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return
|
|
+
|
|
+ # Get all files in the directories
|
|
+ paths = [os.path.join(directory, fname)
|
|
+ for fname in os.listdir(directory) if not fname.startswith('.')]
|
|
+
|
|
+ # Filter out files that don't match the current filter(s)
|
|
+ if self._filters is not None and len(self._filters):
|
|
+ filtered = list()
|
|
+ for fname in paths:
|
|
+ if os.path.isdir(fname):
|
|
+ filtered.append(fname)
|
|
+ continue
|
|
+
|
|
+ for pat in self._filters:
|
|
+ if fnmatch.fnmatch(fname, pat):
|
|
+ filtered.append(fname)
|
|
+ paths = filtered
|
|
+
|
|
+ # Begin searching in the paths
|
|
+ for path in paths:
|
|
+ if recursive and os.path.isdir(path):
|
|
+ # Recursive call to decend into directories
|
|
+ for match in self.SearchInDirectory(path, recursive):
|
|
+ yield match
|
|
+ else:
|
|
+ for match in self.SearchInFile(path):
|
|
+ yield match
|
|
+ return
|
|
+
|
|
+ def SearchInFile(self, fname):
|
|
+ """Search in a file for all lines with matches of the set query and
|
|
+ yield the results as they are found.
|
|
+ @param fname: filename
|
|
+ @todo: unicode handling
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return
|
|
+
|
|
+ checker = fchecker.FileTypeChecker()
|
|
+ if checker.IsReadableText(fname):
|
|
+ try:
|
|
+ fobj = open(fname, 'rb')
|
|
+ except (IOError, OSError):
|
|
+ return
|
|
+ else:
|
|
+ # Special token to signify start of a search
|
|
+ yield (None, fname)
|
|
+
|
|
+ for lnum, line in enumerate(fobj):
|
|
+ if self._regex.search(line) is not None:
|
|
+ yield self._formatter(fname, lnum, line)
|
|
+ fobj.close()
|
|
+ return
|
|
+
|
|
+ def SearchInFiles(self, flist):
|
|
+ """Search in a list of files and yield results as they are found.
|
|
+ @param flist: list of file names
|
|
+
|
|
+ """
|
|
+ if self._regex is None:
|
|
+ return
|
|
+
|
|
+ for fname in flist:
|
|
+ for match in self.SearchInFile(fname):
|
|
+ yield match
|
|
+ return
|
|
+
|
|
+ def SearchInString(self, sstring, startpos=0):
|
|
+ """Search in a string
|
|
+ @param sstring: string to search in
|
|
+ @keyword startpos: search start position
|
|
+
|
|
+ """
|
|
+ raise NotImplementedError
|
|
+
|
|
+ def SetFileFilters(self, filters):
|
|
+ """Set the file filters to specify what type of files to search in
|
|
+ the filter should be a list of wild card patterns to match.
|
|
+ @param filters: list of strings ['*.py', '*.pyw']
|
|
+
|
|
+ """
|
|
+ self._filters = filters
|
|
+
|
|
+ def SetFlags(self, isregex=None, matchcase=None, wholeword=None, down=None):
|
|
+ """Set the search engine flags. Leaving the parameter set to None
|
|
+ will not change the flag. Setting it to non None will change the value.
|
|
+ @keyword isregex: is regex search
|
|
+ @keyword matchcase: matchcase search
|
|
+ @keyword wholeword: wholeword search
|
|
+ @keyword down: search down or up
|
|
+
|
|
+ """
|
|
+ for attr, val in (('_isregex', isregex), ('_matchcase', matchcase),
|
|
+ ('_wholeword', wholeword), ('_next', down)):
|
|
+ if val is not None:
|
|
+ setattr(self, attr, val)
|
|
+ self._CompileRegex()
|
|
+
|
|
+ def SetMatchCase(self, case=True):
|
|
+ """Set whether the engine will use case sensative searches
|
|
+ @keyword case: bool
|
|
+
|
|
+ """
|
|
+ self._matchcase = case
|
|
+ self._CompileRegex()
|
|
+
|
|
+ def SetResultFormatter(self, funct):
|
|
+ """Set the result formatter function
|
|
+ @param funct: callable(filename, linenum, matchstr)
|
|
+
|
|
+ """
|
|
+ assert callable(funct)
|
|
+ self._formatter = funct
|
|
+
|
|
+ def SetSearchPool(self, pool):
|
|
+ """Set the search pool used by the Find methods
|
|
+ @param pool: string to search in
|
|
+
|
|
+ """
|
|
+ del self._pool
|
|
+ self._pool = pool
|
|
+ if isinstance(self._pool, types.UnicodeType):
|
|
+ self._unicode = True
|
|
+ self._CompileRegex()
|
|
+
|
|
+ def SetQuery(self, query):
|
|
+ """Set the search query
|
|
+ @param query: string
|
|
+
|
|
+ """
|
|
+ self._query = query
|
|
+ self._CompileRegex()
|
|
+
|
|
+ def SetUseRegex(self, use=True):
|
|
+ """Set whether the engine is using regular expresion searches or
|
|
+ not.
|
|
+ @keyword use: bool
|
|
+
|
|
+ """
|
|
+ self._isregex = use
|
|
+ self._CompileRegex()
|