@btc-vision/btc-runtime 1.11.0-rc.9 → 1.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (72) hide show
  1. package/README.md +7 -7
  2. package/docs/README.md +39 -39
  3. package/docs/advanced/bitcoin-scripts.md +17 -17
  4. package/docs/advanced/{contract-upgrades.md → contract-updates.md} +90 -98
  5. package/docs/advanced/cross-contract-calls.md +4 -4
  6. package/docs/advanced/plugins.md +21 -21
  7. package/docs/advanced/quantum-resistance.md +32 -32
  8. package/docs/advanced/signature-verification.md +22 -22
  9. package/docs/api-reference/blockchain.md +14 -14
  10. package/docs/api-reference/events.md +2 -2
  11. package/docs/api-reference/op20.md +7 -7
  12. package/docs/api-reference/op721.md +7 -7
  13. package/docs/api-reference/storage.md +2 -2
  14. package/docs/contracts/op-net-base.md +15 -15
  15. package/docs/contracts/op20-token.md +3 -3
  16. package/docs/contracts/op20s-signatures.md +2 -2
  17. package/docs/contracts/op721-nft.md +3 -3
  18. package/docs/contracts/reentrancy-guard.md +5 -7
  19. package/docs/contracts/updatable.md +384 -0
  20. package/docs/core-concepts/blockchain-environment.md +10 -10
  21. package/docs/core-concepts/decorators.md +5 -5
  22. package/docs/core-concepts/events.md +6 -6
  23. package/docs/core-concepts/pointers.md +5 -5
  24. package/docs/core-concepts/security.md +5 -5
  25. package/docs/core-concepts/storage-system.md +24 -24
  26. package/docs/examples/basic-token.md +8 -8
  27. package/docs/examples/nft-with-reservations.md +9 -9
  28. package/docs/examples/oracle-integration.md +13 -13
  29. package/docs/examples/stablecoin.md +10 -10
  30. package/docs/getting-started/first-contract.md +8 -8
  31. package/docs/getting-started/installation.md +2 -2
  32. package/docs/getting-started/project-structure.md +6 -6
  33. package/docs/storage/memory-maps.md +8 -8
  34. package/docs/storage/stored-arrays.md +6 -6
  35. package/docs/storage/stored-maps.md +8 -8
  36. package/docs/storage/stored-primitives.md +6 -6
  37. package/docs/types/address.md +13 -13
  38. package/docs/types/bytes-writer-reader.md +18 -18
  39. package/docs/types/calldata.md +12 -12
  40. package/package.json +10 -10
  41. package/runtime/constants/Exports.ts +0 -30
  42. package/runtime/contracts/OP20.ts +7 -7
  43. package/runtime/contracts/OP721.ts +60 -74
  44. package/runtime/contracts/OP_NET.ts +2 -2
  45. package/runtime/contracts/ReentrancyGuard.ts +1 -5
  46. package/runtime/contracts/Updatable.ts +241 -0
  47. package/runtime/contracts/interfaces/OP721InitParameters.ts +8 -8
  48. package/runtime/env/BlockchainEnvironment.ts +5 -5
  49. package/runtime/env/global.ts +7 -6
  50. package/runtime/events/predefined/{ApprovedEvent.ts → OP20ApprovedEvent.ts} +1 -1
  51. package/runtime/events/predefined/{BurnedEvent.ts → OP20BurnedEvent.ts} +1 -1
  52. package/runtime/events/predefined/{MintedEvent.ts → OP20MintedEvent.ts} +1 -1
  53. package/runtime/events/predefined/{TransferredEvent.ts → OP20TransferredEvent.ts} +1 -1
  54. package/runtime/events/predefined/OP721ApprovedEvent.ts +17 -0
  55. package/runtime/events/predefined/{ApprovedForAll.ts → OP721ApprovedForAllEvent.ts} +1 -1
  56. package/runtime/events/predefined/OP721BurnedEvent.ts +16 -0
  57. package/runtime/events/predefined/OP721MintedEvent.ts +16 -0
  58. package/runtime/events/predefined/OP721TransferredEvent.ts +18 -0
  59. package/runtime/events/predefined/index.ts +5 -5
  60. package/runtime/events/{upgradeable/UpgradeableEvents.ts → updatable/UpdatableEvents.ts} +9 -9
  61. package/runtime/hashing/keccak256.ts +1 -1
  62. package/runtime/index.ts +3 -5
  63. package/runtime/plugins/UpdatablePlugin.ts +276 -0
  64. package/runtime/script/Networks.ts +1 -1
  65. package/runtime/storage/StoredBoolean.ts +23 -12
  66. package/runtime/types/Address.ts +1 -1
  67. package/runtime/types/ExtendedAddress.ts +1 -1
  68. package/docs/contracts/upgradeable.md +0 -396
  69. package/runtime/contracts/Upgradeable.ts +0 -242
  70. package/runtime/contracts/interfaces/IOP1155.ts +0 -33
  71. package/runtime/contracts/interfaces/OP1155InitParameters.ts +0 -11
  72. package/runtime/plugins/UpgradeablePlugin.ts +0 -279
