예제 #1
0
async def test_authenticate():
    st = AsyncSpaceTrackClient('identity', 'wrongpassword')

    loop = asyncio.get_event_loop()
    response = ClientResponse(
        'post',
        ST_URL / 'ajaxauth/login',
        request_info=Mock(),
        writer=Mock(),
        continue100=None,
        timer=TimerNoop(),
        traces=[],
        loop=loop,
        session=st.session,
    )

    response.status = 200
    response.json = Mock()

    async def mock_post(url, data):
        response.json.return_value = asyncio.Future()
        if data['password'] == 'wrongpassword':
            response.json.return_value.set_result({'Login': '******'})
        elif data['password'] == 'unknownresponse':
            # Space-Track doesn't respond like this, but make sure anything
            # other than {'Login': '******'} doesn't raise AuthenticationError
            response.json.return_value.set_result({'Login': '******'})
        else:
            response.json.return_value.set_result('')
        return response

    async with st:
        with patch.object(st.session, 'post', mock_post):
            with pytest.raises(AuthenticationError):
                await st.authenticate()

            assert response.json.call_count == 1

            st.password = '******'
            await st.authenticate()

            # This shouldn't make a HTTP request since we're already authenticated.
            await st.authenticate()

    assert response.json.call_count == 2

    st = AsyncSpaceTrackClient('identity', 'unknownresponse')

    async with st:
        with patch.object(st.session, 'post', mock_post):
            await st.authenticate()

    response.close()
예제 #2
0
async def test_authenticate():
    st = AsyncSpaceTrackClient('identity', 'wrongpassword')

    loop = asyncio.get_event_loop()
    response = ClientResponse(
        'post', URL('https://www.space-track.org/ajaxauth/login'))

    # aiohttp 2.2 uses session
    try:
        response._post_init(loop)
    except TypeError:
        response._post_init(loop, st.session)

    response.status = 200
    response.json = Mock()

    async def mock_post(url, data):
        response.json.return_value = asyncio.Future()
        if data['password'] == 'wrongpassword':
            response.json.return_value.set_result({'Login': '******'})
        elif data['password'] == 'unknownresponse':
            # Space-Track doesn't respond like this, but make sure anything
            # other than {'Login': '******'} doesn't raise AuthenticationError
            response.json.return_value.set_result({'Login': '******'})
        else:
            response.json.return_value.set_result('')
        return response

    with st, patch.object(st.session, 'post', mock_post):
        with pytest.raises(AuthenticationError):
            await st.authenticate()

        assert response.json.call_count == 1

        st.password = '******'
        await st.authenticate()

        # This shouldn't make a HTTP request since we're already authenticated.
        await st.authenticate()

    assert response.json.call_count == 2

    st = AsyncSpaceTrackClient('identity', 'unknownresponse')

    with st, patch.object(st.session, 'post', mock_post):
        await st.authenticate()

    response.close()
예제 #3
0
async def parse_response(response: ClientResponse, schema: dict) -> Any:
    """
    Validate and parse the BMA answer

    :param response: Response of aiohttp request
    :param schema: The expected response structure
    :return: the json data
    """
    try:
        data = await response.json()
        response.close()
        if schema is not None:
            jsonschema.validate(data, schema)
        return data
    except (TypeError, json.decoder.JSONDecodeError) as e:
        raise jsonschema.ValidationError("Could not parse json : {0}".format(str(e)))
예제 #4
0
async def parse_response(response: ClientResponse, schema: dict) -> Any:
    """
    Validate and parse the BMA answer

    :param response: Response of aiohttp request
    :param schema: The expected response structure
    :return: the json data
    """
    try:
        data = await response.json()
        response.close()
        if schema is not None:
            jsonschema.validate(data, schema)
        return data
    except (TypeError, json.decoder.JSONDecodeError) as e:
        raise jsonschema.ValidationError("Could not parse json : {0}".format(
            str(e))) from e
예제 #5
0
async def test_authenticate():
    st = AsyncSpaceTrackClient('identity', 'wrongpassword')

    loop = asyncio.get_event_loop()
    response = ClientResponse(
        'post', 'https://www.space-track.org/ajaxauth/login')
    response._post_init(loop)

    response.status = 200
    response.json = Mock()

    async def mock_post(url, data):
        response.json.return_value = asyncio.Future()
        if data['password'] == 'wrongpassword':
            response.json.return_value.set_result({'Login': '******'})
        elif data['password'] == 'unknownresponse':
            # Space-Track doesn't respond like this, but make sure anything
            # other than {'Login': '******'} doesn't raise AuthenticationError
            response.json.return_value.set_result({'Login': '******'})
        else:
            response.json.return_value.set_result('')
        return response

    with st, patch.object(st.session, 'post', mock_post):
        with pytest.raises(AuthenticationError):
            await st.authenticate()

        assert response.json.call_count == 1

        st.password = '******'
        await st.authenticate()

        # This shouldn't make a HTTP request since we're already authenticated.
        await st.authenticate()

    assert response.json.call_count == 2

    st = AsyncSpaceTrackClient('identity', 'unknownresponse')

    with st, patch.object(st.session, 'post', mock_post):
        await st.authenticate()

    response.close()
