Example #1
0
def test_init_PrivateKey():
    privkey = bitjws.PrivateKey(bitjws.wif_to_privkey(wif))

    client = BitJWSSwaggerClient.from_spec(load_file(specurl),
                                           'https://0.0.0.0:8002',
                                           privkey=privkey)
    assert 'coin' in client.swagger_spec.definitions
    assert 'user' in client.swagger_spec.definitions
    ckey = client.coin.addCoin.swagger_spec.http_client.authenticator.privkey
    assert isinstance(ckey, bitjws.PrivateKey)
    assert bitjws.privkey_to_wif(privkey.private_key) == \
            bitjws.privkey_to_wif(ckey.private_key)
Example #2
0
def test_payload_expired():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    # expire_after must be greater than 0 or None.
    with pytest.raises(bitjws.jws.InvalidPayload):
        bitjws.sign_serialize(key, expire_after=0)

    ser = bitjws.sign_serialize(key, expire_after=0.01)
    time.sleep(0.02)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # payload expired.
        bitjws.validate_deserialize(ser)

    # But the signature can still be verified and the msg decoded
    # if expiration checks are disabled.
    h, p = bitjws.validate_deserialize(ser, check_expiration=False)
    assert h and p

    # Check with multisig.
    ser = bitjws.multisig_sign_serialize([key], expire_after=0.01)
    time.sleep(0.02)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # payload expired.
        bitjws.multisig_validate_deserialize(ser)
Example #3
0
def test_payload_expired():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    # expire_after must be greater than 0 or None.
    with pytest.raises(bitjws.jws.InvalidPayload):
        bitjws.sign_serialize(key, expire_after=0)

    ser = bitjws.sign_serialize(key, expire_after=0.01)
    time.sleep(0.02)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # payload expired.
        bitjws.validate_deserialize(ser)

    # But the signature can still be verified and the msg decoded
    # if expiration checks are disabled.
    h, p = bitjws.validate_deserialize(ser, check_expiration=False)
    assert h and p

    # Check with multisig.
    ser = bitjws.multisig_sign_serialize([key], expire_after=0.01)
    time.sleep(0.02)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # payload expired.
        bitjws.multisig_validate_deserialize(ser)
