Selenium에서 JavaScript 오류 캡처


81

에서 발생하는 오류를 캡처 할 수있는 방법이 있습니까 DOM에서 Selenium아마 페이지에 오류와 같은 플래그는?

간단한 예를 들어, 존재하지 않는 HTML 컨트롤에서 이벤트를 바인딩하려고한다고 가정 해 보겠습니다. 브라우저에서 다음과 같은 오류가 발생합니다.

element abcd not found in the console.

이제 동일한 오류가 셀레늄 테스트에 실패하고 브라우저에 표시되는 메시지가 오류 메시지로 표시되도록하려면.

이런 식으로 할 수 있습니까?


1
이제 2018 년인데 더 깨끗한 해결책이 있을까요?
Fla

답변:


52

이 스크립트를 페이지에 넣은 다음 Selenium에서 JSError를 확인하십시오.

<script type="text/javascript">
    window.onerror=function(msg){
        $("body").attr("JSError",msg);
    }
</script>

3
이것은 JQuery가로드되지 않은 경우에도 쉽게 확장 할 수 있습니다. onerror 호출 외부에 $ ( 'body'). attr ( "JQLoaded", "Yes")를 추가합니다. 그런 다음 Selenium에서 JSError가 있거나 JQLoaded가 없으면 Javascript 오류를 알립니다.
Nils

51
아니면 그냥 document.body.setAttribute("JSError", msg)jQuery에 의존하는 대신 말할 수 있습니다
Kos

3
HTML 페이지에 영구적으로 추가해야합니까, 아니면 테스트를 실행할 때 동적으로 추가해야합니까? 개발자가 모든 페이지에 해당 스 니펫을 추가하도록 설득 할 수 있을지 모르겠습니다. 자세한 정보를 공유해 주셔서 감사합니다.
Michal

3
링크 된 페이지는 더 이상 사용할 수 없습니다.
Chris B. Behrens

54

JavaScript 오류를 캡처하기 위해이 작업을 수행하고 있습니다.

[TestCleanup]
public void TestCleanup()
{
    var errorStrings = new List<string> 
    { 
        "SyntaxError", 
        "EvalError", 
        "ReferenceError", 
        "RangeError", 
        "TypeError", 
        "URIError" 
    };

    var jsErrors = Driver.Manage().Logs.GetLog(LogType.Browser).Where(x => errorStrings.Any(e => x.Message.Contains(e)));

    if (jsErrors.Any())
    {
        Assert.Fail("JavaScript error(s):" + Environment.NewLine + jsErrors.Aggregate("", (s, entry) => s + entry.Message + Environment.NewLine));
    }
}

3
이 솔루션을 정말 좋아합니다
Rob G

2
최신 버전의 Selenium Driver 3.6.0 및 Firefox 56.0을 사용하는 경우 "GetLog"메소드는 "객체 참조가 객체의 인스턴스로 설정되지 않음"을 발생시킵니다. 이유를 알 수 없습니다. 이것은 이전 버전의 WebDriver / Firefox
David Rogers

2
@DavidRogers이 때문에 더 이상 geckodriver에서 작동하지 않는다고 생각합니다. github.com/mozilla/geckodriver/issues/284
Christian Hujer

19

이것이 언제 바뀌 었는지 확실하지 않지만 지금은 Python에서 작동합니다. 이 파일은 자바 스크립트 오류가있는 간단한 페이지입니다.

In [11]: driver.get("file:///tmp/a.html")

In [12]: driver.get_log("browser")
Out[12]: 
[{u'level': u'SEVERE',
  u'message': u'ReferenceError: foo is not defined',
  u'timestamp': 1450769357488,
  u'type': u''},
 {u'level': u'INFO',
  u'message': u'The character encoding of the HTML document was not declared. The document will render with garbled text in some browser configurations if the document contains characters from outside the US-ASCII range. The character encoding of the page must be declared in the document or in the transfer protocol.',
  u'timestamp': 1450769357498,
  u'type': u''}]

Python-Selenium 버전 2.48.0 Linux Firefox 43.0


