예제 #1
0
async def test_connection_execute(nursery):
    ''' Open a connection and execute a command on it. '''
    async def handler(request):
        # It's tricky to catch exceptions from the server, so exceptions are
        # logged instead.
        try:
            ws = await request.accept()
            command = json.loads(await ws.get_message())
            logging.info('Server received:  %r', command)
            assert command['method'] == 'Target.getTargets'
            response = {
                'id': command['id'],
                'result': {
                    'targetInfos': [{
                        'targetId': 'target1',
                        'type': 'tab',
                        'title': 'New Tab',
                        'url': 'about:newtab',
                        'attached': False,
                    }],
                }
            }
            logging.info('Server sending:  %r', response)
            await ws.send_message(json.dumps(response))
        except Exception:
            logging.exception('Server exception')

    server = await start_server(nursery, handler)
    async with open_cdp(server) as conn:
        targets = await conn.execute(target.get_targets())
        assert len(targets) == 1
        assert isinstance(targets[0], target.TargetInfo)
예제 #2
0
async def read_page(browserurl, targeturl):
    """
    read a page and get the title
    originally https://github.com/HyperionGray/trio-chrome-devtools-protocol/blob/master/examples/get_title.py
    """
    logger.info("Connecting to browser: %s", browserurl)
    async with open_cdp(browserurl) as conn:
        logger.info("Listing targets")
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        logger.info("Attaching to target id=%s", target_id)
        session = await conn.open_session(target_id)

        logger.info("Navigating to %s", targeturl)
        await session.execute(page.enable())
        async with session.wait_for(page.LoadEventFired):
            await session.execute(page.navigate(targeturl))
            _, item = await session.execute(page.print_to_pdf())
            print(f"pdf is: {type(item)}")

        logger.info("Extracting page title")
        root_node = await session.execute(dom.get_document())
        title_node_id = await session.execute(
            dom.query_selector(root_node.node_id, "title")
        )
        html = await session.execute(dom.get_outer_html(title_node_id))
예제 #3
0
async def test_connection_browser_error(nursery):
    ''' If the browser sends an error with a valid command ID, then that error
    should be raised at the point where the command was executed. Compare to
    ``test_connection_invalid_json()``, where the error is raised on the reader
    task since there is no way to associate it with a specific commmand. '''
    async def handler(request):
        # It's tricky to catch exceptions from the server, so exceptions
        # are logged instead.
        try:
            ws = await request.accept()
            command = json.loads(await ws.get_message())
            logging.info('Server received:  %r', command)
            response = {
                'id': command['id'],
                'error': {
                    'code': -32000,
                    'message': 'This is a browser error',
                    'data': 'This is additional data'
                }
            }
            logging.info('Server sending reponse: %r', response)
            await ws.send_message(json.dumps(response))
        except Exception:
            logging.exception('Server exception')

    server = await start_server(nursery, handler)

    async with open_cdp(server) as conn:
        with pytest.raises(BrowserError) as exc_info:
            targets = await conn.execute(target.get_targets())

    assert exc_info.value.code == -32000
예제 #4
0
async def main(i):
    # Open connection
    async with open_cdp_connection(uri_pwa) as conn:
        logger.info('Connecting')
        targets = await conn.execute(target.get_targets())
        # Filter the targets to find the PWA one
        targets = list(filter(findPWA, targets))
        logger.info(targets[0])
        target_id = targets[0].target_id

        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        final_data = []

        def addData(data):
            final_data += data

        outfile_path = trio.Path(name + '_' + str(i) + '.json')
        async with await outfile_path.open('a+') as outfile:
            logger.info('Tracing...')
            # write things to file to be readable as a json
            await outfile.write('[')
            # data = '['
            await generateTrace(session, outfile, final_data)
            logger.info('Tracing n° {} ended'.format(i))
            await outfile.write(',\n'.join(final_data))
            await outfile.write("]")
async def main():
    logger.info('Connecting to browser: %s', sys.argv[1])
    async with open_cdp_connection(sys.argv[1]) as conn:
        logger.info('Listing targets')
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        logger.info('Setting device emulation')
        await session.execute(
            emulation.set_device_metrics_override(width=800,
                                                  height=600,
                                                  device_scale_factor=1,
                                                  mobile=False))

        logger.info('Enabling page events')
        await session.execute(page.enable())

        logger.info('Navigating to %s', sys.argv[2])
        await session.execute(page.navigate(url=sys.argv[2]))

        logger.info('Waiting for navigation to finish…')
        event = await session.wait_for(page.LoadEventFired)

        logger.info('Making a screenshot')
        img_data = await session.execute(page.capture_screenshot(format='png'))
        screenshot_file = await trio.open_file('test.png', 'wb')
        async with screenshot_file:
            await screenshot_file.write(b64decode(img_data))
예제 #6
0
async def main():
    logger.info('Connecting to browser: %s', sys.argv[1])
    async with open_cdp_connection(sys.argv[1]) as conn:
        logger.info('Listing targets')
        targets = await conn.execute(target.get_targets())

        for t in targets:
            if (t.type == 'page' and not t.url.startswith('devtools://')
                    and not t.attached):
                target_id = t.target_id
                break

        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        logger.info('Navigating to %s', sys.argv[2])
        await session.execute(page.enable())
        async with session.wait_for(page.LoadEventFired):
            await session.execute(page.navigate(sys.argv[2]))

        logger.info('Extracting page title')
        root_node = await session.execute(dom.get_document())
        title_node_id = await session.execute(
            dom.query_selector(root_node.node_id, 'title'))
        html = await session.execute(dom.get_outer_html(title_node_id))
        print(html)