@@ -615,11 +615,11 @@ protected override encodeData(writer: BytesWriter): void {
615
615
  }
616
616
  ```
617
617
 
618
- ## Solidity vs OPNet Comparison
618
+ ## Solidity vs OP_NET Comparison
619
619
 
620
620
  ### Encoding/Decoding Comparison Table
621
621
 
622
- | Feature | Solidity | OPNet |
622
+ | Feature | Solidity | OP_NET |
623
623
  |---------|----------|-------|
624
624
  | **Encode function** | `abi.encode(...)` | `BytesWriter` methods |
625
625
  | **Decode function** | `abi.decode(data, (types))` | `BytesReader` methods |
@@ -632,7 +632,7 @@ protected override encodeData(writer: BytesWriter): void {
632
632
 
633
633
  ### Type Encoding Comparison
634
634
 
635
- | Solidity Encoding | OPNet Encoding |
635
+ | Solidity Encoding | OP_NET Encoding |
636
636
  |-------------------|----------------|
637
637
  | `abi.encode(uint256)` | `writer.writeU256(value)` |
638
638
  | `abi.encode(uint128)` | `writer.writeU128(value)` |
@@ -659,12 +659,12 @@ bytes memory packed = abi.encodePacked(recipient, amount);
659
659
  ```
660
660
 
661
661
  ```typescript
662
- // OPNet
662
+ // OP_NET
663
663
  const writer = new BytesWriter(64); // 32 + 32 bytes
664
664
  writer.writeAddress(recipient);
665
665
  writer.writeU256(amount);
666
666
  const data: Uint8Array = writer.getBuffer();
667
- // OPNet encoding is similar to encodePacked (no padding)
667
+ // OP_NET encoding is similar to encodePacked (no padding)
668
668
  ```
669
669
 
670
670
  #### Basic Decoding
@@ -675,7 +675,7 @@ const data: Uint8Array = writer.getBuffer();
675
675
  ```
676
676
 
677
677
  ```typescript
678
- // OPNet
678
+ // OP_NET
679
679
  const reader = new BytesReader(data);
680
680
  const to: Address = reader.readAddress();
681
681
  const amount: u256 = reader.readU256();
