Skip to content

Commit 08c707d

Browse files
Merge branch 'develop' into fix/use-counter-pending-transactions
2 parents 8a9b6aa + d6b7829 commit 08c707d

File tree

24 files changed

+414
-244
lines changed

24 files changed

+414
-244
lines changed

app/_locales/en/messages.json

+3
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

development/generate-rc-commits.js

+58-105
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ const octokit = new Octokit({
1010
/**
1111
* This script is used to filter and group commits by teams based on unique commit messages.
1212
* It takes two branches as input and generates a CSV file with the commit message, author,PR link, team,release tag and commit hash
13-
* The teams and their members are defined in the 'authorTeams' object.
13+
* The teams and their members are defined in the 'teams.json' file.
1414
*
1515
* Command to run the script: node development/generate-rc-commits.js origin/branchA origin/branchB
1616
*
@@ -19,96 +19,24 @@ const octokit = new Octokit({
1919
* Output: the generated commits will be in a file named 'commits.csv'.
2020
*/
2121

22-
// JSON mapping authors to teams
23-
const authorTeams = {
24-
Accounts: [
25-
'Owen Craston',
26-
'Gustavo Antunes',
27-
'Monte Lai',
28-
'Daniel Rocha',
29-
'Howard Braham',
30-
'Kate Johnson',
31-
'Xiaoming Wang',
32-
'Charly Chevalier',
33-
'Mike B',
34-
],
35-
'Wallet UX': ['David Walsh', 'Nidhi Kumari', 'Jony Bursztyn'],
36-
'Extension Platform': [
37-
'chloeYue',
38-
'Chloe Gao',
39-
'danjm',
40-
'Danica Shen',
41-
'Brad Decker',
42-
'hjetpoluru',
43-
'Harika Jetpoluru',
44-
'Marina Boboc',
45-
'Gauthier Petetin',
46-
'Dan Miller',
47-
'Dan J Miller',
48-
'David Murdoch',
49-
'Niranjana Binoy',
50-
'Victor Thomas',
51-
'vthomas13',
52-
'seaona',
53-
'Norbert Elter',
54-
],
55-
'Wallet API': ['tmashuang', 'jiexi', 'BelfordZ', 'Shane'],
56-
Confirmations: [
57-
'Pedro Figueiredo',
58-
'Sylva Elendu',
59-
'Olusegun Akintayo',
60-
'Jyoti Puri',
61-
'Ariella Vu',
62-
'OGPoyraz',
63-
'vinistevam',
64-
'Matthew Walsh',
65-
'cryptotavares',
66-
'Vinicius Stevam',
67-
'Derek Brans',
68-
'sleepytanya',
69-
'Priya',
70-
],
71-
'Design Systems': [
72-
'georgewrmarshall',
73-
'Garrett Bear',
74-
'George Marshall',
75-
'Devin',
76-
],
77-
Snaps: [
78-
'David Drazic',
79-
'hmalik88',
80-
'Montoya',
81-
'Mrtenz',
82-
'Frederik Bolding',
83-
'Bowen Sanders',
84-
'Guillaume Roux',
85-
'Hassan Malik',
86-
'Maarten Zuidhoorn',
87-
'Jonathan Ferreira',
88-
],
89-
Assets: ['salimtb', 'sahar-fehri', 'Brian Bergeron'],
90-
Linea: ['VGau', 'Victorien Gauch'],
91-
lavamoat: ['weizman', 'legobeat', 'kumavis', 'LeoTM'],
92-
'Wallet Framework': [
93-
'Michele Esposito',
94-
'Elliot Winkler',
95-
'Gudahtt',
96-
'Jongsun Suh',
97-
'Mark Stacey',
98-
],
99-
MMI: [
100-
'António Regadas',
101-
'Albert Olivé',
102-
'Ramon AC',
103-
'Shane T',
104-
'Bernardo Garces Chapero',
105-
],
106-
Swaps: ['Daniel', 'Davide Brocchetto', 'Nicolas Ferro', 'infiniteflower'],
107-
Devex: ['Thomas Huang', 'Alex Donesky', 'jiexi', 'Zachary Belford'],
108-
Notifications: ['Prithpal-Sooriya', 'Matteo Scurati', 'Prithpal Sooriya'],
109-
Bridging: ['Bilal', 'micaelae', 'Ethan Wessel'],
110-
Ramps: ['George Weiler'],
111-
};
22+
// Function to fetch author teams mapping file from teams.json
23+
async function fetchAuthorTeamsFile() {
24+
try {
25+
const { data } = await octokit.request(
26+
'GET /repos/{owner}/{repo}/contents/{path}',
27+
{
28+
owner: 'MetaMask',
29+
repo: 'MetaMask-planning',
30+
path: 'teams.json',
31+
},
32+
);
33+
const content = Buffer.from(data.content, 'base64').toString('utf-8');
34+
return JSON.parse(content); // Assuming the file is in JSON format
35+
} catch (error) {
36+
console.error('Error fetching author teams mapping file:', error);
37+
return {};
38+
}
39+
}
11240

11341
// Function to get PR labels
11442
async function getPRLabels(owner, repo, prNumber) {
@@ -129,18 +57,26 @@ async function getPRLabels(owner, repo, prNumber) {
12957
}
13058
}
13159

132-
// Function to get the team for a given author
133-
function getTeamForAuthor(authorName) {
134-
for (const [team, authors] of Object.entries(authorTeams)) {
135-
if (authors.includes(authorName)) {
136-
return team;
137-
}
60+
// Function to get the GitHub username for a given commit hash
61+
async function getGitHubUsername(commitHash) {
62+
try {
63+
const { data } = await octokit.request(
64+
'GET /repos/{owner}/{repo}/commits/{ref}',
65+
{
66+
owner: 'MetaMask',
67+
repo: 'metamask-extension',
68+
ref: commitHash,
69+
},
70+
);
71+
return data.author ? data.author.login : null;
72+
} catch (error) {
73+
console.error('Error fetching GitHub username:', error);
74+
return null;
13875
}
139-
return 'Other/Unknown'; // Default team for unknown authors
14076
}
14177

14278
// Function to filter commits based on unique commit messages and group by teams
143-
async function filterCommitsByTeam(branchA, branchB) {
79+
async function filterCommitsByTeam(branchA, branchB, authorTeams) {
14480
try {
14581
const git = simpleGit();
14682

@@ -157,17 +93,27 @@ async function filterCommitsByTeam(branchA, branchB) {
15793
const log = await git.log(logOptions);
15894
const seenMessages = new Set();
15995
const commitsByTeam = {};
96+
let processedCommits = 0;
16097

16198
const MAX_COMMITS = 500; // Limit the number of commits to process
99+
162100
console.log('Generation of the CSV file "commits.csv" is in progress...');
163101

164102
for (const commit of log.all) {
165-
const { author, message, hash } = commit;
166-
if (commitsByTeam.length >= MAX_COMMITS) {
103+
if (processedCommits >= MAX_COMMITS) {
167104
break;
168105
}
169106

170-
const team = getTeamForAuthor(author);
107+
const { author, message, hash } = commit;
108+
const githubUsername = await getGitHubUsername(hash);
109+
let team = authorTeams[githubUsername] || 'Other/Unknown';
110+
111+
// Format the team label
112+
team = team
113+
.replace(/^team-/u, '') // Remove the "team-" prefix
114+
.split('-') // Split the string into an array of words
115+
.map((word) => word.charAt(0).toUpperCase() + word.slice(1)) // Capitalize the first letter of each word
116+
.join(' '); // Join the words back into a string with spaces
171117

172118
// Extract PR number from the commit message using regex
173119
const prMatch = message.match(/\(#(\d+)\)/u);
@@ -206,9 +152,9 @@ async function filterCommitsByTeam(branchA, branchB) {
206152
releaseLabel,
207153
hash: hash.substring(0, 10),
208154
});
155+
processedCommits += 1;
209156
}
210157
}
211-
212158
return commitsByTeam;
213159
} catch (error) {
214160
console.error(error);
@@ -233,7 +179,7 @@ function formatAsCSV(commitsByTeam) {
233179
});
234180
}
235181
csvContent.unshift(
236-
'Commit Message,Author,PR Link,Team,Release Label, Commit Hash',
182+
'Commit Message,Author,PR Link,Team,Release Label,Commit Hash',
237183
);
238184

239185
return csvContent;
@@ -250,7 +196,14 @@ async function main() {
250196
const branchA = args[0];
251197
const branchB = args[1];
252198

253-
const commitsByTeam = await filterCommitsByTeam(branchA, branchB);
199+
// Fetch author teams mapping from the teams.json file
200+
const authorTeams = await fetchAuthorTeamsFile();
201+
202+
const commitsByTeam = await filterCommitsByTeam(
203+
branchA,
204+
branchB,
205+
authorTeams,
206+
);
254207

255208
if (Object.keys(commitsByTeam).length === 0) {
256209
console.log('No unique commits found.');

shared/lib/transaction-controller-utils.test.js

+68
Original file line numberDiff line numberDiff line change
@@ -278,4 +278,72 @@ describe('transaction controller utils', () => {
278278
).toBe(calcTokenAmount(logs[0].data, 8).toString(10), 6);
279279
});
280280
});
281+
282+
it('respects the precision argument for the default token', () => {
283+
const preTxBalance = new Numeric('5000000', 10, EtherDenomination.WEI);
284+
const postTxBalance = new Numeric(
285+
'592624562452462456762123343',
286+
10,
287+
EtherDenomination.WEI,
288+
);
289+
const gasUsed = new Numeric('28000', 10).toPrefixedHexString();
290+
const effectiveGasPrice = new Numeric('21', 10).toPrefixedHexString();
291+
const gasCost = calcGasTotal(gasUsed, effectiveGasPrice);
292+
const ethReceived = postTxBalance
293+
.minus(preTxBalance.minus(gasCost, 16))
294+
.toDenomination(EtherDenomination.ETH);
295+
296+
const get = (precision) =>
297+
getSwapsTokensReceivedFromTxMeta(
298+
'ETH',
299+
{
300+
txReceipt: {
301+
gasUsed,
302+
effectiveGasPrice,
303+
type: TransactionEnvelopeType.feeMarket,
304+
},
305+
preTxBalance: preTxBalance.toPrefixedHexString(),
306+
postTxBalance: postTxBalance.toPrefixedHexString(),
307+
swapMetaData: { token_to_amount: '0x1' },
308+
},
309+
'0x00',
310+
'0x00',
311+
'8',
312+
{},
313+
CHAIN_IDS.MAINNET,
314+
precision,
315+
);
316+
317+
expect(get(null)).toBe(ethReceived.toString());
318+
for (let precision = 1; precision < 10; precision++) {
319+
expect(get(precision)).toBe(ethReceived.round(precision).toString());
320+
}
321+
});
322+
323+
it('respects the precision argument for a non-default token', () => {
324+
const logs = [
325+
{
326+
topics: [TOKEN_TRANSFER_LOG_TOPIC_HASH, '', '0x00'],
327+
address: '0x00',
328+
data: new Numeric('123456789', 10).toPrefixedHexString(),
329+
},
330+
];
331+
const fullPrecision = calcTokenAmount(logs[0].data, 8);
332+
const get = (precision) =>
333+
getSwapsTokensReceivedFromTxMeta(
334+
'USDC',
335+
{ txReceipt: { logs, status: '0x1' } },
336+
'0x00',
337+
'0x00',
338+
'8',
339+
{ txReceipt: {} },
340+
CHAIN_IDS.MAINNET,
341+
precision,
342+
);
343+
344+
expect(get(null)).toBe(fullPrecision.toString());
345+
for (let precision = 1; precision < 10; precision++) {
346+
expect(get(precision)).toBe(fullPrecision.toPrecision(precision));
347+
}
348+
});
281349
});

shared/lib/transactions-controller-utils.js

+14-9
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ export function getSwapsTokensReceivedFromTxMeta(
5252
tokenDecimals,
5353
approvalTxMeta,
5454
chainId,
55+
precision = 6,
5556
) {
5657
const accountAddress = txMeta?.swapAndSendRecipient ?? senderAddress;
5758

@@ -106,9 +107,11 @@ export function getSwapsTokensReceivedFromTxMeta(
106107
)
107108
.minus(preTxBalanceLessGasCost)
108109
.toDenomination(EtherDenomination.ETH)
109-
.toBase(10)
110-
.round(6);
111-
return ethReceived.toString();
110+
.toBase(10);
111+
112+
return (
113+
precision === null ? ethReceived : ethReceived.round(precision)
114+
).toFixed();
112115
}
113116
const txReceiptLogs = txReceipt?.logs;
114117
if (txReceiptLogs && txReceipt?.status !== '0x0') {
@@ -127,12 +130,14 @@ export function getSwapsTokensReceivedFromTxMeta(
127130
isTransferFromGivenAddress
128131
);
129132
});
130-
return tokenTransferLog
131-
? toPrecisionWithoutTrailingZeros(
132-
calcTokenAmount(tokenTransferLog.data, tokenDecimals).toString(10),
133-
6,
134-
)
135-
: '';
133+
134+
if (tokenTransferLog) {
135+
const tokenAmount = calcTokenAmount(tokenTransferLog.data, tokenDecimals);
136+
return precision === null
137+
? tokenAmount.toFixed()
138+
: toPrecisionWithoutTrailingZeros(tokenAmount, precision);
139+
}
140+
return '';
136141
}
137142
return null;
138143
}

test/e2e/accounts/account-custom-name.spec.ts

+4-1
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,10 @@ describe('Account Custom Name Persistence', function (this: Suite) {
4545
'[data-testid="multichain-account-menu-popover-add-account"]',
4646
);
4747
await driver.fill('[placeholder="Account 2"]', anotherAccountLabel);
48-
await driver.clickElement({ text: 'Create', tag: 'button' });
48+
await driver.clickElementAndWaitToDisappear({
49+
text: 'Create',
50+
tag: 'button',
51+
});
4952
await locateAccountBalanceDOM(driver);
5053

5154
// Verify initial custom account label after freshly added account was active

test/e2e/accounts/common.ts

+3
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,9 @@ export async function installSnapSimpleKeyring(
8585
tag: 'button',
8686
});
8787

88+
// Wait until popup is closed before proceeding
89+
await driver.waitUntilXWindowHandles(2);
90+
8891
await driver.switchToWindowWithTitle(WINDOW_TITLES.SnapSimpleKeyringDapp);
8992

9093
await driver.waitForSelector({

0 commit comments

Comments
 (0)