2014-03-27 2 views
0

내 Firefox 확장 프로그램이 onSecurityChange 이벤트 (HTTPS를 통한 페이지로드)를 수신 대기 중입니다. 그런 이유로 nsIWebProgressListener를 구현하고 getBrowser(). addTabsProgressListener()를 사용하여 등록했습니다.새 탭에서 pageloads 수신

이벤트 처리기 안에는 실제 nsIRequest를 일시 중단하고 다시 시작하는 등의 작업을해야합니다. 이벤트 처리기 내부의 대부분의 코드는 if 문에 래핑되어 aRequest.isPending()이 true인지 확인합니다 (그렇지 않으면 일시 중지가 작동하지 않음).

일반적으로 잘 작동합니다. 그러나 새 탭에서 링크를 열면 onSecurityChange는 페이지로드가 완료 될 때까지 호출되지 않습니다 (즉, isPending은 false 임). 그리고 이것은 너무 늦었습니다.

무엇을해야합니까?

답변

0

세 가지 옵션이 있습니다.

  1. 추가 nsIWebProgressListener와 크게되고 onStateChange 계속 : https://developer.mozilla.org/en-US/docs/XPCOM_Interface_Reference/nsIWebProgressListener#onStateChange%28%29
  2. 브라우저에 이벤트의 청취자를 추가 페이지가로드 듣는 모든 채널을 시청하고, 호출 탭을 얻고있다 부착 https://gist.github.com/Noitidart/9287185#
  3. 사용 채널 관찰자 (리디렉션과 여러 채널 실행을 구분할 수있는 메서드를 사용해야하기 때문에 탭을 가져 오기 위해 loadContext를 얻을 수없는 일부 메서드가 있음)
+0

가장 쉬운 것 같아서 첫 번째 옵션을 선호합니다. 하지만 onStateChange 내의 Firefox/NSS에서 SSL 검증 결과를 얻을 수 있습니까? onSecurityChange에는이 정보를 검색 할 수있는 aState 객체가 있습니다. – firefexx

+0

나는 그걸로 놀아야 만 할 지 확신하지 못합니다. 우리가 배우고있는 것을 배운다. 여기도 배우고있다. – Noitidart

+0

그것은 변하지 않는 것처럼 보인다. 쓸모가 없다. google.de를 입력하면 두 개의 onStateChange 이벤트가 발생합니다. 하나의 STATE_START는 request.name = 'http : // www.google.de' (HTTPS 없음)이고 하나의 STATE_STOP은 request.name ='https : // www.google.de'입니다 (HTTPS 사용). STOP이 너무 늦어서 HTTP 페이지에서 리디렉션 될 때 START가 HTTPS에 대해 실행되지 않으므로 인증서로 아무 것도 할 수 없습니다. ..... HTTPS 페이지가로드 될 때마다 무언가를 수행하는 간단한 방법이 아닙니까? – firefexx

0

내가 onLocationChange를 사용하여 HTTPS 페이지로드를 가로채는 해킹 솔루션을 개발할 것입니다. 아직 완벽하지 않을 수도 있습니다.

새 탭에서 링크를 열 때 이벤트가 제대로 시작되지 않았기 때문에 onSecurityChange (내 질문에 설명 된대로)를 사용할 수 없었습니다.

onLocationChange: function(aBrowser, aWebProgress, aRequest, aLocation, aFlags) { 

    if(aRequest != null) { 

     // suspend early, because that becomes impossible later 
     aRequest.suspend(); 

     // check if it is HTTPS (no HTTP, no about:, etc.) 
     if(aLocation.scheme == "https") { 

      var whateverIWantToDo = { 
       notify: function(timer) { 

        try { 
         // for example I'm interested in the validation result: 
         let secUI = aBrowser.securityUI; 
         secUI.QueryInterface(Components.interfaces.nsISSLStatusProvider); 
         let status = secUI.SSLStatus; 

         // do something what you want here 
         // and do not forget to resume the request at any point. otherwise that could lead to problems 
         aRequest.resume(); 
         //.... 
         // the reason I suspend the request at all: 
         // I do not want to completely load the page until I know if the certificate is valid 
        } 
        catch(err) { 
         // maybe it's too early to access the SSLStatus when the event handler kicks in. 
         // in this case an error will be thrown which is caught here 
         // wait 10 ms and try it again, usually that works! (I know, it's a bit hacky) 
         var timer = Components.classes["@mozilla.org/timer;1"].createInstance(Components.interfaces.nsITimer); 
         timer.initWithCallback(whateverIWantToDo, 10, Components.interfaces.nsITimer.TYPE_ONE_SHOT); 
        } 

       } 
      } 

      whateverIWantToDo.notify(); 

     } else { 
      // continue normally when it's not a HTTPS request, we want to intercept 
      aRequest.resume(); 
     } 
    } 
}