hermez-node/config/config.go
config/config.goRaw
1package config
2
3import (
4 "fmt"
5 "io/ioutil"
6 "math/big"
7 "time"
8
9 "github.com/BurntSushi/toml"
10 ethCommon "github.com/ethereum/go-ethereum/common"
11 "github.com/hermeznetwork/hermez-node/common"
12 "github.com/hermeznetwork/tracerr"
13 "github.com/iden3/go-iden3-crypto/babyjub"
14 "gopkg.in/go-playground/validator.v9"
15)
16
17// Duration is a wrapper type that parses time duration from text.
18type Duration struct {
19 time.Duration `validate:"required"`
20}
21
22// UnmarshalText unmarshalls time duration from text.
23func (d *Duration) UnmarshalText(data []byte) error {
24 duration, err := time.ParseDuration(string(data))
25 if err != nil {
26 return tracerr.Wrap(err)
27 }
28 d.Duration = duration
29 return nil
30}
31
32// ServerProof is the server proof configuration data.
33type ServerProof struct {
34 // URL is the server proof API URL
35 URL string `validate:"required"`
36}
37
38// ForgeBatchGasCost is the costs associated to a ForgeBatch transaction, split
39// into different parts to be used in a formula.
40type ForgeBatchGasCost struct {
41 Fixed uint64 `validate:"required"`
42 L1UserTx uint64 `validate:"required"`
43 L1CoordTx uint64 `validate:"required"`
44 L2Tx uint64 `validate:"required"`
45}
46
47// Coordinator is the coordinator specific configuration.
48type Coordinator struct {
49 // ForgerAddress is the address under which this coordinator is forging
50 ForgerAddress ethCommon.Address `validate:"required"`
51 // MinimumForgeAddressBalance is the minimum balance the forger address
52 // needs to start the coordinator in wei. Of set to 0, the coordinator
53 // will not check the balance before starting.
54 MinimumForgeAddressBalance *big.Int
55 // FeeAccount is the Hermez account that the coordinator uses to receive fees
56 FeeAccount struct {
57 // Address is the ethereum address of the account to receive fees
58 Address ethCommon.Address `validate:"required"`
59 // BJJ is the baby jub jub public key of the account to receive fees
60 BJJ babyjub.PublicKeyComp `validate:"required"`
61 } `validate:"required"`
62 // ConfirmBlocks is the number of confirmation blocks to wait for sent
63 // ethereum transactions before forgetting about them
64 ConfirmBlocks int64 `validate:"required"`
65 // L1BatchTimeoutPerc is the portion of the range before the L1Batch
66 // timeout that will trigger a schedule to forge an L1Batch
67 L1BatchTimeoutPerc float64 `validate:"required"`
68 // StartSlotBlocksDelay is the number of blocks of delay to wait before
69 // starting the pipeline when we reach a slot in which we can forge.
70 StartSlotBlocksDelay int64
71 // ScheduleBatchBlocksAheadCheck is the number of blocks ahead in which
72 // the forger address is checked to be allowed to forge (apart from
73 // checking the next block), used to decide when to stop scheduling new
74 // batches (by stopping the pipeline).
75 // For example, if we are at block 10 and ScheduleBatchBlocksAheadCheck
76 // is 5, eventhough at block 11 we canForge, the pipeline will be
77 // stopped if we can't forge at block 15.
78 // This value should be the expected number of blocks it takes between
79 // scheduling a batch and having it mined.
80 ScheduleBatchBlocksAheadCheck int64
81 // SendBatchBlocksMarginCheck is the number of margin blocks ahead in
82 // which the coordinator is also checked to be allowed to forge, apart
83 // from the next block; used to decide when to stop sending batches to
84 // the smart contract.
85 // For example, if we are at block 10 and SendBatchBlocksMarginCheck is
86 // 5, eventhough at block 11 we canForge, the batch will be discarded
87 // if we can't forge at block 15.
88 SendBatchBlocksMarginCheck int64
89 // ProofServerPollInterval is the waiting interval between polling the
90 // ProofServer while waiting for a particular status
91 ProofServerPollInterval Duration `validate:"required"`
92 // ForgeRetryInterval is the waiting interval between calls forge a
93 // batch after an error
94 ForgeRetryInterval Duration `validate:"required"`
95 // ForgeDelay is the delay after which a batch is forged if the slot is
96 // already committed. If set to 0s, the coordinator will continuously
97 // forge at the maximum rate.
98 ForgeDelay Duration `validate:"-"`
99 // ForgeNoTxsDelay is the delay after which a batch is forged even if
100 // there are no txs to forge if the slot is already committed. If set
101 // to 0s, the coordinator will continuously forge even if the batches
102 // are empty.
103 ForgeNoTxsDelay Duration `validate:"-"`
104 // SyncRetryInterval is the waiting interval between calls to the main
105 // handler of a synced block after an error
106 SyncRetryInterval Duration `validate:"required"`
107 // PurgeByExtDelInterval is the waiting interval between calls
108 // to the PurgeByExternalDelete function of the l2db which deletes
109 // pending txs externally marked by the column `external_delete`
110 PurgeByExtDelInterval Duration `validate:"required"`
111 // L2DB is the DB that holds the pool of L2Txs
112 L2DB struct {
113 // SafetyPeriod is the number of batches after which
114 // non-pending L2Txs are deleted from the pool
115 SafetyPeriod common.BatchNum `validate:"required"`
116 // MaxTxs is the maximum number of pending L2Txs that can be
117 // stored in the pool. Once this number of pending L2Txs is
118 // reached, inserts to the pool will be denied until some of
119 // the pending txs are forged.
120 MaxTxs uint32 `validate:"required"`
121 // MinFeeUSD is the minimum fee in USD that a tx must pay in
122 // order to be accepted into the pool. Txs with lower than
123 // minimum fee will be rejected at the API level.
124 MinFeeUSD float64
125 // TTL is the Time To Live for L2Txs in the pool. Once MaxTxs
126 // L2Txs is reached, L2Txs older than TTL will be deleted.
127 TTL Duration `validate:"required"`
128 // PurgeBatchDelay is the delay between batches to purge
129 // outdated transactions. Oudated L2Txs are those that have
130 // been forged or marked as invalid for longer than the
131 // SafetyPeriod and pending L2Txs that have been in the pool
132 // for longer than TTL once there are MaxTxs.
133 PurgeBatchDelay int64 `validate:"required"`
134 // InvalidateBatchDelay is the delay between batches to mark
135 // invalid transactions due to nonce lower than the account
136 // nonce.
137 InvalidateBatchDelay int64 `validate:"required"`
138 // PurgeBlockDelay is the delay between blocks to purge
139 // outdated transactions. Oudated L2Txs are those that have
140 // been forged or marked as invalid for longer than the
141 // SafetyPeriod and pending L2Txs that have been in the pool
142 // for longer than TTL once there are MaxTxs.
143 PurgeBlockDelay int64 `validate:"required"`
144 // InvalidateBlockDelay is the delay between blocks to mark
145 // invalid transactions due to nonce lower than the account
146 // nonce.
147 InvalidateBlockDelay int64 `validate:"required"`
148 } `validate:"required"`
149 TxSelector struct {
150 // Path where the TxSelector StateDB is stored
151 Path string `validate:"required"`
152 } `validate:"required"`
153 BatchBuilder struct {
154 // Path where the BatchBuilder StateDB is stored
155 Path string `validate:"required"`
156 } `validate:"required"`
157 ServerProofs []ServerProof `validate:"required"`
158 Circuit struct {
159 // MaxTx is the maximum number of txs supported by the circuit
160 MaxTx int64 `validate:"required"`
161 // NLevels is the maximum number of merkle tree levels
162 // supported by the circuit
163 NLevels int64 `validate:"required"`
164 } `validate:"required"`
165 EthClient struct {
166 // MaxGasPrice is the maximum gas price allowed for ethereum
167 // transactions
168 MaxGasPrice *big.Int `validate:"required"`
169 // GasPriceIncPerc is the percentage increase of gas price set
170 // in an ethereum transaction from the suggested gas price by
171 // the ehtereum node
172 GasPriceIncPerc int64
173 // CheckLoopInterval is the waiting interval between receipt
174 // checks of ethereum transactions in the TxManager
175 CheckLoopInterval Duration `validate:"required"`
176 // Attempts is the number of attempts to do an eth client RPC
177 // call before giving up
178 Attempts int `validate:"required"`
179 // AttemptsDelay is delay between attempts do do an eth client
180 // RPC call
181 AttemptsDelay Duration `validate:"required"`
182 // TxResendTimeout is the timeout after which a non-mined
183 // ethereum transaction will be resent (reusing the nonce) with
184 // a newly calculated gas price
185 TxResendTimeout Duration `validate:"required"`
186 // NoReuseNonce disables reusing nonces of pending transactions for
187 // new replacement transactions
188 NoReuseNonce bool
189 // Keystore is the ethereum keystore where private keys are kept
190 Keystore struct {
191 // Path to the keystore
192 Path string `validate:"required"`
193 // Password used to decrypt the keys in the keystore
194 Password string `validate:"required"`
195 } `validate:"required"`
196 // ForgeBatchGasCost contains the cost of each action in the
197 // ForgeBatch transaction.
198 ForgeBatchGasCost ForgeBatchGasCost `validate:"required"`
199 } `validate:"required"`
200 API struct {
201 // Coordinator enables the coordinator API endpoints
202 Coordinator bool
203 } `validate:"required"`
204 Debug struct {
205 // BatchPath if set, specifies the path where batchInfo is stored
206 // in JSON in every step/update of the pipeline
207 BatchPath string
208 // LightScrypt if set, uses light parameters for the ethereum
209 // keystore encryption algorithm.
210 LightScrypt bool
211 // RollupVerifierIndex is the index of the verifier to use in
212 // the Rollup smart contract. The verifier chosen by index
213 // must match with the Circuit parameters.
214 RollupVerifierIndex *int
215 }
216}
217
218// Node is the hermez node configuration.
219type Node struct {
220 PriceUpdater struct {
221 // Interval between price updater calls
222 Interval Duration `valudate:"required"`
223 // URL of the token prices provider
224 URL string `valudate:"required"`
225 // Type of the API of the token prices provider
226 Type string `valudate:"required"`
227 } `validate:"required"`
228 StateDB struct {
229 // Path where the synchronizer StateDB is stored
230 Path string `validate:"required"`
231 // Keep is the number of checkpoints to keep
232 Keep int `validate:"required"`
233 } `validate:"required"`
234 // It's possible to use diferentiated SQL connections for read/write.
235 // If the read configuration is not provided, the write one it's going to be used
236 // for both reads and writes
237 PostgreSQL struct {
238 // Port of the PostgreSQL write server
239 PortWrite int `validate:"required"`
240 // Host of the PostgreSQL write server
241 HostWrite string `validate:"required"`
242 // User of the PostgreSQL write server
243 UserWrite string `validate:"required"`
244 // Password of the PostgreSQL write server
245 PasswordWrite string `validate:"required"`
246 // Name of the PostgreSQL write server database
247 NameWrite string `validate:"required"`
248 // Port of the PostgreSQL read server
249 PortRead int
250 // Host of the PostgreSQL read server
251 HostRead string
252 // User of the PostgreSQL read server
253 UserRead string
254 // Password of the PostgreSQL read server
255 PasswordRead string
256 // Name of the PostgreSQL read server database
257 NameRead string
258 } `validate:"required"`
259 Web3 struct {
260 // URL is the URL of the web3 ethereum-node RPC server
261 URL string `validate:"required"`
262 } `validate:"required"`
263 Synchronizer struct {
264 // SyncLoopInterval is the interval between attempts to
265 // synchronize a new block from an ethereum node
266 SyncLoopInterval Duration `validate:"required"`
267 // StatsRefreshPeriod is the interval between updates of the
268 // synchronizer state Eth parameters (`Eth.LastBlock` and
269 // `Eth.LastBatch`). This value only affects the reported % of
270 // synchronization of blocks and batches, nothing else.
271 StatsRefreshPeriod Duration `validate:"required"`
272 } `validate:"required"`
273 SmartContracts struct {
274 // Rollup is the address of the Hermez.sol smart contract
275 Rollup ethCommon.Address `validate:"required"`
276 // Rollup is the address of the HermezAuctionProtocol.sol smart
277 // contract
278 Auction ethCommon.Address `validate:"required"`
279 // WDelayer is the address of the WithdrawalDelayer.sol smart
280 // contract
281 WDelayer ethCommon.Address `validate:"required"`
282 // TokenHEZ is the address of the HEZTokenFull.sol smart
283 // contract
284 TokenHEZ ethCommon.Address `validate:"required"`
285 // TokenHEZName is the name of the HEZ token deployed at
286 // TokenHEZ address
287 TokenHEZName string `validate:"required"`
288 } `validate:"required"`
289 API struct {
290 // Address where the API will listen if set
291 Address string
292 // Explorer enables the Explorer API endpoints
293 Explorer bool
294 // UpdateMetricsInterval is the interval between updates of the
295 // API metrics
296 UpdateMetricsInterval Duration
297 // UpdateRecommendedFeeInterval is the interval between updates of the
298 // recommended fees
299 UpdateRecommendedFeeInterval Duration
300 // Maximum concurrent connections allowed between API and SQL
301 MaxSQLConnections int `validate:"required"`
302 // SQLConnectionTimeout is the maximum amount of time that an API request
303 // can wait to stablish a SQL connection
304 SQLConnectionTimeout Duration
305 } `validate:"required"`
306 Debug struct {
307 // APIAddress is the address where the debugAPI will listen if
308 // set
309 APIAddress string
310 // MeddlerLogs enables meddler debug mode, where unused columns and struct
311 // fields will be logged
312 MeddlerLogs bool
313 // GinDebugMode sets Gin-Gonic (the web framework) to run in
314 // debug mode
315 GinDebugMode bool
316 }
317 Coordinator Coordinator `validate:"-"`
318}
319
320// Load loads a generic config.
321func Load(path string, cfg interface{}) error {
322 bs, err := ioutil.ReadFile(path) //nolint:gosec
323 if err != nil {
324 return tracerr.Wrap(err)
325 }
326 cfgToml := string(bs)
327 if _, err := toml.Decode(cfgToml, cfg); err != nil {
328 return tracerr.Wrap(err)
329 }
330 return nil
331}
332
333// LoadCoordinator loads the Coordinator configuration from path.
334func LoadCoordinator(path string) (*Node, error) {
335 var cfg Node
336 if err := Load(path, &cfg); err != nil {
337 return nil, tracerr.Wrap(fmt.Errorf("error loading node configuration file: %w", err))
338 }
339 validate := validator.New()
340 if err := validate.Struct(cfg); err != nil {
341 return nil, tracerr.Wrap(fmt.Errorf("error validating configuration file: %w", err))
342 }
343 if err := validate.Struct(cfg.Coordinator); err != nil {
344 return nil, tracerr.Wrap(fmt.Errorf("error validating configuration file: %w", err))
345 }
346 return &cfg, nil
347}
348
349// LoadNode loads the Node configuration from path.
350func LoadNode(path string) (*Node, error) {
351 var cfg Node
352 if err := Load(path, &cfg); err != nil {
353 return nil, tracerr.Wrap(fmt.Errorf("error loading node configuration file: %w", err))
354 }
355 validate := validator.New()
356 if err := validate.Struct(cfg); err != nil {
357 return nil, tracerr.Wrap(fmt.Errorf("error validating configuration file: %w", err))
358 }
359 return &cfg, nil
360}