Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
N
nebula
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
exchain
nebula
Commits
955ed992
Unverified
Commit
955ed992
authored
Sep 26, 2023
by
Wyatt Barnes
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Bug fixes. Refactor Metamask Grafana dashboard. Improved tx failure tracking
parent
01c7edb8
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
118 additions
and
140 deletions
+118
-140
metamask.json
ufm-test-services/grafana/dashboards/metamask.json
+60
-86
playwright.config.ts
ufm-test-services/metamask/playwright.config.ts
+0
-2
metamask.spec.ts
ufm-test-services/metamask/tests/metamask.spec.ts
+29
-17
prometheusUtils.ts
ufm-test-services/metamask/tests/prometheusUtils.ts
+29
-35
No files found.
ufm-test-services/grafana/dashboards/metamask.json
View file @
955ed992
...
@@ -18,6 +18,7 @@
...
@@ -18,6 +18,7 @@
"editable"
:
true
,
"editable"
:
true
,
"fiscalYearStartMonth"
:
0
,
"fiscalYearStartMonth"
:
0
,
"graphTooltip"
:
0
,
"graphTooltip"
:
0
,
"id"
:
1
,
"links"
:
[],
"links"
:
[],
"liveNow"
:
false
,
"liveNow"
:
false
,
"panels"
:
[
"panels"
:
[
...
@@ -31,88 +32,57 @@
...
@@ -31,88 +32,57 @@
"color"
:
{
"color"
:
{
"mode"
:
"thresholds"
"mode"
:
"thresholds"
},
},
"custom"
:
{
"axisCenteredZero"
:
true
,
"axisColorMode"
:
"series"
,
"axisGridShow"
:
false
,
"axisPlacement"
:
"auto"
,
"barAlignment"
:
0
,
"drawStyle"
:
"line"
,
"fillOpacity"
:
0
,
"gradientMode"
:
"none"
,
"hideFrom"
:
{
"legend"
:
false
,
"tooltip"
:
false
,
"viz"
:
false
},
"insertNulls"
:
false
,
"lineInterpolation"
:
"stepAfter"
,
"lineWidth"
:
1
,
"pointSize"
:
5
,
"scaleDistribution"
:
{
"type"
:
"linear"
},
"showPoints"
:
"never"
,
"spanNulls"
:
false
,
"stacking"
:
{
"group"
:
"A"
,
"mode"
:
"none"
},
"thresholdsStyle"
:
{
"mode"
:
"off"
}
},
"decimals"
:
0
,
"displayName"
:
"Number of Transactions (positive number = success, negative = failures)"
,
"mappings"
:
[],
"mappings"
:
[],
"thresholds"
:
{
"thresholds"
:
{
"mode"
:
"absolute"
,
"mode"
:
"absolute"
,
"steps"
:
[
"steps"
:
[
{
{
"color"
:
"
red
"
,
"color"
:
"
text
"
,
"value"
:
null
"value"
:
null
},
},
{
{
"color"
:
"
yellow
"
,
"color"
:
"
red
"
,
"value"
:
1
"value"
:
-
1
},
},
{
"color"
:
"green"
,
"value"
:
4
}
]
}
},
"overrides"
:
[]
},
"gridPos"
:
{
"h"
:
5
,
"w"
:
6
,
"x"
:
0
,
"y"
:
0
},
"id"
:
1
,
"options"
:
{
"orientation"
:
"auto"
,
"reduceOptions"
:
{
"calcs"
:
[
"lastNotNull"
],
"fields"
:
""
,
"values"
:
false
},
"showThresholdLabels"
:
false
,
"showThresholdMarkers"
:
true
},
"pluginVersion"
:
"10.1.2"
,
"targets"
:
[
{
"datasource"
:
{
"type"
:
"prometheus"
,
"uid"
:
"PBFA97CFB590B2093"
},
"disableTextWrap"
:
false
,
"editorMode"
:
"builder"
,
"expr"
:
"metamask_tx_success"
,
"fullMetaSearch"
:
false
,
"includeNullMetadata"
:
true
,
"instant"
:
false
,
"legendFormat"
:
"__auto"
,
"range"
:
true
,
"refId"
:
"A"
,
"useBackend"
:
false
}
],
"title"
:
"Successful Transaction Since Last Failure"
,
"type"
:
"gauge"
},
{
"datasource"
:
{
"type"
:
"prometheus"
,
"uid"
:
"PBFA97CFB590B2093"
},
"fieldConfig"
:
{
"defaults"
:
{
"color"
:
{
"mode"
:
"thresholds"
},
"mappings"
:
[],
"thresholds"
:
{
"mode"
:
"absolute"
,
"steps"
:
[
{
{
"color"
:
"text"
,
"color"
:
"text"
,
"value"
:
null
"value"
:
0
},
},
{
{
"color"
:
"
red
"
,
"color"
:
"
green
"
,
"value"
:
1
"value"
:
1
}
}
]
]
...
@@ -121,25 +91,29 @@
...
@@ -121,25 +91,29 @@
"overrides"
:
[]
"overrides"
:
[]
},
},
"gridPos"
:
{
"gridPos"
:
{
"h"
:
5
,
"h"
:
8
,
"w"
:
6
,
"w"
:
24
,
"x"
:
6
,
"x"
:
0
,
"y"
:
0
"y"
:
0
},
},
"id"
:
2
,
"id"
:
1
,
"options"
:
{
"options"
:
{
"orientation"
:
"auto"
,
"legend"
:
{
"reduceOptions"
:
{
"calcs"
:
[
"calcs"
:
[
"last
NotNull
"
"last"
],
],
"fields"
:
""
,
"displayMode"
:
"list"
,
"values"
:
false
"placement"
:
"bottom"
,
"showLegend"
:
true
},
},
"showThresholdLabels"
:
false
,
"timezone"
:
[
"showThresholdMarkers"
:
true
"browser"
],
"tooltip"
:
{
"mode"
:
"single"
,
"sort"
:
"none"
}
},
},
"pluginVersion"
:
"10.1.2"
,
"targets"
:
[
"targets"
:
[
{
{
"datasource"
:
{
"datasource"
:
{
...
@@ -148,7 +122,7 @@
...
@@ -148,7 +122,7 @@
},
},
"disableTextWrap"
:
false
,
"disableTextWrap"
:
false
,
"editorMode"
:
"builder"
,
"editorMode"
:
"builder"
,
"expr"
:
"metamask_
tx_failure
"
,
"expr"
:
"metamask_
self_send
"
,
"fullMetaSearch"
:
false
,
"fullMetaSearch"
:
false
,
"includeNullMetadata"
:
true
,
"includeNullMetadata"
:
true
,
"instant"
:
false
,
"instant"
:
false
,
...
@@ -158,8 +132,8 @@
...
@@ -158,8 +132,8 @@
"useBackend"
:
false
"useBackend"
:
false
}
}
],
],
"title"
:
"
Failed Transactions Since Last Success
"
,
"title"
:
"
Self Transferring on OP Goerli (positive number = success, negative = failures)
"
,
"type"
:
"
gauge
"
"type"
:
"
timeseries
"
}
}
],
],
"refresh"
:
"5s"
,
"refresh"
:
"5s"
,
...
@@ -170,7 +144,7 @@
...
@@ -170,7 +144,7 @@
"list"
:
[]
"list"
:
[]
},
},
"time"
:
{
"time"
:
{
"from"
:
"now-
6h
"
,
"from"
:
"now-
30m
"
,
"to"
:
"now"
"to"
:
"now"
},
},
"timepicker"
:
{},
"timepicker"
:
{},
...
@@ -179,4 +153,4 @@
...
@@ -179,4 +153,4 @@
"uid"
:
"f66f7076-c724-4f81-8ff9-58d6d99f2716"
,
"uid"
:
"f66f7076-c724-4f81-8ff9-58d6d99f2716"
,
"version"
:
1
,
"version"
:
1
,
"weekStart"
:
""
"weekStart"
:
""
}
}
\ No newline at end of file
ufm-test-services/metamask/playwright.config.ts
View file @
955ed992
...
@@ -15,8 +15,6 @@ export default defineConfig({
...
@@ -15,8 +15,6 @@ export default defineConfig({
fullyParallel
:
true
,
fullyParallel
:
true
,
/* Fail the build on CI if you accidentally left test.only in the source code. */
/* Fail the build on CI if you accidentally left test.only in the source code. */
forbidOnly
:
!!
process
.
env
.
CI
,
forbidOnly
:
!!
process
.
env
.
CI
,
/* Retry on CI only */
retries
:
process
.
env
.
CI
?
2
:
0
,
/* Opt out of parallel tests on CI. */
/* Opt out of parallel tests on CI. */
workers
:
process
.
env
.
CI
?
1
:
undefined
,
workers
:
process
.
env
.
CI
?
1
:
undefined
,
/* Reporter to use. See https://playwright.dev/docs/test-reporters */
/* Reporter to use. See https://playwright.dev/docs/test-reporters */
...
...
ufm-test-services/metamask/tests/metamask.spec.ts
View file @
955ed992
...
@@ -6,8 +6,7 @@ import { mnemonicToAccount, privateKeyToAccount } from 'viem/accounts'
...
@@ -6,8 +6,7 @@ import { mnemonicToAccount, privateKeyToAccount } from 'viem/accounts'
import
{
testWithSynpress
}
from
'
./testWithSynpressUtil
'
import
{
testWithSynpress
}
from
'
./testWithSynpressUtil
'
import
{
import
{
incrementMetamaskTxCounter
,
incrementSelfSendTxGauge
,
setMetamaskTxCounter
,
}
from
'
./prometheusUtils
'
}
from
'
./prometheusUtils
'
const
env
=
z
.
object
({
const
env
=
z
.
object
({
...
@@ -24,18 +23,31 @@ const expectedSender =
...
@@ -24,18 +23,31 @@ const expectedSender =
:
mnemonicToAccount
(
:
mnemonicToAccount
(
env
.
METAMASK_SECRET_WORDS_OR_PRIVATEKEY
as
string
env
.
METAMASK_SECRET_WORDS_OR_PRIVATEKEY
as
string
).
address
.
toLowerCase
()
).
address
.
toLowerCase
()
const
expectedRecipient
=
'
0x8fcfbe8953433fd1f2e8375ee99057833e4e1e9e
'
const
expectedRecipient
=
expectedSender
let
sharedPage
:
Page
let
sharedPage
:
Page
let
wasSuccessful
:
boolean
let
handledFailure
:
boolean
test
.
describe
.
configure
({
mode
:
'
serial
'
})
test
.
describe
.
configure
({
mode
:
'
serial
'
})
test
.
beforeAll
(()
=>
{
wasSuccessful
=
false
handledFailure
=
false
})
test
.
afterAll
(
async
()
=>
{
test
.
afterAll
(
async
()
=>
{
// This is handling failure scenarios such as Playwright timeouts
// where are not able to catch and respond to an error.
if
(
!
wasSuccessful
&&
!
handledFailure
)
{
await
incrementSelfSendTxGauge
(
false
)
}
await
sharedPage
.
close
()
await
sharedPage
.
close
()
})
})
testWithSynpress
(
'
Setup wallet and dApp
'
,
async
({
page
})
=>
{
testWithSynpress
(
'
Setup wallet and dApp
'
,
async
({
page
})
=>
{
console
.
log
(
'
Seting up wallet and dApp...
'
)
console
.
log
(
'
Set
t
ing up wallet and dApp...
'
)
sharedPage
=
page
sharedPage
=
page
await
sharedPage
.
goto
(
'
http://localhost:9011
'
)
await
sharedPage
.
goto
(
'
http://localhost:9011
'
)
console
.
log
(
'
Setup wallet and dApp
'
)
console
.
log
(
'
Setup wallet and dApp
'
)
...
@@ -66,8 +78,8 @@ testWithSynpress('Add OP Goerli network', async () => {
...
@@ -66,8 +78,8 @@ testWithSynpress('Add OP Goerli network', async () => {
try
{
try
{
await
expect
(
sharedPage
.
locator
(
'
#chainId
'
)).
toHaveText
(
expectedChainId
)
await
expect
(
sharedPage
.
locator
(
'
#chainId
'
)).
toHaveText
(
expectedChainId
)
}
catch
(
error
)
{
}
catch
(
error
)
{
await
setMetamaskTxCounter
(
true
,
0
)
await
incrementSelfSendTxGauge
(
false
)
await
incrementMetamaskTxCounter
(
false
)
handledFailure
=
true
throw
error
throw
error
}
}
console
.
log
(
'
Added OP Goerli network
'
)
console
.
log
(
'
Added OP Goerli network
'
)
...
@@ -81,15 +93,15 @@ test(`Connect wallet with ${expectedSender}`, async () => {
...
@@ -81,15 +93,15 @@ test(`Connect wallet with ${expectedSender}`, async () => {
try
{
try
{
await
expect
(
sharedPage
.
locator
(
'
#accounts
'
)).
toHaveText
(
expectedSender
)
await
expect
(
sharedPage
.
locator
(
'
#accounts
'
)).
toHaveText
(
expectedSender
)
}
catch
(
error
)
{
}
catch
(
error
)
{
await
setMetamaskTxCounter
(
true
,
0
)
await
incrementSelfSendTxGauge
(
false
)
await
incrementMetamaskTxCounter
(
false
)
handledFailure
=
true
throw
error
throw
error
}
}
console
.
log
(
`Connected wallet with
${
expectedSender
}
`
)
console
.
log
(
`Connected wallet with
${
expectedSender
}
`
)
})
})
test
(
'
Send an EIP-1559 transac
iton and verfi
y success
'
,
async
()
=>
{
test
(
'
Send an EIP-1559 transac
tion and verif
y success
'
,
async
()
=>
{
console
.
log
(
'
Sending an EIP-1559 transac
iton and verfi
y success...
'
)
console
.
log
(
'
Sending an EIP-1559 transac
tion and verif
y success...
'
)
const
expectedTransferAmount
=
'
0x1
'
const
expectedTransferAmount
=
'
0x1
'
const
expectedTxType
=
'
0x2
'
const
expectedTxType
=
'
0x2
'
...
@@ -120,7 +132,7 @@ test('Send an EIP-1559 transaciton and verfiy success', async () => {
...
@@ -120,7 +132,7 @@ test('Send an EIP-1559 transaciton and verfiy success', async () => {
// Waiting for RPC response to be populated on the page
// Waiting for RPC response to be populated on the page
await
sharedPage
.
waitForTimeout
(
2
_000
)
await
sharedPage
.
waitForTimeout
(
2
_000
)
const
transaction
=
JSON
.
parse
(
const
transaction
Receipt
=
JSON
.
parse
(
(
await
sharedPage
.
locator
(
'
body > main
'
).
innerText
()).
replace
(
(
await
sharedPage
.
locator
(
'
body > main
'
).
innerText
()).
replace
(
'
Response:
'
,
'
Response:
'
,
''
''
...
@@ -128,13 +140,13 @@ test('Send an EIP-1559 transaciton and verfiy success', async () => {
...
@@ -128,13 +140,13 @@ test('Send an EIP-1559 transaciton and verfiy success', async () => {
)
)
try
{
try
{
expect
(
transaction
.
status
).
toBe
(
'
0x1
'
)
expect
(
transaction
Receipt
.
status
).
toBe
(
'
0x1
'
)
await
setMetamaskTxCounter
(
false
,
0
)
wasSuccessful
=
true
await
increment
MetamaskTxCounter
(
true
)
await
increment
SelfSendTxGauge
(
true
)
}
catch
(
error
)
{
}
catch
(
error
)
{
await
setMetamaskTxCounter
(
true
,
0
)
await
incrementSelfSendTxGauge
(
false
)
await
incrementMetamaskTxCounter
(
false
)
handledFailure
=
true
throw
error
throw
error
}
}
console
.
log
(
'
Sent an EIP-1559 transac
iton and ver
fied success
'
)
console
.
log
(
'
Sent an EIP-1559 transac
tion and veri
fied success
'
)
})
})
ufm-test-services/metamask/tests/prometheusUtils.ts
View file @
955ed992
import
'
dotenv/config
'
import
'
dotenv/config
'
import
{
z
}
from
'
zod
'
import
{
z
}
from
'
zod
'
import
{
Counter
,
Pushgateway
}
from
'
prom-client
'
import
{
Gauge
,
Pushgateway
}
from
'
prom-client
'
const
env
=
z
const
env
=
z
.
object
({
.
object
({
...
@@ -9,21 +9,15 @@ const env = z
...
@@ -9,21 +9,15 @@ const env = z
})
})
.
parse
(
process
.
env
)
.
parse
(
process
.
env
)
const
txSuccessMetricName
=
'
metamask_tx_success
'
const
selfSendTransactionMetricName
=
'
metamask_self_send
'
const
txFailureMetricName
=
'
metamask_tx_failure
'
const
txSuccessCounter
=
new
Counter
({
const
selfSendGauge
=
new
Gauge
({
name
:
txSuccessMetricName
,
name
:
selfSendTransactionMetricName
,
help
:
'
A counter signifying the number of successful transactions sent with Metamask since last failure
'
,
help
:
'
A gauge signifying the number of transactions sent with Metamask
'
,
})
const
txFailureCounter
=
new
Counter
({
name
:
txFailureMetricName
,
help
:
'
A counter signifying the number of failed transactions sent with Metamask since last successful transaction
'
,
})
})
export
const
getMetamaskTxCounterValue
=
async
(
isSuccess
:
boolean
)
=>
{
export
const
getSelfSendGaugeValue
=
async
()
=>
{
const
metricName
=
isSuccess
?
txSuccessMetricName
:
txFailureMetricName
const
prometheusMetricQuery
=
`
${
env
.
PROMETHEUS_SERVER_URL
}
/api/v1/query?query=
${
selfSendTransactionMetricName
}
`
const
prometheusMetricQuery
=
`
${
env
.
PROMETHEUS_SERVER_URL
}
/api/v1/query?query=
${
metricName
}
`
const
response
=
await
fetch
(
prometheusMetricQuery
)
const
response
=
await
fetch
(
prometheusMetricQuery
)
if
(
!
response
.
ok
)
{
if
(
!
response
.
ok
)
{
...
@@ -37,12 +31,12 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
...
@@ -37,12 +31,12 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
// [
// [
// {
// {
// metric: {
// metric: {
// __name__: 'metamask_
tx_success
',
// __name__: 'metamask_
self_send
',
// exported_job: 'metamask_tx_count',
// exported_job: 'metamask_
self_send_
tx_count',
// instance: 'pushgateway:9091',
// instance: 'pushgateway:9091',
// job: 'pushgateway'
// job: 'pushgateway'
// },
// },
// value: [ 1695
250414.474, '0
' ]
// value: [ 1695
847795.646, '-1
' ]
// }
// }
// ]
// ]
try
{
try
{
...
@@ -66,7 +60,9 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
...
@@ -66,7 +60,9 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
if
(
if
(
error
.
message
===
"
Cannot read properties of undefined (reading 'value')
"
error
.
message
===
"
Cannot read properties of undefined (reading 'value')
"
)
{
)
{
console
.
warn
(
`No data found for metric
${
metricName
}
in Prometheus`
)
console
.
warn
(
`No data found for metric
${
selfSendTransactionMetricName
}
in Prometheus`
)
return
undefined
return
undefined
}
}
...
@@ -74,28 +70,26 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
...
@@ -74,28 +70,26 @@ export const getMetamaskTxCounterValue = async (isSuccess: boolean) => {
}
}
}
}
export
const
setMetamaskTxCounter
=
async
(
export
const
setSelfSendTxGauge
=
async
(
valueToSetTo
:
number
)
=>
{
isSuccess
:
boolean
,
console
.
log
(
`Setting
${
selfSendTransactionMetricName
}
to
${
valueToSetTo
}
`
)
valueToSetTo
:
number
selfSendGauge
.
set
(
valueToSetTo
)
)
=>
{
const
metricName
=
isSuccess
?
txSuccessMetricName
:
txFailureMetricName
const
txCounter
=
isSuccess
?
txSuccessCounter
:
txFailureCounter
txCounter
.
reset
()
console
.
log
(
`Setting
${
metricName
}
to
${
valueToSetTo
}
`
)
txCounter
.
inc
(
valueToSetTo
)
const
pushGateway
=
new
Pushgateway
(
env
.
PROMETHEUS_PUSHGATEWAY_URL
)
const
pushGateway
=
new
Pushgateway
(
env
.
PROMETHEUS_PUSHGATEWAY_URL
)
await
pushGateway
.
pushAdd
({
jobName
:
'
metamask_tx_count
'
})
await
pushGateway
.
pushAdd
({
jobName
:
'
metamask_
self_send_
tx_count
'
})
}
}
export
const
incrementMetamaskTxCounter
=
async
(
isSuccess
:
boolean
)
=>
{
export
const
incrementSelfSendTxGauge
=
async
(
isSuccess
:
boolean
)
=>
{
const
metricName
=
isSuccess
?
txSuccessMetricName
:
txFailureMetricName
const
currentMetricValue
=
(
await
getSelfSendGaugeValue
())
??
0
const
currentMetricValue
=
(
await
getMetamaskTxCounterValue
(
true
))
??
0
let
newMetricValue
:
number
if
(
isSuccess
)
{
newMetricValue
=
currentMetricValue
>=
0
?
currentMetricValue
+
1
:
1
}
else
{
newMetricValue
=
currentMetricValue
<
0
?
currentMetricValue
-
1
:
-
1
}
console
.
log
(
console
.
log
(
`Current value of
${
metricName
}
is
${
currentMetricValue
}
, incrementing to
${
`Current value of
${
selfSendTransactionMetricName
}
is
${
currentMetricValue
}
, incrementing to
${
newMetricValue
}
`
currentMetricValue
+
1
}
`
)
)
await
set
MetamaskTxCounter
(
isSuccess
,
currentMetricValue
+
1
)
await
set
SelfSendTxGauge
(
newMetricValue
)
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment