Skip to main content
Contact our team to know more about our services
select webform
Become a part of our team
select webform
One file only.
1.5 GB limit.
Allowed types: gif, jpg, jpeg, png, bmp, eps, tif, pict, psd, txt, rtf, html, odf, pdf, doc, docx, ppt, pptx, xls, xlsx, xml, avi, mov, mp3, mp4, ogg, wav, bz2, dmg, gz, jar, rar, sit, svg, tar, zip.
Create your own Blockchain using Python and Ethereum
24 Oct 2018

Create your own Blockchain using Python and Ethereum

Blockchain, as the name suggests, is a collection of blocks or data records chained together in a cryptographic fashion. Each block in the chain contains a hash of the previous block, timestamp, and transaction data, securing it from intruders/attackers and modifications in the future. This immutability is one of the most interesting features of the Blockchain. Transactions, once written, are very difficult to modify (it is possible to modify the chain from a particular block, but that means splitting the chain in two, and to do that, 51% of the miners have to agree to use the new chain.)

The best thing about Blockchain that makes it secure is the way it is decentralized, meaning you cannot access it from any centralized location or modify certain blocks in a Blockchain to hack the transactions. Any attempt to modify the chain needs consensus from more than 50% of the miners for the chain. Very difficult to achieve.

In this blog, I will be talking about some basic Blockchain concepts and I will try to illustrate them with an example of creating a simple Blockchain using Ethereum and Python on a Linux/Ubuntu box.


  • Any Ubuntu VM (desktop/server) with a minimum of 2 GB RAM and 10 GB disk space
  • Python 3.5 or 3.5+
  • Ethereum basics
  • Basic understanding of Blockchain
sudo add-apt-repository ppa:jonathonf/python-3.6

sudo apt-get update

sudo apt-get install python3.6

sudo apt-get install ethereum

sudo apt-get install software-properties-common

sudo add-apt-repository -y ppa:ethereum/ethereum

sudo apt-get update

sudo apt-get install ethereum

So, let’s start with your very own Blockchain:

1. The first step in creating Blockchain is to create an initial block of the chain using the config file. This initial block will basically define the properties of your whole Blockchain.

2. Under your working directory, create a JSON file that holds the configuration for the initial block.

