зеркало из https://github.com/mozilla/gecko-dev.git
Merge m-c to b-s.
This commit is contained in:
Коммит
0cc1845191
|
@ -20,9 +20,6 @@
|
|||
return NS_OK; \
|
||||
} else
|
||||
|
||||
#define NS_OK_DEFUNCT_OBJECT \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x22)
|
||||
|
||||
#define NS_ENSURE_A11Y_SUCCESS(res, ret) \
|
||||
PR_BEGIN_MACRO \
|
||||
nsresult __rv = res; /* Don't evaluate |res| more than once */ \
|
||||
|
|
|
@ -17,10 +17,6 @@
|
|||
class Accessible;
|
||||
class nsIAccessibleTraversalRule;
|
||||
|
||||
// raised when current pivot's position is needed but it is not in the tree.
|
||||
#define NS_ERROR_NOT_IN_TREE \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_GENERAL, 0x26)
|
||||
|
||||
/**
|
||||
* Class represents an accessible pivot.
|
||||
*/
|
||||
|
|
|
@ -19,9 +19,6 @@
|
|||
|
||||
using namespace mozilla::a11y;
|
||||
|
||||
#define NS_OK_NO_NAME_CLAUSE_HANDLED \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x24)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// nsTextEquivUtils. Public.
|
||||
|
||||
|
|
|
@ -78,18 +78,6 @@ class nsIView;
|
|||
typedef nsRefPtrHashtable<nsPtrHashKey<const void>, Accessible>
|
||||
AccessibleHashtable;
|
||||
|
||||
// see Accessible::GetAttrValue
|
||||
#define NS_OK_NO_ARIA_VALUE \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x21)
|
||||
|
||||
// see Accessible::GetNameInternal
|
||||
#define NS_OK_EMPTY_NAME \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x23)
|
||||
|
||||
// see Accessible::GetNameInternal
|
||||
#define NS_OK_NAME_FROM_TOOLTIP \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x25)
|
||||
|
||||
|
||||
#define NS_ACCESSIBLE_IMPL_IID \
|
||||
{ /* 133c8bf4-4913-4355-bd50-426bd1d6e1ad */ \
|
||||
|
|
|
@ -33,7 +33,7 @@
|
|||
#include "nsITableLayout.h"
|
||||
#include "nsITableCellLayout.h"
|
||||
#include "nsFrameSelection.h"
|
||||
#include "nsLayoutErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsArrayUtils.h"
|
||||
#include "nsComponentManagerUtils.h"
|
||||
|
||||
|
|
|
@ -459,6 +459,11 @@ window[chromehidden~="toolbar"] toolbar:not(.toolbar-primary):not(.chromeclass-m
|
|||
display: none;
|
||||
}
|
||||
|
||||
#notification-popup .text-link.custom-link {
|
||||
-moz-binding: url("chrome://global/content/bindings/text.xml#text-label");
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
#invalid-form-popup > description {
|
||||
max-width: 280px;
|
||||
}
|
||||
|
@ -471,6 +476,10 @@ window[chromehidden~="toolbar"] toolbar:not(.toolbar-primary):not(.chromeclass-m
|
|||
-moz-binding: url("chrome://browser/content/urlbarBindings.xml#addon-progress-notification");
|
||||
}
|
||||
|
||||
#identity-request-notification {
|
||||
-moz-binding: url("chrome://browser/content/urlbarBindings.xml#identity-request-notification");
|
||||
}
|
||||
|
||||
/* override hidden="true" for the status bar compatibility shim
|
||||
in case it was persisted for the real status bar */
|
||||
#status-bar {
|
||||
|
|
|
@ -564,6 +564,7 @@
|
|||
onblur="setTimeout(function() document.getElementById('identity-box').style.MozUserFocus = '', 0);">
|
||||
<box id="notification-popup-box" hidden="true" align="center">
|
||||
<image id="default-notification-icon" class="notification-anchor-icon" role="button"/>
|
||||
<image id="identity-notification-icon" class="notification-anchor-icon" role="button"/>
|
||||
<image id="geo-notification-icon" class="notification-anchor-icon" role="button"/>
|
||||
<image id="addons-notification-icon" class="notification-anchor-icon" role="button"/>
|
||||
<image id="indexedDB-notification-icon" class="notification-anchor-icon" role="button"/>
|
||||
|
|
|
@ -78,7 +78,7 @@ function runNextTest() {
|
|||
onHidden.call(nextTest, this);
|
||||
if (!onHiddenArray.length)
|
||||
goNext();
|
||||
});
|
||||
}.bind(this));
|
||||
}, onHiddenArray.length);
|
||||
info("[Test #" + gTestIndex + "] added listeners; panel state: " + PopupNotifications.isPanelOpen);
|
||||
}
|
||||
|
|
|
@ -1175,6 +1175,261 @@
|
|||
</implementation>
|
||||
</binding>
|
||||
|
||||
<binding id="identity-request-notification" extends="chrome://global/content/bindings/notification.xml#popup-notification">
|
||||
<content align="start">
|
||||
|
||||
<xul:image class="popup-notification-icon"
|
||||
xbl:inherits="popupid,src=icon"/>
|
||||
|
||||
<xul:vbox flex="1">
|
||||
<xul:vbox anonid="identity-deck">
|
||||
<xul:vbox flex="1" pack="center"> <!-- 1: add an email -->
|
||||
<html:input type="email" anonid="email" required="required" size="30"/>
|
||||
<xul:description anonid="newidentitydesc"/>
|
||||
<xul:spacer flex="1"/>
|
||||
<xul:label class="text-link custom-link small-margin" anonid="chooseemail" hidden="true"/>
|
||||
</xul:vbox>
|
||||
<xul:vbox flex="1" hidden="true"> <!-- 2: choose an email -->
|
||||
<xul:description anonid="chooseidentitydesc"/>
|
||||
<xul:radiogroup anonid="identities">
|
||||
</xul:radiogroup>
|
||||
<xul:label class="text-link custom-link" anonid="newemail"/>
|
||||
</xul:vbox>
|
||||
</xul:vbox>
|
||||
<xul:hbox class="popup-notification-button-container"
|
||||
pack="end" align="center">
|
||||
<xul:label anonid="tos" class="text-link" hidden="true"/>
|
||||
<xul:label anonid="privacypolicy" class="text-link" hidden="true"/>
|
||||
<xul:spacer flex="1"/>
|
||||
<xul:image anonid="throbber" src="chrome://browser/skin/tabbrowser/loading.png"
|
||||
style="visibility:hidden" width="16" height="16"/>
|
||||
<xul:button anonid="button"
|
||||
type="menu-button"
|
||||
class="popup-notification-menubutton"
|
||||
xbl:inherits="oncommand=buttoncommand,label=buttonlabel,accesskey=buttonaccesskey">
|
||||
<xul:menupopup anonid="menupopup"
|
||||
xbl:inherits="oncommand=menucommand">
|
||||
<children/>
|
||||
<xul:menuitem class="menuitem-iconic popup-notification-closeitem"
|
||||
label="&closeNotificationItem.label;"
|
||||
xbl:inherits="oncommand=closeitemcommand"/>
|
||||
</xul:menupopup>
|
||||
</xul:button>
|
||||
</xul:hbox>
|
||||
</xul:vbox>
|
||||
<xul:vbox pack="start">
|
||||
<xul:toolbarbutton anonid="closebutton"
|
||||
class="messageCloseButton popup-notification-closebutton tabbable"
|
||||
xbl:inherits="oncommand=closebuttoncommand"
|
||||
tooltiptext="&closeNotification.tooltip;"/>
|
||||
</xul:vbox>
|
||||
</content>
|
||||
<implementation>
|
||||
<constructor><![CDATA[
|
||||
// this.notification.options.identity is used to pass identity-specific info to the binding
|
||||
let origin = this.identity.origin
|
||||
|
||||
// Populate text
|
||||
this.emailField.placeholder = gNavigatorBundle.
|
||||
getString("identity.newIdentity.email.placeholder");
|
||||
this.newIdentityDesc.textContent = gNavigatorBundle.getFormattedString(
|
||||
"identity.newIdentity.description", [origin]);
|
||||
this.chooseIdentityDesc.textContent = gNavigatorBundle.getFormattedString(
|
||||
"identity.chooseIdentity.description", [origin]);
|
||||
|
||||
// Show optional terms of service and privacy policy links
|
||||
this._populateLink(this.identity.termsOfService, "tos", "identity.termsOfService");
|
||||
this._populateLink(this.identity.privacyPolicy, "privacypolicy", "identity.privacyPolicy");
|
||||
|
||||
// Populate the list of identities to choose from. The origin is used to provide
|
||||
// better suggestions.
|
||||
let identities = this.SignInToWebsiteUX.getIdentitiesForSite(origin);
|
||||
|
||||
this._populateIdentityList(identities);
|
||||
|
||||
if (typeof this.step == "undefined") {
|
||||
// First opening of this notification
|
||||
// Show the add email pane (0) if there are no existing identities otherwise show the list
|
||||
this.step = "result" in identities && identities.result.length ? 1 : 0;
|
||||
} else {
|
||||
// Already opened so restore previous state
|
||||
if (this.identity.typedEmail) {
|
||||
this.emailField.value = this.identity.typedEmail;
|
||||
}
|
||||
if (this.identity.selected) {
|
||||
// If the user already chose an identity then update the UI to reflect that
|
||||
this.onIdentitySelected();
|
||||
}
|
||||
// Update the view for the step
|
||||
this.step = this.step;
|
||||
}
|
||||
|
||||
// Fire notification with the chosen identity when main button is clicked
|
||||
this.button.addEventListener("command", this._onButtonCommand.bind(this), true);
|
||||
|
||||
// Do the same if enter is pressed in the email field
|
||||
this.emailField.addEventListener("keypress", function emailFieldKeypress(aEvent) {
|
||||
if (aEvent.keyCode != aEvent.DOM_VK_RETURN)
|
||||
return;
|
||||
this._onButtonCommand(aEvent);
|
||||
}.bind(this));
|
||||
|
||||
this.addEmailLink.value = gNavigatorBundle.getString("identity.newIdentity.label");
|
||||
this.addEmailLink.accessKey = gNavigatorBundle.getString("identity.newIdentity.accessKey");
|
||||
this.addEmailLink.addEventListener("click", function addEmailClick(evt) {
|
||||
this.step = 0;
|
||||
}.bind(this));
|
||||
|
||||
this.chooseEmailLink.value = gNavigatorBundle.getString("identity.chooseIdentity.label");
|
||||
this.chooseEmailLink.hidden = !("result" in identities && identities.result.length);
|
||||
this.chooseEmailLink.addEventListener("click", function chooseEmailClick(evt) {
|
||||
this.step = 1;
|
||||
}.bind(this));
|
||||
|
||||
this.emailField.addEventListener("blur", function onEmailBlur() {
|
||||
this.identity.typedEmail = this.emailField.value;
|
||||
}.bind(this));
|
||||
]]></constructor>
|
||||
|
||||
<field name="SignInToWebsiteUX" readonly="true">
|
||||
let sitw = {};
|
||||
Components.utils.import("resource:///modules/SignInToWebsite.jsm", sitw);
|
||||
sitw.SignInToWebsiteUX;
|
||||
</field>
|
||||
|
||||
<field name="newIdentityDesc" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "newidentitydesc");
|
||||
</field>
|
||||
|
||||
<field name="chooseIdentityDesc" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "chooseidentitydesc");
|
||||
</field>
|
||||
|
||||
<field name="identityList" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "identities");
|
||||
</field>
|
||||
|
||||
<field name="emailField" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "email");
|
||||
</field>
|
||||
|
||||
<field name="addEmailLink" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "newemail");
|
||||
</field>
|
||||
|
||||
<field name="chooseEmailLink" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "chooseemail");
|
||||
</field>
|
||||
|
||||
<field name="throbber" readonly="true">
|
||||
document.getAnonymousElementByAttribute(this, "anonid", "throbber");
|
||||
</field>
|
||||
|
||||
<field name="identity" readonly="true">
|
||||
this.notification.options.identity;
|
||||
</field>
|
||||
|
||||
<!-- persist the state on the identity object so we can re-create the
|
||||
notification state upon re-opening -->
|
||||
<property name="step">
|
||||
<getter>
|
||||
return this.identity.step;
|
||||
</getter>
|
||||
<setter><![CDATA[
|
||||
let deck = document.getAnonymousElementByAttribute(this, "anonid", "identity-deck");
|
||||
for (let i = 0; i < deck.children.length; i++) {
|
||||
deck.children[i].hidden = (val != i);
|
||||
}
|
||||
this.identity.step = val;
|
||||
switch (val) {
|
||||
case 0:
|
||||
this.emailField.focus();
|
||||
break;
|
||||
}]]>
|
||||
</setter>
|
||||
</property>
|
||||
|
||||
<method name="onIdentitySelected">
|
||||
<body><![CDATA[
|
||||
this.throbber.style.visibility = "visible";
|
||||
this.button.disabled = true;
|
||||
this.emailField.value = this.identity.selected
|
||||
this.emailField.disabled = true;
|
||||
this.identityList.disabled = true;
|
||||
]]></body>
|
||||
</method>
|
||||
|
||||
<method name="_populateLink">
|
||||
<parameter name="aURL"/>
|
||||
<parameter name="aLinkId"/>
|
||||
<parameter name="aStringId"/>
|
||||
<body><![CDATA[
|
||||
if (aURL) {
|
||||
// Show optional link to aURL
|
||||
let link = document.getAnonymousElementByAttribute(this, "anonid", aLinkId);
|
||||
link.value = gNavigatorBundle.getString(aStringId);
|
||||
link.href = aURL;
|
||||
link.hidden = false;
|
||||
}
|
||||
]]></body>
|
||||
</method>
|
||||
|
||||
<method name="_populateIdentityList">
|
||||
<parameter name="aIdentities"/>
|
||||
<body><![CDATA[
|
||||
let foundLastUsed = false;
|
||||
let lastUsed = this.identity.selected || aIdentities.lastUsed;
|
||||
for (let id in aIdentities.result) {
|
||||
let label = aIdentities.result[id];
|
||||
let opt = this.identityList.appendItem(label);
|
||||
if (label == lastUsed) {
|
||||
this.identityList.selectedItem = opt;
|
||||
foundLastUsed = true;
|
||||
}
|
||||
}
|
||||
if (!foundLastUsed) {
|
||||
this.identityList.selectedIndex = -1;
|
||||
}
|
||||
]]></body>
|
||||
</method>
|
||||
|
||||
<method name="_onButtonCommand">
|
||||
<parameter name="aEvent"/>
|
||||
<body><![CDATA[
|
||||
if (aEvent.target != aEvent.currentTarget)
|
||||
return;
|
||||
let chosenId;
|
||||
switch (this.step) {
|
||||
case 0:
|
||||
aEvent.stopPropagation();
|
||||
if (!this.emailField.validity.valid) {
|
||||
this.emailField.focus();
|
||||
return;
|
||||
}
|
||||
chosenId = this.emailField.value;
|
||||
break;
|
||||
case 1:
|
||||
aEvent.stopPropagation();
|
||||
let selectedItem = this.identityList.selectedItem
|
||||
chosenId = selectedItem ? selectedItem.label : null;
|
||||
if (!chosenId)
|
||||
return;
|
||||
break;
|
||||
default:
|
||||
throw new Error("Unknown case");
|
||||
return;
|
||||
}
|
||||
// Actually select the identity
|
||||
this.SignInToWebsiteUX.selectIdentity(this.identity.rpId, chosenId);
|
||||
this.identity.selected = chosenId;
|
||||
this.onIdentitySelected();
|
||||
]]></body>
|
||||
</method>
|
||||
|
||||
</implementation>
|
||||
</binding>
|
||||
|
||||
|
||||
<binding id="splitmenu">
|
||||
<content>
|
||||
<xul:hbox anonid="menuitem" flex="1"
|
||||
|
|
|
@ -12,6 +12,7 @@ const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
|
|||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource:///modules/SignInToWebsite.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "AddonManager",
|
||||
"resource://gre/modules/AddonManager.jsm");
|
||||
|
@ -308,6 +309,7 @@ BrowserGlue.prototype = {
|
|||
if (this._isPlacesShutdownObserver)
|
||||
os.removeObserver(this, "places-shutdown");
|
||||
webappsUI.uninit();
|
||||
SignInToWebsiteUX.uninit();
|
||||
},
|
||||
|
||||
_onAppDefaults: function BG__onAppDefaults() {
|
||||
|
@ -337,6 +339,8 @@ BrowserGlue.prototype = {
|
|||
|
||||
PageThumbs.init();
|
||||
|
||||
SignInToWebsiteUX.init();
|
||||
|
||||
PdfJs.init();
|
||||
|
||||
Services.obs.notifyObservers(null, "browser-ui-startup-complete", "");
|
||||
|
|
|
@ -909,11 +909,6 @@ SourceScripts.prototype = {
|
|||
|
||||
this._addScript({ url: aPacket.url, startLine: aPacket.startLine }, true);
|
||||
|
||||
// Select the script if it's the preferred one.
|
||||
if (aPacket.url === DebuggerView.Scripts.preferredScriptUrl) {
|
||||
DebuggerView.Scripts.selectScript(aPacket.url);
|
||||
}
|
||||
|
||||
// If there are any stored breakpoints for this script, display them again,
|
||||
// both in the editor and the pane.
|
||||
for each (let breakpoint in DebuggerController.Breakpoints.store) {
|
||||
|
@ -932,14 +927,6 @@ SourceScripts.prototype = {
|
|||
}
|
||||
DebuggerView.Scripts.commitScripts();
|
||||
DebuggerController.Breakpoints.updatePaneBreakpoints();
|
||||
|
||||
// Select the preferred script if one exists, the first entry otherwise.
|
||||
let preferredScriptUrl = DebuggerView.Scripts.preferredScriptUrl;
|
||||
if (preferredScriptUrl && DebuggerView.Scripts.contains(preferredScriptUrl)) {
|
||||
DebuggerView.Scripts.selectScript(preferredScriptUrl);
|
||||
} else {
|
||||
DebuggerView.Scripts.selectIndex(0);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
|
|
|
@ -245,16 +245,6 @@ ScriptsView.prototype = {
|
|||
return false;
|
||||
},
|
||||
|
||||
/**
|
||||
* Selects the script with the specified index from the list.
|
||||
*
|
||||
* @param number aIndex
|
||||
* The script index.
|
||||
*/
|
||||
selectIndex: function DVS_selectIndex(aIndex) {
|
||||
this._scripts.selectedIndex = aIndex;
|
||||
},
|
||||
|
||||
/**
|
||||
* Selects the script with the specified URL from the list.
|
||||
*
|
||||
|
@ -293,13 +283,6 @@ ScriptsView.prototype = {
|
|||
this._scripts.selectedItem.value : null;
|
||||
},
|
||||
|
||||
/**
|
||||
* Gets the most recently selected script url.
|
||||
* @return string | null
|
||||
*/
|
||||
get preferredScriptUrl()
|
||||
this._preferredScriptUrl ? this._preferredScriptUrl : null,
|
||||
|
||||
/**
|
||||
* Returns the list of labels in the scripts container.
|
||||
* @return array
|
||||
|
@ -368,7 +351,7 @@ ScriptsView.prototype = {
|
|||
}
|
||||
}
|
||||
// The script is alphabetically the last one.
|
||||
this._createScriptElement(aLabel, aScript, -1);
|
||||
this._createScriptElement(aLabel, aScript, -1, true);
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -388,7 +371,7 @@ ScriptsView.prototype = {
|
|||
|
||||
for (let i = 0, l = newScripts.length; i < l; i++) {
|
||||
let item = newScripts[i];
|
||||
this._createScriptElement(item.label, item.script, -1);
|
||||
this._createScriptElement(item.label, item.script, -1, true);
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -403,8 +386,12 @@ ScriptsView.prototype = {
|
|||
* @param number aIndex
|
||||
* The index where to insert to new script in the container.
|
||||
* Pass -1 to append the script at the end.
|
||||
* @param boolean aSelectIfEmptyFlag
|
||||
* True to set the newly created script as the currently selected item
|
||||
* if there are no other existing scripts in the container.
|
||||
*/
|
||||
_createScriptElement: function DVS__createScriptElement(aLabel, aScript, aIndex)
|
||||
_createScriptElement: function DVS__createScriptElement(
|
||||
aLabel, aScript, aIndex, aSelectIfEmptyFlag)
|
||||
{
|
||||
// Make sure we don't duplicate anything.
|
||||
if (aLabel == "null" || this.containsLabel(aLabel) || this.contains(aScript.url)) {
|
||||
|
@ -417,6 +404,10 @@ ScriptsView.prototype = {
|
|||
|
||||
scriptItem.setAttribute("tooltiptext", aScript.url);
|
||||
scriptItem.setUserData("sourceScript", aScript, null);
|
||||
|
||||
if (this._scripts.itemCount == 1 && aSelectIfEmptyFlag) {
|
||||
this._scripts.selectedItem = scriptItem;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -452,7 +443,6 @@ ScriptsView.prototype = {
|
|||
}
|
||||
|
||||
this._preferredScript = selectedItem;
|
||||
this._preferredScriptUrl = selectedItem.value;
|
||||
this._scripts.setAttribute("tooltiptext", selectedItem.value);
|
||||
DebuggerController.SourceScripts.showScript(selectedItem.getUserData("sourceScript"));
|
||||
},
|
||||
|
|
|
@ -35,7 +35,6 @@ MOCHITEST_BROWSER_TESTS = \
|
|||
browser_dbg_propertyview-09.js \
|
||||
browser_dbg_propertyview-10.js \
|
||||
browser_dbg_propertyview-edit.js \
|
||||
browser_dbg_reload-same-script.js \
|
||||
browser_dbg_panesize.js \
|
||||
browser_dbg_panesize-inner.js \
|
||||
browser_dbg_stack-01.js \
|
||||
|
@ -44,7 +43,6 @@ MOCHITEST_BROWSER_TESTS = \
|
|||
browser_dbg_stack-04.js \
|
||||
browser_dbg_stack-05.js \
|
||||
browser_dbg_location-changes.js \
|
||||
browser_dbg_location-changes-new.js \
|
||||
browser_dbg_location-changes-blank.js \
|
||||
browser_dbg_script-switching.js \
|
||||
browser_dbg_scripts-sorting.js \
|
||||
|
|
|
@ -1,91 +0,0 @@
|
|||
/* vim:set ts=2 sw=2 sts=2 et: */
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
/**
|
||||
* Make sure that changing the tab location URL to a page with other scripts works.
|
||||
*/
|
||||
|
||||
var gPane = null;
|
||||
var gTab = null;
|
||||
var gDebuggee = null;
|
||||
var gDebugger = null;
|
||||
|
||||
function test()
|
||||
{
|
||||
debug_tab_pane(STACK_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
}
|
||||
|
||||
function testSimpleCall() {
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
Services.tm.currentThread.dispatch({
|
||||
run: function() {
|
||||
var frames = gDebugger.DebuggerView.StackFrames._frames,
|
||||
childNodes = frames.childNodes;
|
||||
|
||||
is(gDebugger.DebuggerController.activeThread.state, "paused",
|
||||
"Should only be getting stack frames while paused.");
|
||||
|
||||
is(frames.querySelectorAll(".dbg-stackframe").length, 1,
|
||||
"Should have only one frame.");
|
||||
|
||||
is(childNodes.length, frames.querySelectorAll(".dbg-stackframe").length,
|
||||
"All children should be frames.");
|
||||
|
||||
isnot(gDebugger.DebuggerView.Scripts.selected, null,
|
||||
"There should be a selected script.");
|
||||
isnot(gDebugger.editor.getText().length, 0,
|
||||
"The source editor should have some text displayed.");
|
||||
|
||||
testLocationChange();
|
||||
}
|
||||
}, 0);
|
||||
});
|
||||
|
||||
gDebuggee.simpleCall();
|
||||
}
|
||||
|
||||
function testLocationChange()
|
||||
{
|
||||
gDebugger.DebuggerController.activeThread.resume(function() {
|
||||
gDebugger.DebuggerController.client.addOneTimeListener("tabNavigated", function(aEvent, aPacket) {
|
||||
ok(true, "tabNavigated event was fired.");
|
||||
gDebugger.DebuggerController.client.addOneTimeListener("tabAttached", function(aEvent, aPacket) {
|
||||
ok(true, "Successfully reattached to the tab again.");
|
||||
|
||||
// Wait for the initial resume...
|
||||
gDebugger.gClient.addOneTimeListener("resumed", function() {
|
||||
isnot(gDebugger.DebuggerView.Scripts.selected, null,
|
||||
"There should be a selected script.");
|
||||
isnot(gDebugger.editor.getText().length, 0,
|
||||
"The source editor should have some text displayed.");
|
||||
|
||||
let menulist = gDebugger.DebuggerView.Scripts._scripts;
|
||||
let noScripts = gDebugger.L10N.getStr("noScriptsText");
|
||||
isnot(menulist.getAttribute("label"), noScripts,
|
||||
"The menulist should not display a notice that there are no scripts availalble.");
|
||||
isnot(menulist.getAttribute("tooltiptext"), "",
|
||||
"The menulist should have a tooltip text attributed.");
|
||||
|
||||
closeDebuggerAndFinish();
|
||||
});
|
||||
});
|
||||
});
|
||||
content.location = EXAMPLE_URL + "browser_dbg_iframes.html";
|
||||
});
|
||||
}
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
removeTab(gTab);
|
||||
gPane = null;
|
||||
gTab = null;
|
||||
gDebuggee = null;
|
||||
gDebugger = null;
|
||||
});
|
|
@ -1,126 +0,0 @@
|
|||
/* Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
/**
|
||||
* Tests if the same script is shown after a page is reloaded.
|
||||
*/
|
||||
|
||||
const TAB_URL = EXAMPLE_URL + "browser_dbg_script-switching.html";
|
||||
|
||||
let gPane = null;
|
||||
let gTab = null;
|
||||
let gDebuggee = null;
|
||||
let gDebugger = null;
|
||||
let gView = null;
|
||||
|
||||
function test()
|
||||
{
|
||||
let step = 0;
|
||||
let scriptShown = false;
|
||||
let scriptShownUrl = null;
|
||||
let resumed = false;
|
||||
let testStarted = false;
|
||||
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gView = gDebugger.DebuggerView;
|
||||
resumed = true;
|
||||
|
||||
executeSoon(startTest);
|
||||
});
|
||||
|
||||
function onScriptShown(aEvent)
|
||||
{
|
||||
scriptShown = aEvent.detail.url.indexOf("-01.js") != -1;
|
||||
scriptShownUrl = aEvent.detail.url;
|
||||
executeSoon(startTest);
|
||||
}
|
||||
|
||||
function onUlteriorScriptShown(aEvent)
|
||||
{
|
||||
scriptShownUrl = aEvent.detail.url;
|
||||
executeSoon(testScriptShown);
|
||||
}
|
||||
|
||||
window.addEventListener("Debugger:ScriptShown", onScriptShown);
|
||||
|
||||
function startTest()
|
||||
{
|
||||
if (scriptShown && resumed && !testStarted) {
|
||||
window.removeEventListener("Debugger:ScriptShown", onScriptShown);
|
||||
window.addEventListener("Debugger:ScriptShown", onUlteriorScriptShown);
|
||||
testStarted = true;
|
||||
Services.tm.currentThread.dispatch({ run: performTest }, 0);
|
||||
}
|
||||
}
|
||||
|
||||
function finishTest()
|
||||
{
|
||||
if (scriptShown && resumed && testStarted) {
|
||||
window.removeEventListener("Debugger:ScriptShown", onUlteriorScriptShown);
|
||||
closeDebuggerAndFinish();
|
||||
}
|
||||
}
|
||||
|
||||
function performTest()
|
||||
{
|
||||
testCurrentScript("-01.js", step);
|
||||
step = 1;
|
||||
reloadPage();
|
||||
}
|
||||
|
||||
function testScriptShown()
|
||||
{
|
||||
if (step === 1) {
|
||||
testCurrentScript("-01.js", step);
|
||||
step = 2;
|
||||
reloadPage();
|
||||
}
|
||||
else if (step === 2) {
|
||||
testCurrentScript("-01.js", step);
|
||||
step = 3;
|
||||
gView.Scripts.selectScript(gView.Scripts.scriptLocations[1]);
|
||||
}
|
||||
else if (step === 3) {
|
||||
testCurrentScript("-02.js", step);
|
||||
step = 4;
|
||||
reloadPage();
|
||||
}
|
||||
else if (step === 4) {
|
||||
testCurrentScript("-02.js", step);
|
||||
finishTest();
|
||||
}
|
||||
}
|
||||
|
||||
function testCurrentScript(part, step)
|
||||
{
|
||||
info("Currently preferred script: " + gView.Scripts.preferredScriptUrl);
|
||||
info("Currently selected script: " + gView.Scripts.selected);
|
||||
|
||||
isnot(gView.Scripts.preferredScriptUrl.indexOf(part), -1,
|
||||
"The preferred script url wasn't set correctly. (" + step + ")");
|
||||
isnot(gView.Scripts.selected.indexOf(part), -1,
|
||||
"The selected script isn't the correct one. (" + step + ")");
|
||||
is(gView.Scripts.selected, scriptShownUrl,
|
||||
"The shown script is not the the correct one. (" + step + ")");
|
||||
}
|
||||
|
||||
function reloadPage()
|
||||
{
|
||||
executeSoon(function() {
|
||||
gDebuggee.location.reload();
|
||||
});
|
||||
}
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
removeTab(gTab);
|
||||
gPane = null;
|
||||
gTab = null;
|
||||
gDebuggee = null;
|
||||
gDebugger = null;
|
||||
gView = null;
|
||||
});
|
||||
}
|
|
@ -383,3 +383,21 @@ social.remove.accesskey=R
|
|||
|
||||
# LOCALIZATION NOTE (social.enabled.message): %1$S is the name of the social provider, %2$S is brandShortName (e.g. Firefox)
|
||||
social.activated.message=%1$S integration with %2$S has been activated.
|
||||
|
||||
# Identity notifications popups
|
||||
identity.termsOfService = Terms of Service
|
||||
identity.privacyPolicy = Privacy Policy
|
||||
identity.chooseIdentity.description = Sign in to %S
|
||||
identity.chooseIdentity.label = Use an existing email
|
||||
identity.newIdentity.label = Use a different email
|
||||
identity.newIdentity.accessKey = e
|
||||
identity.newIdentity.email.placeholder = Email
|
||||
# LOCALIZATION NOTE (identity.newIdentity.description, identity.chooseIdentity.description): %S is the website origin (ie. https://www.mozilla.org) shown in popup notifications.
|
||||
identity.newIdentity.description = Enter your email address to sign in to %S
|
||||
identity.next.label = Next
|
||||
identity.next.accessKey = n
|
||||
# LOCALIZATION NOTE: shown in the popup notification when a user successfully logs into a website
|
||||
# LOCALIZATION NOTE (identity.loggedIn.description): %S is the website origin (ie. https://www.mozilla.org)
|
||||
identity.loggedIn.description = Signed in as: %S
|
||||
identity.loggedIn.signOut.label = Sign Out
|
||||
identity.loggedIn.signOut.accessKey = O
|
||||
|
|
|
@ -19,6 +19,7 @@ EXTRA_JS_MODULES = \
|
|||
NetworkPrioritizer.jsm \
|
||||
NewTabUtils.jsm \
|
||||
offlineAppCache.jsm \
|
||||
SignInToWebsite.jsm \
|
||||
TelemetryTimestamps.jsm \
|
||||
Social.jsm \
|
||||
webappsUI.jsm \
|
||||
|
|
|
@ -0,0 +1,235 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
const EXPORTED_SYMBOLS = ["SignInToWebsiteUX"];
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cu = Components.utils;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "IdentityService",
|
||||
"resource://gre/modules/identity/Identity.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "Logger",
|
||||
"resource://gre/modules/identity/LogUtils.jsm");
|
||||
|
||||
function log(...aMessageArgs) {
|
||||
Logger.log.apply(Logger, ["SignInToWebsiteUX"].concat(aMessageArgs));
|
||||
}
|
||||
|
||||
let SignInToWebsiteUX = {
|
||||
|
||||
init: function SignInToWebsiteUX_init() {
|
||||
Services.obs.addObserver(this, "identity-request", false);
|
||||
Services.obs.addObserver(this, "identity-auth", false);
|
||||
Services.obs.addObserver(this, "identity-auth-complete", false);
|
||||
Services.obs.addObserver(this, "identity-login-state-changed", false);
|
||||
},
|
||||
|
||||
uninit: function SignInToWebsiteUX_uninit() {
|
||||
Services.obs.removeObserver(this, "identity-request");
|
||||
Services.obs.removeObserver(this, "identity-auth");
|
||||
Services.obs.removeObserver(this, "identity-auth-complete");
|
||||
Services.obs.removeObserver(this, "identity-login-state-changed");
|
||||
},
|
||||
|
||||
observe: function SignInToWebsiteUX_observe(aSubject, aTopic, aData) {
|
||||
log("observe: received", aTopic, "with", aData, "for", aSubject);
|
||||
let options = null;
|
||||
if (aSubject) {
|
||||
options = aSubject.wrappedJSObject;
|
||||
}
|
||||
switch(aTopic) {
|
||||
case "identity-request":
|
||||
this.requestLogin(options);
|
||||
break;
|
||||
case "identity-auth":
|
||||
this._openAuthenticationUI(aData, options);
|
||||
break;
|
||||
case "identity-auth-complete":
|
||||
this._closeAuthenticationUI(aData);
|
||||
break;
|
||||
case "identity-login-state-changed":
|
||||
let emailAddress = aData;
|
||||
if (emailAddress) {
|
||||
this._removeRequestUI(options);
|
||||
this._showLoggedInUI(emailAddress, options);
|
||||
} else {
|
||||
this._removeLoggedInUI(options);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
Logger.reportError("SignInToWebsiteUX", "Unknown observer notification:", aTopic);
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* The website is requesting login so the user must choose an identity to use.
|
||||
*/
|
||||
requestLogin: function SignInToWebsiteUX_requestLogin(aOptions) {
|
||||
let windowID = aOptions.rpId;
|
||||
log("requestLogin", aOptions);
|
||||
let [chromeWin, browserEl] = this._getUIForWindowID(windowID);
|
||||
|
||||
// message is not shown in the UI but is required
|
||||
let message = aOptions.origin;
|
||||
let mainAction = {
|
||||
label: chromeWin.gNavigatorBundle.getString("identity.next.label"),
|
||||
accessKey: chromeWin.gNavigatorBundle.getString("identity.next.accessKey"),
|
||||
callback: function() {}, // required
|
||||
};
|
||||
let options = {
|
||||
identity: {
|
||||
origin: aOptions.origin,
|
||||
},
|
||||
};
|
||||
let secondaryActions = [];
|
||||
|
||||
// add some extra properties to the notification to store some identity-related state
|
||||
for (let opt in aOptions) {
|
||||
options.identity[opt] = aOptions[opt];
|
||||
}
|
||||
log("requestLogin: rpId: ", options.identity.rpId);
|
||||
|
||||
chromeWin.PopupNotifications.show(browserEl, "identity-request", message,
|
||||
"identity-notification-icon", mainAction,
|
||||
[], options);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the list of possible identities to login to the given origin.
|
||||
*/
|
||||
getIdentitiesForSite: function SignInToWebsiteUX_getIdentitiesForSite(aOrigin) {
|
||||
return IdentityService.RP.getIdentitiesForSite(aOrigin);
|
||||
},
|
||||
|
||||
/**
|
||||
* User chose a new or existing identity from the doorhanger after a request() call
|
||||
*/
|
||||
selectIdentity: function SignInToWebsiteUX_selectIdentity(aRpId, aIdentity) {
|
||||
log("selectIdentity: rpId: ", aRpId, " identity: ", aIdentity);
|
||||
IdentityService.selectIdentity(aRpId, aIdentity);
|
||||
},
|
||||
|
||||
// Private
|
||||
|
||||
/**
|
||||
* Return the chrome window and <browser> for the given outer window ID.
|
||||
*/
|
||||
_getUIForWindowID: function(aWindowID) {
|
||||
let someWindow = Services.wm.getMostRecentWindow("navigator:browser");
|
||||
if (!someWindow) {
|
||||
Logger.reportError("SignInToWebsiteUX", "no window");
|
||||
return [null, null];
|
||||
}
|
||||
|
||||
let windowUtils = someWindow.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDOMWindowUtils);
|
||||
let content = windowUtils.getOuterWindowWithId(aWindowID);
|
||||
|
||||
if (content) {
|
||||
let browser = content.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIWebNavigation)
|
||||
.QueryInterface(Ci.nsIDocShell).chromeEventHandler;
|
||||
let chromeWin = browser.ownerDocument.defaultView;
|
||||
return [chromeWin, browser];
|
||||
}
|
||||
Logger.reportError("SignInToWebsiteUX", "no content");
|
||||
|
||||
return [null, null];
|
||||
},
|
||||
|
||||
/**
|
||||
* Open UI with a content frame displaying aAuthURI so that the user can authenticate with their
|
||||
* IDP. Then tell Identity.jsm the identifier for the window so that it knows that the DOM API
|
||||
* calls are for this authentication flow.
|
||||
*/
|
||||
_openAuthenticationUI: function _openAuthenticationUI(aAuthURI, aContext) {
|
||||
// Open a tab/window with aAuthURI with an identifier (aID) attached so that the DOM APIs know this is an auth. window.
|
||||
let chromeWin = Services.wm.getMostRecentWindow('navigator:browser');
|
||||
let features = "chrome=false,width=640,height=480,centerscreen,location=yes,resizable=yes,scrollbars=yes,status=yes";
|
||||
log("aAuthURI: ", aAuthURI);
|
||||
let authWin = Services.ww.openWindow(chromeWin, "about:blank", "", features, null);
|
||||
let windowID = authWin.QueryInterface(Ci.nsIInterfaceRequestor).getInterface(Ci.nsIDOMWindowUtils).outerWindowID;
|
||||
log("authWin outer id: ", windowID);
|
||||
|
||||
let provId = aContext.provId;
|
||||
// Tell the ID service about the id before loading the url
|
||||
IdentityService.IDP.setAuthenticationFlow(windowID, provId);
|
||||
|
||||
authWin.location = aAuthURI;
|
||||
},
|
||||
|
||||
_closeAuthenticationUI: function _closeAuthenticationUI(aAuthId) {
|
||||
log("_closeAuthenticationUI:", aAuthId);
|
||||
let [chromeWin, browserEl] = this._getUIForWindowID(aAuthId);
|
||||
if (chromeWin)
|
||||
chromeWin.close();
|
||||
else
|
||||
Logger.reportError("SignInToWebsite", "Could not close window with ID", aAuthId);
|
||||
},
|
||||
|
||||
/**
|
||||
* Show a doorhanger indicating the currently logged-in user.
|
||||
*/
|
||||
_showLoggedInUI: function _showLoggedInUI(aIdentity, aContext) {
|
||||
let windowID = aContext.rpId;
|
||||
log("_showLoggedInUI for ", windowID);
|
||||
let [chromeWin, browserEl] = this._getUIForWindowID(windowID);
|
||||
|
||||
let message = chromeWin.gNavigatorBundle.getFormattedString("identity.loggedIn.description",
|
||||
[aIdentity]);
|
||||
let mainAction = {
|
||||
label: chromeWin.gNavigatorBundle.getString("identity.loggedIn.signOut.label"),
|
||||
accessKey: chromeWin.gNavigatorBundle.getString("identity.loggedIn.signOut.accessKey"),
|
||||
callback: function() {
|
||||
log("sign out callback fired");
|
||||
IdentityService.RP.logout(windowID);
|
||||
},
|
||||
};
|
||||
let secondaryActions = [];
|
||||
let options = {
|
||||
dismissed: true,
|
||||
};
|
||||
let loggedInNot = chromeWin.PopupNotifications.show(browserEl, "identity-logged-in", message,
|
||||
"identity-notification-icon", mainAction,
|
||||
secondaryActions, options);
|
||||
loggedInNot.rpId = windowID;
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove the doorhanger indicating the currently logged-in user.
|
||||
*/
|
||||
_removeLoggedInUI: function _removeLoggedInUI(aContext) {
|
||||
let windowID = aContext.rpId;
|
||||
log("_removeLoggedInUI for ", windowID);
|
||||
if (!windowID)
|
||||
throw "_removeLoggedInUI: Invalid RP ID";
|
||||
let [chromeWin, browserEl] = this._getUIForWindowID(windowID);
|
||||
|
||||
let loggedInNot = chromeWin.PopupNotifications.getNotification("identity-logged-in", browserEl);
|
||||
if (loggedInNot)
|
||||
chromeWin.PopupNotifications.remove(loggedInNot);
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove the doorhanger indicating the currently logged-in user.
|
||||
*/
|
||||
_removeRequestUI: function _removeRequestUI(aContext) {
|
||||
let windowID = aContext.rpId;
|
||||
log("_removeRequestUI for ", windowID);
|
||||
let [chromeWin, browserEl] = this._getUIForWindowID(windowID);
|
||||
|
||||
let requestNot = chromeWin.PopupNotifications.getNotification("identity-request", browserEl);
|
||||
if (requestNot)
|
||||
chromeWin.PopupNotifications.remove(requestNot);
|
||||
},
|
||||
|
||||
};
|
|
@ -14,6 +14,7 @@ include $(topsrcdir)/config/rules.mk
|
|||
_BROWSER_FILES = \
|
||||
browser_NetworkPrioritizer.js \
|
||||
browser_TelemetryTimestamps.js \
|
||||
browser_SignInToWebsite.js \
|
||||
$(NULL)
|
||||
|
||||
ifeq ($(MOZ_WIDGET_TOOLKIT),windows)
|
||||
|
|
|
@ -0,0 +1,549 @@
|
|||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
/**
|
||||
* TO TEST:
|
||||
* - test state saved on doorhanger dismissal
|
||||
* - links to switch steps
|
||||
* - TOS and PP link clicks
|
||||
* - identityList is populated correctly
|
||||
*/
|
||||
|
||||
Services.prefs.setBoolPref("toolkit.identity.debug", true);
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "IdentityService",
|
||||
"resource://gre/modules/identity/Identity.jsm");
|
||||
|
||||
const TEST_ORIGIN = "https://example.com";
|
||||
const TEST_EMAIL = "user@example.com";
|
||||
|
||||
let gTestIndex = 0;
|
||||
let outerWinId = gBrowser.contentWindow.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDOMWindowUtils).outerWindowID;
|
||||
|
||||
function NotificationBase(aNotId) {
|
||||
this.id = aNotId;
|
||||
}
|
||||
NotificationBase.prototype = {
|
||||
message: TEST_ORIGIN,
|
||||
mainAction: {
|
||||
label: "",
|
||||
callback: function() {
|
||||
this.mainActionClicked = true;
|
||||
}.bind(this),
|
||||
},
|
||||
secondaryActions: [],
|
||||
options: {
|
||||
"identity": {
|
||||
origin: TEST_ORIGIN,
|
||||
rpId: outerWinId,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
let tests = [
|
||||
{
|
||||
name: "test_request_required_typed",
|
||||
|
||||
run: function() {
|
||||
setupRPFlow();
|
||||
this.notifyOptions = {
|
||||
rpId: outerWinId,
|
||||
origin: TEST_ORIGIN,
|
||||
};
|
||||
this.notifyObj = new NotificationBase("identity-request");
|
||||
Services.obs.notifyObservers({wrappedJSObject: this.notifyOptions},
|
||||
"identity-request", null);
|
||||
},
|
||||
|
||||
onShown: function(popup) {
|
||||
checkPopup(popup, this.notifyObj);
|
||||
let notification = popup.childNodes[0];
|
||||
|
||||
// Check identity popup state
|
||||
let state = notification.identity;
|
||||
ok(!state.typedEmail, "Nothing should be typed yet");
|
||||
ok(!state.selected, "Identity should not be selected yet");
|
||||
ok(!state.termsOfService, "No TOS specified");
|
||||
ok(!state.privacyPolicy, "No PP specified");
|
||||
is(state.step, 0, "Step should be persisted with default value");
|
||||
is(state.rpId, outerWinId, "Check rpId");
|
||||
is(state.origin, TEST_ORIGIN, "Check origin");
|
||||
|
||||
is(notification.step, 0, "Should be on the new email step");
|
||||
is(notification.chooseEmailLink.hidden, true, "Identity list is empty so link to list view should be hidden");
|
||||
is(notification.addEmailLink.parentElement.hidden, true, "We are already on the email input step so choose email pane should be hidden");
|
||||
is(notification.emailField.value, "", "Email field should default to empty on a new notification");
|
||||
let notifDoc = notification.ownerDocument;
|
||||
ok(notifDoc.getAnonymousElementByAttribute(notification, "anonid", "tos").hidden,
|
||||
"TOS link should be hidden");
|
||||
ok(notifDoc.getAnonymousElementByAttribute(notification, "anonid", "privacypolicy").hidden,
|
||||
"PP link should be hidden");
|
||||
|
||||
// Try to continue with a missing email address
|
||||
triggerMainCommand(popup);
|
||||
is(notification.throbber.style.visibility, "hidden", "is throbber visible");
|
||||
ok(!notification.button.disabled, "Button should not be disabled");
|
||||
is(window.gIdentitySelected, null, "Check no identity selected");
|
||||
|
||||
// Fill in an invalid email address and try again
|
||||
notification.emailField.value = "foo";
|
||||
triggerMainCommand(popup);
|
||||
is(notification.throbber.style.visibility, "hidden", "is throbber visible");
|
||||
ok(!notification.button.disabled, "Button should not be disabled");
|
||||
is(window.gIdentitySelected, null, "Check no identity selected");
|
||||
|
||||
// Fill in an email address and try again
|
||||
notification.emailField.value = TEST_EMAIL;
|
||||
triggerMainCommand(popup);
|
||||
is(window.gIdentitySelected.rpId, outerWinId, "Check identity selected rpId");
|
||||
is(window.gIdentitySelected.identity, TEST_EMAIL, "Check identity selected email");
|
||||
is(notification.identity.selected, TEST_EMAIL, "Check persisted email");
|
||||
is(notification.throbber.style.visibility, "visible", "is throbber visible");
|
||||
ok(notification.button.disabled, "Button should be disabled");
|
||||
ok(notification.emailField.disabled, "Email field should be disabled");
|
||||
ok(notification.identityList.disabled, "Identity list should be disabled");
|
||||
|
||||
PopupNotifications.getNotification("identity-request").remove();
|
||||
},
|
||||
|
||||
onHidden: function(popup) { },
|
||||
},
|
||||
{
|
||||
name: "test_request_optional",
|
||||
|
||||
run: function() {
|
||||
this.notifyOptions = {
|
||||
rpId: outerWinId,
|
||||
origin: TEST_ORIGIN,
|
||||
privacyPolicy: TEST_ORIGIN + "/pp.txt",
|
||||
termsOfService: TEST_ORIGIN + "/tos.tzt",
|
||||
};
|
||||
this.notifyObj = new NotificationBase("identity-request");
|
||||
Services.obs.notifyObservers({ wrappedJSObject: this.notifyOptions },
|
||||
"identity-request", null);
|
||||
},
|
||||
|
||||
onShown: function(popup) {
|
||||
checkPopup(popup, this.notifyObj);
|
||||
let notification = popup.childNodes[0];
|
||||
|
||||
// Check identity popup state
|
||||
let state = notification.identity;
|
||||
ok(!state.typedEmail, "Nothing should be typed yet");
|
||||
ok(!state.selected, "Identity should not be selected yet");
|
||||
is(state.termsOfService, this.notifyOptions.termsOfService, "Check TOS URL");
|
||||
is(state.privacyPolicy, this.notifyOptions.privacyPolicy, "Check PP URL");
|
||||
is(state.step, 0, "Step should be persisted with default value");
|
||||
is(state.rpId, outerWinId, "Check rpId");
|
||||
is(state.origin, TEST_ORIGIN, "Check origin");
|
||||
|
||||
is(notification.step, 0, "Should be on the new email step");
|
||||
is(notification.chooseEmailLink.hidden, true, "Identity list is empty so link to list view should be hidden");
|
||||
is(notification.addEmailLink.parentElement.hidden, true, "We are already on the email input step so choose email pane should be hidden");
|
||||
is(notification.emailField.value, "", "Email field should default to empty on a new notification");
|
||||
let notifDoc = notification.ownerDocument;
|
||||
let tosLink = notifDoc.getAnonymousElementByAttribute(notification, "anonid", "tos");
|
||||
ok(!tosLink.hidden, "TOS link should be visible");
|
||||
is(tosLink.href, this.notifyOptions.termsOfService, "Check TOS link URL");
|
||||
let ppLink = notifDoc.getAnonymousElementByAttribute(notification, "anonid", "privacypolicy");
|
||||
ok(!ppLink.hidden, "PP link should be visible");
|
||||
is(ppLink.href, this.notifyOptions.privacyPolicy, "Check PP link URL");
|
||||
|
||||
// Try to continue with a missing email address
|
||||
triggerMainCommand(popup);
|
||||
is(notification.throbber.style.visibility, "hidden", "is throbber visible");
|
||||
ok(!notification.button.disabled, "Button should not be disabled");
|
||||
is(window.gIdentitySelected, null, "Check no identity selected");
|
||||
|
||||
// Fill in an invalid email address and try again
|
||||
notification.emailField.value = "foo";
|
||||
triggerMainCommand(popup);
|
||||
is(notification.throbber.style.visibility, "hidden", "is throbber visible");
|
||||
ok(!notification.button.disabled, "Button should not be disabled");
|
||||
is(window.gIdentitySelected, null, "Check no identity selected");
|
||||
|
||||
// Fill in an email address and try again
|
||||
notification.emailField.value = TEST_EMAIL;
|
||||
triggerMainCommand(popup);
|
||||
is(window.gIdentitySelected.rpId, outerWinId, "Check identity selected rpId");
|
||||
is(window.gIdentitySelected.identity, TEST_EMAIL, "Check identity selected email");
|
||||
is(notification.identity.selected, TEST_EMAIL, "Check persisted email");
|
||||
is(notification.throbber.style.visibility, "visible", "is throbber visible");
|
||||
ok(notification.button.disabled, "Button should be disabled");
|
||||
ok(notification.emailField.disabled, "Email field should be disabled");
|
||||
ok(notification.identityList.disabled, "Identity list should be disabled");
|
||||
|
||||
PopupNotifications.getNotification("identity-request").remove();
|
||||
},
|
||||
|
||||
onHidden: function(popup) {},
|
||||
},
|
||||
{
|
||||
name: "test_login_state_changed",
|
||||
run: function () {
|
||||
this.notifyOptions = {
|
||||
rpId: outerWinId,
|
||||
};
|
||||
this.notifyObj = new NotificationBase("identity-logged-in");
|
||||
this.notifyObj.message = "Signed in as: user@example.com";
|
||||
this.notifyObj.mainAction.label = "Sign Out";
|
||||
this.notifyObj.mainAction.accessKey = "O";
|
||||
Services.obs.notifyObservers({ wrappedJSObject: this.notifyOptions },
|
||||
"identity-login-state-changed", TEST_EMAIL);
|
||||
executeSoon(function() {
|
||||
PopupNotifications.getNotification("identity-logged-in").anchorElement.click();
|
||||
});
|
||||
},
|
||||
|
||||
onShown: function(popup) {
|
||||
checkPopup(popup, this.notifyObj);
|
||||
|
||||
// Fire the notification that the user is no longer logged-in to close the UI.
|
||||
Services.obs.notifyObservers({ wrappedJSObject: this.notifyOptions },
|
||||
"identity-login-state-changed", null);
|
||||
},
|
||||
|
||||
onHidden: function(popup) {},
|
||||
},
|
||||
{
|
||||
name: "test_login_state_changed_logout",
|
||||
run: function () {
|
||||
this.notifyOptions = {
|
||||
rpId: outerWinId,
|
||||
};
|
||||
this.notifyObj = new NotificationBase("identity-logged-in");
|
||||
this.notifyObj.message = "Signed in as: user@example.com";
|
||||
this.notifyObj.mainAction.label = "Sign Out";
|
||||
this.notifyObj.mainAction.accessKey = "O";
|
||||
Services.obs.notifyObservers({ wrappedJSObject: this.notifyOptions },
|
||||
"identity-login-state-changed", TEST_EMAIL);
|
||||
executeSoon(function() {
|
||||
PopupNotifications.getNotification("identity-logged-in").anchorElement.click();
|
||||
});
|
||||
},
|
||||
|
||||
onShown: function(popup) {
|
||||
checkPopup(popup, this.notifyObj);
|
||||
|
||||
// This time trigger the Sign Out button and make sure the UI goes away.
|
||||
triggerMainCommand(popup);
|
||||
},
|
||||
|
||||
onHidden: function(popup) {},
|
||||
},
|
||||
];
|
||||
|
||||
function test_auth() {
|
||||
let notifyOptions = {
|
||||
provId: outerWinId,
|
||||
origin: TEST_ORIGIN,
|
||||
};
|
||||
|
||||
Services.obs.addObserver(function() {
|
||||
// prepare to send auth-complete and close the window
|
||||
let winCloseObs = new WindowObserver(function(closedWin) {
|
||||
info("closed window");
|
||||
finish();
|
||||
}, "domwindowclosed");
|
||||
Services.ww.registerNotification(winCloseObs);
|
||||
Services.obs.notifyObservers(null, "identity-auth-complete", IdentityService.IDP.authenticationFlowSet.authId);
|
||||
|
||||
}, "test-identity-auth-window", false);
|
||||
|
||||
let winObs = new WindowObserver(function(authWin) {
|
||||
ok(authWin, "Authentication window opened");
|
||||
ok(authWin.contentWindow.location);
|
||||
});
|
||||
|
||||
Services.ww.registerNotification(winObs);
|
||||
|
||||
Services.obs.notifyObservers({ wrappedJSObject: notifyOptions },
|
||||
"identity-auth", TEST_ORIGIN + "/auth");
|
||||
}
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
registerCleanupFunction(cleanUp);
|
||||
|
||||
let sitw = {};
|
||||
Components.utils.import("resource:///modules/SignInToWebsite.jsm", sitw);
|
||||
|
||||
ok(sitw.SignInToWebsiteUX, "SignInToWebsiteUX object exists");
|
||||
|
||||
// Replace implementation of ID Service functions for testing
|
||||
window.selectIdentity = sitw.SignInToWebsiteUX.selectIdentity;
|
||||
sitw.SignInToWebsiteUX.selectIdentity = function(aRpId, aIdentity) {
|
||||
info("Identity selected: " + aIdentity);
|
||||
window.gIdentitySelected = {rpId: aRpId, identity: aIdentity};
|
||||
};
|
||||
|
||||
window.setAuthenticationFlow = IdentityService.IDP.setAuthenticationFlow;
|
||||
IdentityService.IDP.setAuthenticationFlow = function(aAuthId, aProvId) {
|
||||
info("setAuthenticationFlow: " + aAuthId + " : " + aProvId);
|
||||
this.authenticationFlowSet = { authId: aAuthId, provId: aProvId };
|
||||
Services.obs.notifyObservers(null, "test-identity-auth-window", aAuthId);
|
||||
};
|
||||
|
||||
runNextTest();
|
||||
}
|
||||
|
||||
// Cleanup between tests
|
||||
function resetState() {
|
||||
delete window.gIdentitySelected;
|
||||
delete IdentityService.IDP.authenticationFlowSet;
|
||||
IdentityService.reset();
|
||||
}
|
||||
|
||||
// Cleanup after all tests
|
||||
function cleanUp() {
|
||||
info("cleanup");
|
||||
resetState();
|
||||
|
||||
for (let topic in gActiveObservers)
|
||||
Services.obs.removeObserver(gActiveObservers[topic], topic);
|
||||
for (let eventName in gActiveListeners)
|
||||
PopupNotifications.panel.removeEventListener(eventName, gActiveListeners[eventName], false);
|
||||
delete IdentityService.RP._rpFlows[outerWinId];
|
||||
|
||||
// Put the JSM functions back to how they were
|
||||
IdentityService.IDP.setAuthenticationFlow = window.setAuthenticationFlow;
|
||||
delete window.setAuthenticationFlow;
|
||||
|
||||
let sitw = {};
|
||||
Components.utils.import("resource:///modules/SignInToWebsite.jsm", sitw);
|
||||
sitw.SignInToWebsiteUX.selectIdentity = window.selectIdentity;
|
||||
delete window.selectIdentity;
|
||||
|
||||
Services.prefs.clearUserPref("toolkit.identity.debug");
|
||||
}
|
||||
|
||||
let gActiveListeners = {};
|
||||
let gActiveObservers = {};
|
||||
let gShownState = {};
|
||||
|
||||
function runNextTest() {
|
||||
let nextTest = tests[gTestIndex];
|
||||
|
||||
function goNext() {
|
||||
resetState();
|
||||
if (++gTestIndex == tests.length)
|
||||
executeSoon(test_auth);
|
||||
else
|
||||
executeSoon(runNextTest);
|
||||
}
|
||||
|
||||
function addObserver(topic) {
|
||||
function observer() {
|
||||
Services.obs.removeObserver(observer, "PopupNotifications-" + topic);
|
||||
delete gActiveObservers["PopupNotifications-" + topic];
|
||||
|
||||
info("[Test #" + gTestIndex + "] observer for " + topic + " called");
|
||||
nextTest[topic]();
|
||||
goNext();
|
||||
}
|
||||
Services.obs.addObserver(observer, "PopupNotifications-" + topic, false);
|
||||
gActiveObservers["PopupNotifications-" + topic] = observer;
|
||||
}
|
||||
|
||||
if (nextTest.backgroundShow) {
|
||||
addObserver("backgroundShow");
|
||||
} else if (nextTest.updateNotShowing) {
|
||||
addObserver("updateNotShowing");
|
||||
} else {
|
||||
doOnPopupEvent("popupshowing", function () {
|
||||
info("[Test #" + gTestIndex + "] popup showing");
|
||||
});
|
||||
doOnPopupEvent("popupshown", function () {
|
||||
gShownState[gTestIndex] = true;
|
||||
info("[Test #" + gTestIndex + "] popup shown");
|
||||
nextTest.onShown(this);
|
||||
});
|
||||
|
||||
// We allow multiple onHidden functions to be defined in an array. They're
|
||||
// called in the order they appear.
|
||||
let onHiddenArray = nextTest.onHidden instanceof Array ?
|
||||
nextTest.onHidden :
|
||||
[nextTest.onHidden];
|
||||
doOnPopupEvent("popuphidden", function () {
|
||||
if (!gShownState[gTestIndex]) {
|
||||
// TODO: needed?
|
||||
info("Popup from test " + gTestIndex + " was hidden before its popupshown fired");
|
||||
}
|
||||
|
||||
let onHidden = onHiddenArray.shift();
|
||||
info("[Test #" + gTestIndex + "] popup hidden (" + onHiddenArray.length + " hides remaining)");
|
||||
executeSoon(function () {
|
||||
onHidden.call(nextTest, this);
|
||||
if (!onHiddenArray.length)
|
||||
goNext();
|
||||
}.bind(this));
|
||||
}, onHiddenArray.length);
|
||||
info("[Test #" + gTestIndex + "] added listeners; panel state: " + PopupNotifications.isPanelOpen);
|
||||
}
|
||||
|
||||
info("[Test #" + gTestIndex + "] running test");
|
||||
nextTest.run();
|
||||
}
|
||||
|
||||
function doOnPopupEvent(eventName, callback, numExpected) {
|
||||
gActiveListeners[eventName] = function (event) {
|
||||
if (event.target != PopupNotifications.panel)
|
||||
return;
|
||||
if (typeof(numExpected) === "number")
|
||||
numExpected--;
|
||||
if (!numExpected) {
|
||||
PopupNotifications.panel.removeEventListener(eventName, gActiveListeners[eventName], false);
|
||||
delete gActiveListeners[eventName];
|
||||
}
|
||||
|
||||
callback.call(PopupNotifications.panel);
|
||||
};
|
||||
PopupNotifications.panel.addEventListener(eventName, gActiveListeners[eventName], false);
|
||||
}
|
||||
|
||||
function checkPopup(popup, notificationObj) {
|
||||
info("[Test #" + gTestIndex + "] checking popup");
|
||||
|
||||
let notifications = popup.childNodes;
|
||||
is(notifications.length, 1, "only one notification displayed");
|
||||
let notification = notifications[0];
|
||||
let icon = document.getAnonymousElementByAttribute(notification, "class", "popup-notification-icon");
|
||||
is(notification.getAttribute("label"), notificationObj.message, "message matches");
|
||||
is(notification.id, notificationObj.id + "-notification", "id matches");
|
||||
if (notificationObj.id != "identity-request" && notificationObj.mainAction) {
|
||||
is(notification.getAttribute("buttonlabel"), notificationObj.mainAction.label, "main action label matches");
|
||||
is(notification.getAttribute("buttonaccesskey"), notificationObj.mainAction.accessKey, "main action accesskey matches");
|
||||
}
|
||||
let actualSecondaryActions = notification.childNodes;
|
||||
let secondaryActions = notificationObj.secondaryActions || [];
|
||||
let actualSecondaryActionsCount = actualSecondaryActions.length;
|
||||
if (secondaryActions.length) {
|
||||
let lastChild = actualSecondaryActions.item(actualSecondaryActions.length - 1);
|
||||
is(lastChild.tagName, "menuseparator", "menuseparator exists");
|
||||
actualSecondaryActionsCount--;
|
||||
}
|
||||
is(actualSecondaryActionsCount, secondaryActions.length, actualSecondaryActions.length + " secondary actions");
|
||||
secondaryActions.forEach(function (a, i) {
|
||||
is(actualSecondaryActions[i].getAttribute("label"), a.label, "label for secondary action " + i + " matches");
|
||||
is(actualSecondaryActions[i].getAttribute("accesskey"), a.accessKey, "accessKey for secondary action " + i + " matches");
|
||||
});
|
||||
}
|
||||
|
||||
function triggerMainCommand(popup) {
|
||||
info("[Test #" + gTestIndex + "] triggering main command");
|
||||
let notifications = popup.childNodes;
|
||||
ok(notifications.length > 0, "at least one notification displayed");
|
||||
let notification = notifications[0];
|
||||
|
||||
// 20, 10 so that the inner button is hit
|
||||
EventUtils.synthesizeMouse(notification.button, 20, 10, {});
|
||||
}
|
||||
|
||||
function triggerSecondaryCommand(popup, index) {
|
||||
info("[Test #" + gTestIndex + "] triggering secondary command");
|
||||
let notifications = popup.childNodes;
|
||||
ok(notifications.length > 0, "at least one notification displayed");
|
||||
let notification = notifications[0];
|
||||
|
||||
notification.button.focus();
|
||||
|
||||
popup.addEventListener("popupshown", function () {
|
||||
popup.removeEventListener("popupshown", arguments.callee, false);
|
||||
|
||||
// Press down until the desired command is selected
|
||||
for (let i = 0; i <= index; i++)
|
||||
EventUtils.synthesizeKey("VK_DOWN", {});
|
||||
|
||||
// Activate
|
||||
EventUtils.synthesizeKey("VK_ENTER", {});
|
||||
}, false);
|
||||
|
||||
// One down event to open the popup
|
||||
EventUtils.synthesizeKey("VK_DOWN", { altKey: (navigator.platform.indexOf("Mac") == -1) });
|
||||
}
|
||||
|
||||
function dismissNotification(popup) {
|
||||
info("[Test #" + gTestIndex + "] dismissing notification");
|
||||
executeSoon(function () {
|
||||
EventUtils.synthesizeKey("VK_ESCAPE", {});
|
||||
});
|
||||
}
|
||||
|
||||
function partial(fn) {
|
||||
let args = Array.prototype.slice.call(arguments, 1);
|
||||
return function() {
|
||||
return fn.apply(this, args.concat(Array.prototype.slice.call(arguments)));
|
||||
};
|
||||
}
|
||||
|
||||
// create a mock "doc" object, which the Identity Service
|
||||
// uses as a pointer back into the doc object
|
||||
function mock_doc(aIdentity, aOrigin, aDoFunc) {
|
||||
let mockedDoc = {};
|
||||
mockedDoc.id = outerWinId;
|
||||
mockedDoc.loggedInEmail = aIdentity;
|
||||
mockedDoc.origin = aOrigin;
|
||||
mockedDoc['do'] = aDoFunc;
|
||||
mockedDoc.doReady = partial(aDoFunc, 'ready');
|
||||
mockedDoc.doLogin = partial(aDoFunc, 'login');
|
||||
mockedDoc.doLogout = partial(aDoFunc, 'logout');
|
||||
mockedDoc.doError = partial(aDoFunc, 'error');
|
||||
mockedDoc.doCancel = partial(aDoFunc, 'cancel');
|
||||
mockedDoc.doCoffee = partial(aDoFunc, 'coffee');
|
||||
|
||||
return mockedDoc;
|
||||
}
|
||||
|
||||
// takes a list of functions and returns a function that
|
||||
// when called the first time, calls the first func,
|
||||
// then the next time the second, etc.
|
||||
function call_sequentially() {
|
||||
let numCalls = 0;
|
||||
let funcs = arguments;
|
||||
|
||||
return function() {
|
||||
if (!funcs[numCalls]) {
|
||||
let argString = Array.prototype.slice.call(arguments).join(",");
|
||||
ok(false, "Too many calls: " + argString);
|
||||
return;
|
||||
}
|
||||
funcs[numCalls].apply(funcs[numCalls], arguments);
|
||||
numCalls += 1;
|
||||
};
|
||||
}
|
||||
|
||||
function setupRPFlow(aIdentity) {
|
||||
IdentityService.RP.watch(mock_doc(aIdentity, TEST_ORIGIN, call_sequentially(
|
||||
function(action, params) {
|
||||
is(action, "ready", "1st callback");
|
||||
is(params, null);
|
||||
},
|
||||
function(action, params) {
|
||||
is(action, "logout", "2nd callback");
|
||||
is(params, null);
|
||||
},
|
||||
function(action, params) {
|
||||
is(action, "ready", "3rd callback");
|
||||
is(params, null);
|
||||
}
|
||||
)));
|
||||
}
|
||||
|
||||
function WindowObserver(aCallback, aObserveTopic = "domwindowopened") {
|
||||
this.observe = function(aSubject, aTopic, aData) {
|
||||
if (aTopic != aObserveTopic) {
|
||||
return;
|
||||
}
|
||||
info(aObserveTopic);
|
||||
Services.ww.unregisterNotification(this);
|
||||
|
||||
SimpleTest.executeSoon(function() {
|
||||
let domWin = aSubject.QueryInterface(Ci.nsIDOMWindow);
|
||||
aCallback(domWin);
|
||||
});
|
||||
};
|
||||
}
|
|
@ -1240,6 +1240,10 @@ toolbar[iconsize="small"] #feed-button {
|
|||
list-style-image: url(chrome://global/skin/icons/information-16.png);
|
||||
}
|
||||
|
||||
#identity-notification-icon {
|
||||
list-style-image: url(chrome://mozapps/skin/profile/profileicon.png);
|
||||
}
|
||||
|
||||
#geo-notification-icon {
|
||||
list-style-image: url(chrome://browser/skin/Geolocation-16.png);
|
||||
}
|
||||
|
|
|
@ -2369,12 +2369,19 @@ toolbarbutton.chevron > .toolbarbutton-menu-dropmarker {
|
|||
list-style-image: url(chrome://global/skin/icons/information-16.png);
|
||||
}
|
||||
|
||||
#identity-notification-icon {
|
||||
list-style-image: url(chrome://mozapps/skin/profile/profileicon.png);
|
||||
}
|
||||
|
||||
#geo-notification-icon {
|
||||
list-style-image: url(chrome://browser/skin/Geolocation-16.png);
|
||||
}
|
||||
|
||||
.geolocation-text-link {
|
||||
#notification-popup .text-link {
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.geolocation-text-link {
|
||||
-moz-margin-start: 0; /* override default label margin to match description margin */
|
||||
}
|
||||
|
||||
|
|
|
@ -2375,6 +2375,10 @@ toolbarbutton.bookmark-item[dragover="true"][open="true"] {
|
|||
list-style-image: url(chrome://global/skin/icons/information-16.png);
|
||||
}
|
||||
|
||||
#identity-notification-icon {
|
||||
list-style-image: url(chrome://mozapps/skin/profile/profileicon.png);
|
||||
}
|
||||
|
||||
#geo-notification-icon {
|
||||
list-style-image: url(chrome://browser/skin/Geolocation-16.png);
|
||||
}
|
||||
|
|
|
@ -2,7 +2,6 @@
|
|||
# License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
# You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
import time
|
||||
import hashlib
|
||||
import socket
|
||||
import os
|
||||
|
|
|
@ -6,8 +6,8 @@ import subprocess
|
|||
from devicemanager import DeviceManager, DMError, _pop_last_line
|
||||
import re
|
||||
import os
|
||||
import sys
|
||||
import tempfile
|
||||
import time
|
||||
|
||||
class DeviceManagerADB(DeviceManager):
|
||||
|
||||
|
@ -65,7 +65,7 @@ class DeviceManagerADB(DeviceManager):
|
|||
self.useRunAs = False
|
||||
try:
|
||||
self.verifyRoot()
|
||||
except DMError, e:
|
||||
except DMError:
|
||||
try:
|
||||
self.checkCmd(["root"])
|
||||
# The root command does not fail even if ADB cannot get
|
||||
|
@ -394,6 +394,8 @@ class DeviceManagerADB(DeviceManager):
|
|||
args.append("-9")
|
||||
args.append(pid)
|
||||
p = self.runCmdAs(args)
|
||||
p.communicate()
|
||||
if p.returncode == 0:
|
||||
didKillProcess = True
|
||||
|
||||
return didKillProcess
|
||||
|
@ -499,11 +501,11 @@ class DeviceManagerADB(DeviceManager):
|
|||
# success: MD5 hash for given filename
|
||||
# failure: None
|
||||
def getRemoteHash(self, filename):
|
||||
data = p = self.runCmd(["shell", "ls", "-l", filename]).stdout.read()
|
||||
data = self.runCmd(["shell", "ls", "-l", filename]).stdout.read()
|
||||
return data.split()[3]
|
||||
|
||||
def getLocalHash(self, filename):
|
||||
data = p = subprocess.Popen(["ls", "-l", filename], stdout=subprocess.PIPE).stdout.read()
|
||||
data = subprocess.Popen(["ls", "-l", filename], stdout=subprocess.PIPE).stdout.read()
|
||||
return data.split()[4]
|
||||
|
||||
# Internal method to setup the device root and cache its value
|
||||
|
|
|
@ -5,17 +5,14 @@
|
|||
import select
|
||||
import socket
|
||||
import SocketServer
|
||||
import time, datetime
|
||||
import time
|
||||
import os
|
||||
import re
|
||||
import hashlib
|
||||
import posixpath
|
||||
import subprocess
|
||||
from threading import Thread
|
||||
import traceback
|
||||
import sys
|
||||
import StringIO
|
||||
from devicemanager import DeviceManager, DMError, FileError, NetworkTools, _pop_last_line
|
||||
from devicemanager import DeviceManager, FileError, NetworkTools, _pop_last_line
|
||||
import errno
|
||||
|
||||
class AgentError(Exception):
|
||||
|
@ -126,7 +123,6 @@ class DeviceManagerSUT(DeviceManager):
|
|||
one fails. this is necessary in particular for pushFile(), where we don't want
|
||||
to accidentally send extra data if a failure occurs during data transmission.
|
||||
'''
|
||||
done = False
|
||||
while self.retries < self.retrylimit:
|
||||
try:
|
||||
self._doCmds(cmdlist, outputfile, timeout)
|
||||
|
@ -187,7 +183,7 @@ class DeviceManagerSUT(DeviceManager):
|
|||
sent = self._sock.send(cmd['data'])
|
||||
if sent != len(cmd['data']):
|
||||
raise AgentError("ERROR: we had %s bytes of data to send, but "
|
||||
"only sent %s" % (len(cmd['data'], sent)))
|
||||
"only sent %s" % (len(cmd['data']), sent))
|
||||
|
||||
if (self.debug >= 4): print "sent cmd: " + str(cmd['cmd'])
|
||||
except socket.error, msg:
|
||||
|
@ -503,7 +499,7 @@ class DeviceManagerSUT(DeviceManager):
|
|||
return None
|
||||
|
||||
try:
|
||||
data = self.runCmds([{ 'cmd': 'exec ' + appname }])
|
||||
self.runCmds([{ 'cmd': 'exec ' + appname }])
|
||||
except AgentError:
|
||||
return None
|
||||
|
||||
|
@ -547,7 +543,7 @@ class DeviceManagerSUT(DeviceManager):
|
|||
if forceKill:
|
||||
print "WARNING: killProcess(): forceKill parameter unsupported on SUT"
|
||||
try:
|
||||
data = self.runCmds([{ 'cmd': 'kill ' + appname }])
|
||||
self.runCmds([{ 'cmd': 'kill ' + appname }])
|
||||
except AgentError:
|
||||
return False
|
||||
|
||||
|
@ -640,7 +636,8 @@ class DeviceManagerSUT(DeviceManager):
|
|||
# or, if error,
|
||||
# <filename>,-1\n<error message>
|
||||
try:
|
||||
data = self.runCmds([{ 'cmd': 'pull ' + remoteFile }])
|
||||
# just send the command first, we read the response inline below
|
||||
self.runCmds([{ 'cmd': 'pull ' + remoteFile }])
|
||||
except AgentError:
|
||||
return None
|
||||
|
||||
|
@ -880,7 +877,6 @@ class DeviceManagerSUT(DeviceManager):
|
|||
cmd = 'rebt'
|
||||
|
||||
if (self.debug > 3): print "INFO: sending rebt command"
|
||||
callbacksvrstatus = None
|
||||
|
||||
if (ipAddr is not None):
|
||||
#create update.info file:
|
||||
|
|
|
@ -268,8 +268,7 @@ class Emulator(object):
|
|||
local_port = s.getsockname()[1]
|
||||
s.close()
|
||||
|
||||
output = self._run_adb(['-s', 'emulator-%d' % self.port,
|
||||
'forward',
|
||||
self._run_adb(['-s', 'emulator-%d' % self.port, 'forward',
|
||||
'tcp:%d' % local_port,
|
||||
'tcp:%d' % remote_port])
|
||||
|
||||
|
|
|
@ -3,15 +3,14 @@
|
|||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
import time
|
||||
import sys
|
||||
import os
|
||||
import socket
|
||||
import automationutils
|
||||
import tempfile
|
||||
import shutil
|
||||
import subprocess
|
||||
|
||||
from automation import Automation
|
||||
from devicemanager import DeviceManager, NetworkTools
|
||||
from devicemanager import NetworkTools
|
||||
|
||||
class RemoteAutomation(Automation):
|
||||
_devicemanager = None
|
||||
|
|
|
@ -5,15 +5,10 @@
|
|||
|
||||
package @ANDROID_PACKAGE_NAME@;
|
||||
|
||||
import java.lang.Class;
|
||||
import java.lang.ClassLoader;
|
||||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Proxy;
|
||||
import java.lang.reflect.InvocationHandler;
|
||||
import java.lang.Long;
|
||||
import java.lang.NoSuchMethodException;
|
||||
import java.util.concurrent.SynchronousQueue;
|
||||
import java.util.ArrayList;
|
||||
|
||||
|
@ -40,15 +35,16 @@ public class FennecNativeActions implements Actions {
|
|||
|
||||
// Objects for reflexive access of fennec classes.
|
||||
private ClassLoader mClassLoader;
|
||||
private Class mGel;
|
||||
private Class mGe;
|
||||
private Class mGas;
|
||||
private Class mDrawListener;
|
||||
private Method mRegisterGEL;
|
||||
private Method mUnregisterGEL;
|
||||
private Method mSendGE;
|
||||
private Method mGetLayerClient;
|
||||
private Class mApiClass;
|
||||
private Class mEventListenerClass;
|
||||
private Class mDrawListenerClass;
|
||||
private Method mRegisterEventListener;
|
||||
private Method mUnregisterEventListener;
|
||||
private Method mBroadcastEvent;
|
||||
private Method mSetDrawListener;
|
||||
private Method mQuerySql;
|
||||
private Object mRobocopApi;
|
||||
|
||||
private static final String LOGTAG = "FennecNativeActions";
|
||||
|
||||
public FennecNativeActions(Activity activity, Solo robocop, Instrumentation instrumentation, Assert asserter) {
|
||||
|
@ -59,29 +55,19 @@ public class FennecNativeActions implements Actions {
|
|||
// Set up reflexive access of java classes and methods.
|
||||
try {
|
||||
mClassLoader = activity.getClassLoader();
|
||||
mGel = mClassLoader.loadClass("org.mozilla.gecko.util.GeckoEventListener");
|
||||
mGe = mClassLoader.loadClass("org.mozilla.gecko.GeckoEvent");
|
||||
mGas = mClassLoader.loadClass("org.mozilla.gecko.GeckoAppShell");
|
||||
Class [] parameters = new Class[2];
|
||||
parameters[0] = String.class;
|
||||
parameters[1] = mGel;
|
||||
mRegisterGEL = mGas.getMethod("registerEventListener", parameters);
|
||||
mUnregisterGEL = mGas.getMethod("unregisterEventListener", parameters);
|
||||
parameters = new Class[1];
|
||||
parameters[0] = mGe;
|
||||
mSendGE = mGas.getMethod("sendEventToGecko", parameters);
|
||||
|
||||
mGetLayerClient = activity.getClass().getMethod("getLayerClient");
|
||||
Class gslc = mClassLoader.loadClass("org.mozilla.gecko.gfx.GeckoLayerClient");
|
||||
mDrawListener = mClassLoader.loadClass("org.mozilla.gecko.gfx.GeckoLayerClient$DrawListener");
|
||||
mSetDrawListener = gslc.getDeclaredMethod("setDrawListener", mDrawListener);
|
||||
} catch (ClassNotFoundException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (SecurityException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (NoSuchMethodException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (IllegalArgumentException e) {
|
||||
mApiClass = mClassLoader.loadClass("org.mozilla.gecko.RobocopAPI");
|
||||
mEventListenerClass = mClassLoader.loadClass("org.mozilla.gecko.util.GeckoEventListener");
|
||||
mDrawListenerClass = mClassLoader.loadClass("org.mozilla.gecko.gfx.GeckoLayerClient$DrawListener");
|
||||
|
||||
mRegisterEventListener = mApiClass.getMethod("registerEventListener", String.class, mEventListenerClass);
|
||||
mUnregisterEventListener = mApiClass.getMethod("unregisterEventListener", String.class, mEventListenerClass);
|
||||
mBroadcastEvent = mApiClass.getMethod("broadcastEvent", String.class, String.class);
|
||||
mSetDrawListener = mApiClass.getMethod("setDrawListener", mDrawListenerClass);
|
||||
mQuerySql = mApiClass.getMethod("querySql", String.class, String.class);
|
||||
|
||||
mRobocopApi = mApiClass.getConstructor(Activity.class).newInstance(activity);
|
||||
} catch (Exception e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
}
|
||||
}
|
||||
|
@ -144,7 +130,7 @@ public class FennecNativeActions implements Actions {
|
|||
}
|
||||
}
|
||||
try {
|
||||
mUnregisterGEL.invoke(null, mRegistrationParams);
|
||||
mUnregisterEventListener.invoke(mRobocopApi, mRegistrationParams);
|
||||
} catch (IllegalAccessException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
@ -192,7 +178,7 @@ public class FennecNativeActions implements Actions {
|
|||
startTime = endTime;
|
||||
}
|
||||
try {
|
||||
mUnregisterGEL.invoke(null, mRegistrationParams);
|
||||
mUnregisterEventListener.invoke(mRobocopApi, mRegistrationParams);
|
||||
} catch (IllegalAccessException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
@ -220,17 +206,14 @@ public class FennecNativeActions implements Actions {
|
|||
FennecNativeDriver.log(FennecNativeDriver.LogLevel.DEBUG,
|
||||
"waiting for "+geckoEvent);
|
||||
try {
|
||||
Class [] interfaces = new Class[1];
|
||||
interfaces[0] = mGel;
|
||||
Object[] finalParams = new Object[2];
|
||||
finalParams[0] = geckoEvent;
|
||||
|
||||
GeckoEventExpecter expecter = new GeckoEventExpecter(geckoEvent, finalParams);
|
||||
wakeInvocationHandler wIH = new wakeInvocationHandler(expecter);
|
||||
Object proxy = Proxy.newProxyInstance(mClassLoader, interfaces, wIH);
|
||||
Object proxy = Proxy.newProxyInstance(mClassLoader, new Class[] { mEventListenerClass }, wIH);
|
||||
finalParams[1] = proxy;
|
||||
mRegisterGEL.invoke(null, finalParams);
|
||||
|
||||
mRegisterEventListener.invoke(mRobocopApi, finalParams);
|
||||
return expecter;
|
||||
} catch (IllegalAccessException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
|
@ -242,11 +225,7 @@ public class FennecNativeActions implements Actions {
|
|||
|
||||
public void sendGeckoEvent(String geckoEvent, String data) {
|
||||
try {
|
||||
Method cbe = mGe.getMethod("createBroadcastEvent", String.class, String.class);
|
||||
Object event = cbe.invoke(null, geckoEvent, data);
|
||||
mSendGE.invoke(null, event);
|
||||
} catch (NoSuchMethodException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
mBroadcastEvent.invoke(mRobocopApi, geckoEvent, data);
|
||||
} catch (IllegalAccessException e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
@ -284,8 +263,8 @@ public class FennecNativeActions implements Actions {
|
|||
private static final int MAX_WAIT_MS = 90000;
|
||||
|
||||
PaintExpecter() throws IllegalAccessException, InvocationTargetException {
|
||||
mLayerClient = mGetLayerClient.invoke(mGeckoApp);
|
||||
mSetDrawListener.invoke(mLayerClient, Proxy.newProxyInstance(mClassLoader, new Class[] { mDrawListener }, new DrawListenerProxy(this)));
|
||||
Object proxy = Proxy.newProxyInstance(mClassLoader, new Class[] { mDrawListenerClass }, new DrawListenerProxy(this));
|
||||
mSetDrawListener.invoke(mRobocopApi, proxy);
|
||||
}
|
||||
|
||||
void notifyOfEvent() {
|
||||
|
@ -312,7 +291,7 @@ public class FennecNativeActions implements Actions {
|
|||
}
|
||||
}
|
||||
try {
|
||||
mSetDrawListener.invoke(mLayerClient, (Object)null);
|
||||
mSetDrawListener.invoke(mRobocopApi, (Object)null);
|
||||
} catch (Exception e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
}
|
||||
|
@ -360,7 +339,7 @@ public class FennecNativeActions implements Actions {
|
|||
startTime = endTime;
|
||||
}
|
||||
try {
|
||||
mSetDrawListener.invoke(mLayerClient, (Object)null);
|
||||
mSetDrawListener.invoke(mRobocopApi, (Object)null);
|
||||
} catch (Exception e) {
|
||||
FennecNativeDriver.log(LogLevel.ERROR, e);
|
||||
}
|
||||
|
@ -415,30 +394,9 @@ public class FennecNativeActions implements Actions {
|
|||
|
||||
public Cursor querySql(String dbPath, String sql) {
|
||||
try {
|
||||
ClassLoader classLoader = mGeckoApp.getClassLoader();
|
||||
Class sqlClass = classLoader.loadClass("org.mozilla.gecko.sqlite.SQLiteBridge");
|
||||
Class stringClass = String.class;
|
||||
Class stringArrayClass = String[].class;
|
||||
Class appshell = classLoader.loadClass("org.mozilla.gecko.GeckoAppShell");
|
||||
Class contextClass = Context.class;
|
||||
|
||||
Constructor bridgeConstructor = sqlClass.getConstructor(stringClass);
|
||||
Method query = sqlClass.getMethod("rawQuery", stringClass, stringArrayClass);
|
||||
Method loadSQLiteLibs = appshell.getMethod("loadSQLiteLibs", contextClass, stringClass);
|
||||
|
||||
Object bridge = bridgeConstructor.newInstance(dbPath);
|
||||
|
||||
String resourcePath = mGeckoApp.getApplication().getPackageResourcePath();
|
||||
loadSQLiteLibs.invoke(null, mGeckoApp, resourcePath);
|
||||
return (Cursor)query.invoke(bridge, sql, null);
|
||||
} catch(ClassNotFoundException ex) {
|
||||
Log.e(LOGTAG, "Error getting class", ex);
|
||||
} catch(NoSuchMethodException ex) {
|
||||
Log.e(LOGTAG, "Error getting method", ex);
|
||||
return (Cursor)mQuerySql.invoke(mRobocopApi, dbPath, sql);
|
||||
} catch(InvocationTargetException ex) {
|
||||
Log.e(LOGTAG, "Error invoking method", ex);
|
||||
} catch(InstantiationException ex) {
|
||||
Log.e(LOGTAG, "Error calling constructor", ex);
|
||||
} catch(IllegalAccessException ex) {
|
||||
Log.e(LOGTAG, "Error using field", ex);
|
||||
}
|
||||
|
|
|
@ -20,12 +20,10 @@ import java.util.HashMap;
|
|||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import java.lang.Class;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Proxy;
|
||||
import java.lang.reflect.InvocationHandler;
|
||||
import java.lang.Long;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.opengl.GLSurfaceView;
|
||||
|
@ -49,17 +47,16 @@ public class FennecNativeDriver implements Driver {
|
|||
|
||||
// Objects for reflexive access of fennec classes.
|
||||
private ClassLoader mClassLoader;
|
||||
private Class mGel;
|
||||
private Class mGe;
|
||||
private Class mGas;
|
||||
private Method mRegisterGEL;
|
||||
private Method mUnregisterGEL;
|
||||
private Method mSendGE;
|
||||
private Method _startFrameRecording;
|
||||
private Method _stopFrameRecording;
|
||||
private Method _startCheckerboardRecording;
|
||||
private Method _stopCheckerboardRecording;
|
||||
private Method _getPixels;
|
||||
private Class mApiClass;
|
||||
private Class mEventListenerClass;
|
||||
private Class mPanningPerfClass;
|
||||
private Method mRegisterEventListener;
|
||||
private Method mGetPixels;
|
||||
private Method mStartFrameRecording;
|
||||
private Method mStopFrameRecording;
|
||||
private Method mStartCheckerboardRecording;
|
||||
private Method mStopCheckerboardRecording;
|
||||
private Object mRobocopApi;
|
||||
|
||||
public enum LogLevel {
|
||||
DEBUG(1),
|
||||
|
@ -89,33 +86,20 @@ public class FennecNativeDriver implements Driver {
|
|||
// Set up reflexive access of java classes and methods.
|
||||
try {
|
||||
mClassLoader = activity.getClassLoader();
|
||||
mGel = mClassLoader.loadClass("org.mozilla.gecko.util.GeckoEventListener");
|
||||
mGe = mClassLoader.loadClass("org.mozilla.gecko.GeckoEvent");
|
||||
mGas = mClassLoader.loadClass("org.mozilla.gecko.GeckoAppShell");
|
||||
Class [] parameters = new Class[2];
|
||||
parameters[0] = String.class;
|
||||
parameters[1] = mGel;
|
||||
mRegisterGEL = mGas.getMethod("registerEventListener", parameters);
|
||||
mUnregisterGEL = mGas.getMethod("unregisterEventListener", parameters);
|
||||
parameters = new Class[1];
|
||||
parameters[0] = mGe;
|
||||
mSendGE = mGas.getMethod("sendEventToGecko", parameters);
|
||||
|
||||
Class gfx = mClassLoader.loadClass("org.mozilla.gecko.gfx.PanningPerfAPI");
|
||||
_startFrameRecording = gfx.getDeclaredMethod("startFrameTimeRecording");
|
||||
_stopFrameRecording = gfx.getDeclaredMethod("stopFrameTimeRecording");
|
||||
_startCheckerboardRecording = gfx.getDeclaredMethod("startCheckerboardRecording");
|
||||
_stopCheckerboardRecording = gfx.getDeclaredMethod("stopCheckerboardRecording");
|
||||
mApiClass = mClassLoader.loadClass("org.mozilla.gecko.RobocopAPI");
|
||||
mEventListenerClass = mClassLoader.loadClass("org.mozilla.gecko.util.GeckoEventListener");
|
||||
mPanningPerfClass = mClassLoader.loadClass("org.mozilla.gecko.gfx.PanningPerfAPI");
|
||||
|
||||
Class layerView = mClassLoader.loadClass("org.mozilla.gecko.gfx.LayerView");
|
||||
_getPixels = layerView.getDeclaredMethod("getPixels");
|
||||
} catch (ClassNotFoundException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (SecurityException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (NoSuchMethodException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (IllegalArgumentException e) {
|
||||
mRegisterEventListener = mApiClass.getMethod("registerEventListener", String.class, mEventListenerClass);
|
||||
mGetPixels = mApiClass.getMethod("getViewPixels", View.class);
|
||||
mStartFrameRecording = mPanningPerfClass.getDeclaredMethod("startFrameTimeRecording");
|
||||
mStopFrameRecording = mPanningPerfClass.getDeclaredMethod("stopFrameTimeRecording");
|
||||
mStartCheckerboardRecording = mPanningPerfClass.getDeclaredMethod("startCheckerboardRecording");
|
||||
mStopCheckerboardRecording = mPanningPerfClass.getDeclaredMethod("stopCheckerboardRecording");
|
||||
|
||||
mRobocopApi = mApiClass.getConstructor(Activity.class).newInstance(activity);
|
||||
} catch (Exception e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
}
|
||||
}
|
||||
|
@ -189,8 +173,7 @@ public class FennecNativeDriver implements Driver {
|
|||
|
||||
public void startFrameRecording() {
|
||||
try {
|
||||
Object [] params = null;
|
||||
_startFrameRecording.invoke(null, params);
|
||||
mStartFrameRecording.invoke(null);
|
||||
} catch (IllegalAccessException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
@ -199,12 +182,8 @@ public class FennecNativeDriver implements Driver {
|
|||
}
|
||||
|
||||
public int stopFrameRecording() {
|
||||
Class [] parameters = new Class[1];
|
||||
parameters[0] = null;
|
||||
|
||||
try {
|
||||
Object [] params = null;
|
||||
List<Long> frames = (List<Long>)_stopFrameRecording.invoke(null, params);
|
||||
List<Long> frames = (List<Long>)mStopFrameRecording.invoke(null);
|
||||
int badness = 0;
|
||||
for (int i = 1; i < frames.size(); i++) {
|
||||
long frameTime = frames.get(i) - frames.get(i - 1);
|
||||
|
@ -230,8 +209,7 @@ public class FennecNativeDriver implements Driver {
|
|||
|
||||
public void startCheckerboardRecording() {
|
||||
try {
|
||||
Object [] params = null;
|
||||
_startCheckerboardRecording.invoke(null, params);
|
||||
mStartCheckerboardRecording.invoke(null);
|
||||
} catch (IllegalAccessException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
@ -240,12 +218,8 @@ public class FennecNativeDriver implements Driver {
|
|||
}
|
||||
|
||||
public float stopCheckerboardRecording() {
|
||||
Class [] parameters = new Class[1];
|
||||
parameters[0] = null;
|
||||
|
||||
try {
|
||||
Object [] params = null;
|
||||
List<Float> checkerboard = (List<Float>)_stopCheckerboardRecording.invoke(null, params);
|
||||
List<Float> checkerboard = (List<Float>)mStopCheckerboardRecording.invoke(null);
|
||||
float total = 0;
|
||||
for (float val : checkerboard) {
|
||||
total += val;
|
||||
|
@ -281,7 +255,7 @@ public class FennecNativeDriver implements Driver {
|
|||
}
|
||||
IntBuffer pixelBuffer;
|
||||
try {
|
||||
pixelBuffer = (IntBuffer)_getPixels.invoke(view);
|
||||
pixelBuffer = (IntBuffer)mGetPixels.invoke(mRobocopApi, view);
|
||||
} catch (Exception e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
return null;
|
||||
|
@ -368,11 +342,11 @@ public class FennecNativeDriver implements Driver {
|
|||
//Setup scrollHandler to catch "robocop:scroll" events.
|
||||
try {
|
||||
Class [] interfaces = new Class[1];
|
||||
interfaces[0] = mGel;
|
||||
interfaces[0] = mEventListenerClass;
|
||||
Object[] finalParams = new Object[2];
|
||||
finalParams[0] = "robocop:scroll";
|
||||
finalParams[1] = Proxy.newProxyInstance(mClassLoader, interfaces, new scrollHandler());
|
||||
mRegisterGEL.invoke(null, finalParams);
|
||||
mRegisterEventListener.invoke(mRobocopApi, finalParams);
|
||||
} catch (IllegalAccessException e) {
|
||||
log(LogLevel.ERROR, e);
|
||||
} catch (InvocationTargetException e) {
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
#include "nsNetUtil.h"
|
||||
#include "nsIClassInfoImpl.h"
|
||||
#include "nsNetCID.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsScriptSecurityManager.h"
|
||||
|
||||
|
|
|
@ -20,7 +20,7 @@
|
|||
#include "nsIObjectInputStream.h"
|
||||
#include "nsIObjectOutputStream.h"
|
||||
#include "nsIClassInfoImpl.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIContentSecurityPolicy.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "jswrapper.h"
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
#include "nsCRT.h"
|
||||
#include "nsCRTGlue.h"
|
||||
#include "nsIJSContextStack.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMCID.h"
|
||||
#include "jsdbgapi.h"
|
||||
#include "nsIXPConnect.h"
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
#include "prprf.h"
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsEscape.h"
|
||||
#include "nsLayoutCID.h"
|
||||
#include "nsNetUtil.h"
|
||||
|
|
|
@ -18,7 +18,6 @@ mozFlushType.h \
|
|||
nsIContent.h \
|
||||
nsIAttribute.h \
|
||||
nsIContentIterator.h \
|
||||
nsContentErrors.h \
|
||||
nsContentPolicyUtils.h \
|
||||
nsContentUtils.h \
|
||||
nsIDocument.h \
|
||||
|
|
|
@ -1,61 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
// vim: ft=cpp sw=2 ts=2 tw=78 et
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsContentErrors_h___
|
||||
#define nsContentErrors_h___
|
||||
|
||||
/** Error codes for nsHTMLStyleSheet */
|
||||
// XXX this is not really used
|
||||
#define NS_HTML_STYLE_PROPERTY_NOT_THERE \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 2)
|
||||
|
||||
/** Error codes for image loading */
|
||||
#define NS_ERROR_IMAGE_SRC_CHANGED \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 4)
|
||||
|
||||
#define NS_ERROR_IMAGE_BLOCKED \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 5)
|
||||
|
||||
/** Error codes for content policy blocking */
|
||||
#define NS_ERROR_CONTENT_BLOCKED \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 6)
|
||||
|
||||
#define NS_ERROR_CONTENT_BLOCKED_SHOW_ALT \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 7)
|
||||
|
||||
/** Success variations of content policy blocking */
|
||||
#define NS_CONTENT_BLOCKED \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 8)
|
||||
|
||||
#define NS_CONTENT_BLOCKED_SHOW_ALT \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 9)
|
||||
|
||||
#define NS_PROPTABLE_PROP_NOT_THERE \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 10)
|
||||
|
||||
#define NS_PROPTABLE_PROP_OVERWRITTEN \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 11)
|
||||
|
||||
/* Error codes for FindBroadcaster in nsXULDocument.cpp */
|
||||
|
||||
#define NS_FINDBROADCASTER_NOT_FOUND \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 12)
|
||||
|
||||
#define NS_FINDBROADCASTER_FOUND \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 13)
|
||||
|
||||
#define NS_FINDBROADCASTER_AWAIT_OVERLAYS \
|
||||
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_CONTENT, 14)
|
||||
|
||||
/* Error codes for CSP */
|
||||
#define NS_ERROR_CSP_FRAME_ANCESTOR_VIOLATION \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_SECURITY, 99)
|
||||
|
||||
/* Error codes for XBL */
|
||||
#define NS_ERROR_XBL_BLOCKED \
|
||||
NS_ERROR_GENERATE_FAILURE(NS_ERROR_MODULE_CONTENT, 15)
|
||||
|
||||
#endif // nsContentErrors_h___
|
|
@ -20,8 +20,8 @@ class Element;
|
|||
} // namespace mozilla
|
||||
|
||||
#define NS_IMUTATION_OBSERVER_IID \
|
||||
{ 0x85eea794, 0xed8e, 0x4e1b, \
|
||||
{ 0xa1, 0x28, 0xd0, 0x93, 0x00, 0xae, 0x51, 0xaa } }
|
||||
{ 0x16fe5e3e, 0xeadc, 0x4312, \
|
||||
{ 0x9d, 0x44, 0xb6, 0xbe, 0xdd, 0x6b, 0x54, 0x74 } }
|
||||
|
||||
/**
|
||||
* Information details about a characterdata change. Basically, we
|
||||
|
@ -192,6 +192,20 @@ public:
|
|||
nsIAtom* aAttribute,
|
||||
PRInt32 aModType) = 0;
|
||||
|
||||
/**
|
||||
* Notification that an attribute of an element has been
|
||||
* set to the value it already had.
|
||||
*
|
||||
* @param aDocument The owner-document of aContent.
|
||||
* @param aElement The element whose attribute changed
|
||||
* @param aNameSpaceID The namespace id of the changed attribute
|
||||
* @param aAttribute The name of the changed attribute
|
||||
*/
|
||||
virtual void AttributeSetToCurrentValue(nsIDocument* aDocument,
|
||||
mozilla::dom::Element* aElement,
|
||||
PRInt32 aNameSpaceID,
|
||||
nsIAtom* aAttribute) {}
|
||||
|
||||
/**
|
||||
* Notification that one or more content nodes have been appended to the
|
||||
* child list of another node in the tree.
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
|
||||
#include "FileIOObject.h"
|
||||
#include "nsDOMFile.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIDOMEvent.h"
|
||||
#include "nsIDOMProgressEvent.h"
|
||||
#include "nsComponentManagerUtils.h"
|
||||
|
|
|
@ -45,7 +45,7 @@
|
|||
#include "nsContentList.h"
|
||||
#include "nsDOMTokenList.h"
|
||||
#include "nsXBLPrototypeBinding.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMString.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsIDOMMutationEvent.h"
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
|
||||
#include "nsBlobProtocolHandler.h"
|
||||
#include "nsBlobURI.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsClassHashtable.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsIPrincipal.h"
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
#include "nsIChannelEventSink.h"
|
||||
#include "nsIPropertyBag2.h"
|
||||
#include "nsIWritablePropertyBag2.h"
|
||||
#include "nsNetError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsChannelProperties.h"
|
||||
#include "nsIAsyncVerifyRedirectCallback.h"
|
||||
#include "nsAsyncRedirectVerifyHelper.h"
|
||||
|
|
|
@ -85,7 +85,7 @@ static NS_DEFINE_CID(kXTFServiceCID, NS_XTFSERVICE_CID);
|
|||
#include "nsContentCreatorFunctions.h"
|
||||
#include "nsMutationEvent.h"
|
||||
#include "nsIMEStateManager.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsUnicharUtilCIID.h"
|
||||
#include "nsINativeKeyBindings.h"
|
||||
#include "nsXULPopupManager.h"
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
#include "nsCrossSiteListenerProxy.h"
|
||||
#include "nsIChannel.h"
|
||||
#include "nsIHttpChannel.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsNetUtil.h"
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
#include "mozilla/dom/Element.h"
|
||||
#include "nsContentCreatorFunctions.h"
|
||||
#include "nsINameSpaceManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsUnicharUtils.h"
|
||||
#include "nsDOMString.h"
|
||||
#include "nsIDocument.h"
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "nsGenericElement.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsINameSpaceManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsNodeInfoManager.h"
|
||||
#include "nsAttrName.h"
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#include "nsContentCID.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsICharsetDetector.h"
|
||||
#include "nsICharsetConverterManager.h"
|
||||
#include "nsIClassInfo.h"
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#include "nsContentUtils.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsDOMFile.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsCharsetAlias.h"
|
||||
#include "nsICharsetConverterManager.h"
|
||||
#include "nsIConverterInputStream.h"
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
*/
|
||||
|
||||
#include "nsDOMLists.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsINode.h"
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
|
||||
#include "nsDOMMutationObserver.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIClassInfo.h"
|
||||
#include "nsIXPCScriptable.h"
|
||||
#include "nsIScriptGlobalObject.h"
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "mozilla/dom/Element.h"
|
||||
#include "nsClassHashtable.h"
|
||||
#include "nsNodeUtils.h"
|
||||
#include "nsIDOMMutationEvent.h"
|
||||
|
||||
class nsDOMMutationObserver;
|
||||
|
||||
|
@ -273,6 +274,16 @@ public:
|
|||
NS_DECL_NSIMUTATIONOBSERVER_CONTENTINSERTED
|
||||
NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED
|
||||
NS_DECL_NSIMUTATIONOBSERVER_NODEWILLBEDESTROYED
|
||||
|
||||
virtual void AttributeSetToCurrentValue(nsIDocument* aDocument,
|
||||
mozilla::dom::Element* aElement,
|
||||
PRInt32 aNameSpaceID,
|
||||
nsIAtom* aAttribute)
|
||||
{
|
||||
// We can reuse AttributeWillChange implementation.
|
||||
AttributeWillChange(aDocument, aElement, aNameSpaceID, aAttribute,
|
||||
nsIDOMMutationEvent::MODIFICATION);
|
||||
}
|
||||
};
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(nsMutationReceiver, NS_MUTATION_OBSERVER_IID)
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
#include "nsNetCID.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMJSUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsPIDOMWindow.h"
|
||||
#include "mozilla/AutoRestore.h"
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "nsString.h"
|
||||
#include "nsContentCID.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
|
||||
nsDOMSerializer::nsDOMSerializer()
|
||||
{
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
#include "nsAttrValue.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsGenericElement.h"
|
||||
#include "dombindings.h"
|
||||
|
||||
|
|
|
@ -62,7 +62,7 @@
|
|||
#include "nsIServiceManager.h"
|
||||
|
||||
#include "nsContentCID.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIPresShell.h"
|
||||
#include "nsPresContext.h"
|
||||
#include "nsIJSON.h"
|
||||
|
@ -130,7 +130,6 @@
|
|||
#include "nsIDocumentLoaderFactory.h"
|
||||
#include "nsIContentViewer.h"
|
||||
#include "nsIXMLContentSink.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsIXULDocument.h"
|
||||
#include "nsIPrompt.h"
|
||||
#include "nsIPropertyBag2.h"
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "nsINameSpaceManager.h"
|
||||
#include "nsINodeInfo.h"
|
||||
#include "nsNodeInfoManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsGkAtoms.h"
|
||||
#include "nsDOMString.h"
|
||||
#include "nsContentUtils.h"
|
||||
|
|
|
@ -33,7 +33,7 @@
|
|||
#include "nsDOMEventTargetHelper.h"
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
|
||||
using namespace mozilla;
|
||||
|
||||
|
|
|
@ -46,7 +46,7 @@
|
|||
#include "nsIFrame.h"
|
||||
#include "nsIScrollableFrame.h"
|
||||
#include "nsSubDocumentFrame.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsGUIEvent.h"
|
||||
#include "nsEventDispatcher.h"
|
||||
#include "nsISHistory.h"
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
#include "ContentChild.h"
|
||||
#include "ContentParent.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIXPConnect.h"
|
||||
#include "jsapi.h"
|
||||
#include "nsJSUtils.h"
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
#include "nsIContent.h"
|
||||
|
||||
#include "nsTextFragment.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsEventListenerManager.h"
|
||||
#include "nsGenericElement.h"
|
||||
#include "nsCycleCollectionParticipant.h"
|
||||
|
|
|
@ -45,7 +45,7 @@
|
|||
#include "nsContentList.h"
|
||||
#include "nsDOMTokenList.h"
|
||||
#include "nsXBLPrototypeBinding.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMString.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsIDOMMutationEvent.h"
|
||||
|
@ -1883,14 +1883,8 @@ nsGenericElement::MaybeCheckSameAttrVal(PRInt32 aNamespaceID,
|
|||
}
|
||||
bool valueMatches = aValue.EqualsAsStrings(*info.mValue);
|
||||
if (valueMatches && aPrefix == info.mName->GetPrefix()) {
|
||||
if (OwnerDoc()->MayHaveDOMMutationObservers()) {
|
||||
// For backward compatibility, don't fire mutation events
|
||||
// when setting an attribute to its old value.
|
||||
*aHasListeners = false;
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
modification = true;
|
||||
}
|
||||
}
|
||||
|
@ -1920,7 +1914,7 @@ nsGenericElement::SetAttr(PRInt32 aNamespaceID, nsIAtom* aName,
|
|||
nsAttrValueOrString value(aValue);
|
||||
nsAttrValue oldValue;
|
||||
|
||||
if (MaybeCheckSameAttrVal(aNamespaceID, aName, aPrefix, value, aNotify,
|
||||
if (OnlyNotifySameValueSet(aNamespaceID, aName, aPrefix, value, aNotify,
|
||||
oldValue, &modType, &hasListeners)) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
@ -1967,7 +1961,7 @@ nsGenericElement::SetParsedAttr(PRInt32 aNamespaceID, nsIAtom* aName,
|
|||
nsAttrValueOrString value(aParsedValue);
|
||||
nsAttrValue oldValue;
|
||||
|
||||
if (MaybeCheckSameAttrVal(aNamespaceID, aName, aPrefix, value, aNotify,
|
||||
if (OnlyNotifySameValueSet(aNamespaceID, aName, aPrefix, value, aNotify,
|
||||
oldValue, &modType, &hasListeners)) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
#include "nsIInlineEventHandlers.h"
|
||||
#include "mozilla/CORSMode.h"
|
||||
#include "mozilla/Attributes.h"
|
||||
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsISMILAttr.h"
|
||||
|
||||
class nsIDOMAttr;
|
||||
|
@ -102,6 +102,22 @@ public:
|
|||
const nsAttrValueOrString& aValue,
|
||||
bool aNotify, nsAttrValue& aOldValue,
|
||||
PRUint8* aModType, bool* aHasListeners);
|
||||
|
||||
bool OnlyNotifySameValueSet(PRInt32 aNamespaceID, nsIAtom* aName,
|
||||
nsIAtom* aPrefix,
|
||||
const nsAttrValueOrString& aValue,
|
||||
bool aNotify, nsAttrValue& aOldValue,
|
||||
PRUint8* aModType, bool* aHasListeners)
|
||||
{
|
||||
if (MaybeCheckSameAttrVal(aNamespaceID, aName, aPrefix, aValue, aNotify,
|
||||
aOldValue, aModType, aHasListeners)) {
|
||||
nsAutoScriptBlocker scriptBlocker;
|
||||
nsNodeUtils::AttributeSetToCurrentValue(this, aNamespaceID, aName);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
virtual nsresult SetAttr(PRInt32 aNameSpaceID, nsIAtom* aName, nsIAtom* aPrefix,
|
||||
const nsAString& aValue, bool aNotify);
|
||||
virtual nsresult SetParsedAttr(PRInt32 aNameSpaceID, nsIAtom* aName,
|
||||
|
|
|
@ -30,7 +30,7 @@
|
|||
#include "nsDOMAttributeMap.h"
|
||||
#include "nsDOMCID.h"
|
||||
#include "nsDOMCSSAttrDeclaration.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMMutationObserver.h"
|
||||
#include "nsDOMString.h"
|
||||
#include "nsDOMTokenList.h"
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
|
||||
#include "nsImageLoadingContent.h"
|
||||
#include "nsAutoPtr.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIContent.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIScriptGlobalObject.h"
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
|
||||
#include "nsIDOMNode.h"
|
||||
#include "nsIDOMNodeFilter.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
|
||||
#include "nsIContent.h"
|
||||
#include "nsIDocument.h"
|
||||
|
|
|
@ -107,6 +107,16 @@ nsNodeUtils::AttributeChanged(Element* aElement,
|
|||
aModType));
|
||||
}
|
||||
|
||||
void
|
||||
nsNodeUtils::AttributeSetToCurrentValue(Element* aElement,
|
||||
PRInt32 aNameSpaceID,
|
||||
nsIAtom* aAttribute)
|
||||
{
|
||||
nsIDocument* doc = aElement->OwnerDoc();
|
||||
IMPL_MUTATION_NOTIFICATION(AttributeSetToCurrentValue, aElement,
|
||||
(doc, aElement, aNameSpaceID, aAttribute));
|
||||
}
|
||||
|
||||
void
|
||||
nsNodeUtils::ContentAppended(nsIContent* aContainer,
|
||||
nsIContent* aFirstNewContent,
|
||||
|
|
|
@ -64,6 +64,16 @@ public:
|
|||
PRInt32 aNameSpaceID,
|
||||
nsIAtom* aAttribute,
|
||||
PRInt32 aModType);
|
||||
/**
|
||||
* Send AttributeSetToCurrentValue notifications to nsIMutationObservers.
|
||||
* @param aElement Element whose data changed
|
||||
* @param aNameSpaceID Namespace of the attribute
|
||||
* @param aAttribute Local-name of the attribute
|
||||
* @see nsIMutationObserver::AttributeSetToCurrentValue
|
||||
*/
|
||||
static void AttributeSetToCurrentValue(mozilla::dom::Element* aElement,
|
||||
PRInt32 aNameSpaceID,
|
||||
nsIAtom* aAttribute);
|
||||
|
||||
/**
|
||||
* Send ContentAppended notifications to nsIMutationObservers
|
||||
|
|
|
@ -38,7 +38,7 @@
|
|||
#include "nsIAsyncVerifyRedirectCallback.h"
|
||||
#include "nsIAppShell.h"
|
||||
|
||||
#include "nsPluginError.h"
|
||||
#include "nsError.h"
|
||||
|
||||
// Util headers
|
||||
#include "prenv.h"
|
||||
|
@ -540,7 +540,7 @@ IsPluginEnabledForType(const nsCString& aMIMEType)
|
|||
|
||||
if (!pluginHost) {
|
||||
NS_NOTREACHED("No pluginhost");
|
||||
return false;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv = pluginHost->IsPluginEnabledForType(aMIMEType.get());
|
||||
|
@ -726,7 +726,7 @@ nsObjectLoadingContent::InstantiatePluginInstance()
|
|||
|
||||
if (!pluginHost) {
|
||||
NS_NOTREACHED("No pluginhost");
|
||||
return false;
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
// If you add early return(s), be sure to balance this call to
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
|
||||
#include "nsPropertyTable.h"
|
||||
#include "pldhash.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIAtom.h"
|
||||
|
||||
struct PropertyListMapEntry : public PLDHashEntryHdr {
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
#include "nsIContent.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIDOMText.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIContentIterator.h"
|
||||
#include "nsIDOMNodeList.h"
|
||||
#include "nsGkAtoms.h"
|
||||
|
|
|
@ -31,7 +31,7 @@
|
|||
#include "nsUnicharUtils.h"
|
||||
#include "nsAutoPtr.h"
|
||||
#include "nsIXPConnect.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsThreadUtils.h"
|
||||
#include "nsDocShellCID.h"
|
||||
#include "nsIContentSecurityPolicy.h"
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
|
||||
#include "nsIDOMNode.h"
|
||||
#include "nsIDOMNodeFilter.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsINode.h"
|
||||
|
||||
#include "nsGkAtoms.h"
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
|
||||
#include "nsIDOMNode.h"
|
||||
#include "nsIDOMNodeFilter.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsINode.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "nsContentUtils.h"
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
#include "nsIXPConnect.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsEventDispatcher.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIScriptObjectPrincipal.h"
|
||||
#include "nsDOMClassInfoID.h"
|
||||
#include "jsapi.h"
|
||||
|
@ -42,7 +42,6 @@
|
|||
#include "nsDOMLists.h"
|
||||
#include "xpcpublic.h"
|
||||
#include "nsContentPolicyUtils.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "jsfriendapi.h"
|
||||
#include "prmem.h"
|
||||
#include "nsDOMFile.h"
|
||||
|
|
|
@ -51,10 +51,9 @@
|
|||
#include "nsCycleCollectionParticipant.h"
|
||||
#include "nsIContentPolicy.h"
|
||||
#include "nsContentPolicyUtils.h"
|
||||
#include "nsContentErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsLayoutStatics.h"
|
||||
#include "nsCrossSiteListenerProxy.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsIHTMLDocument.h"
|
||||
#include "nsIMultiPartChannel.h"
|
||||
#include "nsIScriptObjectPrincipal.h"
|
||||
|
|
|
@ -43,6 +43,7 @@ MOCHITEST_CHROME_FILES = \
|
|||
test_bug752226-3.xul \
|
||||
test_bug752226-4.xul \
|
||||
test_bug682305.html \
|
||||
test_bug780199.xul \
|
||||
$(NULL)
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
<?xml version="1.0"?>
|
||||
<?xml-stylesheet type="text/css" href="chrome://global/skin"?>
|
||||
<?xml-stylesheet type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css"?>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=780199
|
||||
-->
|
||||
<window title="Mozilla Bug 780199"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
|
||||
onload="test()">
|
||||
<script type="application/javascript" src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"/>
|
||||
|
||||
<!-- test results are displayed in the html:body -->
|
||||
<body xmlns="http://www.w3.org/1999/xhtml">
|
||||
<a href="https://bugzilla.mozilla.org/show_bug.cgi?id=780199"
|
||||
target="_blank">Mozilla Bug 780199</a>
|
||||
</body>
|
||||
|
||||
<!-- test code goes here -->
|
||||
<script type="application/javascript">
|
||||
<![CDATA[
|
||||
|
||||
/** Test for Bug 780199 **/
|
||||
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
|
||||
var b;
|
||||
|
||||
function callback(r) {
|
||||
is(r[0].type, "attributes");
|
||||
is(r[0].oldValue, b.getAttribute("src"));
|
||||
setTimeout(continueTest, 500);
|
||||
}
|
||||
|
||||
function continueTest() {
|
||||
// Check that a new page wasn't loaded.
|
||||
is(b.contentDocument.documentElement.textContent, "testvalue");
|
||||
SimpleTest.finish();
|
||||
}
|
||||
|
||||
function test() {
|
||||
b = document.getElementById("b");
|
||||
var m = MutationObserver(callback);
|
||||
m.observe(b, { attributes: true, attributeOldValue: true });
|
||||
b.contentDocument.documentElement.textContent = "testvalue";
|
||||
b.setAttribute("src", b.getAttribute("src"));
|
||||
}
|
||||
|
||||
]]>
|
||||
</script>
|
||||
<browser id="b" src="data:text/plain,initial"/>
|
||||
</window>
|
|
@ -2,7 +2,7 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
do_load_httpd_js();
|
||||
Components.utils.import("resource://testing-common/httpd.js");
|
||||
|
||||
var server = null;
|
||||
|
||||
|
@ -36,7 +36,7 @@ function headerCheckHandler(metadata, response) {
|
|||
}
|
||||
|
||||
function run_test() {
|
||||
var server = new nsHttpServer();
|
||||
var server = new HttpServer();
|
||||
server.registerPathHandler(redirectPath, redirectHandler);
|
||||
server.registerPathHandler(headerCheckPath, headerCheckHandler);
|
||||
server.start(SERVER_PORT);
|
||||
|
|
|
@ -1,5 +1,11 @@
|
|||
Components.utils.import('resource://gre/modules/CSPUtils.jsm');
|
||||
do_load_httpd_js();
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cu = Components.utils;
|
||||
const Cr = Components.results;
|
||||
|
||||
Cu.import('resource://gre/modules/CSPUtils.jsm');
|
||||
Cu.import("resource://testing-common/httpd.js");
|
||||
|
||||
var httpserv = null;
|
||||
|
||||
|
@ -16,8 +22,8 @@ var TESTS = [];
|
|||
|
||||
// helper to make URIs
|
||||
function mkuri(foo) {
|
||||
return Components.classes["@mozilla.org/network/io-service;1"]
|
||||
.getService(Components.interfaces.nsIIOService)
|
||||
return Cc["@mozilla.org/network/io-service;1"]
|
||||
.getService(Ci.nsIIOService)
|
||||
.newURI(foo, null, null);
|
||||
}
|
||||
|
||||
|
@ -87,7 +93,7 @@ listener.prototype = {
|
|||
};
|
||||
|
||||
function run_test() {
|
||||
httpserv = new nsHttpServer();
|
||||
httpserv = new HttpServer();
|
||||
httpserv.registerPathHandler("/document", csp_doc_response);
|
||||
httpserv.registerPathHandler("/policy", csp_policy_response);
|
||||
httpserv.start(POLICY_PORT);
|
||||
|
|
|
@ -2,11 +2,16 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
Components.utils.import('resource://gre/modules/CSPUtils.jsm');
|
||||
Components.utils.import('resource://gre/modules/NetUtil.jsm');
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cu = Components.utils;
|
||||
const Cr = Components.results;
|
||||
|
||||
Cu.import('resource://gre/modules/CSPUtils.jsm');
|
||||
Cu.import('resource://gre/modules/NetUtil.jsm');
|
||||
|
||||
// load the HTTP server
|
||||
do_load_httpd_js();
|
||||
Cu.import("resource://testing-common/httpd.js");
|
||||
|
||||
const REPORT_SERVER_PORT = 9000;
|
||||
const REPORT_SERVER_URI = "http://localhost";
|
||||
|
@ -87,7 +92,7 @@ function run_test() {
|
|||
":" + REPORT_SERVER_PORT +
|
||||
"/foo/self");
|
||||
|
||||
httpServer = new nsHttpServer();
|
||||
httpServer = new HttpServer();
|
||||
httpServer.start(REPORT_SERVER_PORT);
|
||||
|
||||
// test that inline script violations cause a report.
|
||||
|
|
|
@ -2,14 +2,19 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cu = Components.utils;
|
||||
const Cr = Components.results;
|
||||
|
||||
//load('CSPUtils.jsm');
|
||||
Components.utils.import('resource://gre/modules/CSPUtils.jsm');
|
||||
Components.utils.import('resource://gre/modules/NetUtil.jsm');
|
||||
Cu.import('resource://gre/modules/CSPUtils.jsm');
|
||||
Cu.import('resource://gre/modules/NetUtil.jsm');
|
||||
|
||||
// load the HTTP server
|
||||
do_load_httpd_js();
|
||||
Cu.import("resource://testing-common/httpd.js");
|
||||
|
||||
var httpServer = new nsHttpServer();
|
||||
var httpServer = new HttpServer();
|
||||
|
||||
const POLICY_FROM_URI = "allow 'self'; img-src *";
|
||||
const POLICY_PORT = 9000;
|
||||
|
@ -18,8 +23,8 @@ const POLICY_URI_RELATIVE = "/policy";
|
|||
|
||||
//converts string to nsIURI
|
||||
function URI(uriString) {
|
||||
var ioService = Components.classes["@mozilla.org/network/io-service;1"]
|
||||
.getService(Components.interfaces.nsIIOService);
|
||||
var ioService = Cc["@mozilla.org/network/io-service;1"]
|
||||
.getService(Ci.nsIIOService);
|
||||
return ioService.newURI(uriString, null, null);
|
||||
}
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIDOMCanvasRenderingContext2D.h"
|
||||
#include "mozilla/CheckedInt.h"
|
||||
#include "nsMathUtils.h"
|
||||
|
|
|
@ -11,7 +11,7 @@
|
|||
#include "nsIClassInfoImpl.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsIXPConnect.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIGfxInfo.h"
|
||||
|
||||
#include "nsIPropertyBag.h"
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "gfxPlatform.h"
|
||||
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsLayoutUtils.h"
|
||||
|
||||
#include "CanvasUtils.h"
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
#include "nsIVariant.h"
|
||||
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIScriptError.h"
|
||||
|
||||
#include "nsCSSParser.h"
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIFrame.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIScriptError.h"
|
||||
|
||||
#include "nsCSSParser.h"
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsDOMLists.h"
|
||||
#include "nsGUIEvent.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIDragService.h"
|
||||
#include "nsIScriptableRegion.h"
|
||||
#include "nsContentUtils.h"
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
#include "IPC/IPCMessageUtils.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMEvent.h"
|
||||
#include "nsEventStateManager.h"
|
||||
#include "nsIFrame.h"
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMNotifyAudioAvailableEvent.h"
|
||||
#include "nsDOMClassInfoID.h" // DOMCI_DATA, NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO
|
||||
#include "nsContentUtils.h" // NS_DROP_JS_OBJECTS
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#include "nsPresContext.h"
|
||||
#include "nsEventListenerManager.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "mozilla/FunctionTimer.h"
|
||||
#include "nsMutationEvent.h"
|
||||
#include NEW_H
|
||||
|
|
|
@ -32,7 +32,7 @@
|
|||
#include "nsCOMPtr.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIJSContextStack.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIPresShell.h"
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
#include "nsGenericHTMLElement.h"
|
||||
#include "nsGkAtoms.h"
|
||||
#include "nsSize.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsNodeInfoManager.h"
|
||||
|
||||
#include "nsICanvasElementExternal.h"
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsDOMStringMap.h"
|
||||
|
||||
#include "nsDOMClassInfoID.h"
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
#include "nsGkAtoms.h"
|
||||
#include "nsIFormControl.h"
|
||||
#include "nsIDOMHTMLFormElement.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsGenericHTMLElement.h"
|
||||
#include "nsISaveAsCharset.h"
|
||||
#include "nsIFile.h"
|
||||
|
|
|
@ -44,7 +44,7 @@
|
|||
#include "nsIDocShell.h"
|
||||
#include "nsIDocShellTreeItem.h"
|
||||
#include "nsINameSpaceManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsScriptLoader.h"
|
||||
#include "nsRuleData.h"
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIDOMHTMLAudioElement.h"
|
||||
#include "nsHTMLAudioElement.h"
|
||||
#include "nsGenericHTMLElement.h"
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
#include "nsLayoutUtils.h"
|
||||
#include "nsEventDispatcher.h"
|
||||
#include "nsPresState.h"
|
||||
#include "nsLayoutErrors.h"
|
||||
#include "nsError.h"
|
||||
#include "nsFocusManager.h"
|
||||
#include "nsHTMLFormElement.h"
|
||||
#include "nsIConstraintValidation.h"
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
#include "nsPresContext.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIFormControlFrame.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsInterfaceHashtable.h"
|
||||
#include "nsContentList.h"
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
#include "nsIDOMHTMLFrameElement.h"
|
||||
#include "nsGenericHTMLFrameElement.h"
|
||||
#include "nsGkAtoms.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
|
||||
class nsIDOMDocument;
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#include "nsIDOMSVGDocument.h"
|
||||
#include "nsGkAtoms.h"
|
||||
#include "nsMappedAttributes.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsRuleData.h"
|
||||
#include "nsStyleConsts.h"
|
||||
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
#include "nsEventStates.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsDOMError.h"
|
||||
#include "nsError.h"
|
||||
#include "nsIEditor.h"
|
||||
#include "nsGUIEvent.h"
|
||||
#include "nsIIOService.h"
|
||||
|
@ -44,7 +44,6 @@
|
|||
#include "nsAttrValueOrString.h"
|
||||
|
||||
#include "nsPresState.h"
|
||||
#include "nsLayoutErrors.h"
|
||||
#include "nsIDOMEvent.h"
|
||||
#include "nsIDOMNodeList.h"
|
||||
#include "nsIDOMHTMLCollection.h"
|
||||
|
|
Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше
Загрузка…
Ссылка в новой задаче