代码之家  ›  专栏  ›  技术社区  ›  Totty.js

如何点击木偶戏中有特定内容的链接?

  •  13
  • Totty.js  · 技术社区  · 8 年前

    如果我的页面中有一些内容,例如:

    <a>Hi!</a>
    

    我如何使用Google的Puppeter来自动点击该元素?

    我需要能够根据其内容单独选择它,而不是id、类或属性。

    有没有类似的 $('a:contains("Hi!")') 我可以利用它来选择此元素?

    我怎样才能做到这一点 https://github.com/GoogleChrome/puppeteer

    谢谢

    2 回复  |  直到 8 年前
        1
  •  18
  •   Thomas Dondorf    6 年前

    使用XPath的替代方法

    使用 XPath 表达式:

    const aElementsWithHi = await page.$x("//a[contains(., 'Hi!')]");
    await aElementsWithHi[0].click();
    

    使用 page.$x ,此代码将查找所有 a 包含文本的元素 Hi! 在…内结果将是一个包含匹配项的数组 元素句柄。使用 elementHandle.click 函数,然后可以单击元素。

        2
  •  9
  •   Edo    7 年前

    首先,我们必须通过文本找到元素。

    /**
     * findElemByText - Find an Element By Text
     *
     * @param  {String} str                case-insensitive string to search
     * @param  {String} selector = '*'     selector to search
     * @param  {String} leaf = 'outerHTML' leaf of the element
     * @return {Array}                     array of elements
     */
    function findElemByText({str, selector = '*', leaf = 'outerHTML'}){
      // generate regex from string
      const regex = new RegExp(str, 'gmi');
    
      // search the element for specific word
      const matchOuterHTML = e => (regex.test(e[leaf]))
    
      // array of elements
      const elementArray = [...document.querySelectorAll(selector)];
    
      // return filtered element list
      return elementArray.filter(matchOuterHTML)
    }
    
    // usage
    // findElemByText({str: 'Example', leaf: 'innerHTML', selector: 'title'});
    // findElemByText({str: 'Example', selector: 'h1'});
    // findElemByText({str: 'Example'});
    

    将其保存在与木偶演员脚本相同的文件夹中,命名为 script.js .

    现在,我们可以在我们的木偶戏剧本中使用这个。我们可以使用ElementHandle,但为了便于理解,我将使用 .evaluate() 木偶师提供的功能。

    const puppeteer = require('puppeteer');
    
    (async () => {
      const browser = await puppeteer.launch();
      const page = await browser.newPage();
      await page.goto('https://example.com');
    
      // expose the function
      await page.addScriptTag({path: 'script.js'});
    
      // Find Element by Text and Click it
      await page.evaluate(() => {
       // click the first element 
       return findElemByText({str: 'More'})[0].click();
      });
    
      // Wait for navigation, Take Screenshot, Do other stuff
      await page.screenshot({path: 'screenshot.png'});
      await browser.close();
    })();
    

    不要复制粘贴上面的代码,试着理解它并自己键入。如果上述代码失败,请尝试找出失败的原因。