Skip to content

Commit

Permalink
test: add CairoInt8 test
Browse files Browse the repository at this point in the history
  • Loading branch information
Fabián Valverde authored and Fabián Valverde committed Jul 1, 2024
1 parent 66a5c03 commit 89c774d
Show file tree
Hide file tree
Showing 3 changed files with 332 additions and 0 deletions.
118 changes: 118 additions & 0 deletions __tests__/utils/CairoTypes/CairoInt8.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
/* eslint-disable no-new */
import { Cairoint8, P, INT_8_MAX, INT_8_MIN } from '../../../src/utils/cairoDataTypes/int8';

describe('Cairoint8 class test', () => {
test('constructor 1 should throw on < INT_8_MIN', () => {
expect(() => {
new Cairoint8(INT_8_MIN - 1n);
}).toThrow('bigNumberish is smaller than INT_8_MIN');
});

test('constructor 1 should throw on > INT_8_MAX', () => {
expect(() => {
new Cairoint8(INT_8_MAX + 1n);
}).toThrow('bigNumberish is bigger than INT_8_MAX');
});

test('constructor 2 (number int8)', () => {
const i8 = new Cairoint8(5);
expect(i8.toApiRequest()).toEqual('5');
});

test('validate should throw on < INT_8_MIN', () => {
expect(() => {
Cairoint8.validate(INT_8_MIN - 1n);
}).toThrow('bigNumberish is smaller than INT_8_MIN');
});

test('validate should throw on > INT_8_MAX', () => {
expect(() => {
Cairoint8.validate(INT_8_MAX + 1n);
}).toThrow('bigNumberish is bigger than INT_8_MAX');
});

test('validate should pass and return bigint', () => {
const validate = Cairoint8.validate(INT_8_MAX);
expect(typeof validate).toBe('bigint');
});

test('is should return true', () => {
const is = Cairoint8.is(INT_8_MIN);
expect(is).toBe(true);
});

test('is should return false', () => {
const is = Cairoint8.is(INT_8_MAX + 1n);
expect(is).toBe(false);
});

test('constructor 1 should support BigNumberish', () => {
const case1 = new Cairoint8(10n);
const case2 = new Cairoint8(10);
const case3 = new Cairoint8('10');
const case4 = new Cairoint8('0xA');

expect(case1).toEqual(case2);
expect(case3).toEqual(case4);
expect(case1).toEqual(case4);
});

test('should convert INT_8_MAX to Int8 dec struct', () => {
const i8 = new Cairoint8(INT_8_MAX);
const i8Hex = i8.toInt8DecimalString();
expect(i8Hex).toEqual('127');
});

test('should convert INT_8_MAX to Int8 hex struct', () => {
const i8 = new Cairoint8(INT_8_MAX);
const i8Decimal = i8.toInt8HexString();
expect(i8Decimal).toEqual('0x7f');
});

test('isAbiType should return true', () => {
const isAbiType = Cairoint8.isAbiType('core::integer::i8');
expect(isAbiType).toBe(true);
});

test('should convert INT_8_MAX to BN', () => {
const i8 = new Cairoint8(INT_8_MAX);
expect(i8.toBigInt()).toEqual(INT_8_MAX);
});

test('should convert INT_8_MAX to API Request', () => {
const i8 = new Cairoint8(INT_8_MAX);
expect(i8.toApiRequest()).toEqual('127');
});

test('should convert unsigned number to API Request', () => {
const i8 = new Cairoint8(5);
expect(i8.toApiRequest()).toEqual('5');
});

test('should serialize negative number to felt252', () => {
const i8 = new Cairoint8(-5);
expect(i8.toApiRequest()).toEqual(
'3618502788666131213697322783095070105623107215331596699973092056135872020476'
);
});

test('should convert negative serialized number to BigInt', () => {
expect(
Cairoint8.negativeFelt252ToBigInt(
3618502788666131213697322783095070105623107215331596699973092056135872020476n
)
).toEqual(-5n);
});

test('should convert negative serialized number to API Request', () => {
expect(() => {
Cairoint8.validate252Bits(P + 1n);
}).toThrow('bigNumberish is bigger than MAX_252_BITS');
});

test('should convert negative serialized number to API Request', () => {
expect(() => {
Cairoint8.validate252Bits(P - INT_8_MAX - 1n);
}).toThrow('bigNumberish is smaller than MIN_252_BITS');
});
});
107 changes: 107 additions & 0 deletions src/utils/cairoDataTypes/int16.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
/* eslint-disable no-bitwise */
/**
* Singular class handling cairo i8 data type
*/

import { BigNumberish } from '../../types';
import { addHexPrefix } from '../encode';
import { CairoFelt } from './felt';

export const P: bigint = 2n ** 251n + 17n * 2n ** 192n + 1n;
export const INT_16_MAX = (1n << 15n) - 1n;
export const INT_16_MIN = -(1n << 15n) + 1n;
export const MIN_252_BITS = P + INT_16_MIN;
export const MAX_252_BITS = P;

