-
Notifications
You must be signed in to change notification settings - Fork 1.4k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* feat: ABI parser * remove casts * remove unnecessary throw * centralize abi cleanup logic * remove rawUntypedPtr from swayTypeMatchers * rename method * Update cleanup-abi.ts * Update cleanup-abi.ts * refactor abi type mappers * refactor into using maps for types * refactor from array of tuples into `Map` * rename variables * refactorings, comments * split test up into multiple tests --------- Co-authored-by: Peter Smith <[email protected]>
- Loading branch information
1 parent
6962abb
commit 44f6590
Showing
38 changed files
with
2,858 additions
and
18 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
--- | ||
"@fuel-ts/abi": patch | ||
"fuels": patch | ||
"@fuel-ts/errors": patch | ||
--- | ||
|
||
feat: ABI parser |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -343,4 +343,5 @@ Workspaces | |
WSL | ||
XOR | ||
XORs | ||
matcher | ||
YAML | ||
matcher |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
// #region full | ||
import { AbiParser } from 'fuels'; | ||
import type { Abi, AbiSpecificationV1 } from 'fuels'; | ||
|
||
import { Counter } from '../../../typegend'; | ||
|
||
const parsedAbi: Abi = AbiParser.parse(Counter.abi as AbiSpecificationV1); | ||
// #endregion full | ||
console.log('Parsed ABI:', parsedAbi); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
# Working with the ABI | ||
|
||
Building a Sway program with `forc build` outputs multiple files, one of which is a JSON representation of the program's ABI. Because ABI specifications can change from one `forc` version to another, working directly with the ABI is cumbersome due to having to manage all ABI specification versions in order to ensure proper functionality. | ||
|
||
<!-- TODO: fix links once it's live --> | ||
<!-- AbiParser: https://fuels-ts-docs-api.vercel.app/classes/_fuel_ts_abi.AbiParser.html--> | ||
<!-- ABI: https://fuels-ts-docs-api.vercel.app/interfaces/_fuel_ts_abi.Abi.html --> | ||
|
||
To mitigate this, The SDK provides [`AbiParser`](#working-with-the-abi) which can parse all ABI specification versions and output an object that conforms to the [`Abi`](#working-with-the-abi) interface. The SDK also internally uses this `Abi` interface for implementing its encoding/decoding and TS type generation. | ||
|
||
<<< @./snippets/parsing-the-abi.ts#full{ts:line-numbers} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,3 @@ | ||
export * from './coder'; | ||
export * from './gen'; | ||
export * from './parser'; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
import { FuelError } from '@fuel-ts/errors'; | ||
|
||
import type { Abi } from './abi'; | ||
import type { AbiSpecificationV1 } from './specifications'; | ||
import { AbiParserV1 } from './specifications'; | ||
|
||
/** | ||
* A typed ABI object or a stringified json of a Sway program's ABI | ||
*/ | ||
export type AbiSpecification = AbiSpecificationV1; | ||
|
||
export class AbiParser { | ||
/** | ||
* ABI specifications transpilers | ||
*/ | ||
private static specifications = { | ||
'1': AbiParserV1.parse, | ||
} as const; | ||
|
||
/** | ||
* Parses an ABI in JSON format. | ||
* | ||
* @param abi - a JSON ABI of a Sway program | ||
* @returns an public interface for the Abi | ||
*/ | ||
static parse(abi: AbiSpecification): Abi { | ||
if (typeof abi.specVersion !== 'string') { | ||
throw new FuelError( | ||
FuelError.CODES.ABI_SPECIFICATION_INVALID, | ||
'Invalid ABI: the specification version is not a string.' | ||
); | ||
} | ||
|
||
const parse = AbiParser.specifications[abi.specVersion]; | ||
if (!parse) { | ||
throw new FuelError( | ||
FuelError.CODES.ABI_SPECIFICATION_INVALID, | ||
`Invalid ABI: Unsupported ABI specification version ("${abi.specVersion}").` | ||
); | ||
} | ||
|
||
return parse(abi); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,142 @@ | ||
/** | ||
* This interface serves as a representation of the ABI format outputted by `forc build` | ||
* that won't be changing with the introduction of new abi specifications in Sway. | ||
* Its purpose is to provide a stable interface for users to work with, | ||
* which won't be affected by changing ABI specification versions. | ||
*/ | ||
export interface Abi { | ||
encodingVersion: string; | ||
programType: 'contract' | 'predicate' | 'script' | 'library'; | ||
/** | ||
* Metadata types describe the structure of the types used in the `concreteTypes` field. | ||
* One metadata type can be referenced multiple times if it is used in multiple concrete types. | ||
*/ | ||
metadataTypes: AbiMetadataType[]; | ||
/** | ||
* Concrete types are types that are used in: | ||
* function inputs/outputs, configurables, logged types, or message types. | ||
* | ||
* Their structure is fully known and they do not contain any unresolved generic parameters. | ||
*/ | ||
concreteTypes: AbiConcreteType[]; | ||
functions: AbiFunction[]; | ||
loggedTypes: AbiLoggedType[]; | ||
messageTypes: AbiMessageType[]; | ||
configurables: AbiConfigurable[]; | ||
} | ||
|
||
export interface AbiConcreteType { | ||
swayType: string; | ||
concreteTypeId: string; | ||
/** | ||
* The components field is populated when the type is any non-primitive type. | ||
* That includes structs, enums, arrays, and tuples. | ||
*/ | ||
components?: AbiTypeComponent[]; | ||
/** | ||
* A concrete type can be an implementation of a metadata type, | ||
* in which case the `metadata` field is populated. | ||
* If the underlying metadata type has type parameters (is generic), | ||
* the `typeArguments` field corresponds to those type parameters. | ||
*/ | ||
metadata?: { | ||
metadataTypeId: number; | ||
/** | ||
* Type arguments used to resolve the type parameters in the metadata type. | ||
* They are ordered in the same way as the type parameters in the metadata type. | ||
*/ | ||
typeArguments?: AbiConcreteType[]; | ||
}; | ||
} | ||
|
||
export interface AbiMetadataType { | ||
swayType: string; | ||
metadataTypeId: number; | ||
/** | ||
* The components field is populated when the type is any non-primitive type. | ||
* That includes structs, enums, arrays, and tuples. | ||
*/ | ||
components?: AbiTypeComponent[]; | ||
/** | ||
* The existence of type parameters indicates that the metadata type is generic. | ||
*/ | ||
typeParameters?: AbiMetadataType[]; | ||
} | ||
|
||
export interface AbiTypeComponent { | ||
name: string; | ||
type: AbiConcreteType | AbiAppliedMetadataType; | ||
} | ||
|
||
/** | ||
* AbiAppliedMetadataType point to a metadata type but aren't the same as metadata types, | ||
* as the metadata type describes the structure of the type, | ||
* whereas the component is an actual implementation of that type. | ||
*/ | ||
export interface AbiAppliedMetadataType { | ||
swayType: string; | ||
components?: AbiTypeComponent[]; | ||
metadata: { | ||
metadataTypeId: number; | ||
typeArguments?: AbiTypeArgument[]; | ||
}; | ||
} | ||
|
||
export type AbiTypeArgument = AbiConcreteType | AbiAppliedMetadataType; | ||
|
||
export interface AbiFunctionInput { | ||
name: string; | ||
type: AbiConcreteType; | ||
} | ||
|
||
export interface AbiFunction { | ||
name: string; | ||
inputs: AbiFunctionInput[]; | ||
output: AbiConcreteType; | ||
attributes?: readonly AbiFunctionAttribute[]; | ||
} | ||
|
||
export interface AbiLoggedType { | ||
logId: string; | ||
type: AbiConcreteType; | ||
} | ||
|
||
export interface AbiMessageType { | ||
messageId: string; | ||
type: AbiConcreteType; | ||
} | ||
|
||
export interface AbiConfigurable { | ||
name: string; | ||
offset: number; | ||
type: AbiConcreteType; | ||
} | ||
|
||
export type AbiFunctionAttribute = | ||
| StorageAttr | ||
| PayableAttr | ||
| TestAttr | ||
| InlineAttr | ||
| DocCommentAttr; | ||
|
||
export interface PayableAttr { | ||
readonly name: 'payable'; | ||
} | ||
|
||
export interface StorageAttr { | ||
readonly name: 'storage'; | ||
readonly arguments: readonly ('read' | 'write')[]; | ||
} | ||
|
||
export interface TestAttr { | ||
readonly name: 'test'; | ||
} | ||
export interface InlineAttr { | ||
readonly name: 'inline'; | ||
readonly arguments: 'never' | 'always'; | ||
} | ||
|
||
export interface DocCommentAttr { | ||
readonly name: 'doc-comment'; | ||
readonly arguments: readonly string[]; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
export { AbiParser, type AbiSpecification } from './abi-parser'; | ||
export * from './abi'; | ||
export * from './specifications/v1/specification'; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
export { AbiParserV1 } from './v1/parser'; | ||
export * from './v1/specification'; |
Oops, something went wrong.