We live in a dynamic, rapidly changing age where technology-led interventions are the way forward. While there are a lot of technologies floating around, most experts agree that blockchain is going to play a major role in transforming businesses across industries and geographies. Digital platforms and applications are set to be enhanced by the ecosystem vision rendered by blockchain technology, and any discussion of blockchain technology in an enterprise application context is incomplete unless it touches upon smart contracts. In this article, we will delve into the design principles of and design considerations for, smart contracts.
To start with, let us quickly examine the nature of smart contracts. A smart contract is basically a set of computer codes that run on top of the blockchain stack. These codes constitute of a set of terms pre-agreed upon by all the involved parties, and when the pre-defined terms are met, the agreement is automatically executed per the underlying business logic.
Smart contracts can be visualized as the next step for the progression of blockchain applications which extends their capability from recording transactions immutably to automatically implementing the contracts. Simple and effective, smart contracts are capable of enabling modernization of blockchain and blockchain-mixed applications on digital platforms with their ability to automate business processes. For this reason, the underlying design principles and implementation of smart contracts has become an essential element for the successful upgradation of blockchain-based applications.
Smart Contract Characteristics:
A smart contract relies upon information obtained from an internal source i.e. databases/ledgers of involved parties and/or external sources, where the required input is fed with the help of oracles to execute it on the digital platforms.
The key stated characteristics of a smart contract are:
Let us now understand the process of creating a smart contract
- Defining the smart contract: In this first step, we need to define the agreement in its scope and establish the terms of agreement by all stakeholders.
Then, we identify all the parties involved in the execution of the contract and determine the consensus strategy. Also, future smart code upgrading/change scenarios should be brainstormed so that the architecture should establish a scope for those situations.
- Smart contract design:
- The next step is designing the contract. We start by determining the events which have the potential to trigger the implementation of the contract
- Examine if any inputs are impacting the execution feasibility
- Identify the limitation(s) of the underlying blockchain platform
- Define the data elements
- Set conditions of execution per the business logic
- Coding the business logic
A set of codes is developed and tested to represent the intended business contract. Also, the protocol for messaging and secure authentication is established between the parties involved in the contract.
The terms of the contracts determine the flow of value. The output is stored on an immutable blockchain ledger.
- Updating the network
Once the contract gets executed, every ledger node gets updated with the newly acquired state. Any new update can only be appended.
By design, the smart contract can range from a simple contract (a simple digital value exchange) to a very complex contract (a distributed autonomous organization).
13 key design principles for smart contracts
Below are some of the key design principles one should keep in mind while creating a smart contract. The drafting of the below design principles has been done using Ethereum smart contracts as the base. However, most of the principles are valid for developing smart contracts on any blockchain engine:
- Simple and coherent smart contract code
- Ensure that the contract in question solves an individual problem. This helps keep things simple and helps avoid design and code errors
- Modularize the code to keep contracts and functions small
- Keep only the necessary data in the smart contract
- Blockchain should be used only for the parts of the system that require decentralization
- Analyze the application data and separate them into on-chain an off-chain data
- Design the state variables for the smart contract to be efficient storage for the on-chain data
- Leave the off-chain data to be managed by higher-level applications
- Confidential information should not be stored in a smart contract
- Avoid gas costly patterns (Only for Ethereum)
The creator and user of under-optimized smart contracts will always be overcharged during deployment and running because they consume more gas than is required.
- Expect and prepare for failure
The smart contract code must be able to respond to errors and vulnerabilities. This includes:
- Inserting rules/ code to pause the contract whenever there is an observed deviation
- There should be a limit on how much money the contract is handling thus confining the risks
- There should be provision for upgrade, bug fixes and improvement
- Oracl-ize the smart contract
Oracles can help the contract amend itself by taking in external feeds from reliable sources, but caution should be exercised for external contract calls; they may enable the execution of malicious codes
- Design for re-entrancy attack
- Avoid external calls when possible, as calls to untrusted contracts can introduce several unexpected risks or errors
- Finish all internal work (i.e. state changes) first, and only then call the external function
- Design for denial of service (DoS) attack
Use pull over push for external calls to avoid a denial of service attack, or a DoS attack for short. This becomes more germane where payments are involved. In such cases, it is advisable to create a pull or withdraw mechanism to obtain fund rather than pushing funds to the user. This will help circumventing the DoS attack
- Timestamps are imprecise on a blockchain and can be influenced
- Timestamp of the block can be manipulated within margin of seconds, so a loophole is created when the execution of any smart contract depends on the timestamp. Serious risks get attached to such contracts where they are programmed to transfer funds.
- Timestamps are not random and should not be used in that context.
- Avoid using it for contract expiration time
- Appropriate data types selection
Proper examination of the data type should be conducted prior to their usage in the smart contract. The most suitable ones should be selected to avoid any errors.
For example, Ethereum Virtual Machine (EVM) is a 256-bit processor. It is best suited for integer computations. Now, a string (which is another data type) is a dynamic sized variable in a smart contract, so we should replace its usage by an integer type data.
- Understand the visibility modifier for data
Any variable on the blockchain is viewable to all, irrespective of the visibility modifier
- Pay attention to the order of statements within a function
- Use secure hashing for protecting data
Hashing is a very important function in a blockchain; data in the blockchain is viewable by all, so a secure hash should be used to protect its visibility
- Use of Access Modifiers
Access modifiers should be used to define accessibility rules. It ensures that only appropriate authority is performing critical functions affecting any smart contract. The important areas where the access modifiers must be implemented are-
- Implementation of policies, rules, and regulations.
- Defining the accessibility of a function for any user
- Declaring the auditable elements of a smart contract. This will help to audit and verify the correctness of the smart contract.
Leading the way with astute smart contract design:
Smart contracts have enabled us to develop new business models and foster business relationships built on technology-based trust. Based on blockchain technology, smart contracts inherently offer immutability, security, and transparency which differentiates them from traditional contracts, giving involved parties a credible mechanism to execute their business agreements with added cryptographic security.
The above guiding principles will help anyone design better smart contracts, but it should be noted that, “A smart contract can only be as smart as the people who code it.”
The blockchain programs are new, complex, and highly experimental. Constant changes are expected in the development and security landscape, as new bugs and security risks are discovered, and new best practices are developed.
Finally, if the smart contract is to be entrusted with anything of significant value, one should always go for a comprehensive audit and even for a bug bounty. Zero defects are always easier said than done.