예제 #6
0
async def __medium_info_callback(
        response: aiohttp.ClientResponse) -> tuple[int, int]:
    content_type = response.headers.get('Content-Type', '').lower()
    content_length = int(response.headers.get('Content-Length', '1024'))
    content = response.content
    preloaded_length = content.total_bytes  # part of response body already came with the response headers
    if not (  # hey, here is a `not`!
            # a non-webp-or-svg image
        (content_type.startswith('image')
         and all(keyword not in content_type
                 for keyword in ('webp', 'svg'))) or
        (
            # an un-truncated webp image
            any(keyword in content_type for keyword in ('webp', 'application'))
            # PIL cannot handle a truncated webp image
            and
            content_length <= max(preloaded_length, IMAGE_MAX_FETCH_SIZE))):
        return -1, -1
    is_jpeg = None
    already_read = 0
    eof_flag = False
    exit_flag = False
    with BytesIO() as buffer:
        while not exit_flag:
            curr_chunk_length = 0
            preloaded_length = content.total_bytes - already_read
            while preloaded_length > IMAGE_READ_BUFFER_SIZE or curr_chunk_length < IMAGE_ITER_CHUNK_SIZE:
                # get almost all preloaded bytes, but leaving some to avoid next automatic preloading
                chunk = await content.read(
                    max(preloaded_length - IMAGE_READ_BUFFER_SIZE,
                        IMAGE_READ_BUFFER_SIZE))
                if chunk == b'':  # EOF
                    eof_flag = True
                    break
                if is_jpeg is None:
                    is_jpeg = chunk.startswith(SOI)
                already_read += len(chunk)
                curr_chunk_length += len(chunk)
                buffer.seek(0, SEEK_END)
                buffer.write(chunk)
                preloaded_length = content.total_bytes - already_read

            if eof_flag or already_read >= IMAGE_MAX_FETCH_SIZE:
                response.close(
                )  # immediately close the connection to block any incoming data or retransmission
                exit_flag = True

            # noinspection PyBroadException
            try:
                image = PIL.Image.open(buffer)
                width, height = image.size
                return width, height
            except UnidentifiedImageError:
                return -1, -1  # not a format that PIL can handle
            except Exception:
                if is_jpeg:
                    file_header = buffer.getvalue()
                    find_start_pos = 0
                    for _ in range(3):
                        pointer = -1
                        for marker in (b'\xff\xc2', b'\xff\xc1', b'\xff\xc0'):
                            p = file_header.find(marker, find_start_pos)
                            if p != -1:
                                pointer = p
                                break
                        if pointer != -1 and pointer + 9 <= len(file_header):
                            if file_header.count(EOI, 0,
                                                 pointer) != file_header.count(
                                                     SOI, 0, pointer) - 1:
                                # we are currently entering the thumbnail in Exif, bypassing...
                                # (why the specifications makers made Exif so freaky?)
                                eoi_pos = file_header.find(EOI, pointer)
                                if eoi_pos == -1:
                                    break  # no EOI found, we could never leave the thumbnail...
                                find_start_pos = eoi_pos + len(EOI)
                                continue
                            width = int(
                                file_header[pointer + 7:pointer + 9].hex(), 16)
                            height = int(
                                file_header[pointer + 5:pointer + 7].hex(), 16)
                            if min(width, height) <= 0:
                                find_start_pos = pointer + 1
                                continue
                            return width, height
                        break
    return -1, -1
