Instructions on generating a fresh Ethereum or Solidity contract for every test using JavaScript and Truffle

overview

After developing an Ethereum smart contract using the Solidity language, I utilized Ganache to deploy my contract for testing purposes. However, in order to conduct tests effectively, I need to create a new instance of my contract using JavaScript.

approach

To achieve this, I proceeded to write a test script named tests/test.js within my project directory:

const expect = require('chai').expect

const Round = artifacts.require('Round')


contract('pledgersLength1', async function(accounts) {
    it('1 pledger', async function() {
        let r = await Round.deployed()
        await r.pledge(5)
        let len = (await r.pledgersLength()).toNumber()
        expect(len).to.equal(1)
    })
})

contract('pledgersLength2', async function(accounts) {
    it('2 pledgers', async function() {
        let r = await Round.deployed()
        await r.pledge(5)
        await r.pledge(6)
        let len = (await r.pledgersLength()).toNumber()
        expect(len).to.equal(2)
    })
}

Running the test with truffle test (which is based on Mocha), revealed a discrepancy in how the contract instances are handled. Despite utilizing the truffle contract function similar to Mocha's describe, there was an unexpected behavior where the contract was not created anew each time.

I explored the possibility of using new Round() instead of Round.deployed(), but am uncertain about its implementation. The key is to ensure that each test case operates on a fresh instance of the contract.

While my preference is to resolve this issue without depending solely on truffle, any alternative solution that achieves the desired outcome is welcome.

Answer №1

It's important to understand that .new and .deployed are not interchangeable terms. You can learn more about the difference here.

By following this example, you can resolve your issue:

// File path: ./test/SimpleStorage.js
var simpleStorage = artifacts.require("./SimpleStorage.sol");

contract('SimpleStorage', function(accounts) {

  var contract_instance;

  before(async function() {
    contract_instance = await simpleStorage.new();
  });

  it("The owner should be the first account", async function(){
    var owner = await contract_instance.owner.call();
    expect(owner).to.equal(accounts[0]);
  });

});

The use of .new will instantiate a new instance of your contract in a fresh context.

On the other hand, when using .deployed, it refers to the previously deployed contract (usually done with the truffle migrate command).

For unit testing purposes, it is recommended to utilize .new to ensure a clean starting point for each test.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Detecting the click area within a window using JavaScript to automatically close an element

Hello everyone, I am currently working on implementing a JavaScript code that is commonly used to detect click areas for closing an element such as a side navigation or a floating division when the user clicks outside of the element. The functionality wo ...

Is it possible to retrieve values from my model when working with Django Templates and incorporating them in the JavaScript header?

With Django, I have managed to successfully retrieve and display data from my model in the content section of the template. However, I am facing issues retrieving data from the model in the header section of the template. Below is the code --> view.py ...

My SF2 app is experiencing issues with AngularJS integration

I am currently developing a straightforward API using Symfony2 and now I am experimenting with integrating AngularJS into my bundle to visualize the results of my API calls. How can I effectively implement AngularJS? I initiated a bundle via app/console ...

How do I pass input values when calling an AJAX function to submit a form in HTML?

Utilizing a modal to submit new data via AJAX API consumption. Although sending the data through the API is not an issue, my lack of HTML skills makes it confusing on how to pass form data values. This scenario involves displaying a modal for users to in ...

execute a function upon selecting a radio button

Below is the HTML code that includes two radio buttons. The default checked button is the "lease" option. <input id="quotation_request_payment_option_lease" class="choose_payment_option" name="quotation_request[payment_option]" type ...

Editing HTML using the retrieved jQuery html() content

I need to modify some HTML that is stored in a variable. For example: var testhtml = $('.agenda-rename').html(); console.log($('input',testhtml).attr('name')); I also tried the following: console.log($(testhtml).find(' ...

Send the Vue component as an argument to the function

Currently, I am in the process of transferring a project to Vue and utilizing Muuri as a layout manager. In my code, I have the following snippet: grid.add(itemElem, { layout: false, active: false }); The variable itemElem used to be an HTML element c ...

Tips for displaying Facebook comments with JavaScript

Can anyone help me figure out how to customize the data-href for Facebook comments using JavaScript (jQuery)? I tried incorporating the code below, but it's not displaying anything in the div col2. $("#col2").html( id+"<div class='fb-comm ...

Button ng-click with identical function parameters

I am facing an issue with two buttons that have the same ng-click but different parameters. <label class="item item-input"> <button ng-click="takePicture(true)">Save Settings</button> <button ng-click="takePicture(false)">Choos ...

When programming with PHP and JavaScript, managing events' start dates and end dates

In my current project, I am developing a script that deals with events. An event is scheduled to start on 12/02/2016 at 11:20 and end on 01/04/2016 at 8:20. When the end date is reached, I need to trigger a specific action using JavaScript. if (t.getFullY ...

Generating a random number to be input into the angular 2 form group index can be done by following these

One interesting feature of my form is the dynamic input field where users can easily add more fields by simply clicking on a button. These input fields are then linked to the template using ngFor, as shown below: *ngFor="let data of getTasks(myFormdata); ...

Picking a variety of elements and determining their heights using the height

I'm curious why this jQuery code isn't working as expected: hdr = $('.header-wrapper, #top-bar, #new-showroom-header').height(); My intention is to retrieve the heights of multiple elements and store them in a variable. I assumed that ...

What are the steps to effectively utilize data retrieved from readFragment using Apollo?

Once a user logs in, the system returns a jwt token and a user object containing the id and firstName, which are then stored in cache (refer to the image link provided below). https://i.stack.imgur.com/oSXZ5.png I aim to retrieve the user information fro ...

Dealing with an Undefined Property: Troubleshooting Guide

Encountering an error message Uncaught TypeError: Cannot read property 'top' of undefined at VM32939 own.js:819 resulting from var hands_corrected = (hands_original.top + 680) this issue arises because "hands_original" is not used in any par ...

What is the best way to include keys in my JSON data, rather than just values?

I've encountered an issue with the PrimeVue datatable I created, as it is only showing empty rows. After investigating, I believe the problem lies in my JSON data structure, where the fields do not have keys. What modifications should be made to stan ...

Leveraging JSON for fetching distinct identifiers from a database

When a user hovers over a parent span containing an empty img tag, I use JSON and jQuery to retrieve the src of the image from the database. The issue arises when the retrieved src is applied to all looped span images on the same page, instead of each imag ...

When using Vue.js testing, the toBe() method will only return an object when the expected value is a 'string' or other

I've been exploring the testing of Vue.js apps and recently focused on testing the data of my root component. Below is the code I have written: import { mount } from '@vue/test-utils' import App from '../../src/App' describe(&apo ...

What is the best way to conceal the button?

I'm working on a program that involves flipping cards and creating new ones using three components: App, CardEditor, and CardViewer. Within the CardEditor component, I am trying to implement a function that hides the button leading to CardViewer until ...

Multer failing to generate file during request process

My current setup involves a router and multer middleware, but I'm facing an issue where the file requested is not being created. As a result, req.file always remains undefined. const multer = require('multer'); let storage = multe ...

What is the best way to group a Pie Chart by a string field in a .csv file using dc.js, d3.js, and crossfilter.js in a Node environment?

I've successfully set up several Dimensions and groups, but I'm encountering an issue with a Pie Chart that needs to be grouped based on domain names like bing.com. Each domain name is parsed consistently to xxxx.xxx format and the data is clean. ...