Skip to content

Commit a7890a6

Browse files
committed
Fixed bug and added scenarior unit test which not covered in e2e
1 parent a06a4e4 commit a7890a6

File tree

2 files changed

+106
-11
lines changed

2 files changed

+106
-11
lines changed

src/model/receipt/ResolutionStatement.ts

Lines changed: 54 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -102,38 +102,70 @@ export class ResolutionStatement {
102102
*/
103103
const resolvedPrimaryId = this.getMaxAvailablePrimaryId(primaryId);
104104

105+
/*
106+
If no primaryId found, it means there's no resolution entry available for the process. Invalid entry.
107+
108+
e.g. Given:
109+
Entries: [{P:2, S:0}, {P5:, S:6}]
110+
Transaction: [Inx:1(0+1), AggInx:0]
111+
It should return Entry: undefined
112+
*/
105113
if (resolvedPrimaryId === 0) {
106114
return undefined;
107115
} else if (primaryId > resolvedPrimaryId) {
108116
/*
109117
If the transaction index is greater than the overall most recent source primary id.
110118
Use the most recent resolution entry (Max.PrimaryId + Max.SecondaryId)
119+
120+
e.g. Given:
121+
Entries: [{P:1, S:0}, {P:2, S:0}, {P:4, S:2}, {P:4, S:4} {P7:, S:6}]
122+
Transaction: [Inx:5(0+1), AggInx:0]
123+
It should return Entry: {P:3, S:4}
124+
125+
e.g. Given:
126+
Entries: [{P:1, S:0}, {P:2, S:0}, {P:4, S:2}, {P:4, S:4}, {P7:, S:6}]
127+
Transaction: [Inx:3(2+1), AggInx:0]
128+
It should return Entry: {P:2, S:0}
111129
*/
112130
return this.resolutionEntries
113131
.find((entry) => entry.source.primaryId === resolvedPrimaryId &&
114132
entry.source.secondaryId === this.getMaxSecondaryIdByPrimaryId(resolvedPrimaryId));
115133
}
116134

117-
// When transaction index matches a primary id, get the most recent secondaryId
118-
const resolvedSecondaryId = this.getMaxSecondaryIdByPrimaryId(resolvedPrimaryId);
135+
// When transaction index matches a primary id, get the most recent secondaryId (resolvedPrimaryId can only <= primaryId)
136+
const resolvedSecondaryId = this.getMaxSecondaryIdByPrimaryIdAndSecondaryId(resolvedPrimaryId, secondaryId);
119137

120-
if (resolvedSecondaryId === 0 && secondaryId !== resolvedSecondaryId) {
121-
/*
122-
If no most recent secondaryId matched transaction index, find previous resolution entry (most recent).
123-
*/
138+
/*
139+
If no most recent secondaryId matched transaction index, find previous resolution entry (most recent).
140+
This means the resolution entry for the specific innter transaction (inside Aggregate) /
141+
was generated previously outside the aggregate. It should return the previous entry (privious primarId)
142+
143+
e.g. Given:
144+
Entries: [{P:1, S:0}, {P:2, S:0}, {P5:, S:6}]
145+
Transaction: [Inx:5(4+1), AggInx:3(2+1)]
146+
It should return Entry: {P:2, S:0}
147+
*/
148+
if (resolvedSecondaryId === 0 && resolvedSecondaryId !== secondaryId) {
124149
const lastPrimaryId = this.getMaxAvailablePrimaryId(resolvedPrimaryId - 1);
125-
return this.resolutionEntries
126-
.find((entry) => entry.source.primaryId === lastPrimaryId &&
127-
entry.source.secondaryId === this.getMaxSecondaryIdByPrimaryId(lastPrimaryId));
150+
return this.resolutionEntries.find((entry) => entry.source.primaryId === lastPrimaryId &&
151+
entry.source.secondaryId === this.getMaxSecondaryIdByPrimaryId(lastPrimaryId));
128152
}
129-
// All matched
153+
154+
/*
155+
Found a matched resolution entry on both primaryId and secondaryId
156+
157+
e.g. Given:
158+
Entries: [{P:1, S:0}, {P:2, S:0}, {P5:, S:6}]
159+
Transaction: [Inx:5(4+1), AggInx:6(2+1)]
160+
It should return Entry: {P:5, S:6}
161+
*/
130162
return this.resolutionEntries
131163
.find((entry) => entry.source.primaryId === resolvedPrimaryId && entry.source.secondaryId === resolvedSecondaryId);
132164
}
133165

134166
/**
135167
* @internal
136-
* Get most `recent` secondary id by a given primaryId
168+
* Get max secondary id by a given primaryId
137169
* @param primaryId Primary source id
138170
* @returns {number}
139171
*/
@@ -142,6 +174,17 @@ export class ResolutionStatement {
142174
.map((filtered) => filtered.source.secondaryId));
143175
}
144176