예제 #7
0
async def save_pdf(browserurl, targeturl, pdfpath, sleeptime):
    """
    make a pdf from a webpage
    originally https://github.com/HyperionGray/trio-chrome-devtools-protocol/blob/master/examples/screenshot.py

    Parameters

    browserurl: str
        ws address for chrome developer protocol commands

    targeturl: str
        url of page to print to pdf

    pngfile: str
        filename for png file
    """
    logger.info("Connecting to browser: %s", browserurl)
    async with open_cdp(browserurl) as conn:
        logger.info("Listing targets")
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        logger.info("Attaching to target id=%s", target_id)
        async with conn.open_session(target_id) as session:
            logger.info("Setting device emulation")
            await session.execute(
                emulation.set_device_metrics_override(
                    width=1200, height=2000, device_scale_factor=1, mobile=False
                )
            )

            logger.info("Enabling page events")
            await session.execute(page.enable())

            logger.info("Navigating to %s", targeturl)
            async with session.wait_for(page.LoadEventFired):
                await session.execute(page.navigate(url=targeturl))

            time.sleep(sleeptime)
            root_node = await session.execute(dom.get_document())
            title_node_id = await session.execute(
                dom.query_selector(root_node.node_id, "body")
            )
            body_html = await session.execute(dom.get_outer_html(title_node_id))

            logger.debug(body_html)

            logger.info("Saving a pdf")
            # TODO: make sure that javascript finishes rendering
            # await session.execute(page.capture_screenshot(format="png"))
            pdf_data, _ = await session.execute(page.print_to_pdf())

            pdf_file = await trio.open_file(pdfpath, "wb")
            async with pdf_file:
                await pdf_file.write(b64decode(pdf_data))
            logger.info(f"wrote {pdfpath}")
예제 #8
0
async def main():
    cdp_uri = sys.argv[1]
    async with open_cdp_connection(cdp_uri) as conn:
        logger.info('Connecting')
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        # First page
        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        logger.info('Started heap snapshot')
        outfile_path = trio.Path('%s.heapsnapshot' %
                                 datetime.today().isoformat())
        async with await outfile_path.open('a') as outfile:
            logger.info('Started writing heap snapshot')
            await _take_heap_snapshot(session, outfile, report_progress=True)
예제 #9
0
async def merge_pages_in(ethox_doc, ws_addr, reduction_code):
    async with open_cdp_connection(ws_addr) as conn:
        logger.info('Listing targets')
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        logger.info('Setting device emulation')
        await session.execute(
            emulation.set_device_metrics_override(width=800,
                                                  height=600,
                                                  device_scale_factor=1,
                                                  mobile=False))

        logger.info('Enabling page events')
        await session.execute(page.enable())

        logger.info('Starting to crawl documentation')

        contents = {}
        for doc_page in glob.iglob(os.path.join(ethox_doc, '**', '*.html'),
                                   recursive=True):
            (target_item,
             main_contents) = await convert_page(session, doc_page,
                                                 reduction_code)
            contents[target_item] = main_contents

        await convert_page(session, os.path.join(ethox_doc, 'index.html'),
                           reduction_code)
        root_id = (await session.execute(dom.get_document())).node_id
        body_id = await session.execute(dom.query_selector(root_id, 'body'))
        footer_id = await session.execute(dom.query_selector(
            root_id, 'footer'))
        main_id = await session.execute(dom.query_selector(root_id, '#main'))

        for (_, contents) in contents.items():
            cloned_id = await session.execute(
                dom.copy_to(main_id, body_id, footer_id))
            await session.execute(dom.set_outer_html(cloned_id, contents))

        await print_page(session, 'cargo_doc.pdf')
예제 #10
0
async def main():
    logger.info('Connecting to browser: %s', sys.argv[1])
    async with open_cdp_connection(sys.argv[1]) as conn:
        logger.info('Listing targets')
        targets = await conn.execute(target.get_targets())
        target_id = targets[0].target_id

        logger.info('Attaching to target id=%s', target_id)
        session = await conn.open_session(target_id)

        logger.info('Navigating to %s', sys.argv[2])
        await session.execute(page.enable())
        await session.execute(page.navigate(sys.argv[2]))
        event = await session.wait_for(page.LoadEventFired)

        logger.info('Extracting page title')
        root_node = await session.execute(dom.get_document())
        title_node_id = await session.execute(
            dom.query_selector(root_node.node_id, 'title'))
        html = await session.execute(dom.get_outer_html(title_node_id))
        print(html)
예제 #11
0
async def test_connection_invalid_json():
    ''' If the server sends invalid JSON, that exception is raised on the reader
    task, which crashes the entire connection. Therefore, the entire test needs
    to be wrapped in try/except. '''
    with pytest.raises(BrowserError) as exc_info:
        async with trio.open_nursery() as nursery:
            async def handler(request):
                # It's tricky to catch exceptions from the server, so exceptions
                # are logged instead.
                try:
                    ws = await request.accept()
                    command = json.loads(await ws.get_message())
                    logging.info('Server received:  %r', command)
                    logging.info('Server sending bogus reponse')
                    await ws.send_message('bogus')
                except Exception:
                    logging.exception('Server exception')
            server = await start_server(nursery, handler)

            async with open_cdp_connection(server) as conn:
                targets = await conn.execute(target.get_targets())
    assert exc_info.value.code == -32700 # JSON parse error