Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update browser_tab.py #426

Open
wants to merge 16 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Empty file modified bin/splash
100755 → 100644
Empty file.
Empty file modified debian/rules
100755 → 100644
Empty file.
Empty file modified dockerfiles/splash/provision.sh
100755 → 100644
Empty file.
Empty file modified scripts/rst2inspections.py
100755 → 100644
Empty file.
Empty file modified setup.cfg
100755 → 100644
Empty file.
Empty file modified setup.py
100755 → 100644
Empty file.
15 changes: 13 additions & 2 deletions splash/browser_tab.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@
import weakref
import uuid

from PyQt5.QtCore import QObject, QSize, Qt, QTimer, pyqtSlot
from PyQt5.QtCore import QObject, QSize, QPoint, Qt, QTimer, QEvent, pyqtSlot
from PyQt5.QtGui import QMouseEvent
from PyQt5.QtWidgets import QApplication
from PyQt5.QtNetwork import QNetworkRequest
from PyQt5.QtWebKitWidgets import QWebPage
from PyQt5.QtWebKit import QWebSettings
Expand Down Expand Up @@ -729,6 +731,15 @@ def html(self):
self.store_har_timing("_onHtmlRendered")
return result

def mouse_click(self, x, y):
""" mouse click on given point(x, y) of web_page"""
self.logger.log("mouse clicking on point(%d, %d)" % (x,y), min_level=2)
evt = QMouseEvent(QEvent.MouseButtonPress, QPoint(x,y), Qt.LeftButton, Qt.LeftButton, Qt.NoModifier)
QApplication.sendEvent(self.web_page, evt)
evt = QMouseEvent(QEvent.MouseButtonRelease, QPoint(x,y), Qt.LeftButton, Qt.LeftButton, Qt.NoModifier)
QApplication.sendEvent(self.web_page, evt)
self.store_har_timing("_onMouseClicked")

def _get_image(self, image_format, width, height, render_all,
scale_method, region):
old_size = self.web_page.viewportSize()
Expand Down Expand Up @@ -912,7 +923,7 @@ def _send_request(self, url, callback, method='GET', body=None,
ua_from_headers = _get_header_value(headers, b'user-agent')
web_page_ua = self.web_page.userAgentForUrl(to_qurl(url))
user_agent = ua_from_headers or web_page_ua
request.setRawHeader(b"user-agent", to_bytes(user_agent))
request.setRawHeader(b"User-Agent", to_bytes(user_agent))

if method.upper() == "POST":
reply = self.network_manager.post(request, body)
Expand Down
13 changes: 12 additions & 1 deletion splash/kernel/inspections/splash-auto.json
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,17 @@
"details": "Example:\n\n.. code-block:: lua\n\n -- A simplistic implementation of render.html endpoint\n function main(splash)\n splash:set_result_content_type(\"text/html; charset=utf-8\")\n assert(splash:go(splash.args.url))\n return splash:html()\n end\n\nNothing prevents us from taking multiple HTML snapshots. For example, let's\nvisit first 3 pages on a website, and for each page store\ninitial HTML snapshot and an HTML snapshot after waiting 0.5s:\n\ntreat = require(\"treat\")\n\n-- Given an url, this function returns a table\n-- with the page screenshoot, it's HTML contents\n-- and it's title.\nfunction page_info(splash, url)\n local ok, msg = splash:go(url)\n if not ok then\n return {ok=false, reason=msg}\n end\n local res = {\n html=splash:html(),\n title=splash:evaljs('document.title'),\n image=splash:png(),\n ok=true,\n }\n return res\nend\n\n-- visit first 3 pages of hacker news\nlocal base = \"https://news.ycombinator.com/news?p=\"\nfunction main(splash)\n local result = treat.as_array({})\n for i=1,3 do\n local url = base .. i\n result[i] = page_info(splash, url)\n end\n return result\nend",
"params": null
},
"splash:mouse_click": {
"name": "mouse_click",
"header": "splash:mouse_click",
"content": "Click a given point(x, y) of web_page, usually (x, y) relate to an element of html",
"short": "Click a given point(x, y) of web_page",
"signature": "splash:mouse_click(x, y)",
"returns": "nil",
"async": "no.",
"details": "",
"params": "* x - integer, position of the mouse cursor relative to web_page.\n* y - integer, position of the mouse cursor relative to web_page."
},
"splash:png": {
"name": "png",
"header": "splash:png",
Expand Down Expand Up @@ -516,4 +527,4 @@
"details": "As of now, this table contains:\n\n* ``splash`` - (string) Splash version\n* ``major`` - (int) Splash major version\n* ``minor`` - (int) Splash minor version\n* ``python`` - (string) Python version\n* ``qt`` - (string) Qt version\n* ``pyqt`` - (string) PyQt version\n* ``webkit`` - (string) WebKit version\n* ``sip`` - (string) SIP version\n* ``twisted`` - (string) Twisted version\n\nExample:\n\n.. code-block:: lua\n\n function main(splash)\n local version = splash:get_version()\n if version.major < 2 and version.minor < 8 then\n error(\"Splash 1.8 or newer required\")\n end\n end",
"params": null
}
}
}
4 changes: 4 additions & 0 deletions splash/qtrender_lua.py
Original file line number Diff line number Diff line change
Expand Up @@ -567,6 +567,10 @@ def error(error_info):
def html(self):
return self.tab.html()

