зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1621110 - Enable message editing for CFRs and Snippets on the general tab r=pdahiya
Differential Revision: https://phabricator.services.mozilla.com/D79916
This commit is contained in:
Родитель
2ba9319525
Коммит
aaf096ab28
|
@ -508,6 +508,7 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
messageFilter: "all",
|
messageFilter: "all",
|
||||||
WNMessages: [],
|
WNMessages: [],
|
||||||
collapsedMessages: [],
|
collapsedMessages: [],
|
||||||
|
modifiedMessages: [],
|
||||||
evaluationStatus: {},
|
evaluationStatus: {},
|
||||||
trailhead: {},
|
trailhead: {},
|
||||||
stringTargetingParameters: null,
|
stringTargetingParameters: null,
|
||||||
|
@ -580,6 +581,23 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
return () => ASRouterUtils.unblockById(msg.id);
|
return () => ASRouterUtils.unblockById(msg.id);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
resetJSON(msg) {
|
||||||
|
// reset the displayed JSON for the given message
|
||||||
|
document.getElementById(`${msg.id}-textarea`).value = JSON.stringify(
|
||||||
|
msg,
|
||||||
|
null,
|
||||||
|
2
|
||||||
|
);
|
||||||
|
// remove the message from the list of modified IDs
|
||||||
|
let index = this.state.modifiedMessages.indexOf(msg.id);
|
||||||
|
this.setState(prevState => ({
|
||||||
|
modifiedMessages: [
|
||||||
|
...prevState.modifiedMessages.slice(0, index),
|
||||||
|
...prevState.modifiedMessages.slice(index + 1),
|
||||||
|
],
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
|
||||||
handleOverride(id) {
|
handleOverride(id) {
|
||||||
return () => ASRouterUtils.overrideMessage(id);
|
return () => ASRouterUtils.overrideMessage(id);
|
||||||
}
|
}
|
||||||
|
@ -788,6 +806,20 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
modifyJson(msg) {
|
||||||
|
ASRouterUtils.modifyMessageJson(
|
||||||
|
JSON.parse(document.getElementById(`${msg.id}-textarea`).value)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
handleChange(msgId) {
|
||||||
|
if (!this.state.modifiedMessages.includes(msgId)) {
|
||||||
|
this.setState(prevState => ({
|
||||||
|
modifiedMessages: prevState.modifiedMessages.concat(msgId),
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
renderMessageItem(msg) {
|
renderMessageItem(msg) {
|
||||||
const isBlockedByGroup = this.state.groups
|
const isBlockedByGroup = this.state.groups
|
||||||
.filter(group => msg.groups.includes(group.id))
|
.filter(group => msg.groups.includes(group.id))
|
||||||
|
@ -805,6 +837,7 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
? this.state.messageImpressions[msg.id].length
|
? this.state.messageImpressions[msg.id].length
|
||||||
: 0;
|
: 0;
|
||||||
const isCollapsed = this.state.collapsedMessages.includes(msg.id);
|
const isCollapsed = this.state.collapsedMessages.includes(msg.id);
|
||||||
|
const isModified = this.state.modifiedMessages.includes(msg.id);
|
||||||
|
|
||||||
let itemClassName = "message-item";
|
let itemClassName = "message-item";
|
||||||
if (isBlocked) {
|
if (isBlocked) {
|
||||||
|
@ -834,11 +867,32 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
>
|
>
|
||||||
{isBlocked ? "Unblock" : "Block"}
|
{isBlocked ? "Unblock" : "Block"}
|
||||||
</button>
|
</button>
|
||||||
{isBlocked ? null : (
|
{// eslint-disable-next-line no-nested-ternary
|
||||||
<button className="button" onClick={this.handleOverride(msg.id)}>
|
isBlocked ? null : isModified ? (
|
||||||
|
<button
|
||||||
|
className="button restore"
|
||||||
|
// eslint-disable-next-line react/jsx-no-bind
|
||||||
|
onClick={e => this.resetJSON(msg)}
|
||||||
|
>
|
||||||
|
Reset
|
||||||
|
</button>
|
||||||
|
) : (
|
||||||
|
<button
|
||||||
|
className="button show"
|
||||||
|
onClick={this.handleOverride(msg.id)}
|
||||||
|
>
|
||||||
Show
|
Show
|
||||||
</button>
|
</button>
|
||||||
)}
|
)}
|
||||||
|
{isBlocked ? null : (
|
||||||
|
<button
|
||||||
|
className="button modify"
|
||||||
|
// eslint-disable-next-line react/jsx-no-bind
|
||||||
|
onClick={e => this.modifyJson(msg)}
|
||||||
|
>
|
||||||
|
Modify
|
||||||
|
</button>
|
||||||
|
)}
|
||||||
<br />({impressions} impressions)
|
<br />({impressions} impressions)
|
||||||
</td>
|
</td>
|
||||||
<td className="message-summary">
|
<td className="message-summary">
|
||||||
|
@ -852,7 +906,16 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
)}
|
)}
|
||||||
<tr>
|
<tr>
|
||||||
<pre className={isCollapsed ? "collapsed" : "expanded"}>
|
<pre className={isCollapsed ? "collapsed" : "expanded"}>
|
||||||
|
<textarea
|
||||||
|
id={`${msg.id}-textarea`}
|
||||||
|
name={msg.id}
|
||||||
|
className="general-textarea"
|
||||||
|
disabled={isBlocked}
|
||||||
|
// eslint-disable-next-line react/jsx-no-bind
|
||||||
|
onChange={e => this.handleChange(msg.id)}
|
||||||
|
>
|
||||||
{JSON.stringify(msg, null, 2)}
|
{JSON.stringify(msg, null, 2)}
|
||||||
|
</textarea>
|
||||||
</pre>
|
</pre>
|
||||||
</tr>
|
</tr>
|
||||||
</td>
|
</td>
|
||||||
|
@ -959,12 +1022,19 @@ export class ASRouterAdminInner extends React.PureComponent {
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<button
|
<button
|
||||||
className="ASRouterButton slim button"
|
className="ASRouterButton slim"
|
||||||
// eslint-disable-next-line react/jsx-no-bind
|
// eslint-disable-next-line react/jsx-no-bind
|
||||||
onClick={e => this.toggleAllMessages(messagesToShow)}
|
onClick={e => this.toggleAllMessages(messagesToShow)}
|
||||||
>
|
>
|
||||||
Collapse/Expand All
|
Collapse/Expand All
|
||||||
</button>
|
</button>
|
||||||
|
<p className="helpLink">
|
||||||
|
<span className="icon icon-small-spacer icon-info" />{" "}
|
||||||
|
<span>
|
||||||
|
To modify a message, change the JSON and click 'Modify' to see your
|
||||||
|
changes. Click 'Reset' to restore the JSON to the original.
|
||||||
|
</span>
|
||||||
|
</p>
|
||||||
<table>
|
<table>
|
||||||
<tbody>
|
<tbody>
|
||||||
{messagesToShow.map(msg => this.renderMessageItem(msg))}
|
{messagesToShow.map(msg => this.renderMessageItem(msg))}
|
||||||
|
|
|
@ -78,6 +78,15 @@
|
||||||
margin-bottom: 0;
|
margin-bottom: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.general-textarea {
|
||||||
|
width: 740px;
|
||||||
|
height: 500px;
|
||||||
|
overflow: auto;
|
||||||
|
resize: none;
|
||||||
|
border-radius: 4px;
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
.wnp-textarea {
|
.wnp-textarea {
|
||||||
width: 740px;
|
width: 740px;
|
||||||
height: 500px;
|
height: 500px;
|
||||||
|
|
|
@ -1727,6 +1727,13 @@ main {
|
||||||
padding: 6px 12px;
|
padding: 6px 12px;
|
||||||
margin-inline-start: 5px;
|
margin-inline-start: 5px;
|
||||||
margin-bottom: 0; }
|
margin-bottom: 0; }
|
||||||
|
.asrouter-admin .general-textarea {
|
||||||
|
width: 740px;
|
||||||
|
height: 500px;
|
||||||
|
overflow: auto;
|
||||||
|
resize: none;
|
||||||
|
border-radius: 4px;
|
||||||
|
display: flex; }
|
||||||
.asrouter-admin .wnp-textarea {
|
.asrouter-admin .wnp-textarea {
|
||||||
width: 740px;
|
width: 740px;
|
||||||
height: 500px;
|
height: 500px;
|
||||||
|
|
|
@ -1730,6 +1730,13 @@ main {
|
||||||
padding: 6px 12px;
|
padding: 6px 12px;
|
||||||
margin-inline-start: 5px;
|
margin-inline-start: 5px;
|
||||||
margin-bottom: 0; }
|
margin-bottom: 0; }
|
||||||
|
.asrouter-admin .general-textarea {
|
||||||
|
width: 740px;
|
||||||
|
height: 500px;
|
||||||
|
overflow: auto;
|
||||||
|
resize: none;
|
||||||
|
border-radius: 4px;
|
||||||
|
display: flex; }
|
||||||
.asrouter-admin .wnp-textarea {
|
.asrouter-admin .wnp-textarea {
|
||||||
width: 740px;
|
width: 740px;
|
||||||
height: 500px;
|
height: 500px;
|
||||||
|
|
|
@ -1727,6 +1727,13 @@ main {
|
||||||
padding: 6px 12px;
|
padding: 6px 12px;
|
||||||
margin-inline-start: 5px;
|
margin-inline-start: 5px;
|
||||||
margin-bottom: 0; }
|
margin-bottom: 0; }
|
||||||
|
.asrouter-admin .general-textarea {
|
||||||
|
width: 740px;
|
||||||
|
height: 500px;
|
||||||
|
overflow: auto;
|
||||||
|
resize: none;
|
||||||
|
border-radius: 4px;
|
||||||
|
display: flex; }
|
||||||
.asrouter-admin .wnp-textarea {
|
.asrouter-admin .wnp-textarea {
|
||||||
width: 740px;
|
width: 740px;
|
||||||
height: 500px;
|
height: 500px;
|
||||||
|
|
|
@ -1189,6 +1189,7 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
messageFilter: "all",
|
messageFilter: "all",
|
||||||
WNMessages: [],
|
WNMessages: [],
|
||||||
collapsedMessages: [],
|
collapsedMessages: [],
|
||||||
|
modifiedMessages: [],
|
||||||
evaluationStatus: {},
|
evaluationStatus: {},
|
||||||
trailhead: {},
|
trailhead: {},
|
||||||
stringTargetingParameters: null,
|
stringTargetingParameters: null,
|
||||||
|
@ -1266,6 +1267,16 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
return () => _asrouter_asrouter_content__WEBPACK_IMPORTED_MODULE_1__["ASRouterUtils"].unblockById(msg.id);
|
return () => _asrouter_asrouter_content__WEBPACK_IMPORTED_MODULE_1__["ASRouterUtils"].unblockById(msg.id);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
resetJSON(msg) {
|
||||||
|
// reset the displayed JSON for the given message
|
||||||
|
document.getElementById(`${msg.id}-textarea`).value = JSON.stringify(msg, null, 2); // remove the message from the list of modified IDs
|
||||||
|
|
||||||
|
let index = this.state.modifiedMessages.indexOf(msg.id);
|
||||||
|
this.setState(prevState => ({
|
||||||
|
modifiedMessages: [...prevState.modifiedMessages.slice(0, index), ...prevState.modifiedMessages.slice(index + 1)]
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
|
||||||
handleOverride(id) {
|
handleOverride(id) {
|
||||||
return () => _asrouter_asrouter_content__WEBPACK_IMPORTED_MODULE_1__["ASRouterUtils"].overrideMessage(id);
|
return () => _asrouter_asrouter_content__WEBPACK_IMPORTED_MODULE_1__["ASRouterUtils"].overrideMessage(id);
|
||||||
}
|
}
|
||||||
|
@ -1510,6 +1521,18 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
modifyJson(msg) {
|
||||||
|
_asrouter_asrouter_content__WEBPACK_IMPORTED_MODULE_1__["ASRouterUtils"].modifyMessageJson(JSON.parse(document.getElementById(`${msg.id}-textarea`).value));
|
||||||
|
}
|
||||||
|
|
||||||
|
handleChange(msgId) {
|
||||||
|
if (!this.state.modifiedMessages.includes(msgId)) {
|
||||||
|
this.setState(prevState => ({
|
||||||
|
modifiedMessages: prevState.modifiedMessages.concat(msgId)
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
renderMessageItem(msg) {
|
renderMessageItem(msg) {
|
||||||
const isBlockedByGroup = this.state.groups.filter(group => msg.groups.includes(group.id)).some(group => !group.enabled);
|
const isBlockedByGroup = this.state.groups.filter(group => msg.groups.includes(group.id)).some(group => !group.enabled);
|
||||||
const msgProvider = this.state.providers.find(provider => provider.id === msg.provider) || {};
|
const msgProvider = this.state.providers.find(provider => provider.id === msg.provider) || {};
|
||||||
|
@ -1518,6 +1541,7 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
const isBlocked = isMessageBlocked || isBlockedByGroup || isProviderExcluded;
|
const isBlocked = isMessageBlocked || isBlockedByGroup || isProviderExcluded;
|
||||||
const impressions = this.state.messageImpressions[msg.id] ? this.state.messageImpressions[msg.id].length : 0;
|
const impressions = this.state.messageImpressions[msg.id] ? this.state.messageImpressions[msg.id].length : 0;
|
||||||
const isCollapsed = this.state.collapsedMessages.includes(msg.id);
|
const isCollapsed = this.state.collapsedMessages.includes(msg.id);
|
||||||
|
const isModified = this.state.modifiedMessages.includes(msg.id);
|
||||||
let itemClassName = "message-item";
|
let itemClassName = "message-item";
|
||||||
|
|
||||||
if (isBlocked) {
|
if (isBlocked) {
|
||||||
|
@ -1538,14 +1562,30 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
}, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
}, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
||||||
className: `button ${isBlocked ? "" : " primary"}`,
|
className: `button ${isBlocked ? "" : " primary"}`,
|
||||||
onClick: isBlocked ? this.handleUnblock(msg) : this.handleBlock(msg)
|
onClick: isBlocked ? this.handleUnblock(msg) : this.handleBlock(msg)
|
||||||
}, isBlocked ? "Unblock" : "Block"), isBlocked ? null : react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
}, isBlocked ? "Unblock" : "Block"), // eslint-disable-next-line no-nested-ternary
|
||||||
className: "button",
|
isBlocked ? null : isModified ? react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
||||||
|
className: "button restore" // eslint-disable-next-line react/jsx-no-bind
|
||||||
|
,
|
||||||
|
onClick: e => this.resetJSON(msg)
|
||||||
|
}, "Reset") : react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
||||||
|
className: "button show",
|
||||||
onClick: this.handleOverride(msg.id)
|
onClick: this.handleOverride(msg.id)
|
||||||
}, "Show"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("br", null), "(", impressions, " impressions)"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("td", {
|
}, "Show"), isBlocked ? null : react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
||||||
|
className: "button modify" // eslint-disable-next-line react/jsx-no-bind
|
||||||
|
,
|
||||||
|
onClick: e => this.modifyJson(msg)
|
||||||
|
}, "Modify"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("br", null), "(", impressions, " impressions)"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("td", {
|
||||||
className: "message-summary"
|
className: "message-summary"
|
||||||
}, isBlocked && react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tr", null, "Block reason:", isBlockedByGroup && " Blocked by group", isProviderExcluded && " Excluded by provider", isMessageBlocked && " Message blocked"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tr", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("pre", {
|
}, isBlocked && react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tr", null, "Block reason:", isBlockedByGroup && " Blocked by group", isProviderExcluded && " Excluded by provider", isMessageBlocked && " Message blocked"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tr", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("pre", {
|
||||||
className: isCollapsed ? "collapsed" : "expanded"
|
className: isCollapsed ? "collapsed" : "expanded"
|
||||||
}, JSON.stringify(msg, null, 2)))));
|
}, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("textarea", {
|
||||||
|
id: `${msg.id}-textarea`,
|
||||||
|
name: msg.id,
|
||||||
|
className: "general-textarea",
|
||||||
|
disabled: isBlocked // eslint-disable-next-line react/jsx-no-bind
|
||||||
|
,
|
||||||
|
onChange: e => this.handleChange(msg.id)
|
||||||
|
}, JSON.stringify(msg, null, 2))))));
|
||||||
}
|
}
|
||||||
|
|
||||||
restoreWNMessageState() {
|
restoreWNMessageState() {
|
||||||
|
@ -1622,10 +1662,14 @@ class ASRouterAdminInner extends react__WEBPACK_IMPORTED_MODULE_4___default.a.Pu
|
||||||
|
|
||||||
const messagesToShow = this.state.messageFilter === "all" ? this.state.messages : this.state.messages.filter(message => message.provider === this.state.messageFilter);
|
const messagesToShow = this.state.messageFilter === "all" ? this.state.messages : this.state.messages.filter(message => message.provider === this.state.messageFilter);
|
||||||
return react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("div", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
return react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("div", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("button", {
|
||||||
className: "ASRouterButton slim button" // eslint-disable-next-line react/jsx-no-bind
|
className: "ASRouterButton slim" // eslint-disable-next-line react/jsx-no-bind
|
||||||
,
|
,
|
||||||
onClick: e => this.toggleAllMessages(messagesToShow)
|
onClick: e => this.toggleAllMessages(messagesToShow)
|
||||||
}, "Collapse/Expand All"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("table", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tbody", null, messagesToShow.map(msg => this.renderMessageItem(msg)))));
|
}, "Collapse/Expand All"), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("p", {
|
||||||
|
className: "helpLink"
|
||||||
|
}, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("span", {
|
||||||
|
className: "icon icon-small-spacer icon-info"
|
||||||
|
}), " ", react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("span", null, "To modify a message, change the JSON and click 'Modify' to see your changes. Click 'Reset' to restore the JSON to the original.")), react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("table", null, react__WEBPACK_IMPORTED_MODULE_4___default.a.createElement("tbody", null, messagesToShow.map(msg => this.renderMessageItem(msg)))));
|
||||||
}
|
}
|
||||||
|
|
||||||
renderWNMessages() {
|
renderWNMessages() {
|
||||||
|
|
|
@ -266,7 +266,7 @@ describe("ASRouterAdmin", () => {
|
||||||
});
|
});
|
||||||
|
|
||||||
assert.lengthOf(wrapper.find(".message-id"), 1);
|
assert.lengthOf(wrapper.find(".message-id"), 1);
|
||||||
wrapper.find(".message-item button:not(.primary)").simulate("click");
|
wrapper.find(".message-item button.show").simulate("click");
|
||||||
// first call is ADMIN_CONNECT_STATE
|
// first call is ADMIN_CONNECT_STATE
|
||||||
assert.propertyVal(
|
assert.propertyVal(
|
||||||
sendMessageStub.secondCall.args[1],
|
sendMessageStub.secondCall.args[1],
|
||||||
|
|
Загрузка…
Ссылка в новой задаче