@@ -696,7 +696,7 @@ function encodeTransferData(
696
696
  ```
697
697
 
698
698
  ```typescript
699
- // OPNet
699
+ // OP_NET
700
700
  function encodeTransferData(
701
701
  from: Address,
702
702
  to: Address,
@@ -724,7 +724,7 @@ bytes memory callData = abi.encodeWithSignature("transfer(address,uint256)", to,
724
724
  ```
725
725
 
726
726
  ```typescript
727
- // OPNet
727
+ // OP_NET
728
728
  const TRANSFER_SELECTOR: Selector = Selector.from("transfer(address,uint256)");
729
729
  const writer = new BytesWriter(68); // 4 + 32 + 32
730
730
  writer.writeSelector(TRANSFER_SELECTOR);
@@ -745,7 +745,7 @@ function getInfo() public view returns (address, uint256, bool) {
745
745
  ```
746
746
 
747
747
  ```typescript
748
- // OPNet - Manual return encoding
748
+ // OP_NET - Manual return encoding
749
749
  public getInfo(_calldata: Calldata): BytesWriter {
750
750
  const writer = new BytesWriter(65); // 32 + 32 + 1
751
751
  writer.writeAddress(this._owner.value);
@@ -766,7 +766,7 @@ if (success) {
766
766
  ```
767
767
 
768
768
  ```typescript
769
- // OPNet
769
+ // OP_NET
770
770
  const result = Blockchain.call(target, callData, true);
771
771
  if (result.success) {
772
772
  const reader = new BytesReader(result.data);
@@ -793,7 +793,7 @@ function encodeOrder(Order memory order) public pure returns (bytes memory) {
793
793
  ```
794
794
 
795
795
  ```typescript
796
- // OPNet
796
+ // OP_NET
797
797
  class Order {
798
798
  maker: Address;
799
799
  taker: Address;
@@ -826,7 +826,7 @@ function _transfer(address from, address to, uint256 amount) internal {
826
826
  ```
827
827
 
828
828
  ```typescript
829
- // OPNet - Custom event class with manual encoding
829
+ // OP_NET - Custom event class with manual encoding
830
830
  export class TransferEvent extends NetEvent {
831
831
  constructor(
832
832
  public readonly from: Address,
@@ -861,7 +861,7 @@ function extractAddress(bytes calldata data, uint offset) public pure returns (a
861
861
  ```
862
862
 
863
863
  ```typescript
864
- // OPNet
864
+ // OP_NET
865
865
  function extractSelector(data: Uint8Array): Selector {
866
866
  const reader = new BytesReader(data);
867
867
  return reader.readSelector();
@@ -879,7 +879,7 @@ function extractAddress(data: Uint8Array, offset: u32): Address {
879
879
 
880
880
  ### Size Comparison (Encoding Overhead)
881
881
 
882
- | Data | Solidity abi.encode | Solidity encodePacked | OPNet |
882
+ | Data | Solidity abi.encode | Solidity encodePacked | OP_NET |
883
883
  |------|---------------------|----------------------|-------|
884
884
  | `bool` | 32 bytes | 1 byte | 1 byte |
885
885
  | `uint8` | 32 bytes | 1 byte | 1 byte |
@@ -893,7 +893,7 @@ function extractAddress(data: Uint8Array, offset: u32): Address {
893
893
 
894
894
  ### Key Differences Summary
895
895
 
896
- | Aspect | Solidity | OPNet |
896
+ | Aspect | Solidity | OP_NET |
897
897
  |--------|----------|-------|
898
898
  | **Encoding approach** | `abi.encode()` function | BytesWriter object methods |
899
899
  | **Decoding approach** | `abi.decode()` with type tuple | BytesReader sequential reads |
@@ -914,7 +914,7 @@ bytes memory encoded = abi.encode(addr, amount, flag);
914
914
  ```
915
915
 
916
916
  ```typescript
917
- // OPNet equivalent
917
+ // OP_NET equivalent
918
918
  const writer = new BytesWriter(65); // 32 + 32 + 1
919
919
  writer.writeAddress(addr);
920
920
  writer.writeU256(amount);
@@ -930,7 +930,7 @@ const encoded = writer.getBuffer();
930
930
  ```
931
931
 
932
932
  ```typescript
933
- // OPNet equivalent
933
+ // OP_NET equivalent
934
934
  const reader = new BytesReader(data);
935
935
  const addr = reader.readAddress();
936
936
  const amount = reader.readU256();
@@ -949,7 +949,7 @@ bytes memory data = abi.encodeWithSelector(
949
949
  ```
950
950
 
951
951
  ```typescript
952
- // OPNet equivalent
952
+ // OP_NET equivalent
953
953
  const TRANSFER_SELECTOR: Selector = Selector.from("transfer(address,uint256)");
954
954
  const writer = new BytesWriter(68);
955
955
  writer.writeSelector(TRANSFER_SELECTOR);
@@ -235,11 +235,11 @@ Arrays use a u16 length prefix (max 65535 elements):
235
235
  |----------------------|-----------|-----------|-----|
236
236
  ```
237
237
 
238
- ## Solidity vs OPNet Comparison
238
+ ## Solidity vs OP_NET Comparison
239
239
 
240
240
  ### Calldata Decoding Comparison Table
241
241
 
242
- | Feature | Solidity | OPNet |
242
+ | Feature | Solidity | OP_NET |
243
243
  |---------|----------|-------|
244
244
  | **Parameter access** | Automatic (named parameters) | Manual sequential reading |
245
245
  | **Decode function** | `abi.decode(data, (T1, T2))` | `calldata.readT1(); calldata.readT2();` |
@@ -251,7 +251,7 @@ Arrays use a u16 length prefix (max 65535 elements):
251
251
 
252
252
  ### Type-by-Type Decoding Comparison
253
253
 
254
- | Solidity Decoding | OPNet Decoding |
254
+ | Solidity Decoding | OP_NET Decoding |
255
255
  |-------------------|----------------|
256
256
  | `abi.decode(data, (uint256))` | `calldata.readU256()` |
257
257
  | `abi.decode(data, (uint128))` | `calldata.readU128()` |
@@ -282,7 +282,7 @@ function transfer(address to, uint256 amount) public returns (bool) {
282
282
  ```
283
283
 
284
284
  ```typescript
285
- // OPNet - Parameters read sequentially
285
+ // OP_NET - Parameters read sequentially
286
286
  public transfer(calldata: Calldata): BytesWriter {
287
287
  // Must read in exact order they were encoded
288
288
  const to: Address = calldata.readAddress();
@@ -312,7 +312,7 @@ function transferFrom(
312
312
  ```
313
313
 
314
314
  ```typescript
315
- // OPNet
315
+ // OP_NET
316
316
  public transferFrom(calldata: Calldata): BytesWriter {
317
317
  const from: Address = calldata.readAddress();
318
318
  const to: Address = calldata.readAddress();
@@ -344,7 +344,7 @@ function decodeWithOffset(bytes calldata data) public pure {
344
344
  ```
345
345
 
346
346
  ```typescript
347
- // OPNet - Sequential reading handles offset automatically
347
+ // OP_NET - Sequential reading handles offset automatically
348
348
  public decodeTransfer(calldata: Calldata): BytesWriter {
349
349
  const to: Address = calldata.readAddress(); // Reads bytes 0-31
350
350
  const amount: u256 = calldata.readU256(); // Reads bytes 32-63
@@ -372,7 +372,7 @@ function processData(bytes calldata data) public {
372
372
  ```
373
373
 
374
374
  ```typescript
375
- // OPNet
375
+ // OP_NET
376
376
  public setName(calldata: Calldata): BytesWriter {
377
377
  const name: string = calldata.readString(); // Length-prefixed
378
378
  if (name.length == 0) {
@@ -408,7 +408,7 @@ function batchTransfer(
408
408
  ```
409
409
 
410
410
  ```typescript
411
- // OPNet
411
+ // OP_NET
412
412
  public batchTransfer(calldata: Calldata): BytesWriter {
413
413
  const recipients: Address[] = calldata.readAddressArray();
414
414
  const amounts: u256[] = calldata.readU256Array();
@@ -443,7 +443,7 @@ function safeTransferFrom(
443
443
  ```
444
444
 
445
445
  ```typescript
446
- // OPNet - Check for remaining data
446
+ // OP_NET - Check for remaining data
447
447
  public safeTransferFrom(calldata: Calldata): BytesWriter {
448
448
  const from: Address = calldata.readAddress();
449
449
  const to: Address = calldata.readAddress();
@@ -466,7 +466,7 @@ public safeTransferFrom(calldata: Calldata): BytesWriter {
466
466
 
467
467
  ### Encoding Format Differences
468
468
 
469
- | Aspect | Solidity ABI | OPNet |
469
+ | Aspect | Solidity ABI | OP_NET |
470
470
  |--------|--------------|-------|
471
471
  | **Byte order** | Big-endian | Big-endian (default) |
472
472
  | **Address padding** | Left-padded to 32 bytes | 32 bytes (native size) |
@@ -478,7 +478,7 @@ public safeTransferFrom(calldata: Calldata): BytesWriter {
478
478
 
479
479
  ### Encoding Size Comparison
480
480
 
481
- | Type | Solidity ABI Size | OPNet Size |
481
+ | Type | Solidity ABI Size | OP_NET Size |
482
482
  |------|-------------------|------------|
483
483
  | `bool` | 32 bytes | 1 byte |
484
484
  | `uint8` | 32 bytes | 1 byte |
@@ -492,7 +492,7 @@ public safeTransferFrom(calldata: Calldata): BytesWriter {
492
492
 
493
493
  ### Key Differences Summary
494
494
 
495
- | Solidity | OPNet |
495
+ | Solidity | OP_NET |
496
496
  |----------|-------|
497
497
  | Named parameters in function signature | Single `Calldata` parameter |
498
498
  | Automatic ABI decoding | Manual `read*()` methods |
package/package.json CHANGED
@@ -1,10 +1,10 @@
1
1
  {
2
2
  "name": "@btc-vision/btc-runtime",
3
- "version": "1.11.0-rc.9",
4
- "description": "Bitcoin L1 Smart Contract Runtime for OPNet. Build decentralized applications on Bitcoin using AssemblyScript and WebAssembly. Fully audited.",
3
+ "version": "1.11.0",
4
+ "description": "Bitcoin L1 Smart Contract Runtime for OP_NET. Build decentralized applications on Bitcoin using AssemblyScript and WebAssembly. Fully audited.",
5
5
  "main": "btc/index.ts",
6
6
  "types": "btc/index.ts",
7
- "author": "OPNet <support@opnet.org>",
7
+ "author": "OP_NET <support@opnet.org>",
8
8
  "license": "Apache-2.0",
9
9
  "homepage": "https://opnet.org",
10
10
  "repository": {
@@ -59,16 +59,16 @@
59
59
  "node": ">=24.0.0"
60
60
  },
61
61
  "dependencies": {
62
- "@assemblyscript/loader": "^0.28.9",
63
- "@btc-vision/as-bignum": "^0.1.2",
64
- "@btc-vision/assemblyscript": "^0.29.2",
65
- "@btc-vision/opnet-transform": "^1.2.0",
62
+ "@btc-vision/as-bignum": "^1.0.0",
63
+ "@btc-vision/as-loader": "^0.0.0",
64
+ "@btc-vision/assemblyscript": "^0.29.3",
65
+ "@btc-vision/opnet-transform": "^1.2.2",
66
66
  "@eslint/js": "^10.0.1",
67
- "eslint": "^10.0.0",
67
+ "eslint": "^10.0.3",
68
68
  "gulplog": "^2.2.0",
69
69
  "ts-node": "^10.9.2",
70
70
  "typescript": "^5.9.3",
71
- "typescript-eslint": "^8.56.0"
71
+ "typescript-eslint": "^8.57.1"
72
72
  },
73
73
  "devDependencies": {
74
74
  "@btc-vision/as-covers-assembly": "^0.4.4",
@@ -76,6 +76,6 @@
76
76
  "@btc-vision/as-pect-assembly": "^8.2.0",
77
77
  "@btc-vision/as-pect-cli": "^8.2.0",
78
78
  "@btc-vision/as-pect-transform": "^8.2.0",
79
- "@types/node": "^25.2.3"
79
+ "@types/node": "^25.5.0"
80
80
  }
81
81
  }
@@ -16,39 +16,9 @@ export const ALLOWANCE_DECREASE_TYPE_HASH: u8[] = [
16
16
  // onOP721Received(address,address,uint256,bytes)
17
17
  export const ON_OP721_RECEIVED_SELECTOR: u32 = 0x5349f6de;
18
18
 
19
- // onOP1155Received(address,address,uint256,uint256,bytes)
20
- export const ON_OP1155_RECEIVED_MAGIC: u32 = 0xcedc9fdf;
21
-
22
- // onOP1155BatchReceived(address,address,uint256[],uint256[],bytes)
23
- export const ON_OP1155_BATCH_RECEIVED_MAGIC: u32 = 0x5d95545f;
24
-
25
- // Interface IDs
26
- // balanceOf(address,uint256) -> 0x7ab6c0bc
27
- // balanceOfBatch(address[],uint256[]) -> 0xed4db4b0
28
- // safeTransferFrom(address,address,uint256,uint256,bytes) -> 0x0875aead
29
- // safeBatchTransferFrom(address,address,uint256[],uint256[],bytes) -> 0x1917c486
30
- // setApprovalForAll(address,bool) -> 0xd97fb4c0
31
- // isApprovedForAll(address,address) -> 0x67da1fb2
32
- export const INTERFACE_ID_OP1155: u32 = 0x383cb555;
33
-
34
- // sha256("uri(uint256)")
35
- export const INTERFACE_ID_OP1155_METADATA_URI: u32 = 0x31473f54;
36
-
37
19
  // sha256("supportsInterface(bytes4)")
38
20
  export const INTERFACE_ID_ERC165: u32 = 0x0e2b7fe2;
39
21
 
40
- // OP1155Transfer(address from,address to,uint256 id,uint256 amount,uint256 nonce,uint64 deadline)
41
- export const OP1155_TRANSFER_TYPE_HASH: u8[] = [
42
- 0x5a, 0x64, 0x2c, 0xa2, 0xd8, 0xfd, 0xe9, 0xe1, 0x28, 0x87, 0x7c, 0xf5, 0x5d, 0x71, 0x96, 0xe3,
43
- 0x3a, 0xd4, 0x4b, 0xb3, 0x4b, 0x0a, 0x8d, 0x85, 0x8d, 0xa8, 0x04, 0xbd, 0x3b, 0x86, 0x21, 0x0e,
44
- ];
45
-
46
- // OP1155BatchTransfer(address from,address to,uint256[] ids,uint256[] amounts,uint256 nonce,uint64 deadline)
47
- export const OP1155_BATCH_TRANSFER_TYPE_HASH: u8[] = [
48
- 0x7b, 0xf8, 0xb6, 0x39, 0x5f, 0xea, 0xcc, 0x15, 0x97, 0x12, 0x38, 0x00, 0x91, 0xb9, 0x2b, 0x96,
49
- 0x67, 0x6b, 0x2b, 0x73, 0x46, 0xff, 0x29, 0x27, 0xbf, 0x1a, 0x54, 0xf8, 0xfc, 0xef, 0x9c, 0x0b,
50
- ];
51
-
52
22
  // sha256("OP712Domain(string name,string version,bytes32 chainId,bytes32 protocolId,address verifyingContract)")
53
23
  export const OP712_DOMAIN_TYPE_HASH: u8[] = [
54
24
  0xfe, 0xe8, 0x22, 0x92, 0x35, 0x1d, 0x1a, 0x8b, 0xab, 0x21, 0xc4, 0xef, 0xdd, 0x15, 0x7e, 0x31,
@@ -21,7 +21,7 @@ import {
21
21
  } from '../constants/Exports';
22
22
  import { Blockchain } from '../env';
23
23
  import { sha256, sha256String } from '../env/global';
24
- import { ApprovedEvent, BurnedEvent, MintedEvent, TransferredEvent } from '../events/predefined';
24
+ import { OP20ApprovedEvent, OP20BurnedEvent, OP20MintedEvent, OP20TransferredEvent } from '../events/predefined';
25
25
  import { Selector } from '../math/abi';
26
26
  import { EMPTY_POINTER } from '../math/bytes';
27
27
  import { AddressMemoryMap } from '../memory/AddressMemoryMap';
@@ -56,7 +56,7 @@ const allowanceMapPointer: u16 = Blockchain.nextPointer;
56
56
  const nonceMapPointer: u16 = Blockchain.nextPointer;
57
57
 
58
58
  /**
59
- * OP20 Token Standard Implementation for OPNet.
59
+ * OP20 Token Standard Implementation for OP_NET.
60
60
  *
61
61
  * This abstract class implements the OP20 token standard, providing a complete
62
62
  * fungible token implementation with advanced features including:
@@ -67,7 +67,7 @@ const nonceMapPointer: u16 = Blockchain.nextPointer;
67
67
  * - Unlimited approval optimization (u256.Max)
68
68
  *
69
69
  * @remarks
70
- * OP20 is OPNet's equivalent of ERC20, adapted for Bitcoin's UTXO model with
70
+ * OP20 is OP_NET's equivalent of ERC20, adapted for Bitcoin's UTXO model with
71
71
  * additional security features. All storage uses persistent pointers for
72
72
  * cross-transaction state management. The contract includes built-in protection
73
73
  * against common attack vectors including reentrancy and integer overflow.
@@ -949,15 +949,15 @@ export abstract class OP20 extends ReentrancyGuard implements IOP20 {
949
949
 
950
950
  /** Event creation helpers */
951
951
  protected createBurnedEvent(from: Address, amount: u256): void {
952
- this.emitEvent(new BurnedEvent(from, amount));
952
+ this.emitEvent(new OP20BurnedEvent(from, amount));
953
953
  }
954
954
 
955
955
  protected createApprovedEvent(owner: Address, spender: Address, amount: u256): void {
956
- this.emitEvent(new ApprovedEvent(owner, spender, amount));
956
+ this.emitEvent(new OP20ApprovedEvent(owner, spender, amount));
957
957
  }
958
958
 
959
959
  protected createMintedEvent(to: Address, amount: u256): void {
960
- this.emitEvent(new MintedEvent(to, amount));
960
+ this.emitEvent(new OP20MintedEvent(to, amount));
961
961
  }
962
962
 
963
963
  protected createTransferredEvent(
@@ -966,6 +966,6 @@ export abstract class OP20 extends ReentrancyGuard implements IOP20 {
966
966
  to: Address,
967
967
  amount: u256,
968
968
  ): void {
969
- this.emitEvent(new TransferredEvent(operator, from, to, amount));
969
+ this.emitEvent(new OP20TransferredEvent(operator, from, to, amount));
970
970
  }
971
971
  }
@@ -28,13 +28,7 @@ import { IOP721 } from './interfaces/IOP721';
28
28
  import { OP721InitParameters } from './interfaces/OP721InitParameters';
29
29
  import { ReentrancyGuard } from './ReentrancyGuard';
30
30
  import { StoredMapU256 } from '../storage/maps/StoredMapU256';
31
- import {
32
- ApprovedEvent,
33
- ApprovedForAllEvent,
34
- MAX_URI_LENGTH,
35
- TransferredEvent,
36
- URIEvent,
37
- } from '../events/predefined';
31
+ import { MAX_URI_LENGTH, OP721ApprovedForAllEvent, URIEvent } from '../events/predefined';
38
32
  import {
39
33
  ON_OP721_RECEIVED_SELECTOR,
40
34
  OP712_DOMAIN_TYPE_HASH,
@@ -43,6 +37,10 @@ import {
43
37
  OP721_APPROVAL_TYPE_HASH,
44
38
  } from '../constants/Exports';
45
39
  import { ExtendedAddress } from '../types/ExtendedAddress';
40
+ import { OP721TransferredEvent } from '../events/predefined/OP721TransferredEvent';
41
+ import { OP721ApprovedEvent } from '../events/predefined/OP721ApprovedEvent';
42
+ import { OP721MintedEvent } from '../events/predefined/OP721MintedEvent';
43
+ import { OP721BurnedEvent } from '../events/predefined/OP721BurnedEvent';
46
44
 
47
45
  const stringPointer: u16 = Blockchain.nextPointer;
48
46
  const totalSupplyPointer: u16 = Blockchain.nextPointer;
@@ -63,10 +61,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
63
61
  protected readonly _name: StoredString;
64
62
  protected readonly _symbol: StoredString;
65
63
  protected readonly _baseURI: StoredString;
66
- protected readonly _collectionBanner: StoredString;
67
- protected readonly _collectionIcon: StoredString;
68
- protected readonly _collectionDescription: StoredString;
69
- protected readonly _collectionWebsite: StoredString;
64
+ protected readonly _banner: StoredString;
65
+ protected readonly _icon: StoredString;
66
+ protected readonly _description: StoredString;
67
+ protected readonly _website: StoredString;
70
68
 
71
69
  protected readonly _totalSupply: StoredU256;
72
70
  protected readonly _maxSupply: StoredU256;
@@ -97,10 +95,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
97
95
  this._name = new StoredString(stringPointer, 0);
98
96
  this._symbol = new StoredString(stringPointer, 2);
99
97
  this._baseURI = new StoredString(stringPointer, 3);
100
- this._collectionBanner = new StoredString(stringPointer, 4);
101
- this._collectionIcon = new StoredString(stringPointer, 5);
102
- this._collectionDescription = new StoredString(stringPointer, 6);
103
- this._collectionWebsite = new StoredString(stringPointer, 7);
98
+ this._banner = new StoredString(stringPointer, 4);
99
+ this._icon = new StoredString(stringPointer, 5);
100
+ this._description = new StoredString(stringPointer, 6);
101
+ this._website = new StoredString(stringPointer, 7);
104
102
 
105
103
  this._totalSupply = new StoredU256(totalSupplyPointer, EMPTY_POINTER);
106
104
  this._maxSupply = new StoredU256(maxSupplyPointer, EMPTY_POINTER);
@@ -128,6 +126,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
128
126
  return this._symbol.value;
129
127
  }
130
128
 
129
+ public get icon(): string {
130
+ return this._icon.value;
131
+ }
132
+
131
133
  public get baseURI(): string {
132
134
  return this._baseURI.value;
133
135
  }
@@ -140,20 +142,16 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
140
142
  return this._maxSupply.value;
141
143
  }
142
144
 
143
- public get collectionBanner(): string {
144
- return this._collectionBanner.value;
145
+ public get banner(): string {
146
+ return this._banner.value;
145
147
  }
146
148
 
147
- public get collectionIcon(): string {
148
- return this._collectionIcon.value;
149
+ public get description(): string {
150
+ return this._description.value;
149
151
  }
150
152
 
151
- public get collectionDescription(): string {
152
- return this._collectionDescription.value;
153
- }
154
-
155
- public get collectionWebsite(): string {
156
- return this._collectionWebsite.value;
153
+ public get website(): string {
154
+ return this._website.value;
157
155
  }
158
156
 
159
157
  public instantiate(
@@ -175,10 +173,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
175
173
  this._initialized.value = u256.One;
176
174
  this._tokenURICounter.value = u256.Zero;
177
175
 
178
- this._collectionBanner.value = params.collectionBanner;
179
- this._collectionIcon.value = params.collectionIcon;
180
- this._collectionDescription.value = params.collectionDescription;
181
- this._collectionWebsite.value = params.collectionWebsite;
176
+ this._banner.value = params.banner;
177
+ this._icon.value = params.icon;
178
+ this._description.value = params.description;
179
+ this._website.value = params.website;
182
180
  }
183
181
 
184
182
  @method('name')
@@ -207,28 +205,6 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
207
205
  return w;
208
206
  }
209
207
 
210
- @method('collectionInfo')
211
- @returns(
212
- { name: 'icon', type: ABIDataTypes.STRING },
213
- { name: 'banner', type: ABIDataTypes.STRING },
214
- { name: 'description', type: ABIDataTypes.STRING },
215
- { name: 'website', type: ABIDataTypes.STRING },
216
- )
217
- public collectionInfo(_: Calldata): BytesWriter {
218
- const length =
219
- String.UTF8.byteLength(this.collectionIcon) +
220
- String.UTF8.byteLength(this.collectionDescription) +
221
- String.UTF8.byteLength(this.collectionWebsite) +
222
- String.UTF8.byteLength(this.collectionBanner);
223
-
224
- const w = new BytesWriter(U32_BYTE_LENGTH * 4 + length);
225
- w.writeStringWithLength(this.collectionIcon);
226
- w.writeStringWithLength(this.collectionBanner);
227
- w.writeStringWithLength(this.collectionDescription);
228
- w.writeStringWithLength(this.collectionWebsite);
229
- return w;
230
- }
231
-
232
208
  @method({ name: 'tokenId', type: ABIDataTypes.UINT256 })
233
209
  @returns({ name: 'uri', type: ABIDataTypes.STRING })
234
210
  public tokenURI(calldata: Calldata): BytesWriter {
@@ -272,10 +248,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
272
248
  if (description.length == 0) throw new Revert('Description cannot be empty');
273
249
  if (website.length == 0) throw new Revert('Website cannot be empty');
274
250
 
275
- this._collectionIcon.value = icon;
276
- this._collectionBanner.value = banner;
277
- this._collectionDescription.value = description;
278
- this._collectionWebsite.value = website;
251
+ this._icon.value = icon;
252
+ this._banner.value = banner;
253
+ this._description.value = description;
254
+ this._website.value = website;
279
255
 
280
256
  return new BytesWriter(0);
281
257
  }
@@ -489,7 +465,7 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
489
465
  }
490
466
 
491
467
  @method({ name: 'tokenId', type: ABIDataTypes.UINT256 })
492
- @emit('Transferred')
468
+ @emit('Burned')
493
469
  public burn(calldata: Calldata): BytesWriter {
494
470
  const tokenId = calldata.readU256();
495
471
  this._burn(tokenId);
@@ -526,7 +502,7 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
526
502
 
527
503
  @method({ name: 'owner', type: ABIDataTypes.ADDRESS })
528
504
  @returns({ name: 'nonce', type: ABIDataTypes.UINT256 })
529
- public getApproveNonce(calldata: Calldata): BytesWriter {
505
+ public nonceOf(calldata: Calldata): BytesWriter {
530
506
  const owner = calldata.readAddress();
531
507
  const nonce = this._approveNonceMap.get(owner);
532
508
  const w = new BytesWriter(U256_BYTE_LENGTH);
@@ -565,10 +541,10 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
565
541
  public metadata(_: Calldata): BytesWriter {
566
542
  const name = this.name;
567
543
  const symbol = this.symbol;
568
- const icon = this.collectionIcon;
569
- const banner = this.collectionBanner;
570
- const description = this.collectionDescription;
571
- const website = this.collectionWebsite;
544
+ const icon = this.icon;
545
+ const banner = this.banner;
546
+ const description = this.description;
547
+ const website = this.website;
572
548
  const domainSeparator = this._buildDomainSeparator();
573
549
 
574
550
  const nameLength = String.UTF8.byteLength(name);
@@ -628,7 +604,7 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
628
604
  // Update total supply
629
605
  this._totalSupply.value = SafeMath.add(this._totalSupply.value, u256.One);
630
606
 
631
- this.createTransferEvent(Address.zero(), to, tokenId);
607
+ this.createMintedEvent(to, tokenId);
632
608
  }
633
609
 
634
610
  protected _burn(tokenId: u256): void {
@@ -667,12 +643,17 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
667
643
  // Update total supply
668
644
  this._totalSupply.value = SafeMath.sub(this._totalSupply.value, u256.One);
669
645
 
670
- this.createTransferEvent(owner, Address.zero(), tokenId);
646
+ this.createBurnedEvent(owner, tokenId);
671
647
  }
672
648
 
673
649
  protected _transfer(from: Address, to: Address, tokenId: u256): void {
674
- // Skip self-transfers
675
- if (from === to) return;
650
+ if (from === Address.zero()) {
651
+ throw new Revert('Invalid sender');
652
+ }
653
+
654
+ if (to === Address.zero()) {
655
+ throw new Revert('Invalid receiver');
656
+ }
676
657
 
677
658
  const owner = this._ownerOf(tokenId);
678
659
 
@@ -680,10 +661,6 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
680
661
  throw new Revert('Transfer from incorrect owner');
681
662
  }
682
663
 
683
- if (to === Address.zero()) {
684
- throw new Revert('Transfer to zero address');
685
- }
686
-
687
664
  // Check authorization
688
665
  const sender = Blockchain.tx.sender;
689
666
  if (sender !== from && !this._isApprovedForAll(from, sender)) {
@@ -712,7 +689,7 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
712
689
  // Transfer ownership
713
690
  this.ownerOfMap.set(tokenId, this._u256FromAddress(to));
714
691
 
715
- this.createTransferEvent(from, to, tokenId);
692
+ this.createTransferredEvent(from, to, tokenId);
716
693
  }
717
694
 
718
695
  protected _safeTransfer(from: Address, to: Address, tokenId: u256, data: Uint8Array): void {
@@ -1019,19 +996,28 @@ export abstract class OP721 extends ReentrancyGuard implements IOP721 {
1019
996
  }
1020
997
 
1021
998
  // Event creation helpers
1022
- protected createTransferEvent(from: Address, to: Address, tokenId: u256): void {
1023
- this.emitEvent(new TransferredEvent(Blockchain.tx.sender, from, to, tokenId));
999
+ protected createTransferredEvent(from: Address, to: Address, tokenId: u256): void {
1000
+ this.emitEvent(new OP721TransferredEvent(Blockchain.tx.sender, from, to, tokenId));
1024
1001
  }
1025
1002
 
1026
1003
  protected createApprovedEvent(owner: Address, approved: Address, tokenId: u256): void {
1027
- this.emitEvent(new ApprovedEvent(owner, approved, tokenId));
1004
+ this.emitEvent(new OP721ApprovedEvent(owner, approved, tokenId));
1005
+ }
1006
+
1007
+ protected createMintedEvent(to: Address, tokenId: u256): void {
1008
+ this.emitEvent(new OP721MintedEvent(to, tokenId));
1028
1009
  }
1029
1010
 
1011
+ protected createBurnedEvent(from: Address, tokenId: u256): void {
1012
+ this.emitEvent(new OP721BurnedEvent(from, tokenId));
1013
+ }
1014
+
1015
+
1030
1016
  protected createApprovedForAllEvent(
1031
1017
  owner: Address,
1032
1018
  operator: Address,
1033
1019
  approved: boolean,
1034
1020
  ): void {
1035
- this.emitEvent(new ApprovedForAllEvent(owner, operator, approved));
1021
+ this.emitEvent(new OP721ApprovedForAllEvent(owner, operator, approved));
1036
1022
  }
1037
1023
  }
@@ -33,7 +33,7 @@ export class OP_NET implements IBTC {
33
33
 
34
34
  /**
35
35
  * Called when the contract's bytecode is updated via updateContractFromExisting.
36
- * Override this method to perform migration logic when the contract is upgraded.
36
+ * Override this method to perform migration logic when the contract is updated.
37
37
  *
38
38
  * @param calldata - The calldata passed to updateContractFromExisting
39
39
  *
@@ -100,7 +100,7 @@ export class OP_NET implements IBTC {
100
100
  * ```typescript
101
101
  * public constructor() {
102
102
  * super();
103
- * this.registerPlugin(new UpgradeablePlugin(144));
103
+ * this.registerPlugin(new UpdatablePlugin(144));
104
104
  * }
105
105
  * ```
106
106
  *