@renproject/rentx
Version:
XState Statemachines for tracking RenVM transactions reactively
177 lines (176 loc) • 6.56 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.depositMachine = void 0;
const xstate_1 = require("xstate");
const actions_1 = require("xstate/lib/actions");
// Statemachine that tracks individual deposits
exports.depositMachine = xstate_1.Machine({
id: "RenVMDepositTransaction",
initial: "restoringDeposit",
states: {
errorRestoring: { entry: [actions_1.log("restore error")] },
restoringDeposit: {
entry: ["listenerAction"],
on: {
LISTENING: {
actions: xstate_1.send((context) => {
// If we don't have a raw tx, we can't restore
if (context.deposit.rawSourceTx) {
return {
type: "RESTORE",
data: context.deposit.rawSourceTx,
};
}
else {
return { type: "NOOP" };
}
}, {
to: (context) => {
// Named listener as ref does not seem to work
return `${context.deposit.sourceTxHash}DepositListener`;
},
}),
},
DETECTED: [
{
target: "restoredDeposit",
},
],
},
},
restoredDeposit: {
entry: [xstate_1.send("RESTORED")],
on: {
RESTORED: [
{
target: "errorRestoring",
},
{
target: "srcSettling",
cond: "isSrcSettling",
},
{
target: "srcConfirmed",
cond: "isSrcSettled",
},
{
target: "accepted",
cond: "isAccepted",
},
{
target: "destInitiated",
cond: "isDestInitiated",
},
].reverse(),
},
},
srcSettling: {
entry: xstate_1.send("SETTLE", {
to: (context) => {
const id = `${context.deposit.sourceTxHash}DepositListener`;
return id;
},
}),
on: {
CONFIRMED: [
{
target: "srcConfirmed",
actions: [
xstate_1.sendParent((ctx, _) => {
return {
type: "DEPOSIT_UPDATE",
data: ctx.deposit,
};
}),
xstate_1.assign({
deposit: (context, _) => (Object.assign({}, context.deposit)),
}),
],
},
],
CONFIRMATION: [
{
actions: [
xstate_1.assign({
deposit: (context, evt) => {
var _a, _b;
return (Object.assign(Object.assign({}, context.deposit), { sourceTxConfs: ((_a = evt.data) === null || _a === void 0 ? void 0 : _a.sourceTxConfs) || 0, sourceTxConfTarget: ((_b = evt.data) === null || _b === void 0 ? void 0 : _b.sourceTxConfTarget) || 1 }));
},
}),
xstate_1.sendParent((ctx, evt) => ({
type: "DEPOSIT_UPDATE",
data: Object.assign(Object.assign({}, ctx.deposit), evt.data),
})),
],
},
],
},
},
srcConfirmed: {
entry: xstate_1.send("SIGN", {
to: (context) => `${context.deposit.sourceTxHash}DepositListener`,
}),
on: {
SIGNED: {
target: "accepted",
actions: xstate_1.assign({
deposit: (ctx, evt) => (Object.assign(Object.assign({}, ctx.deposit), evt.data)),
}),
},
},
},
accepted: {
entry: xstate_1.sendParent((ctx, _) => {
return {
type: "CLAIMABLE",
data: ctx.deposit,
};
}),
on: {
CLAIM: "claiming",
REJECT: "rejected",
},
},
claiming: {
entry: xstate_1.send("MINT", {
to: (context) => `${context.deposit.sourceTxHash}DepositListener`,
}),
on: {
SUBMITTED: [
{
target: "destInitiated",
actions: [
xstate_1.assign({
deposit: (ctx, evt) => (Object.assign(Object.assign({}, ctx.deposit), evt.data)),
}),
xstate_1.sendParent((ctx, _) => ({
type: "DEPOSIT_UPDATE",
data: ctx.deposit,
})),
],
},
],
},
},
destInitiated: {
on: {
ACKNOWLEDGE: "completed",
},
},
rejected: {},
completed: {
entry: xstate_1.sendParent((ctx, _) => ({
type: "DEPOSIT_COMPLETED",
data: ctx.deposit,
})),
},
},
}, {
guards: {
isSrcSettling: ({ deposit: { sourceTxConfs } }) => (sourceTxConfs || 0) <= 1,
isSrcConfirmed: () => false,
isSrcSettled: ({ deposit: { sourceTxConfs } }) => (sourceTxConfs || 0) > 1,
isAccepted: ({ deposit: { renSignature } }) => renSignature ? true : false,
isDestInitiated: ({ deposit: { destTxHash } }) => destTxHash ? true : false,
},
});