Blockchain-based voting system

Shashikant Pareek
5 min readOct 16, 2021

What is Blockchain?

A blockchain is a collection of decentralized nodes, in which each block is linked together using a cryptography hash. Blockchain generally uses the SHA-256 hashing algorithm as their hash function. Because of this, it is not easy to hack blockchain as it is decentralized a hacker will need to take control over half or more of all the computers in the same distributed ledger. This is very unlikely to happen but it's not impossible to do so.

What is the need?

Every one of us knows the importance of voting. We know that voting plays a major role in selecting the Government. But when it comes to an existing system we always doubt its security. So we can overcome this issue using a blockchain-based voting system. Also, Blockchain supports transparency, fraud prevention, unchangeable transactions. So let's begin.

We need to install some tools and software to develop the blockchain system. 1. Visual Studio Code 2. Meta Mask 3. Ganache 4.Node.js 5. Truffle

Install Visual Studio Code press here.

Install Meta mask press here.

Install Ganache press here.

Install Node.js press here.

For installing Truffle open cmd and type this command npm install -g truffle . This will install the truffle globally.

Step1: Open Visual Studio Code and Ganache. Create a folder and type truffle unbox pet shop in cmd. This will Download the box. This also takes care of installing the necessary dependencies.

Step2:Now we are going to create a smart contract. So go to contracts and create a file with extension .sol. Solidity is a object oriented programming language for writing smart contract.Below is the code for solidity with explaination.

pragma solidity ^ 0.5.16;
contract Election{
struct Candidate
{
uint id;
string name;
uint votecount;
}
//Storing the accounts that have voted.
mapping(address = > bool) public voters;
//Store and fetch candidate
mapping(uint = > Candidate) public candidates;
//Storing the candidate count
uint public candidatesCount;
//voted event
event votedEvent(
uint indexed _candidateId);
constructor() public
{
addCandidate("BJP");
addCandidate("Congress");
addCandidate("Aam Aadmi Party");
}
function addCandidate(string memory _name) private
{candidatesCount++;
candidates[candidatesCount] = Candidate(candidatesCount, _name, 0);
}
function vote(uint _candidateId) public
{
//require that they haven't voted before
require(!voters[msg.sender]);
//requie a valid candidate
require(_candidateId > 0 && _candidateId <= candidatesCount);
//record that voter has voted
voters[msg.sender] = true;
//Update candidate vote count
candidates[_candidateId].votecount++;
//trigger voted event
emit votedEvent(_candidateId);
}
}

Step3:Goto migrations -> Create a file with the name 2_deploy_contacts.js.In this file, I am deploying my smart contract. In the below code ./Election.sol is the name of my smart contract make sure you replace it with your smart contract.

var Election = artifacts.require("./Election.sol"); 
module.exports = function(deployer)
{
deployer.deploy(Election);
};

Step4:Go to src/js/app.js. In App.js we are going use library web3.js for connecting ethereum to our local network.web3.js is a collection of libraries that allow you to interact with a local or remote ethereum node using HTTP, IPC or WebSocket.