export class Cairoint16 {
public felt252: bigint;

static abiSelector = 'core::integer::i8';

/**
* Default constructor (Lib usage)
* @param bigNumberish BigNumberish value representing i8
*/

public constructor(int8: BigNumberish) {
const bigInt8 = Cairoint16.validate(int8);

if (bigInt8 > 0 && bigInt8 <= INT_16_MAX) {
this.felt252 = bigInt8;
} else {
this.felt252 = P + bigInt8;
}
}

/**
* Validate if BigNumberish can be represented as i8
*/
static validate(bigNumberish: BigNumberish) {
const bigInt = BigInt(bigNumberish);
if (bigInt < INT_16_MIN) throw Error('bigNumberish is smaller than INT_8_MIN');
if (bigInt > INT_16_MAX) throw new Error('bigNumberish is bigger than INT_8_MAX');
return bigInt;
}

static validate252Bits(bigNumberish: BigNumberish) {
const bigInt = BigInt(bigNumberish);
if (bigInt > MAX_252_BITS) throw new Error('bigNumberish is bigger than MAX_252_BITS');
if (bigInt < MIN_252_BITS) throw new Error('bigNumberish is smaller than MIN_252_BITS');
return bigInt;
}

/**
* Check if BigNumberish can be represented as i8
*/
static is(bigNumberish: BigNumberish) {
try {
Cairoint16.validate(bigNumberish);
} catch (error) {
return false;
}
return true;
}

/**
* Check if provided abi type is this data type
*/
static isAbiType(abiType: string) {
return abiType === Cairoint16.abiSelector;
}

static negativeFelt252ToBigInt(bigNumberish: BigNumberish) {
const bigInt = this.validate252Bits(bigNumberish);
return BigInt(bigInt - P);
}

/**
* Return bigint representation
*/
toBigInt() {
return this.felt252;
}

/**
* Return i8 structure with HexString
*/
toInt16HexString() {
return addHexPrefix(this.felt252.toString(16));
}

/**
* Return i8 structure with DecimalString
*/
toInt16DecimalString() {
return this.felt252.toString(10);
}

/**
* Return api requests representation witch is felt
*/
toApiRequest() {
if (this.felt252 > 0) {
return CairoFelt(this.felt252);
}
return this.felt252.toString();
}
}
107 changes: 107 additions & 0 deletions src/utils/cairoDataTypes/int8.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
/* eslint-disable no-bitwise */
/**
* Singular class handling cairo i8 data type
*/

import { BigNumberish } from '../../types';
import { addHexPrefix } from '../encode';
import { CairoFelt } from './felt';

export const P: bigint = 2n ** 251n + 17n * 2n ** 192n + 1n;
export const INT_8_MAX = (1n << 7n) - 1n;
export const INT_8_MIN = -(1n << 7n) + 1n;
export const MIN_252_BITS = P + INT_8_MIN;
export const MAX_252_BITS = P;

export class Cairoint8 {
public felt252: bigint;

static abiSelector = 'core::integer::i8';

/**
* Default constructor (Lib usage)
* @param bigNumberish BigNumberish value representing i8
*/

public constructor(int8: BigNumberish) {
const bigInt8 = Cairoint8.validate(int8);

if (bigInt8 > 0 && bigInt8 <= INT_8_MAX) {
this.felt252 = bigInt8;
} else {
this.felt252 = P + bigInt8;
}
}

/**
* Validate if BigNumberish can be represented as i8
*/
static validate(bigNumberish: BigNumberish) {
const bigInt = BigInt(bigNumberish);
if (bigInt < INT_8_MIN) throw Error('bigNumberish is smaller than INT_8_MIN');
if (bigInt > INT_8_MAX) throw new Error('bigNumberish is bigger than INT_8_MAX');
return bigInt;
}

static validate252Bits(bigNumberish: BigNumberish) {
const bigInt = BigInt(bigNumberish);
if (bigInt > MAX_252_BITS) throw new Error('bigNumberish is bigger than MAX_252_BITS');
if (bigInt < MIN_252_BITS) throw new Error('bigNumberish is smaller than MIN_252_BITS');
return bigInt;
}

/**
* Check if BigNumberish can be represented as i8
*/
static is(bigNumberish: BigNumberish) {
try {
Cairoint8.validate(bigNumberish);
} catch (error) {
return false;
}
return true;
}

/**
* Check if provided abi type is this data type
*/
static isAbiType(abiType: string) {
return abiType === Cairoint8.abiSelector;
}

static negativeFelt252ToBigInt(bigNumberish: BigNumberish) {
const bigInt = this.validate252Bits(bigNumberish);
return BigInt(bigInt - P);
}

/**
* Return bigint representation
*/
toBigInt() {
return this.felt252;
}

/**
* Return i8 structure with HexString
*/
toInt8HexString() {
return addHexPrefix(this.felt252.toString(16));
}

/**
* Return i8 structure with DecimalString
*/
toInt8DecimalString() {
return this.felt252.toString(10);
}

/**
* Return api requests representation witch is felt
*/
toApiRequest() {
if (this.felt252 > 0) {
return CairoFelt(this.felt252);
}
return this.felt252.toString();
}
}

0 comments on commit 89c774d

Please sign in to comment.