@command()
def mouse_click(self, x, y):
return self.tab.mouse_click(x, y)

@command()
def png(self, width=None, height=None, render_all=False,
scale_method=None, region=None):
Expand Down
Empty file modified splash/tests/mockserver.py
100755 → 100644
Empty file.
44 changes: 22 additions & 22 deletions splash/tests/test_execute.py
Original file line number Diff line number Diff line change
Expand Up @@ -1395,24 +1395,24 @@ class JsonPostArgsTest(ArgsTest):
request_handler = JsonPostRequestHandler

def test_headers(self):
headers = {"user-agent": "Firefox", "content-type": "text/plain"}
headers = {"User-Agent": "Firefox", "content-type": "text/plain"}
self.assertArgsPassed({"headers": headers})

def test_headers_items(self):
headers = [["user-agent", "Firefox"], ["content-type", "text/plain"]]
headers = [["User-Agent", "Firefox"], ["content-type", "text/plain"]]
self.assertArgsPassed({"headers": headers})

def test_access_headers(self):
func = """
function main(splash)
local ua = "Unknown"
if splash.args.headers then
ua = splash.args.headers['user-agent']
ua = splash.args.headers['User-Agent']
end
return {ua=ua, firefox=(ua=="Firefox")}
end
"""
resp = self.request_lua(func, {'headers': {"user-agent": "Firefox"}})
resp = self.request_lua(func, {'headers': {"User-Agent": "Firefox"}})
self.assertStatusCode(resp, 200)
self.assertEqual(resp.json(), {"ua": "Firefox", "firefox": True})

Expand Down Expand Up @@ -1876,13 +1876,13 @@ def test_set_user_agent(self):
self.assertNotIn("Mozilla", data["res3"])

if six.PY3:
self.assertNotIn("b'user-agent': b'Foozilla'", data["res1"])
self.assertIn("b'user-agent': b'Foozilla'", data["res2"])
self.assertIn("b'user-agent': b'Foozilla'", data["res3"])
self.assertNotIn("b'User-Agent': b'Foozilla'", data["res1"])
self.assertIn("b'User-Agent': b'Foozilla'", data["res2"])
self.assertIn("b'User-Agent': b'Foozilla'", data["res3"])
else:
self.assertNotIn("'user-agent': 'Foozilla'", data["res1"])
self.assertIn("'user-agent': 'Foozilla'", data["res2"])
self.assertIn("'user-agent': 'Foozilla'", data["res3"])
self.assertNotIn("'User-Agent': 'Foozilla'", data["res1"])
self.assertIn("'User-Agent': 'Foozilla'", data["res2"])
self.assertIn("'User-Agent': 'Foozilla'", data["res3"])