App = {
web3Provider: null,
contracts: {},
account: '0x0',
hasVoted: false,
init: function () {
return App.initWeb3();
},
initWeb3: function () {
if (typeof web3 !== 'undefined') {
// If a web3 instance is already provided by Meta Mask.
App.web3Provider = web3.currentProvider;
web3 = new Web3(web3.currentProvider);
} else {
// Specify default instance if no web3 instance provided
App.web3Provider = new Web3.providers.HttpProvider('http://localhost:7545');
web3 = new Web3(App.web3Provider);
}
return App.initContract();
},
initContract: function () {
$.getJSON("Election.json", function (election) {
// Instantiate a new truffle contract from the artifact
App.contracts.Election = TruffleContract(election);
// Connect provider to interact with contract
App.contracts.Election.setProvider(App.web3Provider);
App.listenForEvents();
return App.render();
});
},
// Listen for events emitted from the contract
listenForEvents: function () {
App.contracts.Election.deployed().then(function (instance) {instance.votedEvent({}, {
fromBlock: 0,
toBlock: 'latest'
}).watch(function (error, event) {
console.log("event triggered", event)
// Reload when a new vote is recorded
App.empty()
App.render();
});
});
},
render: function () {
var electionInstance;
var loader = $("#loader");
var content = $("#content");
loader.show();
content.hide();
// Load account data
web3.eth.getCoinbase(function (err, account) {
if (err === null) {
App.account = account;
$("#accountAddress").html("Your Account: " + account);
}
});
// Load contract data
App.contracts.Election.deployed().then(function (instance) {
electionInstance = instance;
return electionInstance.candidatesCount();
}).then(function (candidatesCount) {
var candidatesResults = $("#candidatesResults");
candidatesResults.empty();
var candidatesSelect = $('#candidatesSelect');
candidatesSelect.empty();
for (var i = 1; i <= candidatesCount; i++) {
electionInstance.candidates(i).then(function (candidate) {
var id = candidate[0];
var name = candidate[1];
var voteCount = candidate[2];
// Render candidate Result
var candidateTemplate = "<tr><th>" + id + "</th><td>" + name + "</td><td>" + voteCount + "</td></tr>"
candidatesResults.append(candidateTemplate);
// Render candidate ballot option
var candidateOption = "<option value='" + id + "' >" + name + "</ option>"
candidatesSelect.append(candidateOption);
});
}
return electionInstance.voters(App.account);
}).then(function (hasVoted) {
// Do not allow a user to vote
if (hasVoted) {
$('form').hide();
}
loader.hide();
content.show();
}).catch(function (error) {
console.warn(error);
});
},
castVote: function () {
var candidateId = $('#candidatesSelect').val();
App.contracts.Election.deployed().then(function (instance) {
return instance.vote(candidateId, { from: App.account });
}).then(function (result) {
// Wait for votes to update
$("#content").hide();
$("#loader").show();
}).catch(function (err) {
console.error(err);
});
}
};
$(function () {
$(window).load(function () {
App.init();
});
});
});

Step5:Creating Frontend using html 5.

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Blockchain Voting</title>
<link href="css/bootstrap.min.css" rel="stylesheet">
</head>
<body>
<div class="container" style="width: 650px;">
<div class="row">
<div class="col-lg-12">
<h1 class="text-center">Election Results</h1>
<hr/>
<br/>
<div id="loader">
<p class="text-center">Loading...</p>
</div>
<div id="content" style="display: none;">
<table class="table">
<thead>
<tr>
<th scope="col">#</th>
<th scope="col">Name</th>
<th scope="col">Votes</th>
</tr>
</thead>
<tbody id="candidatesResults">
</tbody>
</table>
<hr/>
<form onSubmit="App.castVote(); return false;">
<div class="form-group">
<label for="candidatesSelect">Select Candidate</label>
<select class="form-control" id="candidatesSelect">
</select>
</div>
<button type="submit" class="btn btn-primary">Vote</button>
<hr />
</form>
<p id="accountAddress" class="text-center"></p>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<script src="js/bootstrap.min.js"></script>
<script src="js/web3.min.js"></script>
<script src="js/truffle-contract.js"></script>
<script src="js/app.js"></script>
</body>
</html>

Step6: Configure Metamask .Go to metamask and click on setting then go to networks and click on Add network . Enter Network name , in New RPC URL enter http://localhost:7545 , in chain id write 1337 or 0x539.

Step7:Deploy smart contract on local network using this command.Remember to replace Election with your smart contract Election.deployed().then(function(instance) { app = instance })

Step8:Run the command npm run dev this will redirect you to http://localhost:3000.

Step9: Import an account from Ganache by copying the private key and paste it on the localhost:3000 page under accounts and press submit to cast a vote.

Click on the key symbol and copy the private key.

Step10:If you need to do any change in contract type truffle console in cmd and press enter then type truffle — — migrate reset this will redeploy the smart contract and repeat step 7.

Suggestions: You can also enhance this project by using biometric which will add more security to the system.

References: 1. Refer to this link to get more knowledge about Truffle and Ganache. 2. Refer to this link to get more knowledge about Blockchain.

--

--