【问题标题】:Human-like mouse movements via Selenium通过 Selenium 进行类似人类的鼠标移动
【发布时间】:2017-01-18 05:55:18
【问题描述】:

故事:

解决验证码的方法之一是尝试模仿人类鼠标操作:移动、悬停和点击。

Some users reported 让鼠标像B-spline curves 一样移动对他们有用。

问题:

如何通过 Selenium 将鼠标移动到遵循 B 样条轨迹的特定元素?


请注意,常规的browser.actions().mouseMove(elm).perform(); 会直接“跳转”到元素,而且太快了。我的理解是减慢运动速度,顺着B样条轨迹的数学模型从一个点到另一个点平滑地“跳跃”。

我们正在使用 Protractor/JavaScript,但这个问题确实与语言无关。请注意,我并不是要解决验证码,也不是为“解决验证码的制作”做出贡献新的邪恶机器人在各处违反使用条款”空间。我只是好奇并渴望在测试自动化领域获得更多技能。

【问题讨论】:

    标签: selenium selenium-webdriver automation protractor bots


    【解决方案1】:

    您可以使用 scipy.interpolate 插入 B 样条曲线,就像您在 question 中看到的那样。

    在这里,我将使用 B 样条 示例之一来获取 xy 的值:

    import numpy as np
    import scipy.interpolate as si
    
    # Curve base:
    points = [[0, 0], [0, 2], [2, 3], [4, 0], [6, 3], [8, 2], [8, 0]];
    points = np.array(points)
    
    x = points[:,0]
    y = points[:,1]
    
    
    t = range(len(points))
    ipl_t = np.linspace(0.0, len(points) - 1, 100)
    
    x_tup = si.splrep(t, x, k=3)
    y_tup = si.splrep(t, y, k=3)
    
    x_list = list(x_tup)
    xl = x.tolist()
    x_list[1] = xl + [0.0, 0.0, 0.0, 0.0]
    
    y_list = list(y_tup)
    yl = y.tolist()
    y_list[1] = yl + [0.0, 0.0, 0.0, 0.0]
    
    x_i = si.splev(ipl_t, x_list) # x interpolate values
    y_i = si.splev(ipl_t, y_list) # y interpolate values
    

    使用xy 的值,您可以使用ActionChains 移动鼠标光标:

    from selenium import webdriver
    from selenium.webdriver.common.action_chains import ActionChains
    
    url = "https://codepen.io/falldowngoboone/pen/PwzPYv"
    driver = webdriver.Chrome(executable_path="/home/selenium/chromedriver2.25")
    driver.get(url)
    
    action =  ActionChains(driver);
    
    startElement = driver.find_element_by_id('drawer')
    
    # First, go to your start point or Element:
    action.move_to_element(startElement);
    action.perform();
    
    for mouse_x, mouse_y in zip(x_i, y_i):
        action.move_by_offset(mouse_x,mouse_y);
        action.perform();
        print(mouse_x, mouse_y)
    

    【讨论】:

    • 我使用的曲线只是一个例子,有必要根据预期的路线制作一个。或者通过网站的特定点
    • @NinoŠkopac 肯定有 Selenium PHP WebDriver(或类似的)
    • 我不明白。这使得鼠标只是从原始位置跳到样条曲线的第一个位置然后再次返回,然后跳到第二个点并再次返回,等等。只要你不能,它看起来根本不像人类锁定光标并沿样条线移动,而不会在每次“睡眠”后跳回原点。如果您将“action.perform()”放在循环之后并移除睡眠,它会起作用。但是,这种方式您无法直接控制移动的速度。您可以添加更多点以减慢速度
    • @ODIUM 您需要根据需要进行调整。开始和结束位置应该是您需要鼠标在屏幕上执行的路径(按钮位置)。然后在这两点之间生成一条曲线,这将是鼠标移动的路径。
    【解决方案2】:

    如果您从桌面魔杖运行此程序,想要使用实际的鼠标移动,使用AutoIt 您可以延迟鼠标移动。

    【讨论】:

    • 欢迎来到 SO!基于链接的答案非常冒险,好像链接消失了,就没有答案了。请对其进行编辑并解释在链接中可以找到的内容。
    【解决方案3】:

    @ODIUM @Guilherme 或任何仍在寻找修复的人。在 Guilherme 的回答中,ODIUM 将其描述为跳转到第一个曲线位置然后回到起点,然后是第二个曲线位置并再次回到起点,这是由所提供代码中的一个小错误引起的。它将通过在每次执行后“重置”动作链来修复,如下所示:

    action =  ActionChains(driver);
    startElement = driver.find_element_by_id('drawer')
    
    # First, go to your start point or Element:
    action.move_to_element(startElement);
    action.perform();
    
    for mouse_x, mouse_y in zip(x_i, y_i):
        # Here you should reset the ActionChain and the 'jump' wont happen:
        action =  ActionChains(driver)
        action.move_by_offset(mouse_x,mouse_y);
        action.perform();
        print(mouse_x, mouse_y)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-10-09
      • 1970-01-01
      • 1970-01-01
      • 2012-08-08
      • 1970-01-01
      • 2013-09-07
      • 2014-04-27
      相关资源
      最近更新 更多