def test_set_user_agent_base_url(self):
resp = self.request_lua("""
Expand Down Expand Up @@ -2534,7 +2534,7 @@ def test_get_with_default_headers(self):
headers = resp.json()
self.assertNotEqual(len(headers), 0)
self.assertEqual(len(headers), 1)
self.assertIn("Mozilla/5.0", headers["user-agent"])
self.assertIn("Mozilla/5.0", headers["User-Agent"])

def test_get_with_custom_headers(self):
resp = self.request_lua("""
Expand All @@ -2552,7 +2552,7 @@ def test_get_with_custom_headers(self):
self.assertNotEqual(len(headers), 0)
self.assertEqual(headers["Header-1"], "Value 1")
self.assertEqual(headers["Header-2"], "Value 2")
self.assertIn("user-agent", headers)
self.assertIn("User-Agent", headers)

def test_get_with_custom_ua(self):
resp = self.request_lua("""
Expand All @@ -2565,26 +2565,26 @@ def test_get_with_custom_ua(self):
self.assertStatusCode(resp, 200)
headers = resp.json()
self.assertNotEqual(len(headers), 0)
self.assertEqual(headers["user-agent"], "CUSTOM UA")
self.assertEqual(headers["User-Agent"], "CUSTOM UA")

def test_get_with_custom_ua_in_headers(self):
resp = self.request_lua("""
function main(splash)
response = assert(splash:http_get{splash.args.url, headers={["user-agent"]="Value 1"}})
response = assert(splash:http_get{splash.args.url, headers={["User-Agent"]="Value 1"}})
return response.request.headers
end
""", {"url": self.mockurl("jsrender")})
self.assertStatusCode(resp, 200)
headers = resp.json()
self.assertNotEqual(len(headers), 0)
self.assertEqual(headers["user-agent"], "Value 1")
self.assertEqual(headers["User-Agent"], "Value 1")

def test_get_with_custom_ua_in_headers_and_set_with_splash(self):
resp = self.request_lua("""
function main(splash)
splash:set_user_agent("CUSTOM UA")
response1 = assert(splash:http_get(splash.args.url))
response2 = assert(splash:http_get{splash.args.url, headers={["user-agent"]="Value 1"}})
response2 = assert(splash:http_get{splash.args.url, headers={["User-Agent"]="Value 1"}})
response3 = assert(splash:http_get(splash.args.url))

return {
Expand All @@ -2597,10 +2597,10 @@ def test_get_with_custom_ua_in_headers_and_set_with_splash(self):
self.assertStatusCode(resp, 200)
resp = resp.json()
headers1, headers2, headers3 = resp["result1"], resp["result2"], resp["result3"]
self.assertTrue(all("user-agent" in h for h in (headers1, headers2, headers3)))
self.assertEqual(headers1["user-agent"], "CUSTOM UA")
self.assertEqual(headers2["user-agent"], "Value 1")
self.assertEqual(headers3["user-agent"], "CUSTOM UA")
self.assertTrue(all("User-Agent" in h for h in (headers1, headers2, headers3)))
self.assertEqual(headers1["User-Agent"], "CUSTOM UA")
self.assertEqual(headers2["User-Agent"], "Value 1")
self.assertEqual(headers3["User-Agent"], "CUSTOM UA")

def test_ua_on_rendering(self):
resp = self.request_lua("""
Expand All @@ -2611,13 +2611,13 @@ def test_ua_on_rendering(self):
result[#result+1] = response.request.headers
end)

response = assert(splash:go{splash.args.url, headers={["user-agent"]="Value 1"}})
response = assert(splash:go{splash.args.url, headers={["User-Agent"]="Value 1"}})
return result
end
""", {"url": self.mockurl("subresources")})
self.assertStatusCode(resp, 200)
resp = resp.json()
uas = [r.get("User-Agent", r.get("user-agent")) for r in resp]
uas = [r.get("User-Agent", r.get("User-Agent")) for r in resp]
self.assertTrue(all(h == "Value 1" for h in uas))

def test_bad_url(self):
Expand Down