From 5a1c30f2493d501241bfe353bbe35bf43e61e236 Mon Sep 17 00:00:00 2001 From: Scott Dennison Date: Sat, 3 May 2014 22:02:57 +0100 Subject: [PATCH 1/2] Fix get-logins-all, Add get-logins-by-names. Fixed get-logins-all to actually do what it says in its name, rather than a unpredictable subset due to incorrect regular expression use, and also added get-logins-by-names, to allow returning of multiple non-linked credentials. --- KeePassHttp.plgx | Bin 157492 -> 158874 bytes KeePassHttp/Handlers.cs | 158 ++++++++++++++++++++++++--------- KeePassHttp/KeePassHttp.cs | 4 +- KeePassHttp/KeePassHttp.csproj | 3 +- KeePassHttp/Protocol.cs | 8 +- latest-version.txt | 2 +- update-version.txt | 3 - 7 files changed, 128 insertions(+), 50 deletions(-) delete mode 100644 update-version.txt diff --git a/KeePassHttp.plgx b/KeePassHttp.plgx index 6d364963fa98e922f8356c8615616744ebebe389..02a24a28ee52451003111b037472ffb8f275aed5 100644 GIT binary patch delta 15600 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 A`yUe)DAV|3Wss)lNw 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 diff --git a/KeePassHttp/Handlers.cs b/KeePassHttp/Handlers.cs index 48eb44d..2f49428 100644 --- a/KeePassHttp/Handlers.cs +++ b/KeePassHttp/Handlers.cs @@ -85,15 +85,14 @@ private void GetAllLoginsHandler(Request r, Response resp, Aes aes) if (!VerifyRequest(r, aes)) return; - var list = new PwObjectList(); - var root = host.Database.RootGroup; var parms = MakeSearchParameters(); - parms.SearchString = @"^[A-Za-z0-9:/-]+\.[A-Za-z0-9:/-]+$"; // match anything looking like a domain or url + parms.SearchString = "^.*$"; + + var list = root.GetEntries(true); - root.SearchEntries(parms, list); foreach (var entry in list) { var name = entry.Strings.ReadSafe(PwDefs.TitleField); @@ -429,43 +428,7 @@ private void GetLoginsHandler(Request r, Response resp, Aes aes) itemsList = items2.ToList(); } - foreach (var entryDatabase in itemsList) - { - var e = PrepareElementForResponseEntries(configOpt, entryDatabase); - resp.Entries.Add(e); - } - - if (itemsList.Count > 0) - { - var names = (from e in resp.Entries select e.Name).Distinct(); - var n = String.Join("\n ", names.ToArray()); - - if (configOpt.ReceiveCredentialNotification) - ShowNotification(String.Format("{0}: {1} is receiving credentials for:\n {2}", r.Id, host, n)); - } - - resp.Success = true; - resp.Id = r.Id; - SetResponseVerifier(resp, aes); - - foreach (var entry in resp.Entries) - { - entry.Name = CryptoTransform(entry.Name, false, true, aes, CMode.ENCRYPT); - entry.Login = CryptoTransform(entry.Login, false, true, aes, CMode.ENCRYPT); - entry.Uuid = CryptoTransform(entry.Uuid, false, true, aes, CMode.ENCRYPT); - entry.Password = CryptoTransform(entry.Password, false, true, aes, CMode.ENCRYPT); - - if (entry.StringFields != null) - { - foreach (var sf in entry.StringFields) - { - sf.Key = CryptoTransform(sf.Key, false, true, aes, CMode.ENCRYPT); - sf.Value = CryptoTransform(sf.Value, false, true, aes, CMode.ENCRYPT); - } - } - } - - resp.Count = resp.Entries.Count; + CompleteGetLoginsResult(itemsList,configOpt,resp,r.Id,host,aes); } else { @@ -475,6 +438,119 @@ private void GetLoginsHandler(Request r, Response resp, Aes aes) } } + private void CompleteGetLoginsResult(List itemsList, ConfigOpt configOpt, Response resp, String rId, String host, Aes aes) + { + foreach (var entryDatabase in itemsList) + { + var e = PrepareElementForResponseEntries(configOpt, entryDatabase); + resp.Entries.Add(e); + } + + if (itemsList.Count > 0) + { + var names = (from e in resp.Entries select e.Name).Distinct(); + var n = String.Join("\n ", names.ToArray()); + + if (configOpt.ReceiveCredentialNotification) + { + String notificationMessage; + if (host == null) + { + notificationMessage = rId; + } + else + { + notificationMessage = String.Format("{0}: {1}", rId, host); + } + notificationMessage = String.Format("{0} is receiving credentials for:\n {1}", notificationMessage, n); + ShowNotification(notificationMessage); + } + } + + resp.Success = true; + resp.Id = rId; + SetResponseVerifier(resp, aes); + + foreach (var entry in resp.Entries) + { + entry.Name = CryptoTransform(entry.Name, false, true, aes, CMode.ENCRYPT); + entry.Login = CryptoTransform(entry.Login, false, true, aes, CMode.ENCRYPT); + entry.Uuid = CryptoTransform(entry.Uuid, false, true, aes, CMode.ENCRYPT); + entry.Password = CryptoTransform(entry.Password, false, true, aes, CMode.ENCRYPT); + + if (entry.StringFields != null) + { + foreach (var sf in entry.StringFields) + { + sf.Key = CryptoTransform(sf.Key, false, true, aes, CMode.ENCRYPT); + sf.Value = CryptoTransform(sf.Value, false, true, aes, CMode.ENCRYPT); + } + } + } + + resp.Count = resp.Entries.Count; + } + + private void GetLoginsByNamesHandler(Request r, Response resp, Aes aes) + { + if (!VerifyRequest(r, aes)) + return; + + if (r.Names == null) + { + return; + } + List decryptedNames = new List(); + foreach (String name in r.Names) { + if (name != null) { + decryptedNames.Add(CryptoTransform(name, true, false, aes, CMode.DECRYPT)); + } + } + + List listDatabases = new List(); + + var configOpt = new ConfigOpt(this.host.CustomConfig); + if (configOpt.SearchInAllOpenedDatabases) + { + foreach (PwDocument doc in host.MainWindow.DocumentManager.Documents) + { + if (doc.Database.IsOpen) + { + listDatabases.Add(doc.Database); + } + } + } + else + { + listDatabases.Add(host.Database); + } + + var listEntries = new List(); + foreach (PwDatabase db in listDatabases) + { + foreach (var le in db.RootGroup.GetEntries(true)) { + var title = le.Strings.ReadSafe(PwDefs.TitleField); + bool titleMatched = false; + if (title != null) { + foreach (String name in decryptedNames) + { + if (name.Equals(title)) + { + titleMatched = true; + break; + } + } + } + if (titleMatched) + { + listEntries.Add(new PwEntryDatabase(le, db)); + } + } + } + + CompleteGetLoginsResult(listEntries, configOpt, resp, r.Id, null, aes); + } + private ResponseEntry PrepareElementForResponseEntries(ConfigOpt configOpt, PwEntryDatabase entryDatabase) { var name = entryDatabase.entry.Strings.ReadSafe(PwDefs.TitleField); diff --git a/KeePassHttp/KeePassHttp.cs b/KeePassHttp/KeePassHttp.cs index 0cc3c5c..bb4efcb 100644 --- a/KeePassHttp/KeePassHttp.cs +++ b/KeePassHttp/KeePassHttp.cs @@ -46,7 +46,6 @@ public sealed partial class KeePassHttpExt : Plugin /// /// TODO make configurable /// - private int port = DEFAULT_PORT; private const string HTTP_PREFIX = "http://localhost:"; //private const string HTTPS_PREFIX = "https://localhost:"; //private int HTTPS_PORT = DEFAULT_PORT + 1; @@ -55,7 +54,7 @@ public sealed partial class KeePassHttpExt : Plugin Dictionary handlers = new Dictionary(); //public string UpdateUrl = ""; - public override string UpdateUrl { get { return "https://passifox.appspot.com/kph/latest-version.txt"; } } + public override string UpdateUrl { get { return "https://raw.githubusercontent.com/DarthCrap/keepasshttp/master/latest-version.txt"; } } private SearchParameters MakeSearchParameters() { @@ -190,6 +189,7 @@ public override bool Initialize(IPluginHost host) handlers.Add(Request.TEST_ASSOCIATE, TestAssociateHandler); handlers.Add(Request.ASSOCIATE, AssociateHandler); handlers.Add(Request.GET_LOGINS, GetLoginsHandler); + handlers.Add(Request.GET_LOGINS_BY_NAMES, GetLoginsByNamesHandler); handlers.Add(Request.GET_LOGINS_COUNT, GetLoginsCountHandler); handlers.Add(Request.GET_ALL_LOGINS, GetAllLoginsHandler); handlers.Add(Request.SET_LOGIN, SetLoginHandler); diff --git a/KeePassHttp/KeePassHttp.csproj b/KeePassHttp/KeePassHttp.csproj index 51569ee..b4e24c6 100644 --- a/KeePassHttp/KeePassHttp.csproj +++ b/KeePassHttp/KeePassHttp.csproj @@ -33,8 +33,7 @@ - C:\Program Files (x86)\KeePass Password Safe 2\KeePass.exe - False + ..\..\..\Dropbox\Software\Useful Applications\KeePass\KeePass.exe .\Newtonsoft.Json.dll diff --git a/KeePassHttp/Protocol.cs b/KeePassHttp/Protocol.cs index af29db1..c5428c5 100644 --- a/KeePassHttp/Protocol.cs +++ b/KeePassHttp/Protocol.cs @@ -61,6 +61,7 @@ public class Request { public const string GET_LOGINS = "get-logins"; public const string GET_LOGINS_COUNT = "get-logins-count"; + public const string GET_LOGINS_BY_NAMES = "get-logins-by-names"; public const string GET_ALL_LOGINS = "get-all-logins"; public const string SET_LOGIN = "set-login"; public const string ASSOCIATE = "associate"; @@ -92,6 +93,11 @@ public class Request /// public string Url; + /// + /// Always encrypted, used get-logins-by-names + /// + public List Names; + /// /// Always encrypted, used with get-login /// @@ -129,7 +135,7 @@ public Response(string request, string hash) { RequestType = request; - if (request == Request.GET_LOGINS || request == Request.GET_ALL_LOGINS || request == Request.GENERATE_PASSWORD) + if (request == Request.GET_LOGINS || request == Request.GET_ALL_LOGINS || request == Request.GET_LOGINS_BY_NAMES || request == Request.GENERATE_PASSWORD) Entries = new List(); else Entries = null; diff --git a/latest-version.txt b/latest-version.txt index 3927bff..f84220a 100644 --- a/latest-version.txt +++ b/latest-version.txt @@ -1,3 +1,3 @@ : -KeePassHttp:1.8.3.0 +KeePass-DarthCrap:1.8.3.0 : diff --git a/update-version.txt b/update-version.txt deleted file mode 100644 index 3927bff..0000000 --- a/update-version.txt +++ /dev/null @@ -1,3 +0,0 @@ -: -KeePassHttp:1.8.3.0 -: From 2b11a6ea6232b281b9c3151b800dc287ee4e11c5 Mon Sep 17 00:00:00 2001 From: Scott Dennison Date: Sat, 15 Aug 2015 11:54:59 +0100 Subject: [PATCH 2/2] Tidied up commit 5a1c30f2493d501241bfe353bbe35bf43e61e236 by removing white-space, unused variables, recompiling pglx and removing some unnecessary changes, so that it is hopefully ready for a pull request. --- KeePassHttp.plgx | Bin 157117 -> 159237 bytes KeePassHttp/Handlers.cs | 232 ++++++++++++++++----------------- KeePassHttp/KeePassHttp.cs | 2 +- KeePassHttp/KeePassHttp.csproj | 3 +- KeePassHttp/Protocol.cs | 10 +- 5 files changed, 122 insertions(+), 125 deletions(-) diff --git a/KeePassHttp.plgx b/KeePassHttp.plgx index 52609afe6eb58b7b213bc32e43602dba2989c313..6e1cce5b29c84697166d612498f15a253318139c 100644 GIT binary patch delta 20672 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 Q15-*oV^A2k1ylmK5rBtwDgXcg delta 18529 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

pg?W0Aj3Vw%2rt#@mk)K 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 L5&^eYTmr5U{fxZq diff --git a/KeePassHttp/Handlers.cs b/KeePassHttp/Handlers.cs index 5760f49..3f9a19b 100644 --- a/KeePassHttp/Handlers.cs +++ b/KeePassHttp/Handlers.cs @@ -87,11 +87,7 @@ private void GetAllLoginsHandler(Request r, Response resp, Aes aes) var root = host.Database.RootGroup; - var parms = MakeSearchParameters(); - - parms.SearchString = "^.*$"; - - var list = root.GetEntries(true); + var list = root.GetEntries(true); foreach (var entry in list) { @@ -369,7 +365,7 @@ orderby e.entry.UsageCount itemsList = items2.ToList(); } - CompleteGetLoginsResult(itemsList,configOpt,resp,r.Id,host,aes); + CompleteGetLoginsResult(itemsList,configOpt,resp,r.Id,host,aes); } else { @@ -419,118 +415,118 @@ private int LevenshteinDistance(string source, string target) return distance[currentRow, m]; } - private void CompleteGetLoginsResult(List itemsList, ConfigOpt configOpt, Response resp, String rId, String host, Aes aes) - { - foreach (var entryDatabase in itemsList) - { - var e = PrepareElementForResponseEntries(configOpt, entryDatabase); - resp.Entries.Add(e); - } - - if (itemsList.Count > 0) - { - var names = (from e in resp.Entries select e.Name).Distinct(); - var n = String.Join("\n ", names.ToArray()); - - if (configOpt.ReceiveCredentialNotification) - { - String notificationMessage; - if (host == null) - { - notificationMessage = rId; - } - else - { - notificationMessage = String.Format("{0}: {1}", rId, host); - } - notificationMessage = String.Format("{0} is receiving credentials for:\n {1}", notificationMessage, n); - ShowNotification(notificationMessage); - } - } - - resp.Success = true; - resp.Id = rId; - SetResponseVerifier(resp, aes); - - foreach (var entry in resp.Entries) - { - entry.Name = CryptoTransform(entry.Name, false, true, aes, CMode.ENCRYPT); - entry.Login = CryptoTransform(entry.Login, false, true, aes, CMode.ENCRYPT); - entry.Uuid = CryptoTransform(entry.Uuid, false, true, aes, CMode.ENCRYPT); - entry.Password = CryptoTransform(entry.Password, false, true, aes, CMode.ENCRYPT); - - if (entry.StringFields != null) - { - foreach (var sf in entry.StringFields) - { - sf.Key = CryptoTransform(sf.Key, false, true, aes, CMode.ENCRYPT); - sf.Value = CryptoTransform(sf.Value, false, true, aes, CMode.ENCRYPT); - } - } - } - - resp.Count = resp.Entries.Count; - } - - private void GetLoginsByNamesHandler(Request r, Response resp, Aes aes) - { - if (!VerifyRequest(r, aes)) - return; - - if (r.Names == null) - { - return; - } - List decryptedNames = new List(); - foreach (String name in r.Names) { - if (name != null) { - decryptedNames.Add(CryptoTransform(name, true, false, aes, CMode.DECRYPT)); - } - } - - List listDatabases = new List(); - - var configOpt = new ConfigOpt(this.host.CustomConfig); - if (configOpt.SearchInAllOpenedDatabases) - { - foreach (PwDocument doc in host.MainWindow.DocumentManager.Documents) - { - if (doc.Database.IsOpen) - { - listDatabases.Add(doc.Database); - } - } - } - else - { - listDatabases.Add(host.Database); - } - - var listEntries = new List(); - foreach (PwDatabase db in listDatabases) - { - foreach (var le in db.RootGroup.GetEntries(true)) { - var title = le.Strings.ReadSafe(PwDefs.TitleField); - bool titleMatched = false; - if (title != null) { - foreach (String name in decryptedNames) - { - if (name.Equals(title)) - { - titleMatched = true; - break; - } - } - } - if (titleMatched) - { - listEntries.Add(new PwEntryDatabase(le, db)); - } - } - } - - CompleteGetLoginsResult(listEntries, configOpt, resp, r.Id, null, aes); - } + private void CompleteGetLoginsResult(List itemsList, ConfigOpt configOpt, Response resp, String rId, String host, Aes aes) + { + foreach (var entryDatabase in itemsList) + { + var e = PrepareElementForResponseEntries(configOpt, entryDatabase); + resp.Entries.Add(e); + } + + if (itemsList.Count > 0) + { + var names = (from e in resp.Entries select e.Name).Distinct(); + var n = String.Join("\n ", names.ToArray()); + + if (configOpt.ReceiveCredentialNotification) + { + String notificationMessage; + if (host == null) + { + notificationMessage = rId; + } + else + { + notificationMessage = String.Format("{0}: {1}", rId, host); + } + notificationMessage = String.Format("{0} is receiving credentials for:\n {1}", notificationMessage, n); + ShowNotification(notificationMessage); + } + } + + resp.Success = true; + resp.Id = rId; + SetResponseVerifier(resp, aes); + + foreach (var entry in resp.Entries) + { + entry.Name = CryptoTransform(entry.Name, false, true, aes, CMode.ENCRYPT); + entry.Login = CryptoTransform(entry.Login, false, true, aes, CMode.ENCRYPT); + entry.Uuid = CryptoTransform(entry.Uuid, false, true, aes, CMode.ENCRYPT); + entry.Password = CryptoTransform(entry.Password, false, true, aes, CMode.ENCRYPT); + + if (entry.StringFields != null) + { + foreach (var sf in entry.StringFields) + { + sf.Key = CryptoTransform(sf.Key, false, true, aes, CMode.ENCRYPT); + sf.Value = CryptoTransform(sf.Value, false, true, aes, CMode.ENCRYPT); + } + } + } + + resp.Count = resp.Entries.Count; + } + + private void GetLoginsByNamesHandler(Request r, Response resp, Aes aes) + { + if (!VerifyRequest(r, aes)) + return; + + if (r.Names == null) + { + return; + } + List decryptedNames = new List(); + foreach (String name in r.Names) { + if (name != null) { + decryptedNames.Add(CryptoTransform(name, true, false, aes, CMode.DECRYPT)); + } + } + + List listDatabases = new List(); + + var configOpt = new ConfigOpt(this.host.CustomConfig); + if (configOpt.SearchInAllOpenedDatabases) + { + foreach (PwDocument doc in host.MainWindow.DocumentManager.Documents) + { + if (doc.Database.IsOpen) + { + listDatabases.Add(doc.Database); + } + } + } + else + { + listDatabases.Add(host.Database); + } + + var listEntries = new List(); + foreach (PwDatabase db in listDatabases) + { + foreach (var le in db.RootGroup.GetEntries(true)) { + var title = le.Strings.ReadSafe(PwDefs.TitleField); + bool titleMatched = false; + if (title != null) { + foreach (String name in decryptedNames) + { + if (name.Equals(title)) + { + titleMatched = true; + break; + } + } + } + if (titleMatched) + { + listEntries.Add(new PwEntryDatabase(le, db)); + } + } + } + + CompleteGetLoginsResult(listEntries, configOpt, resp, r.Id, null, aes); + } private ResponseEntry PrepareElementForResponseEntries(ConfigOpt configOpt, PwEntryDatabase entryDatabase) { diff --git a/KeePassHttp/KeePassHttp.cs b/KeePassHttp/KeePassHttp.cs index 886ebce..0c99986 100644 --- a/KeePassHttp/KeePassHttp.cs +++ b/KeePassHttp/KeePassHttp.cs @@ -192,7 +192,7 @@ public override bool Initialize(IPluginHost host) handlers.Add(Request.TEST_ASSOCIATE, TestAssociateHandler); handlers.Add(Request.ASSOCIATE, AssociateHandler); handlers.Add(Request.GET_LOGINS, GetLoginsHandler); - handlers.Add(Request.GET_LOGINS_BY_NAMES, GetLoginsByNamesHandler); + handlers.Add(Request.GET_LOGINS_BY_NAMES, GetLoginsByNamesHandler); handlers.Add(Request.GET_LOGINS_COUNT, GetLoginsCountHandler); handlers.Add(Request.GET_ALL_LOGINS, GetAllLoginsHandler); handlers.Add(Request.SET_LOGIN, SetLoginHandler); diff --git a/KeePassHttp/KeePassHttp.csproj b/KeePassHttp/KeePassHttp.csproj index b4e24c6..51569ee 100644 --- a/KeePassHttp/KeePassHttp.csproj +++ b/KeePassHttp/KeePassHttp.csproj @@ -33,7 +33,8 @@ - ..\..\..\Dropbox\Software\Useful Applications\KeePass\KeePass.exe + C:\Program Files (x86)\KeePass Password Safe 2\KeePass.exe + False .\Newtonsoft.Json.dll diff --git a/KeePassHttp/Protocol.cs b/KeePassHttp/Protocol.cs index c5428c5..b794778 100644 --- a/KeePassHttp/Protocol.cs +++ b/KeePassHttp/Protocol.cs @@ -61,7 +61,7 @@ public class Request { public const string GET_LOGINS = "get-logins"; public const string GET_LOGINS_COUNT = "get-logins-count"; - public const string GET_LOGINS_BY_NAMES = "get-logins-by-names"; + public const string GET_LOGINS_BY_NAMES = "get-logins-by-names"; public const string GET_ALL_LOGINS = "get-all-logins"; public const string SET_LOGIN = "set-login"; public const string ASSOCIATE = "associate"; @@ -93,10 +93,10 @@ public class Request /// public string Url; - ///

- /// Always encrypted, used get-logins-by-names - /// - public List Names; + /// + /// Always encrypted, used get-logins-by-names + /// + public List Names; /// /// Always encrypted, used with get-login