sudo vi firstblock.json and paste the below content in it.


    "config": {

   	"chainId": 1,

   	"homesteadBlock": 0,

   	"eip155Block": 0,

   	"eip158Block": 0,

   	"byzantiumBlock": 0


    "difficulty": "100",

    "gasLimit": "4000000",

    "alloc": {

   	"8c684d22367d208c46584dcf7f09d8bc8f56ffff": {

           "balance": "500000000000000000000000"


     "ge14d41d66af28385c7af6d825ab102eb271ffff": {

       	"balance": "10000000000000000000000"




Let's have a look at the information headings in the JSON file:

  • chainId: This is your chain’s identifier and is used in replay protection.
  • homesteadBlock, eip155Block, eip158Block, byzantiumBlock : These relate to chain forking and versioning, so in this particular case lets just keep them aside as you are starting a new Blockchain.
  • Difficulty: This dictates how difficult it is to mine a block. Setting this to a low value (~10–10000) is helpful in a private Blockchain as it lets you mine blocks quickly, which equals fast transactions and plenty of ETH to test with.
  • gasLimit: This is the total amount of gas that can be used in each block. With such a low mining difficulty, blocks will be moving pretty quickly, but you should still set this value pretty high to avoid hitting the limit and slowing down your network.
  • Alloc: Here, you can allocate ETH to specific addresses. This won’t create the account for you, so make sure it's an account you already have control of. You will need to add the account to your private chain in order to use it, and to do so; you need access to the keystore/utc file

3. Initialize your data-directory for the first node creation.

geth --datadir ./node1 init ./firstblock.json

You should see output similar to this:

INFO [09-04|10:07:13.814] Maximum peer count                       ETH=25 LES=0 total=25

INFO [09-04|10:07:13.815] Allocated cache and file handles         database=/home/vinay/my-chain/node1/geth/chaindata cache=16 handles=16

INFO [09-04|10:07:13.821] Writing custom genesis block

INFO [09-04|10:07:13.821] Persisted trie from memory database      nodes=3 size=413.00B time=83.769µs gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B

INFO [09-04|10:07:13.822] Successfully wrote genesis state         database=chaindata                                            hash=9d236a...641806

INFO [09-04|10:07:13.822] Allocated cache and file handles         database=/home/vinay/my-chain/node1/geth/lightchaindata cache=16 handles=16

INFO [09-04|10:07:13.827] Writing custom genesis block

INFO [09-04|10:07:13.827] Persisted trie from memory database      nodes=3 size=413.00B time=57.041µs gcnodes=0 gcsize=0.00B gctime=0s livenodes=1 livesize=0.00B

INFO [09-04|10:07:13.827] Successfully wrote genesis state         database=lightchaindata                                            hash=9d236a...641806

4. Now you can start your node with the below command:

geth --datadir ./node1 --networkid 111 console 2>> node1.log

This will ensure that all the logs are redirected to node1.log under your specified working directory for your node, which is node1 in our case.

After running the above command, you should see something like this in your output:

INFO [09-04|10:07:27.687] Maximum peer count                       ETH=25 LES=0 total=25

INFO [09-04|10:07:27.688] Starting peer-to-peer node               instance=Geth/v1.8.15-stable-89451f7c/linux-amd64/go1.10

INFO [09-04|10:07:27.688] Allocated cache and file handles         database=/home/vinay/my-chain/node1/geth/chaindata cache=768 handles=512

INFO [09-04|10:07:27.698] Initialised chain configuration          config="{ChainID: 1994 Homestead: 0 DAO: 
     DAOSupport: false EIP150: 
     EIP155: 0 EIP158: 0 Byzantium: 0 Constantinople: 
     Engine: unknown}" 
 INFO [09-04|10:07:27.698] Disk storage enabled for ethash caches dir=/home/vinay/my-chain/node1/geth/ethash count=3 
 INFO [09-04|10:07:27.698] Disk storage enabled for ethash DAGs dir=/root/.ethash count=2 
 INFO [09-04|10:07:27.699] Initialising Ethereum protocol versions="[63 62]" network=1114 
 INFO [09-04|10:07:27.700] Loaded most recent local header number=0 hash=9d236a...641806 td=400 
 INFO [09-04|10:07:27.700] Loaded most recent local full block number=0 hash=9d236a...641806 td=400 
 INFO [09-04|10:07:27.700] Loaded most recent local fast block number=0 hash=9d236a...641806 td=400 
 INFO [09-04|10:07:27.700] Regenerated local transaction journal transactions=0 accounts=0 
 INFO [09-04|10:07:27.700] Starting P2P networking 
 INFO [09-04|10:07:29.811] UDP listener up self=enode://75dc65374999c58d39ae9f8e8e40d3c750ff4561d67995827a907c91d0e1ed718239dd1e5817f99d3544ad32a81a002cdd925e21afb3f1c39823cb8fcdf28b7b@ 
 INFO [09-04|10:07:29.811] RLPx listener up self=enode://75dc65374999c58d39ae9f8e8e40d3c750ff4561d67995827a907c91d0e1ed718239dd1e5817f99d3544ad32a81a002cdd925e21afb3f1c39823cb8fcdf28b7b@ 
 INFO [09-04|10:07:29.815] IPC endpoint opened url=/home/vinay/my-chain/node1/geth.ipc 
 Welcome to the Geth JavaScript console! 
 instance: Geth/v1.8.15-stable-89451f7c/linux-amd64/go1.10 
 modules: admin:1.0 debug:1.0 eth:1.0 ethash:1.0 miner:1.0 net:1.0 personal:1.0 rpc:1.0 txpool:1.0 web3:1.0 

This is your javascript console where you can use different Blockchain commands to play around with your Blockchain.

5. Create your personal account:
If you have already created this as a part of the JSON file created (alloc param), then you can simply import that into your keystore folder created during data directory instantiation, which in our case is “/node1/keystore” and jump to the next step.

You can create a new account using the following command:


Remember the passphrase you give to your account because if you forget it, there is no way to recover your account.

You can view the accounts created using the following command:

> web3.eth.accounts

["0x46574bcfce83947b684097fd21395fa22c4d8cb8", "0x1ef45cc951acfff4c2101c9b3ca7131a2fd7c809"]

To set your default account, use the following command:

> miner.setEtherbase(web3.eth.accounts[0])

This will set the first account in the list to be the default account.

You can check your balance for the given account with the following command:

> eth.getBalance(eth.coinbase)

6. Run mining command, and you will see your account balance increasing:


You should also see the mining logs being dumped to the log that we instantiated as part of data directory initialization.


This will stop the mining action.

Now that your first node is ready, you can add peer nodes to the original node by following these steps:

1. Initialize a new data directory for the new node just like your first node using the same JSON that you created initially.

geth --datadir ./node2 init ./firstnode.json

2. Launch the peer node from some different port on a separate console:

geth --datadir ./node2 --networkid 111 --port 30304 console 2>> node2.log

Remember that you need to provide the same networkid that you used for the first node so that it becomes a peer node for the first node.

This will open a new javascript console, and you can run all the Ethereum commands similar to your first node.

3. Type the following on the javascript console of the first node:


You should see an output similar to this:


4. Now run the following command on your second node’s console:

> admin.addPeer("enode://483ae85d264b8ebdc6c01565694cd8e24d17cd9ad9ba9c05ab83e8a9d477ad9b397eb2afd84d65e581ef2007f1e0338268f526cbd4b93481713c1ae2080533c5@")

5. Verify that your nodes are communicating.
Type the following command on the console of the second node:

> admin.peers
The output should be something similar to this:
   caps: ["eth/63"],
    id: "483ae85d264b8ebdc6c01565694cd8e24d17cd9ad9ba9c05ab83e8a9d477ad9b397eb2afd84d65e581ef2007f1e0338268f526cbd4b93481713c1ae2080533c5",
    name: "Geth/v1.8.15-stable-89451f7c/linux-amd64/go1.10",
    network: {
      inbound: false,
      localAddress: "",
      remoteAddress: "",
      static: true,
      trusted: false
    protocols: {
      eth: {
       difficulty: 72443634457,
        head: "0x49a60106a525099d51f1a093d21676a2081c8e4b3d0322c5cc40d95563ba13bd",
        version: 63

remoteAddress: "" -> indication that the node is listening to the first node that is created over 30303.

Congratulations! Your Blockchain is ready!

Subscribe to our feed

select webform