이것은 webdriver.io에서도 작동합니다. driver.log("browser").then(function(results){ console.log(results.value); }
Tyler Hawkins

이것은 인해 현재이 문제에 파이어 폭스와 함께 작동하지 않습니다 github.com/mozilla/geckodriver/issues/284
기독교 Hujer에게

7

내가 사용하는 python webdriver 솔루션은 다음과 같습니다.

def check_browser_errors(driver):
    """
    Checks browser for errors, returns a list of errors
    :param driver:
    :return:
    """
    try:
        browserlogs = driver.get_log('browser')
    except (ValueError, WebDriverException) as e:
        # Some browsers does not support getting logs
        LOGGER.debug("Could not get browser logs for driver %s due to exception: %s",
                     driver, e)
        return []

    errors = []
    for entry in browserlogs:
        if entry['level'] == 'SEVERE':
            errors.append(entry)
    return errors

6

JSErrorCollector 가 작업을 수행합니다.

일단 구성되면 다음과 같은 문제가 있습니다.

List<JavaScriptError> jsErrorList = JavaScriptError.readErrors(driver);

2
참고 :이 프로젝트는 현재 파이어 폭스 지원
AlignedDev

1
4 년 전 마지막 커밋에서 Firefox 36과 Firebug에 대해 이야기합니다. 그 이후로 많은 것이 변경되었습니다.
Fla

이것에 대한 원래 블로그 게시물입니까? mguillem.wordpress.com/2011/10/11/…
David


3

jhanifen의 답변을 반복하고 싶습니다. 다음은 jQuery에 의존하지 않는 자바 스크립트 솔루션입니다. 페이지 하단에 보이지 않는 HTML 목록을 만들어 오류를 계속합니다.

(function () {
    var ul = null;
    function createErrorList() {
        ul = document.createElement('ul');
        ul.setAttribute('id', 'js_error_list');
        ul.style.display = 'none';
        document.body.appendChild(ul);
    }
    window.onerror = function(msg){
        if (ul === null)
            createErrorList();
        var li = document.createElement("li");
        li.appendChild(document.createTextNode(msg));
        ul.appendChild(li);
    };
})();

2

"window.onerror"솔루션이 작동하지 않았습니다.

그래서 저에게 도움이 된 user-extensions.js를 변경하는 또 다른 솔루션을 지적하고 싶습니다.
Selenium이 페이지에 JavaScript 오류가 있는지 감지 할 수 있습니까?

주요 이점 : 확인을 위해 페이지 소스변경할 필요가 없습니다 .

다음은 user-extensions.js를 사용하는 방법입니다 :
Selenium-IDE와 함께 사용자 확장 사용

참고 :이 솔루션은 Firefox에서만 작동합니다.


2

여기 jhanifen의 응답에서 영감을 얻은 내 솔루션 :

// common.js - js file common to the entire app
globalError = []
window.onerror = function (msg, url, line, col, error) {
    globalError.push({msg:msg, url:url, line:line})
};

# tests.py
def tearDown(driver):
    # assert on js error 
    ret = driver.selenium.execute_script("return globalError ")
    driver.assertFalse(ret, "errors %r " % ret)
    # ret will be a dict looking like 
    # {'line': 50, 'url': 'http://localhost:8081/static/js/common.js', 'msg': 'Uncaught ReferenceError: s is not defined'}

1

Java를 사용하는 경우 테스트 메서드에 대한 주석을 사용하여 Chromedriver 세션에서 수신 된 JS 오류를 쉽게 수집 할 수있는 이 라이브러리 를 사용해보십시오 . 확장 된 주석이있는 JUnit5와 주석을 구문 분석하는 리스너가있는 TestNG에서 작동합니다. 주석에는 테스트 실행 후 발견 된 오류를 어설 션할지 또는 기록할지 여부를 결정할 수있는 부울 값이 포함됩니다.

JUnit5 예 :

@Test
@JSErrorsCollectorJUnit
void referenceErrorTest(TestInfo testInfo) throws InterruptedException {

    // Create a new instance of ChromeDriver.
    driver = new ChromeDriver();

    // Set your test name to point its ChromeDriver session in HashMap.
    JSErrorsDriverHolder.setDriverForTest(testInfo.getDisplayName(), driver);

    // Navigate to URL.
    driver.get("http://testjs.site88.net");

    // The click on the button in the test site should cause JS reference error.
    driver.findElement(By.name("testClickButton")).click();
    waitBeforeClosingBrowser();
}

1

TestCase.tearDown()JavaScript 오류가 발생한 경우 테스트를 실패하게 만드는 Python Selenium 테스트에서 다음 을 사용합니다 .

def tearDown(self):
    browser_logs = driver.get_log("browser")
    errors = [logentry['message'] for logentry in browser_logs if logentry['level'] == 'SEVERE']
    if errors:
        self.fail(f'The following JavaScript errors occurred: {"; ".join(errors)}')

이것은 @kleptog 및 @ d3ming 답변에서 영감을 얻었습니다.


0

페이지에 windows.onerror 이벤트를 포함 시키거나 IE 옵션에서 오류 표시 대화 상자를 활성화합니다. 나중에 Se1을 선택하면 중단됩니다. 추신 : 이것은 여기서 논의되었습니다. 검색하십시오.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.