Example #4
0
def test_bad_signature():
    wif = 'L2Ai1TBwKfyPshmqosKRBvJ47qUCDKesfZXh2zLoYoB7NHgdPS6d'
    key = bitjws.PrivateKey(bitjws.wif_to_privkey(wif))
    assert bitjws.privkey_to_wif(key.private_key) == wif

    ser = bitjws.sign_serialize(key)
    # Drop the last byte from the signature.
    ser = ser[:-1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        # It will fail to decode as base64 due to padding.
        bitjws.validate_deserialize(ser)
    # Drop another byte.
    ser = ser[:-1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Although it can be decoded now, the length is incorrect.
        bitjws.validate_deserialize(ser)

    # Replace the signature by something that has the correct
    # length before decoding but becomes invalid after it.
    dummy = bitjws.base64url_encode(b'a' * 88)
    ser = ser[:ser.rfind('.')] + '.' + dummy.decode('utf8')
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Now it fails because the dummy signature above produces
        # 66 bytes (instead of 65) after being decoded.
        bitjws.validate_deserialize(ser)
Example #5
0
def test_bad_signature():
    wif = 'L2Ai1TBwKfyPshmqosKRBvJ47qUCDKesfZXh2zLoYoB7NHgdPS6d'
    key = bitjws.PrivateKey(bitjws.wif_to_privkey(wif))
    assert bitjws.privkey_to_wif(key.private_key) == wif

    ser = bitjws.sign_serialize(key)
    # Drop the last byte from the signature.
    ser = ser[:-1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        # It will fail to decode as base64 due to padding.
        bitjws.validate_deserialize(ser)
    # Drop another byte.
    ser = ser[:-1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Although it can be decoded now, the length is incorrect.
        bitjws.validate_deserialize(ser)

    # Replace the signature by something that has the correct
    # length before decoding but becomes invalid after it.
    dummy = bitjws.base64url_encode(b'a' * 88)
    ser = ser[:ser.rfind('.')] + '.' + dummy.decode('utf8')
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Now it fails because the dummy signature above produces
        # 66 bytes (instead of 65) after being decoded.
        bitjws.validate_deserialize(ser)
Example #6
0
    def from_spec(cls, spec_dict, origin_url=None, http_client=None,
                  privkey=None, **kwargs):
        """
        Build a :class:`SwaggerClient` from swagger api docs

        :param spec_dict: a dict with a Swagger spec in json-like form
        :param origin_url: the url used to retrieve the spec_dict
        :type  origin_url: str
        :param http_client: an HTTP client used to perform requests
        :type  http_client: :class:`bravado.http_client.HttpClient`
        :param str privkey: The WIF private key to use for bitjws signing
        """
        if privkey is None:
            privkey = bitjws.PrivateKey()
        elif isinstance(privkey, str):
            privkey = bitjws.PrivateKey(bitjws.wif_to_privkey(privkey))

        if http_client is None:
            host = urlparse.urlsplit(origin_url).hostname
            http_client = BitJWSRequestsClient()
            private_key = bitjws.privkey_to_wif(privkey.private_key)
            http_client.set_bitjws_key(host, private_key)

        return SwaggerClient.from_spec(spec_dict, http_client=http_client,
                                       **kwargs)
Example #7
0
def test_init_url_PrivateKey():
    privkey = bitjws.PrivateKey(bitjws.wif_to_privkey(wif))

    url = "http://spec.com/swagger.json"
    spec = load_file(specurl)
    httpretty.enable()
    httpretty.register_uri(httpretty.GET, url,
                           body=json.dumps(spec))

    client = BitJWSSwaggerClient.from_url(url, privkey=privkey)
    assert 'coin' in client.swagger_spec.definitions
    assert 'user' in client.swagger_spec.definitions
    ckey = client.coin.addCoin.swagger_spec.http_client.authenticator.privkey
    assert isinstance(ckey, bitjws.PrivateKey)
    assert bitjws.privkey_to_wif(privkey.private_key) == bitjws.privkey_to_wif(ckey.private_key)

    httpretty.disable()
    httpretty.reset()
Example #8
0
def test_invalid_audience():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key, requrl='https://example.com/api/login')

    with pytest.raises(bitjws.jws.InvalidPayload):
        # audience not specified.
        bitjws.validate_deserialize(ser)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # audience does not match.
        bitjws.validate_deserialize(ser, requrl='https://example.com/api')
Example #9
0
def test_invalid_audience():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key, requrl='https://example.com/api/login')

    with pytest.raises(bitjws.jws.InvalidPayload):
        # audience not specified.
        bitjws.validate_deserialize(ser)
    with pytest.raises(bitjws.jws.InvalidPayload):
        # audience does not match.
        bitjws.validate_deserialize(ser, requrl='https://example.com/api')
Example #10
0
def test_invalid_signature_key():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Decode header.
    rawheader = ser.rsplit('.')[0]
    origheader = bitjws.base64url_decode(rawheader.encode('utf8'))
    header = json.loads(origheader.decode('utf8'))

    # Modify the key declared to be used in the signature.
    header['kid'] = '123'
    ser = _encode_header(header, ser)
    header, payload = bitjws.validate_deserialize(ser)
    # If both header or payload are None then it failed to validate
    # the signature (as expected).
    assert header is None
    assert payload is None
Example #11
0
def test_invalid_signature_key():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Decode header.
    rawheader = ser.rsplit('.')[0]
    origheader = bitjws.base64url_decode(rawheader.encode('utf8'))
    header = json.loads(origheader.decode('utf8'))

    # Modify the key declared to be used in the signature.
    header['kid'] = '123'
    ser = _encode_header(header, ser)
    header, payload = bitjws.validate_deserialize(ser)
    # If both header or payload are None then it failed to validate
    # the signature (as expected).
    assert header is None
    assert payload is None
Example #12
0
def test_invalid_header():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Decode header.
    rawheader = ser.split('.')[0]
    origheader = bitjws.base64url_decode(rawheader.encode('utf8'))
    header = json.loads(origheader.decode('utf8'))

    # Modify the algorithm specified (by removing it).
    algorithm = header.pop('alg')

    # Encode header and try to deserialize.
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Unknown algorithm.
        bitjws.validate_deserialize(ser)

    # Set some other algorithm.
    header['alg'] = 'SHA256'
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Unknown algorithm.
        bitjws.validate_deserialize(ser)

    # Drop the key used to sign.
    header['alg'] = algorithm
    kid = header.pop('kid')
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # No address specified.
        bitjws.validate_deserialize(ser)

    # Try to decode the original one.
    ser = rawheader + '.' + ser.split('.', 1)[1]
    header, payload = bitjws.validate_deserialize(ser)
    assert header is not None
    assert payload is not None
    h, p = bitjws.validate_deserialize(ser, check_expiration=False)
    assert h == header
    assert p == payload
Example #13
0
def test_invalid_header():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Decode header.
    rawheader = ser.split('.')[0]
    origheader = bitjws.base64url_decode(rawheader.encode('utf8'))
    header = json.loads(origheader.decode('utf8'))

    # Modify the algorithm specified (by removing it).
    algorithm = header.pop('alg')

    # Encode header and try to deserialize.
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Unknown algorithm.
        bitjws.validate_deserialize(ser)

    # Set some other algorithm.
    header['alg'] = 'SHA256'
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # Unknown algorithm.
        bitjws.validate_deserialize(ser)

    # Drop the key used to sign.
    header['alg'] = algorithm
    kid = header.pop('kid')
    ser = _encode_header(header, ser)
    with pytest.raises(bitjws.jws.InvalidMessage):
        # No address specified.
        bitjws.validate_deserialize(ser)

    # Try to decode the original one.
    ser = rawheader + '.' + ser.split('.', 1)[1]
    header, payload = bitjws.validate_deserialize(ser)
    assert header is not None
    assert payload is not None
    h, p = bitjws.validate_deserialize(ser, check_expiration=False)
    assert h == header
    assert p == payload
Example #14
0
def test_malformed():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Drop one of the segments.
    ser = ser.split('.', 1)[1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        bitjws.validate_deserialize(ser)

    # Add an empty segment.
    ser = '.' + ser
    with pytest.raises(bitjws.jws.InvalidMessage):
        bitjws.validate_deserialize(ser)

    # Add an invalid segment.
    ser = ' ' + ser
    with pytest.raises(bitjws.jws.InvalidMessage):
        # This will fail while trying to parse it as JSON.
        bitjws.validate_deserialize(ser)
Example #15
0
def test_malformed():
    key = bitjws.PrivateKey()
    print(bitjws.privkey_to_wif(key.private_key))

    ser = bitjws.sign_serialize(key)
    # Drop one of the segments.
    ser = ser.split('.', 1)[1]
    with pytest.raises(bitjws.jws.InvalidMessage):
        bitjws.validate_deserialize(ser)

    # Add an empty segment.
    ser = '.' + ser
    with pytest.raises(bitjws.jws.InvalidMessage):
        bitjws.validate_deserialize(ser)

    # Add an invalid segment.
    ser = ' ' + ser
    with pytest.raises(bitjws.jws.InvalidMessage):
        # This will fail while trying to parse it as JSON.
        bitjws.validate_deserialize(ser)
Example #16
0
    def from_url(cls, spec_url, http_client=None, privkey=None, **kwargs):
        """
        Build a :class:`SwaggerClient` from a url to the Swagger
        specification for a RESTful API.

        :param spec_url: url pointing at the swagger API specification
        :type spec_url: str
        :param http_client: an HTTP client used to perform requests
        :type  http_client: :class:`bravado.http_client.HttpClient`
        """
        if privkey is None:
            privkey = bitjws.PrivateKey()
        elif isinstance(privkey, str):
            privkey = bitjws.PrivateKey(bitjws.wif_to_privkey(privkey))

        if http_client is None:
            host = urlparse.urlsplit(spec_url).hostname
            http_client = BitJWSRequestsClient()
            private_key = bitjws.privkey_to_wif(privkey.private_key)
            http_client.set_bitjws_key(host, private_key)
        return SwaggerClient.from_url(spec_url, http_client=http_client,
                                      **kwargs)
Example #17
0
# Install requirements: pip install requests
import requests
import bitjws

# Load existing private key. In this example the server always
# create a new private key while the client loads an existing one.
wif = "KxZUqanyzZEGptbauar66cQo8bfGHwDauHogkxCaqTeMGY1stH6E"
priv = bitjws.wif_to_privkey(wif)
privkey = bitjws.PrivateKey(priv)
assert wif == bitjws.privkey_to_wif(privkey.private_key)
# The resulting bitcoin address can be derived for debugging
# purposes.
my_pubkey = privkey.pubkey.serialize()
my_address = bitjws.pubkey_to_addr(my_pubkey)
assert my_address == "1G9sChbyDSmuAXNVpjuRwakTmcHdxKGqpp"
print("My WIF key: {}".format(wif))
print("My key address: {}".format(my_address))

# Prepare a request to be sent. This one uses a single custom
# parameter named 'echo'.
echo_msg = 'hello'
data = bitjws.sign_serialize(privkey, echo=echo_msg)
# Send and receive signed requests.
resp = requests.post('http://localhost:8001/', data=data)
headers, payload = bitjws.validate_deserialize(resp.content.decode('utf8'))
print(headers)  # headers['kid'] contains the key used by the server.
print(payload)

# In this example the server returns a response containing the
# echo parameter specified earlier and also a param named 'address'.
assert payload['echo'] == echo_msg
Example #18
0
def test_init_WIF():
    app = Flask(__name__)
    fbj = FlaskBitjws(app, privkey=wif)
    assert wif == bitjws.privkey_to_wif(app.bitjws._privkey.private_key)
Example #19
0
def test_init_PrivateKey():
    privkey = bitjws.PrivateKey(bitjws.wif_to_privkey(wif))
    app = Flask(__name__)
    fbj = FlaskBitjws(app, privkey=privkey)
    assert wif == bitjws.privkey_to_wif(app.bitjws._privkey.private_key)
Example #20
0
# Install requirements: pip install flask flask-login
import flask
from flask.ext import login
import bitjws

# Server key used to sign responses. The client can optionally
# check that the response was signed by a key it knows to belong
# to this server.
privkey = bitjws.PrivateKey()
print("Server WIF key: {}".format(bitjws.privkey_to_wif(privkey.private_key)))
print("Server key address: {}".format(
    bitjws.pubkey_to_addr(privkey.pubkey.serialize())))

# Setup flask app with flask-login.
app = flask.Flask(__name__)
login_manager = login.LoginManager()
login_manager.init_app(app)

# Dummy User.
class User(login.UserMixin):
    def __init__(self, address):
        self.id = address

# Custom request authentication based on bitjws.
@login_manager.request_loader
def load_user_from_request(request):
    header, payload = bitjws.validate_deserialize(request.data.decode('utf8'))
    if header is None:
        # Validation failed.
        return None
# Install requirements: pip install flask flask-login
import flask
from flask.ext import login
import bitjws

# Server key used to sign responses. The client can optionally
# check that the response was signed by a key it knows to belong
# to this server.
privkey = bitjws.PrivateKey()
print("Server WIF key: {}".format(bitjws.privkey_to_wif(privkey.private_key)))
print("Server key address: {}".format(
    bitjws.pubkey_to_addr(privkey.pubkey.serialize())))

# Setup flask app with flask-login.
app = flask.Flask(__name__)
login_manager = login.LoginManager()
login_manager.init_app(app)


# Dummy User.
class User(login.UserMixin):
    def __init__(self, address):
        self.id = address


# Custom request authentication based on bitjws.
@login_manager.request_loader
def load_user_from_request(request):
    header, payload = bitjws.validate_deserialize(request.data.decode('utf8'))
    if header is None:
        # Validation failed.
Example #22
0
# Install requirements: pip install requests
import requests
import bitjws

# Load existing private key. In this example the server always
# create a new private key while the client loads an existing one.
wif = "KxZUqanyzZEGptbauar66cQo8bfGHwDauHogkxCaqTeMGY1stH6E"
priv = bitjws.wif_to_privkey(wif)
privkey = bitjws.PrivateKey(priv)
assert wif == bitjws.privkey_to_wif(privkey.private_key)
# The resulting bitcoin address can be derived for debugging
# purposes.
my_pubkey = privkey.pubkey.serialize()
my_address = bitjws.pubkey_to_addr(my_pubkey)
assert my_address == "1G9sChbyDSmuAXNVpjuRwakTmcHdxKGqpp"
print("My WIF key: {}".format(wif))
print("My key address: {}".format(my_address))

# Prepare a request to be sent. This one uses a single custom
# parameter named 'echo'.
echo_msg = "hello"
data = bitjws.sign_serialize(privkey, echo=echo_msg)
# Send and receive signed requests.
resp = requests.post("http://localhost:8001/", data=data)
headers, payload = bitjws.validate_deserialize(resp.content.decode("utf8"))
print(headers)  # headers['kid'] contains the key used by the server.
print(payload)

# In this example the server returns a response containing the
# echo parameter specified earlier and also a param named 'address'.
assert payload["echo"] == echo_msg