예제 #7
0
async def test_generic_request():
    def mock_authenticate(self):
        result = asyncio.Future()
        result.set_result(None)
        return result

    def mock_download_predicate_data(self, class_, controller=None):
        result = asyncio.Future()
        data = [{
            'Default': '0000-00-00 00:00:00',
            'Extra': '',
            'Field': 'PUBLISH_EPOCH',
            'Key': '',
            'Null': 'NO',
            'Type': 'datetime'
        }, {
            'Default': '',
            'Extra': '',
            'Field': 'TLE_LINE1',
            'Key': '',
            'Null': 'NO',
            'Type': 'char(71)'
        }, {
            'Default': '',
            'Extra': '',
            'Field': 'TLE_LINE2',
            'Key': '',
            'Null': 'NO',
            'Type': 'char(71)'
        }]

        result.set_result(data)
        return result

    st = AsyncSpaceTrackClient('identity', 'password')

    loop = asyncio.get_event_loop()
    response = ClientResponse(
        'get',
        ST_URL / 'basicspacedata/query/class/tle_publish/format/tle',
        request_info=Mock(),
        writer=Mock(),
        continue100=None,
        timer=TimerNoop(),
        traces=[],
        loop=loop,
        session=st.session,
    )

    tle = (
        '1 25544U 98067A   08264.51782528 -.00002182  00000-0 -11606-4 0  2927\r\n'
        '2 25544  51.6416 247.4627 0006703 130.5360 325.0288 15.72125391563537\r\n'
    )

    normalised_tle = tle.replace('\r\n', '\n')

    response.status = 200
    response.text = Mock()

    response.text.return_value = asyncio.Future()
    response.text.return_value.set_result(tle)

    mock_get = asyncio.Future()
    mock_get.set_result(response)

    patch_authenticate = patch.object(AsyncSpaceTrackClient, 'authenticate',
                                      mock_authenticate)

    patch_download_predicate_data = patch.object(AsyncSpaceTrackClient,
                                                 '_download_predicate_data',
                                                 mock_download_predicate_data)

    patch_get = patch.object(st.session, 'get', return_value=mock_get)

    with patch_authenticate, patch_download_predicate_data, patch_get:
        assert await st.tle_publish(format='tle') == normalised_tle

    response.close()
    response = ClientResponse(
        'get',
        ST_URL / 'basicspacedata/query/class/tle_publish',
        request_info=Mock(),
        writer=Mock(),
        continue100=None,
        timer=TimerNoop(),
        traces=[],
        loop=loop,
        session=st.session,
    )

    response.status = 200
    response.json = Mock()
    response.json.return_value = asyncio.Future()
    response.json.return_value.set_result({'a': 5})

    mock_get = asyncio.Future()
    mock_get.set_result(response)

    patch_get = patch.object(st.session, 'get', return_value=mock_get)

    with patch_authenticate, patch_download_predicate_data, patch_get:
        result = await st.tle_publish()
        assert result['a'] == 5

    response.close()

    await st.close()
예제 #8
0
async def test_generic_request():
    def mock_authenticate(self):
        result = asyncio.Future()
        result.set_result(None)
        return result

    def mock_download_predicate_data(self, class_):
        result = asyncio.Future()
        data = [
            {
                'Default': '0000-00-00 00:00:00',
                'Extra': '',
                'Field': 'PUBLISH_EPOCH',
                'Key': '',
                'Null': 'NO',
                'Type': 'datetime'
            },
            {
                'Default': '',
                'Extra': '',
                'Field': 'TLE_LINE1',
                'Key': '',
                'Null': 'NO',
                'Type': 'char(71)'
            },
            {
                'Default': '',
                'Extra': '',
                'Field': 'TLE_LINE2',
                'Key': '',
                'Null': 'NO',
                'Type': 'char(71)'
            }
        ]

        result.set_result(data)
        return result

    st = AsyncSpaceTrackClient('identity', 'password')

    loop = asyncio.get_event_loop()
    response = ClientResponse(
        'get', 'https://www.space-track.org/basicspacedata/query/class'
        '/tle_publish/format/tle')
    response._post_init(loop)

    tle = (
        '1 25544U 98067A   08264.51782528 -.00002182  00000-0 -11606-4 0  2927\r\n'
        '2 25544  51.6416 247.4627 0006703 130.5360 325.0288 15.72125391563537\r\n')

    normalised_tle = tle.replace('\r\n', '\n')

    response.status = 200
    response.text = Mock()

    response.text.return_value = asyncio.Future()
    response.text.return_value.set_result(tle)

    mock_get = asyncio.Future()
    mock_get.set_result(response)

    patch_authenticate = patch.object(
        AsyncSpaceTrackClient, 'authenticate', mock_authenticate)

    patch_download_predicate_data = patch.object(
        AsyncSpaceTrackClient, '_download_predicate_data',
        mock_download_predicate_data)

    patch_get = patch.object(st.session, 'get', return_value=mock_get)

    with patch_authenticate, patch_download_predicate_data, patch_get:
        assert await st.tle_publish(format='tle') == normalised_tle

    response.close()

    response = ClientResponse(
        'get', 'https://www.space-track.org/basicspacedata/query/class'
        '/tle_publish')
    response._post_init(loop)

    response.status = 200
    response.json = Mock()
    response.json.return_value = asyncio.Future()
    response.json.return_value.set_result({'a': 5})

    mock_get = asyncio.Future()
    mock_get.set_result(response)

    patch_get = patch.object(st.session, 'get', return_value=mock_get)

    with patch_authenticate, patch_download_predicate_data, patch_get:
        result = await st.tle_publish()
        assert result['a'] == 5

    response.close()

    st.close()