Exploring Code Reuse in Solidity

Consensys
ConsenSys Media
Published in
5 min readJun 8, 2016

My first impression of Solidity, the most popular programming language that runs on Ethereum’s virtual machine, was that the language was quite approachable. As someone who has been working with languages like Ruby, JavaScript, Perl, and Java for 16 years, I was able read it immediately and started writing some basic smart contracts within a few days.

I’ve been around long enough to witness several programming language ecosystems mature. Code reuse tends to be at the center of this maturity, as the community builds increasingly powerful code libraries and frameworks on top of previous work. Perl has CPAN, Ruby has RubyGems, and Javascript has npm. It’s clear that code reuse in the Solidity ecosystem is still in its infancy.

Recognizing this void, my first month at ConsenSys I focused on filling it. I’m assuming that Solidity will follow in the footsteps of its modern predecessors and benefit significantly from the distribution of foundational libraries and frameworks. I started with an exploration into where Solidity reuse is already underway.

There’s a precursor to a Solidity Standard Library that already ships with the language (source). These contracts allow developers to inherit from owned and mortal without having to reinvent these common smart contract patterns.

There is a smattering of reusable libraries and contracts on Github, which developers can copy into their projects and deploy alongside their custom contracts. dapp-bin, Density, solidity-stringutils, and Standard Contracts are examples.

On the topic of Github, it’s possible to import code directly from Github in ethereum.github.io/browser-solidity like this: import “github.com/ethereum/dapp-bin/library/iterable_mapping.sol”;

And if you want to pull in code from Github when compiling via solc on the command line, that’s explained here.

The people behind Dapple have created the dapphub-registry of contracts, which can be imported into Dapple projects. This is an ambitious project and includes storing source code via IPFS. The home page (under construction) is at dapphub.io.

After speaking with friends and colleagues at ConsenSys and in the Ethereum community, I was convinced that facilitating code reuse in Solidity was a worthy project. I fully anticipate that other reuse-related projects will be on the rise this year, and I look forward to lots of collaboration.

Being new to Ethereum, my instincts led me to focus on the smallest possible unit of reuse: the humble Solidity library. In Solidity, a library is a collection of functions that do not maintain any inherent state. Libraries are meant to be imported into a contract’s bytecode, rather than provided to a contract via a constructor or a method call.

Let’s look at an example of a contract using a library:

library Math {
function add(uint a, uint b) constant returns(uint) {
return a + b;
}
}
contract Example {
uint public c;
function grow(uint d) {
c = Math.add(d, 2*c);
}
}
This syntax is straightforward. Math 's functions are called directly rather than through an instance of Math . If we were in Java, this would be a static method. In Ruby, a class method.
Deploying this is a little less straightforward. First, you must compile and deploy Math, storing its address. Then we must compile Example and link Math's address into Example's bytecode. Thankfully solc does this for us via the --libraries and --links flags (docs).As I learned the basics of how libraries work, it struck me that reusing Solidity libraries (and possibly contracts) could be quite different than reusing code in other languages. Once a Solidity library is deployed to the blockchain, it can be used by anyone, assuming you know its address and ABI. It occurred to me that a good first step toward spreading reuse in Solidity could be to provide a registry that mapped library names to the data needed to compile and link to those libraries, specifically their addresses and ABIs.Thus, the Live Libs project was born. Live Libs is a command line and JavaScript interface to a smart contract which stores a registry of libraries. Live Libs provides all the data you need in order to reuse a registered library, including the generated source code to compile against. Let's take that example again, but this time, instead of writing Math ourselves, we'll use Live Libs to get a registered version of Math.import "Math";contract Example {
uint public c;
function grow(uint d) {
c = Math.add(d, 2*c);
}
}
Looks simple, right? Well, it's not.
That import "Math" has a big question mark behind it. Another current area of active development in Solidity is how to hook into the import process in order to resolve these statements dynamically.Let's assume that someone has written a JavaScript wrapper around solc to intercept that import "Math" and delegate the definition to Live Libs. Behind the scenes, you would call var libInfo = liveLibs.get("Math") , which would provide you with two key items: libInfo.address and libInfo.abstractSource() . You would provide the address, along with "Math" to the compiler via --libraries --link , in order to tell Example where Math lives on the blockchain. But first, you would provide the generated abstract source code to the compiler so that Example would compile. Live Libs generates this code from the ABI that was stored when Math was registered. To be clear, that generated source is an abstract library:library Math {
function add(uint a, uint b) constant returns(uint);
}
The above example demonstrates the core of what Live Libs is trying to accomplish technically.The project is premised on the assumption that the Ethereum developer community is open to this style of reuse. Live Libs aims to keep common code from being unnecessarily duplicated on the blockchain. Most developers are accustomed to downloading modules to their local environments and then uploading those modules to private servers, effectively copying common modules (like Math ) thousands of times over. Developers who use the public Ethereum blockchain are all deploying to the same "world computer" running on the same virtual machine. These deployments have direct costs (spending Ether on gas), so there's incentive to keep deployments lean. Ethereum’s unique characteristics thus present us with some unique opportunities.If you have thoughts or reactions to this post, please start conversations via issues!The Live Libs project is exploring:
  • Building out a website to expose library information, blockchain events, documentation, and support testing. (project)
  • Whether the Ethereum community would fund library development via Vitalik’s article ransom (see 2:30) technique. The first version of this is documented here.
  • Storing libraries that are written in Serpent in Live Libs.
  • How this approach is affected by a sharded blockchain.

--

--

Consensys
ConsenSys Media

A complete suite of products to create and participate in web3.