diff options
Diffstat (limited to 'src/leap/mx/couchdbhelper.py')
-rw-r--r-- | src/leap/mx/couchdbhelper.py | 139 |
1 files changed, 30 insertions, 109 deletions
diff --git a/src/leap/mx/couchdbhelper.py b/src/leap/mx/couchdbhelper.py index f20f1dd..7bcb5aa 100644 --- a/src/leap/mx/couchdbhelper.py +++ b/src/leap/mx/couchdbhelper.py @@ -15,24 +15,15 @@ # You should have received a copy of the GNU General Public License # along with this program. If not, see <http://www.gnu.org/licenses/>. + """ Classes for working with CouchDB or BigCouch instances which store email alias maps, user UUIDs, and GPG keyIDs. """ -from functools import partial - -try: - from paisley import client -except ImportError: - print "This software requires paisley. Please see the README file" - print "for instructions on getting required dependencies." -try: - from twisted.python import log -except ImportError: - print "This software requires Twisted. Please see the README file" - print "for instructions on getting required dependencies." +from paisley import client +from twisted.python import log class ConnectedCouchDB(client.CouchDB): @@ -66,24 +57,8 @@ class ConnectedCouchDB(client.CouchDB): username=username, password=password, *args, **kwargs) - self._cache = {} - if dbName is None: - databases = self.listDB() - databases.addCallback(self._print_databases) - - def _print_databases(self, data): - """ - Callback for listDB that prints the available databases - - :param data: response from the listDB command - :type data: array - """ - log.msg("Available databases:") - for database in data: - log.msg(" * %s" % (database,)) - def createDB(self, dbName): """ Overrides ``paisley.client.CouchDB.createDB``. @@ -100,106 +75,52 @@ class ConnectedCouchDB(client.CouchDB): """ Check to see if a particular email or alias exists. - :param alias: A string representing the email or alias to check. - :type alias: str + :param address: A string representing the email or alias to check. + :type address: str :return: a deferred for this query :rtype twisted.defer.Deferred """ - assert isinstance(address, (str, unicode)), "Email or alias queries must be string" - # TODO: Cache results - d = self.openView(docId="Identity", viewId="by_address/", key=address, - reduce=False, - include_docs=True) + reduce=True, + include_docs=False) - d.addCallbacks(partial(self._get_uuid, address), log.err) + def _callback(result): + if len(result["rows"]): + return address + return None + + d.addCallbacks(_callback, log.err) return d - def _get_uuid(self, address, result): - """ - Parses the result of the by_address query and gets the uuid - - :param address: alias looked up - :type address: string - :param result: result dictionary - :type result: dict - :return: The uuid for alias if available - :rtype: str - """ - for row in result["rows"]: - if row["key"] == address: - uuid = row["doc"].get("user_id", None) - if uuid is None: - log.msg("ERROR: Found doc for %s but there's not user_id!" - % (address,)) - return uuid - return None - - def getPubKey(self, uuid): + def getPubKey(self, address): """ - Returns a deferred that will return the pubkey for the uuid provided + Returns a deferred that will fire with the pubkey for the address. - :param uuid: uuid for the user to query - :type uuid: str + :param address: email address to query + :type address: str :rtype: Deferred """ d = self.openView(docId="Identity", viewId="pgp_key_by_email/", - user_id=uuid, + key=address, reduce=False, - include_docs=True) - - d.addCallbacks(partial(self._get_pgp_key, uuid), log.err) + include_docs=False) - return d - - def _get_pgp_key(self, uuid, result): - """ - Callback used to filter the correct pubkey from the result of - the query to the couchdb + def _callback(result): + if not result["rows"]: + log.msg("No PGP public key found for %s." % address) + return None + if len(result["rows"]) > 1: + log.msg("More than one PGP public key found for %s, " + "will pick the first one found." % address) + row = result["rows"].pop(0) + return row["value"] - :param uuid: uuid for the user that was queried - :type uuid: str - :param result: result dictionary for the db query - :type result: dict + d.addCallbacks(_callback, log.err) - :rtype: str or None - """ - for row in result["rows"]: - user_id = row["doc"].get("user_id") - if not user_id: - print("User %s is in an inconsistent state") - continue - if user_id == uuid: - return row["value"] - return None - -if __name__ == "__main__": - from twisted.internet import reactor - cdb = ConnectedCouchDB("localhost", - port=6666, - dbName="users", - username="", - password="") - - d = cdb.queryByLoginOrAlias("test1") - - @d.addCallback - def right(result): - print "Should be an actual uuid:", result - print "Public Key:" - print cdb.getPubKey(result) - - d2 = cdb.queryByLoginOrAlias("asdjaoisdjoiqwjeoi") - - @d2.addCallback - def wrong(result): - print "Should be None:", result - - reactor.callLater(5, reactor.stop) - reactor.run() + return d |