Smart Contract

FlowEVMBridgeTemplates

A.1e4aa0b87d10b141.FlowEVMBridgeTemplates

Valid From

85,982,212

Deployed

1w ago
Feb 16, 2026, 08:14:21 PM UTC

Dependents

1 imports
1import FungibleToken from 0xf233dcee88fe0abe
2import NonFungibleToken from 0x1d7e57aa55817448
3
4import EVM from 0xe467b9dd11fa00df
5
6import FlowEVMBridgeUtils from 0x1e4aa0b87d10b141
7
8/// This contract serves Cadence code from chunked templates, replacing the contract name with the name derived from
9/// given arguments - either Cadence Type or EVM contract address.
10///
11access(all)
12contract FlowEVMBridgeTemplates {
13
14    /// Canonical path for the Admin resource
15    access(all)
16    let AdminStoragePath: StoragePath
17    /// Chunked Hex-encoded Cadence contract code, to be joined on derived contract name
18    access(self)
19    let templateCodeChunks: {String: [[UInt8]]}
20
21    /// Emitted whenever there is a change to templated code
22    access(all)
23    event Updated(name: String, isNew: Bool?)
24
25    /**************
26        Getters
27     **************/
28
29    /// Serves bridged asset contract code for a given type, deriving the contract name from the EVM contract info
30    access(all)
31    fun getBridgedAssetContractCode(_ cadenceContractName: String, isERC721: Bool): [UInt8]? {
32        if isERC721 {
33            return self.getBridgedNFTContractCode(contractName: cadenceContractName)
34        } else {
35            return self.getBridgedTokenContractCode(contractName: cadenceContractName)
36        }
37    }
38
39    /**************
40        Internal
41     **************/
42
43    access(self)
44    fun getBridgedNFTContractCode(contractName: String): [UInt8]? {
45        if let chunks = self.templateCodeChunks["bridgedNFT"] {
46            return self.joinChunks(chunks, with: String.encodeHex(contractName.utf8))
47        }
48        return nil
49    }
50
51    access(self)
52    fun getBridgedTokenContractCode(contractName: String): [UInt8]? {
53        if let chunks = self.templateCodeChunks["bridgedToken"] {
54            return self.joinChunks(chunks, with: String.encodeHex(contractName.utf8))
55        }
56        return nil
57    }
58
59    access(self)
60    fun joinChunks(_ chunks: [[UInt8]], with name: String): [UInt8] {
61        let nameBytes: [UInt8] = name.decodeHex()
62        let code: [UInt8] = []
63        for i, chunk in chunks {
64            code.appendAll(chunk)
65            // No need to append the contract name after the last chunk
66            if i == chunks.length - 1 {
67                break
68            }
69            code.appendAll(nameBytes)
70        }
71        return code
72    }
73
74    /************
75        Admin
76     ************/
77
78    /// Resource enabling updates to the contract template code
79    ///
80    access(all)
81    resource Admin {
82
83        /// Adds a new template to the templateCodeChunks mapping, preventing overwrites of existing templates
84        ///
85        /// @param newTemplate: The name of the new template
86        /// @param chunks: The chunks of hex-encoded Cadence contract code
87        ///
88        /// @emits Updated with the name of the template and `isNew` set to true by way of the pre-condition
89        ///
90        access(all)
91        fun addNewContractCodeChunks(newTemplate: String, chunks: [String]) {
92            pre {
93                FlowEVMBridgeTemplates.templateCodeChunks[newTemplate] == nil: "Code already exists for template"
94            }
95            self.upsertContractCodeChunks(forTemplate: newTemplate, chunks: chunks)
96        }
97
98        /// Upserts the contract code chunks for a given template, overwriting the existing template if exists
99        ///
100        /// @param newTemplate: The name of the new template
101        /// @param chunks: The chunks of hex-encoded Cadence contract code
102        ///
103        /// @emits Updated with the name of the template and a boolean indicating if it was a newly named
104        ///     template or an existing one was overwritten
105        ///
106        access(all)
107        fun upsertContractCodeChunks(forTemplate: String, chunks: [String]) {
108            let byteChunks: [[UInt8]] = []
109            for chunk in chunks {
110                byteChunks.append(chunk.decodeHex())
111            }
112
113            let isNew = FlowEVMBridgeTemplates.templateCodeChunks[forTemplate] == nil
114            emit Updated(name: forTemplate, isNew: isNew)
115
116            FlowEVMBridgeTemplates.templateCodeChunks[forTemplate] = byteChunks
117        }
118
119        /// Removes the template from the templateCodeChunks mapping
120        ///
121        /// @param name: The name of the template to remove
122        ///
123        /// @return true if the template was removed, false if it did not exist
124        ///
125        /// @emits Updated with the name of the template and `isNew` set `nil`
126        ///
127        access(all)
128        fun removeTemplate(name: String): Bool {
129            if let removed = FlowEVMBridgeTemplates.templateCodeChunks.remove(key: name) {
130                emit Updated(name: name, isNew: nil)
131                return true
132            }
133            return false
134        }
135    }
136
137    init() {
138        self.AdminStoragePath = /storage/flowEVMBridgeTemplatesAdmin
139        self.templateCodeChunks = {}
140
141        self.account.storage.save(<-create Admin(), to: self.AdminStoragePath)
142    }
143}
144