milestone 1.0.0 release readiness: user-facing fixes, security review, release procedure #388
@@ -360,6 +360,11 @@ function init(_ctx) {
|
||||
});
|
||||
|
||||
$("btn-address-token-back").addEventListener("click", () => {
|
||||
// AddressDetail's show() clears the token, but Back onto a drawn
|
||||
// screen only unhides it. "Send" below may have left the dropdown on
|
||||
// the token as well.
|
||||
state.selectedToken = null;
|
||||
$("send-token").value = "ETH";
|
||||
goBack();
|
||||
});
|
||||
|
||||
|
||||
@@ -0,0 +1,165 @@
|
||||
// "Back" from AddressToken leaves no token selected. AddressDetail's show()
|
||||
// would clear it, but Back onto a drawn screen only unhides that screen, and
|
||||
// Send and Receive both read the field
|
||||
// (https://git.eeqj.de/sneak/AutistMask/issues/751). Driven through the real
|
||||
// popup over a stored profile.
|
||||
|
||||
const {
|
||||
bootPopup,
|
||||
cleanupPopup,
|
||||
unversionedValidProfile,
|
||||
TOKEN_ADDRESS,
|
||||
} = require("./support/popupBoot");
|
||||
|
||||
const RECIPIENT = "0x711e691962E5c054b78071C789A0C8CE657377aD";
|
||||
const TOKEN = {
|
||||
address: TOKEN_ADDRESS,
|
||||
symbol: "TST",
|
||||
decimals: 18,
|
||||
name: "Test Token",
|
||||
};
|
||||
|
||||
afterEach(() => {
|
||||
cleanupPopup();
|
||||
});
|
||||
|
||||
// The popup reopened onto AddressDetail, at an address holding 1.5 ETH and
|
||||
// 2.5 TST.
|
||||
function bootOnAddress() {
|
||||
const profile = unversionedValidProfile({
|
||||
currentView: "address",
|
||||
viewStack: ["main"],
|
||||
selectedWallet: 0,
|
||||
selectedAddress: 0,
|
||||
trackedTokens: [TOKEN],
|
||||
});
|
||||
profile.wallets[0].addresses[0].tokenBalances = [
|
||||
{ ...TOKEN, balance: "2.5" },
|
||||
];
|
||||
return bootPopup(profile);
|
||||
}
|
||||
|
||||
// AddressToken opened from AddressDetail, as tapping the token's row does.
|
||||
async function openToken(page) {
|
||||
const { state } = require("../src/shared/state");
|
||||
state.selectedToken = TOKEN_ADDRESS;
|
||||
require("../src/popup/views/helpers").pushCurrentView();
|
||||
require("../src/popup/views/addressToken").show();
|
||||
await page.settle();
|
||||
expect(page.visibleViews()).toEqual(["address-token"]);
|
||||
}
|
||||
|
||||
async function backFromToken(page) {
|
||||
await page.click("btn-address-token-back");
|
||||
expect(page.visibleViews()).toEqual(["address"]);
|
||||
}
|
||||
|
||||
// ETH chosen in Send's dropdown, as the user does.
|
||||
async function chooseEth(page) {
|
||||
const dropdown = page.node("send-token");
|
||||
dropdown.value = "ETH";
|
||||
for (const fn of dropdown.listeners.change) await fn();
|
||||
}
|
||||
|
||||
// Review for 1 of the token Send has, to RECIPIENT.
|
||||
async function review(page) {
|
||||
page.node("send-to").value = RECIPIENT;
|
||||
page.node("send-amount").value = "1";
|
||||
await page.click("btn-send-review");
|
||||
expect(page.visibleViews()).toEqual(["confirm-tx"]);
|
||||
}
|
||||
|
||||
describe("after Back from AddressToken", () => {
|
||||
test("no token is selected, on the page or in the stored record", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await backFromToken(page);
|
||||
|
||||
const { state } = require("../src/shared/state");
|
||||
expect(state.selectedToken).toBeNull();
|
||||
expect(page.storage.read("autistmask").selectedToken).toBeNull();
|
||||
});
|
||||
|
||||
test("Send with ETH chosen shows the ETH balance", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await backFromToken(page);
|
||||
|
||||
await page.click("btn-send");
|
||||
await chooseEth(page);
|
||||
|
||||
expect(page.text("send-balance")).toBe("Current balance: 1.5000 ETH");
|
||||
});
|
||||
|
||||
test("Send with ETH chosen reviews ETH", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await backFromToken(page);
|
||||
|
||||
await page.click("btn-send");
|
||||
await chooseEth(page);
|
||||
await review(page);
|
||||
|
||||
expect(page.text("confirm-type")).toBe("Native ETH transfer");
|
||||
});
|
||||
|
||||
test("Receive shows no token warning", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await backFromToken(page);
|
||||
|
||||
await page.click("btn-receive");
|
||||
|
||||
expect(page.visibleViews()).toEqual(["receive"]);
|
||||
expect(page.text("receive-erc20-warning")).toBe("");
|
||||
});
|
||||
|
||||
// AddressToken's Send sets the dropdown to the token, and nothing else
|
||||
// rebuilds it on the way back to AddressDetail.
|
||||
test("Send opens on ETH after AddressToken's Send has been used", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await page.click("btn-address-token-send");
|
||||
await page.click("btn-send-back");
|
||||
await backFromToken(page);
|
||||
|
||||
await page.click("btn-send");
|
||||
|
||||
expect(page.value("send-token")).toBe("ETH");
|
||||
expect(page.text("send-balance")).toBe("Current balance: 1.5000 ETH");
|
||||
});
|
||||
});
|
||||
|
||||
describe("Send opened from AddressToken sends that token", () => {
|
||||
async function expectSendsToken(page) {
|
||||
await page.click("btn-address-token-send");
|
||||
expect(page.text("send-balance")).toBe("Current balance: 2.5000 TST");
|
||||
await review(page);
|
||||
expect(page.text("confirm-type")).toBe("ERC-20 token transfer (TST)");
|
||||
}
|
||||
|
||||
test("the first time", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
|
||||
await expectSendsToken(page);
|
||||
});
|
||||
|
||||
test("after Back from Send", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await page.click("btn-address-token-send");
|
||||
await page.click("btn-send-back");
|
||||
|
||||
await expectSendsToken(page);
|
||||
});
|
||||
|
||||
test("when the token is opened again after Back from AddressToken", async () => {
|
||||
const page = await bootOnAddress();
|
||||
await openToken(page);
|
||||
await backFromToken(page);
|
||||
await openToken(page);
|
||||
|
||||
await expectSendsToken(page);
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user