Fix bug in keyring fetching code

Leading to infinite loop when the password is simply not there.

Also fixed some import styling again
This commit is contained in:
Markus Unterwaditzer 2014-06-19 18:06:34 +02:00
parent 289ac2cfac
commit 2fb58d6bcd
5 changed files with 50 additions and 7 deletions

View file

@ -15,6 +15,10 @@ from vdirsyncer.utils.vobject import normalize_item as _normalize_item
vdirsyncer.log.set_level(vdirsyncer.log.logging.DEBUG)
def blow_up(*a, **kw):
raise AssertionError('Did not expect to be called.')
def normalize_item(item):
if not isinstance(item, text_type):
item = item.raw

View file

@ -7,11 +7,13 @@
:license: MIT, see LICENSE for more details.
'''
import click
from click.testing import CliRunner
import pytest
import vdirsyncer.utils as utils
from vdirsyncer.utils.vobject import split_collection
from .. import normalize_item, SIMPLE_TEMPLATE, BARE_EVENT_TEMPLATE
from .. import blow_up, normalize_item, SIMPLE_TEMPLATE, BARE_EVENT_TEMPLATE
def test_parse_options():
@ -58,7 +60,7 @@ def test_get_password_from_netrc(monkeypatch):
return username, 'bogus', password
monkeypatch.setattr('netrc.netrc', Netrc)
monkeypatch.setattr('getpass.getpass', None)
monkeypatch.setattr('getpass.getpass', blow_up)
_password = utils.get_password(username, resource)
assert _password == password
@ -101,13 +103,46 @@ def test_get_password_from_system_keyring(monkeypatch, resources_to_test):
return None
monkeypatch.setattr('netrc.netrc', Netrc)
monkeypatch.setattr('getpass.getpass', None)
monkeypatch.setattr('getpass.getpass', blow_up)
_password = utils.get_password(username, resource)
assert _password == password
assert netrc_calls == [hostname]
def test_get_password_from_prompt(monkeypatch):
getpass_calls = []
class Netrc(object):
def authenticators(self, hostname):
return None
class Keyring(object):
def get_password(self, *a, **kw):
return None
monkeypatch.setattr('netrc.netrc', Netrc)
monkeypatch.setattr(utils, 'keyring', Keyring())
user = 'my_user'
resource = 'http://example.com'
@click.command()
def fake_app():
x = utils.get_password(user, resource)
click.echo('Password is {}'.format(x))
runner = CliRunner()
result = runner.invoke(fake_app, input='my_password\n\n')
assert not result.exception
assert result.output.splitlines() == [
'Server password for {} at the resource {}: '.format(user, resource),
'Save this password in the keyring? [y/N]: ',
'Password is my_password'
]
def test_get_class_init_args():
class Foobar(object):
def __init__(self, foo, bar, baz=None):

View file

@ -7,10 +7,10 @@
:license: MIT, see LICENSE for more details.
'''
import functools
import json
import os
import sys
import functools
import click

View file

@ -7,6 +7,7 @@
:license: MIT, see LICENSE for more details.
'''
import logging
import click

View file

@ -9,9 +9,10 @@
import os
import requests
import click
import requests
from .. import exceptions, log
from .compat import iteritems, urlparse
@ -117,7 +118,9 @@ def _password_from_keyring(username, resource):
parsed = urlparse.urlsplit(key)
path = parsed.path
if path.endswith('/'):
if not path:
return None
elif path.endswith('/'):
path = path.rstrip('/')
else:
path = path.rsplit('/', 1)[0] + '/'
@ -165,7 +168,7 @@ def get_password(username, resource):
prompt = ('Server password for {} at the resource {}'
.format(username, resource))
password = click.prompt(prompt=prompt, hide_input=True)
password = click.prompt(prompt, hide_input=True)
if keyring is not None and \
click.confirm('Save this password in the keyring?', default=False):