Commits

Erik Grinaker  committed 9b4f955

added password checker dialog

  • Participants
  • Parent commits f0ee067

Comments (0)

Files changed (9)

 
 	* use better lock icon
 
+	* added a password checker dialog
+
 2005-03-17  Erik Grinaker <erikg@codepoet.no>
 
 	* fix potential crash on quit with some pygtk versions
 ============================
 
 New features:
+- option to autolock file after a period of inactivity
 - check password strength while entering, using cracklib
-- option to autolock file after a period of inactivity
 - ask user to reload file if it is changed outside revelation
 - added preference to select doubleclick action; go to, or edit
+- added password checker dialog
 - improved the preference dialog
 - improved user interface for copying passwords (and optionally
   usernames) to the clipboard
 0.4.x:
 - string cleanups
-- add "password strength" dialog
 - add import/export of PasswordSafe files
 - add import/export of GPasMan files
 - add import/export of zsafe files

File data/ui/actions.xml

 		</action>
 
 		<action>
+			<name>pwchecker</name>
+			<label>Password _Checker</label>
+			<stock>revelation-password-check</stock>
+			<description>Opens a password checker</description>
+		</action>
+
+		<action>
 			<name>pwgenerator</name>
 			<label>Password _Generator</label>
 			<stock>revelation-generate</stock>

File data/ui/menubar.xml

 			<menuitem action="view-statusbar" />
 			<separator />
 			<menuitem action="pwgenerator" />
+			<menuitem action="pwchecker" />
 			<menuitem action="view-passwords" />
 		</menu>
 

File src/lib/dialog.py

 
 
 
+class PasswordChecker(Utility):
+	"A password checker dialog"
+
+	def __init__(self, parent):
+		Utility.__init__(
+			self, parent, "Password Generator",
+			( ( gtk.STOCK_CLOSE, gtk.RESPONSE_CLOSE ), ( ui.STOCK_PASSWORD_CHECK, gtk.RESPONSE_OK ) )
+		)
+
+		self.set_modal(False)
+		self.set_size_request(300, -1)
+
+		self.section = self.add_section("Password Checker")
+
+		self.entry = ui.Entry()
+		self.tooltips.set_tip(self.entry, "Enter a password to check")
+		self.section.append_widget("Password", self.entry)
+
+		self.result = ui.ImageLabel()
+		self.tooltips.set_tip(self.result, "The result of the check")
+		self.section.append_widget(None, self.result, False)
+
+		self.connect("response", self.__cb_response)
+		self.response(gtk.RESPONSE_OK)
+
+
+	def __cb_response(self, widget, response):
+		"Callback for dialog responses"
+
+		if response == gtk.RESPONSE_OK:
+			password = self.entry.get_text()
+
+			try:
+				if len(password) == 0:
+					icon	= ui.STOCK_UNKNOWN
+					result	= "Enter a password to check"
+
+				else:
+					util.check_password(password)
+					icon	= ui.STOCK_PASSWORD_STRONG
+					result	= "The password is good"
+
+			except ValueError, result:
+				icon	= ui.STOCK_PASSWORD_WEAK
+				result	= "The password " + str(result)
+
+				result = result.replace("simplistic/systematic", "systematic")
+
+			self.result.set_text(result)
+			self.result.set_stock(icon, ui.ICON_SIZE_LABEL)
+
+		else:
+			self.destroy()
+
+
+	def run(self):
+		"Displays the dialog"
+
+		self.show_all()
+		self.get_button(0).grab_focus()
+
+		if EVENT_FILTER != None:
+			self.window.add_filter(EVENT_FILTER)
+
+
+
 class PasswordGenerator(Utility):
 	"A password generator dialog"
 

File src/lib/ui.py

 STOCK_NEXT			= "revelation-next"
 STOCK_OVERWRITE			= "revelation-overwrite"
 STOCK_PASSWORD_CHANGE		= "revelation-password-change"
+STOCK_PASSWORD_CHECK		= "revelation-password-check"
+STOCK_PASSWORD_STRONG		= "revelation-password-strong"
+STOCK_PASSWORD_WEAK		= "revelation-password-weak"
 STOCK_PREVIOUS			= "revelation-previous"
 STOCK_RELOAD			= "revelation-reload"
 STOCK_REMOVE			= "revelation-remove"
+STOCK_UNKNOWN			= "revelation-unknown"
 
 
 STOCK_ENTRY_FOLDER		= "revelation-folder"
 
 ICON_SIZE_DATAVIEW		= gtk.icon_size_from_name("revelation-dataview")
 ICON_SIZE_DROPDOWN		= gtk.icon_size_from_name("revelation-dropdown")
