|  | @@ -5,14 +5,50 @@ to view and create/edit file comments
 | 
											
												
													
														|  |  comments are stored in xattr user.xdg.comment
 |  |  comments are stored in xattr user.xdg.comment
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  depends on python-pyxattr
 |  |  depends on python-pyxattr
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +because files are so often over-written, save a copy
 | 
											
												
													
														|  | 
 |  | +of the comments in a database ~/.dirnotes.db
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +these comments stick to the symlink
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  |  """
 |  |  """
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  COMMENT_KEY = "user.xdg.comment"
 |  |  COMMENT_KEY = "user.xdg.comment"
 | 
											
												
													
														|  | 
 |  | +DATABASE_NAME = "~/.dirnotes.db"
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  import sys,os,argparse
 |  |  import sys,os,argparse
 | 
											
												
													
														|  |  from PyQt4.QtGui import *
 |  |  from PyQt4.QtGui import *
 | 
											
												
													
														|  |  from PyQt4 import QtGui, QtCore
 |  |  from PyQt4 import QtGui, QtCore
 | 
											
												
													
														|  | -import xattr
 |  | 
 | 
											
												
													
														|  | 
 |  | +import xattr, sqlite3, time
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +DATABASE_NAME = os.path.expanduser(DATABASE_NAME)
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +class DataBase:
 | 
											
												
													
														|  | 
 |  | +	''' the date here is the st_mtime, a float
 | 
											
												
													
														|  | 
 |  | +		and the filName is a fully qualified name'''
 | 
											
												
													
														|  | 
 |  | +	def __init__(self):
 | 
											
												
													
														|  | 
 |  | +		try:
 | 
											
												
													
														|  | 
 |  | +			self.db = sqlite3.connect(DATABASE_NAME)
 | 
											
												
													
														|  | 
 |  | +		except sqlite3.OperationalError:
 | 
											
												
													
														|  | 
 |  | +			print("Database %s not found" % DATABASE_NAME)
 | 
											
												
													
														|  | 
 |  | +			raise OperationalError
 | 
											
												
													
														|  | 
 |  | +		c = self.db.cursor()
 | 
											
												
													
														|  | 
 |  | +		try:
 | 
											
												
													
														|  | 
 |  | +			c.execute("select * from dirnotes")
 | 
											
												
													
														|  | 
 |  | +		except sqlite3.OperationalError:
 | 
											
												
													
														|  | 
 |  | +			print("Table %s created" % ("dirnotes"))
 | 
											
												
													
														|  | 
 |  | +			c.execute("create table dirnotes (name, date, size, comment)")
 | 
											
												
													
														|  | 
 |  | +		
 | 
											
												
													
														|  | 
 |  | +	def getData(self, fileName):
 | 
											
												
													
														|  | 
 |  | +		c = self.db.cursor()
 | 
											
												
													
														|  | 
 |  | +		c.execute("select * from dirnotes where name=?",(fileName,))
 | 
											
												
													
														|  | 
 |  | +		return c.fetchone()
 | 
											
												
													
														|  | 
 |  | +	def setData(self, fileName, _date, _size, comment):
 | 
											
												
													
														|  | 
 |  | +		c = self.db.cursor()
 | 
											
												
													
														|  | 
 |  | +		c.execute("insert into dirnotes values (?,?,?,?)",
 | 
											
												
													
														|  | 
 |  | +			(fileName, _date, _size, comment))
 | 
											
												
													
														|  | 
 |  | +		self.db.commit()
 | 
											
												
													
														|  | 
 |  | +		return True
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  def parse():
 |  |  def parse():
 | 
											
												
													
														|  |  	parser = argparse.ArgumentParser(description='dirnotes application')
 |  |  	parser = argparse.ArgumentParser(description='dirnotes application')
 | 
											
										
											
												
													
														|  | @@ -25,60 +61,103 @@ def parse():
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  def debug(x):
 |  |  def debug(x):
 | 
											
												
													
														|  |  	print("debugging " + x.text() + " r:" + str(x.row()) + " c:" + str(x.column()))
 |  |  	print("debugging " + x.text() + " r:" + str(x.row()) + " c:" + str(x.column()))
 | 
											
												
													
														|  | 
 |  | +	the_file = dn.files[x.row()]
 | 
											
												
													
														|  | 
 |  | +	the_file.setComment(str(x.text())) 
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +class FileObj():
 | 
											
												
													
														|  | 
 |  | +	def __init__(self, fileName):
 | 
											
												
													
														|  | 
 |  | +		self.fileName = fileName
 | 
											
												
													
														|  | 
 |  | +		# also get the date, directory or not, etc
 | 
											
												
													
														|  | 
 |  | +		self.directory = "a"
 | 
											
												
													
														|  | 
 |  | +		self.comment = ''
 | 
											
												
													
														|  | 
 |  | +		try:
 | 
											
												
													
														|  | 
 |  | +			self.comment = xattr.getxattr(fileName,COMMENT_KEY)
 | 
											
												
													
														|  | 
 |  | +		except:
 | 
											
												
													
														|  | 
 |  | +			pass
 | 
											
												
													
														|  | 
 |  | +	def getName(self):
 | 
											
												
													
														|  | 
 |  | +		return self.fileName
 | 
											
												
													
														|  | 
 |  | +	def getComment(self):
 | 
											
												
													
														|  | 
 |  | +		return self.comment
 | 
											
												
													
														|  | 
 |  | +	def setComment(self,newComment):
 | 
											
												
													
														|  | 
 |  | +		self.comment = newComment
 | 
											
												
													
														|  | 
 |  | +		try:
 | 
											
												
													
														|  | 
 |  | +			xattr.setxattr(self.fileName,COMMENT_KEY,self.comment)
 | 
											
												
													
														|  | 
 |  | +		except:
 | 
											
												
													
														|  | 
 |  | +			print("problem setting the comment on file %s" % self.fileName)
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  |  class DirNotes(QMainWindow):
 |  |  class DirNotes(QMainWindow):
 | 
											
												
													
														|  | -	def __init__(self, parent=None):
 |  | 
 | 
											
												
													
														|  | 
 |  | +	def __init__(self, filename, parent=None):
 | 
											
												
													
														|  |  		super(DirNotes,self).__init__(parent)
 |  |  		super(DirNotes,self).__init__(parent)
 | 
											
												
													
														|  | -		pass
 |  | 
 | 
											
												
													
														|  | 
 |  | +		win = QWidget()
 | 
											
												
													
														|  | 
 |  | +		self.setCentralWidget(win)
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		lb = QTableWidget()
 | 
											
												
													
														|  | 
 |  | +		lb.setColumnCount(2)
 | 
											
												
													
														|  | 
 |  | +		lb.horizontalHeader().setResizeMode( 1, QHeaderView.Stretch );
 | 
											
												
													
														|  | 
 |  | +		# resize the comments column
 | 
											
												
													
														|  | 
 |  | +		# and resize the parent window to match the directory size
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		# allow multiple entries on the line at this point
 | 
											
												
													
														|  | 
 |  | +		#d = os.listdir(p.filename[0])
 | 
											
												
													
														|  | 
 |  | +		#d.sort()
 | 
											
												
													
														|  | 
 |  | +		current, dirs, files = os.walk(filename,followlinks=True).next()
 | 
											
												
													
														|  | 
 |  | +		dirs = map(lambda x:x+'/', dirs)
 | 
											
												
													
														|  | 
 |  | +		dirs.sort()
 | 
											
												
													
														|  | 
 |  | +		files.sort()
 | 
											
												
													
														|  | 
 |  | +		
 | 
											
												
													
														|  | 
 |  | +		d = dirs + files
 | 
											
												
													
														|  | 
 |  | +		lb.setRowCount(len(d))
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		self.files = []
 | 
											
												
													
														|  | 
 |  | +		for i in range(len(d)):
 | 
											
												
													
														|  | 
 |  | +			this_file = FileObj(d[i])
 | 
											
												
													
														|  | 
 |  | +			self.files = self.files + [this_file]
 | 
											
												
													
														|  | 
 |  | +			item = QTableWidgetItem(this_file.getName())
 | 
											
												
													
														|  | 
 |  | +			item.setFlags(QtCore.Qt.ItemIsEnabled)
 | 
											
												
													
														|  | 
 |  | +			lb.setItem(i,0,item)
 | 
											
												
													
														|  | 
 |  | +			#lb.itemAt(i,0).setFlags(Qt.ItemIsEnabled) #NoItemFlags)
 | 
											
												
													
														|  | 
 |  | +			comment = this_file.getComment()
 | 
											
												
													
														|  | 
 |  | +			lb.setItem(i,1,QTableWidgetItem(comment))
 | 
											
												
													
														|  | 
 |  | +		lb.setHorizontalHeaderItem(0,QTableWidgetItem("file"))
 | 
											
												
													
														|  | 
 |  | +		lb.setHorizontalHeaderItem(1,QTableWidgetItem("comment"))
 | 
											
												
													
														|  | 
 |  | +		lb.resizeColumnsToContents()
 | 
											
												
													
														|  | 
 |  | +		lb.verticalHeader().setVisible(False)
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		e = QLabel("View and edit file comments stored in extended attributes user.xdg.comment")
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		layout = QVBoxLayout()
 | 
											
												
													
														|  | 
 |  | +		layout.addWidget(e)
 | 
											
												
													
														|  | 
 |  | +		layout.addWidget(lb)
 | 
											
												
													
														|  | 
 |  | +		win.setLayout(layout)
 | 
											
												
													
														|  | 
 |  | +		
 | 
											
												
													
														|  | 
 |  | +		lb.itemChanged.connect(debug)
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +		QShortcut(QKeySequence("Ctrl+Q"), self, self.close)	
 | 
											
												
													
														|  | 
 |  | +		self.setWindowTitle("test")
 | 
											
												
													
														|  | 
 |  | +		self.setMinimumSize(600,400)
 | 
											
												
													
														|  |  	def closeEvent(self,e):
 |  |  	def closeEvent(self,e):
 | 
											
												
													
														|  |  		print("closing")
 |  |  		print("closing")
 | 
											
												
													
														|  |  		
 |  |  		
 | 
											
												
													
														|  |  if __name__=="__main__":
 |  |  if __name__=="__main__":
 | 
											
												
													
														|  |  	p = parse()
 |  |  	p = parse()
 | 
											
												
													
														|  | -
 |  | 
 | 
											
												
													
														|  | -	a = QApplication([])
 |  | 
 | 
											
												
													
														|  | -
 |  | 
 | 
											
												
													
														|  | -	# allow multiple entries on the line at this point
 |  | 
 | 
											
												
													
														|  | -	d = os.listdir(p.filename[0])
 |  | 
 | 
											
												
													
														|  | -	d.sort()
 |  | 
 | 
											
												
													
														|  | -
 |  | 
 | 
											
												
													
														|  | -	lb = QTableWidget()
 |  | 
 | 
											
												
													
														|  | -	lb.setRowCount(len(d))
 |  | 
 | 
											
												
													
														|  | -	lb.setColumnCount(2)
 |  | 
 | 
											
												
													
														|  | -	lb.horizontalHeader().setResizeMode( 1, QHeaderView.Stretch );
 |  | 
 | 
											
												
													
														|  | -	# resize the comments column
 |  | 
 | 
											
												
													
														|  | -	# and resize the parent window to match the directory size
 |  | 
 | 
											
												
													
														|  | -	for i in range(len(d)):
 |  | 
 | 
											
												
													
														|  | -		item = QTableWidgetItem(d[i])
 |  | 
 | 
											
												
													
														|  | -		item.setFlags(QtCore.Qt.ItemIsEnabled)
 |  | 
 | 
											
												
													
														|  | -		lb.setItem(i,0,item)
 |  | 
 | 
											
												
													
														|  | -		#lb.itemAt(i,0).setFlags(Qt.ItemIsEnabled) #NoItemFlags)
 |  | 
 | 
											
												
													
														|  | -		comment = ""
 |  | 
 | 
											
												
													
														|  | -		try:
 |  | 
 | 
											
												
													
														|  | -			comment = xattr.getxattr(d[i],COMMENT_KEY)
 |  | 
 | 
											
												
													
														|  | -		except:
 |  | 
 | 
											
												
													
														|  | -			continue
 |  | 
 | 
											
												
													
														|  | -		lb.setItem(i,1,QTableWidgetItem(comment))
 |  | 
 | 
											
												
													
														|  | -	lb.setHorizontalHeaderItem(0,QTableWidgetItem("file"))
 |  | 
 | 
											
												
													
														|  | -	lb.setHorizontalHeaderItem(1,QTableWidgetItem("comment"))
 |  | 
 | 
											
												
													
														|  | -	lb.resizeColumnsToContents()
 |  | 
 | 
											
												
													
														|  | -
 |  | 
 | 
											
												
													
														|  | -	win = QWidget()
 |  | 
 | 
											
												
													
														|  | -	layout = QVBoxLayout()
 |  | 
 | 
											
												
													
														|  | -	win.setLayout(layout)
 |  | 
 | 
											
												
													
														|  | -	e = QLabel(win)
 |  | 
 | 
											
												
													
														|  | -	e.setText("View and edit file comments stored in extended attributes user.xdg.comment")
 |  | 
 | 
											
												
													
														|  | -	layout.addWidget(e)
 |  | 
 | 
											
												
													
														|  | -	layout.addWidget(lb)
 |  | 
 | 
											
												
													
														|  |  	
 |  |  	
 | 
											
												
													
														|  | -	lb.itemChanged.connect(debug)
 |  | 
 | 
											
												
													
														|  | 
 |  | +	db = DataBase()
 | 
											
												
													
														|  | 
 |  | +	db.setData("a",float(time.time()),12345,"a comment")
 | 
											
												
													
														|  | 
 |  | +	print(db.getData("a"))
 | 
											
												
													
														|  | 
 |  | +	(f,d,s,c) = db.getData("a")
 | 
											
												
													
														|  | 
 |  | +	print(time.strftime("%Y-%m-%d %H:%M:%S",time.localtime(d)))
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  | -	QShortcut(QKeySequence("Ctrl+Q"), win, win.close)	
 |  | 
 | 
											
												
													
														|  | -	win.setWindowTitle("test")
 |  | 
 | 
											
												
													
														|  | -	win.setMinimumSize(600,400)
 |  | 
 | 
											
												
													
														|  | -	win.show()
 |  | 
 | 
											
												
													
														|  | 
 |  | +	a = QApplication([])
 | 
											
												
													
														|  | 
 |  | +	dn = DirNotes(p.filename[0])
 | 
											
												
													
														|  | 
 |  | +	dn.show()
 | 
											
												
													
														|  |  	
 |  |  	
 | 
											
												
													
														|  |  	a.exec_()
 |  |  	a.exec_()
 | 
											
												
													
														|  |  	
 |  |  	
 | 
											
												
													
														|  |  	#xattr.setxattr(filename,COMMENT_KEY,commentText)
 |  |  	#xattr.setxattr(filename,COMMENT_KEY,commentText)
 | 
											
												
													
														|  |  
 |  |  
 | 
											
												
													
														|  | 
 |  | +
 | 
											
												
													
														|  | 
 |  | +''' files from directories
 | 
											
												
													
														|  | 
 |  | +use os.isfile()
 | 
											
												
													
														|  | 
 |  | +os.isdir()
 | 
											
												
													
														|  | 
 |  | +current, dirs, files = os.walk("path").next()
 | 
											
												
													
														|  | 
 |  | +possible set folllowLinks=True'''
 |