177+
/**
178+
* Get most `recent` available secondary id by a given primaryId
179+
* @param primaryId Primary source id
180+
* @param secondaryId Secondary source id
181+
* @returns {number}
182+
*/
183+
private getMaxSecondaryIdByPrimaryIdAndSecondaryId(primaryId: number, secondaryId: number): number {
184+
return Math.max(...this.resolutionEntries.filter((entry) => entry.source.primaryId === primaryId)
185+
.map((filtered) => secondaryId >= filtered.source.secondaryId ? filtered.source.secondaryId : 0));
186+
}
187+
145188
/**
146189
* @internal
147190
* Get most `recent` primary source id by a given id (transaction index) as PrimaryId might not be the same as block transaction index.

test/model/receipt/ResolutionStatement.spec.ts

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,42 @@ describe('ResolutionStatement', () => {
105105
],
106106
},
107107
},
108+
{
109+
statement: {
110+
height: '1500',
111+
unresolved: '85BBEA6CC462B244',
112+
resolutionEntries: [
113+
{
114+
source: {
115+
primaryId: 1,
116+
secondaryId: 1,
117+
},
118+
resolved: '0DC67FBE1CAD29E5',
119+
},
120+
{
121+
source: {
122+
primaryId: 1,
123+
secondaryId: 4,
124+
},
125+
resolved: '7CDF3B117A3C40CC',
126+
},
127+
{
128+
source: {
129+
primaryId: 1,
130+
secondaryId: 7,
131+
},
132+
resolved: '0DC67FBE1CAD29E5',
133+
},
134+
{
135+
source: {
136+
primaryId: 2,
137+
secondaryId: 4,
138+
},
139+
resolved: '7CDF3B117A3C40CC',
140+
},
141+
],
142+
},
143+
},
108144
];
109145

110146
statementDTO = {
@@ -164,4 +200,20 @@ describe('ResolutionStatement', () => {
164200
expect(entry).to.be.undefined;
165201
});
166202

203+
it('resolution change in the block (more than one AGGREGATE)', () => {
204+
const statement = CreateStatementFromDTO(statementDTO, NetworkType.MIJIN_TEST);
205+
const resolution = statement.mosaicResolutionStatements[2];
206+
expect((resolution.getResolutionEntryById(1, 1)!.resolved as MosaicId).toHex()).to.be.equal('0DC67FBE1CAD29E5');
207+
expect((resolution.getResolutionEntryById(1, 4)!.resolved as MosaicId).toHex()).to.be.equal('7CDF3B117A3C40CC');
208+
expect((resolution.getResolutionEntryById(1, 7)!.resolved as MosaicId).toHex()).to.be.equal('0DC67FBE1CAD29E5');
209+
expect((resolution.getResolutionEntryById(2, 1)!.resolved as MosaicId).toHex()).to.be.equal('0DC67FBE1CAD29E5');
210+
expect((resolution.getResolutionEntryById(2, 4)!.resolved as MosaicId).toHex()).to.be.equal('7CDF3B117A3C40CC');
211+
212+
expect((resolution.getResolutionEntryById(3, 0)!.resolved as MosaicId).toHex()).to.be.equal('7CDF3B117A3C40CC');
213+
expect((resolution.getResolutionEntryById(2, 2)!.resolved as MosaicId).toHex()).to.be.equal('0DC67FBE1CAD29E5');
214+
expect(resolution.getResolutionEntryById(1, 0)).to.be.undefined;
215+
expect((resolution.getResolutionEntryById(1, 6)!.resolved as MosaicId).toHex()).to.be.equal('7CDF3B117A3C40CC');
216+
expect((resolution.getResolutionEntryById(1, 2)!.resolved as MosaicId).toHex()).to.be.equal('0DC67FBE1CAD29E5');
217+
});
218+
167219
});

0 commit comments

Comments
 (0)