+ICON_SIZE_LABEL			= gtk.icon_size_from_name("revelation-label")
 ICON_SIZE_LOGO			= gtk.icon_size_from_name("revelation-logo")
 ICON_SIZE_TREEVIEW		= gtk.icon_size_from_name("revelation-treeview")
 
 if ICON_SIZE_DROPDOWN == gtk.ICON_SIZE_INVALID:
 	ICON_SIZE_DROPDOWN	= gtk.icon_size_register("revelation-dropdown", 18, 18)
 
+if ICON_SIZE_LABEL == gtk.ICON_SIZE_INVALID:
+	ICON_SIZE_LABEL		= gtk.icon_size_register("revelation-label", 24, 24)
+
 if ICON_SIZE_LOGO == gtk.ICON_SIZE_INVALID:
 	ICON_SIZE_LOGO		= gtk.icon_size_register("revelation-logo", 32, 32)
 
 			self.sizegroup = gtk.SizeGroup(gtk.SIZE_GROUP_HORIZONTAL)
 
 
-	def append_widget(self, title, widget):
+	def append_widget(self, title, widget, indent = True):
 		"Adds a widget to the section"
 
 		row = HBox()
 		row.set_spacing(12)
 		self.pack_start(row, False, False)
 
-		if self.title is not None:
+		if self.title is not None and indent == True:
 			row.pack_start(Label("   "), False, False)
 
 		if title is not None:
 class ImageLabel(gtk.Alignment):
 	"A label with an image"
 
-	def __init__(self, text, stock, size):
+	def __init__(self, text = None, stock = None, size = None):
 		gtk.Alignment.__init__(self, 0.5, 0.5, 0, 0)
 
 		self.hbox = HBox()
 
 		self.image = Image()
 		self.hbox.pack_start(self.image, False, False)
-		self.set_stock(stock, size)
-
-		self.label = Label(text, gtk.JUSTIFY_CENTER)
+
+		self.label = Label("", gtk.JUSTIFY_CENTER)
 		self.hbox.pack_start(self.label)
 
+		if text != None:
+			self.set_text(text)
+
+		if stock != None:
+			self.set_stock(stock, size)
+
 
 	def set_stock(self, stock, size):
 		"Sets the image"
 			( STOCK_NEXT,		"Ne_xt",	gtk.STOCK_GO_FORWARD ),
 			( STOCK_OVERWRITE,	"_Overwrite",	gtk.STOCK_SAVE_AS ),
 			( STOCK_PASSWORD_CHANGE,"_Change",	"stock_lock-ok" ),
+			( STOCK_PASSWORD_CHECK,	"_Check",	"stock_lock-ok" ),
+			( STOCK_PASSWORD_STRONG,"",		"stock_lock-ok" ),
+			( STOCK_PASSWORD_WEAK,	"",		"stock_lock-broken" ),
 			( STOCK_PREVIOUS,	"Pre_vious",	gtk.STOCK_GO_BACK ),
 			( STOCK_RELOAD,		"_Reload",	gtk.STOCK_REFRESH ),
-			( STOCK_REMOVE,		"Re_move",	gtk.STOCK_DELETE )
+			( STOCK_REMOVE,		"Re_move",	gtk.STOCK_DELETE ),
+			( STOCK_UNKNOWN,	"Unknown",	gtk.STOCK_DIALOG_QUESTION ),
 		)
 
 		for id, name, icon in items:
 			self.add(id, iconset)
 
 		else:
-			self.load_stock_icon(id, icon, ( gtk.ICON_SIZE_SMALL_TOOLBAR, gtk.ICON_SIZE_LARGE_TOOLBAR, gtk.ICON_SIZE_MENU, gtk.ICON_SIZE_BUTTON ))
+			self.load_stock_icon(id, icon, ( gtk.ICON_SIZE_SMALL_TOOLBAR, gtk.ICON_SIZE_LARGE_TOOLBAR, gtk.ICON_SIZE_MENU, gtk.ICON_SIZE_BUTTON, ICON_SIZE_LABEL ))
 
 
 	def load_icon(self, id, size):

File src/lib/util.py

 		chars[char] += 1
 
 	if len(chars) < 6:
-		raise ValueError, "has too few different characters"
+		raise ValueError, "isn't varied enough"
 
 
 	# check if the password is a palindrome
 			cred += cred_other
 
 	if cred < limit:
-		raise ValueError, "is too simple"
+		raise ValueError, "is too weak"
 
 
 	# check password with cracklib

File src/revelation.in

 			"help-about"		: lambda w: dialog.About(self).run(),
 			"help-homepage"		: lambda w: gnome.url_show(config.URL),
 			"prefs"			: lambda w: dialog.Preferences(self, self.config).run(),
+			"pwchecker"		: lambda w: dialog.PasswordChecker(self).run(),
 			"pwgenerator"		: lambda w: dialog.PasswordGenerator(self, self.config).run(),
 			"quit"			: self.__cb_quit,
 			"redo"			: lambda w: self.redo(),