Issues with getting the quote, last video Javascript course(1inchQuote and Swap Plugin)

Hello,

I always get the the right error message (The conversion did not succeed) if I click the get quote button. But how I get the necessary quote as we see in the Video. I think I took exactly the same code mentioned in the video but it does not work

 //Submission of the quote request


    const fromDecimals = $selectedToken.dataset.decimals;
    const fromTokenAddress = $selectedToken.dataset.address;

    const [toTokenAddress, toDecimals] = document.querySelector('[name=to-token]').value.split('-');
    
    try {
        const quote = await Moralis.Plugins.oneInch.quote({
            chain: 'polygon', // The blockchain you want to use (eth/bsc/polygon)
            fromTokenAddress, // The token you want to swap
            toTokenAddress, // The token you want to receive
            amount: Moralis.Units.Token(fromAmount, fromDecimals).toString(),
          });
     

          const toAmount = tokenValue(quote.toTokenAmount, toDecimals);
          document.querySelector('.js-quote-container').innerHTML = `
          <p>
            ${fromAmount} ${quote.fromToken.symbol} = ${toAmount} ${quote.toToken.symbol} 
          </p>
          <p>
            Gas fee: ${quote.estimadGas}
          </p>
          `;
        
    }   catch(e) {
            document.querySelector('.js-quote-container').innerHTML = `
               <p class="error">The conversion did not succeed.</p>
            `;
    }
}

You can also add console.log(e) in the catch error body, which will log the error in the console and you can check why is failing :nerd_face:

Carlos Z

@thecil This is my code here:

async function formSubmitted(event) {
    const fromAmount = Number.parseFloat($amountInput.value);
    const fromMaxValue = Number.parseFloat($selectedToken.dataset.max);
    if (Number.isNaN(fromAmount) || fromAmount > fromMaxValue) {
        // Invalid input
        document.querySelector('.js-amount-error').innerText = 'Invalid amount';
    } else {
        document.querySelector('.js-amount-error').innerText = '';
    }

    // Submission of the quote
    const fromDecimals = $selectedToken.dataset.decimals;
    const fromTokenAddress = $selectedToken.dataset.address;

    const [toTokenAddress, toDecimals] = document.querySelector('[name=to-token]').value.split('-');

    try {
        const quote = await Moralis.Plugins.oneInch.quote({
            chain: 'polygon', // The blockchain you want to use (eth/bsc/polygon)
            fromTokenAddress, // The token you want to swap
            toTokenAddress, // The token you want to receive
            amount: Moralis.Units.Token(fromAmount, fromDecimals),
        });
        console.log(quote);

        // const toAmount = tokenValue(, toDecimals)

Whenever I click ‘Get quote’, I’m given the error: Failed to load resource: the server responded with a status of 405 ().

What am I doing wrong?

Also another thing which I don’t know how to overcome is the error which comes about when I test the quote function in the console:

I’ve done everything from restarting my DApp, to refreshing the webpage, and I can’t get around this error.

Any support would be grand @thecil !

1 Like

Have you installed the 1inch plugin on the server? If you already installed it, please share again your code so i can replicate the issue :eyes:

Carlos Z

1 Like

After deleting and reinstalling the 1inch Plugin, and updating my server, it still doesn’t work for me.

Here’s my code so far:

/* Moralis init code */
// init is short for initiation btw...
const serverUrl = "";
const appId = "";
Moralis.start({ serverUrl, appId });

Moralis
    .initPlugins()
    .then(() => console.log('Plugins have been initiated'));

const $tokenBalanceTBody = document.querySelector('.js-token-balances');
const $selectedToken = document.querySelector('.js-from-token');
const $amountInput = document.querySelector('.js-from-amount');

/** Utilities */

//Convert token value to ETH style with 18 decimals
//If you do not specify decimals, 18 decimals will be automatically used
const tokenValue = Moralis.Units.FromWei("2000000000000000000");

/** Login/Logout and initialization */
/* Authentication code */
async function login() {
    let user = Moralis.User.current();
    if (!user) {
        user = await Moralis.authenticate({
            signingMessage: "Log in using Moralis",
        })
            .then(function (user) {
                console.log("logged in user:", user);
                console.log(user.get("ethAddress"));
            })
            .catch(function (error) {
                console.log(error);
            });
    }
    getStats();
}


async function initSwapForm(event) {
    event.preventDefault();
    $selectedToken.innerText = event.target.dataset.symbol;
    $selectedToken.dataset.address = event.target.dataset.address;
    $selectedToken.dataset.decimals = event.target.dataset.decimals;
    $selectedToken.dataset.max = event.target.dataset.max;
    $amountInput.removeAttribute('disabled');
    $amountInput.value = '';
    document.querySelector('.js-submit').removeAttribute('disabled');
    document.querySelector('.js-cancel').removeAttribute('disabled');
    document.querySelector('.js-quote-container').innerHTML = '';
    document.querySelector('.js-amount-error').innerText = '';
}

// Getting the balances of the token!
async function getStats() {
    const balances = await Moralis.Web3API.account.getTokenBalances({ chain: "polygon" });
    console.log(balances);
    $tokenBalanceTBody.innerHTML = balances.map((token, index) => `
        <tr>
            <td>${index + 1}.</td>
            <td>${token.symbol}</td>
            <td>${Moralis.Units.FromWei(token.balance, token.decimals)}</td>
            <td>
                <button
                    class="js-swap btn btn-success"
                    data-address="${token.token_address}"
                    data-symbol="${token.symbol}"
                    data-decimals="${token.decimals}"
                    data-max="${Moralis.Units.FromWei(token.balance, token.decimals)}"
                >
                    Swap
                </button>
            </td>
        </tr>
    `).join('');

    for (let $btn of $tokenBalanceTBody.querySelectorAll('.js-swap')) {
        $btn.addEventListener('click', initSwapForm);
    }

}

// Fiat onramper function
async function buyCrypto() {
    Moralis.Plugins.fiat.buy();
}

async function logOut() {
    await Moralis.User.logOut();
    console.log("logged out");
}

document.querySelector("#btn-login").addEventListener('click', login);
document
    .getElementById("btn-buy-crypto")
    .addEventListener('click', buyCrypto);
document.getElementById("btn-logout").addEventListener('click', logOut);

/** Quote / Swap */
async function formSubmitted(event) {
    const fromAmount = Number.parseFloat($amountInput.value);
    const fromMaxValue = Number.parseFloat($selectedToken.dataset.max);
    if (Number.isNaN(fromAmount) || fromAmount > fromMaxValue) {
        // Invalid input
        document.querySelector('.js-amount-error').innerText = 'Invalid amount';
    } else {
        document.querySelector('.js-amount-error').innerText = '';

    }

    // Submission of the quote request

    const fromDecimals = $selectedToken.dataset.decimals;
    const fromTokenAddress = $selectedToken.dataset.address;

    const [toTokenAddress, toDecimals] = document.querySelector('[name=to-token]').value.split('-');

    try {

        const quote = await Moralis.Plugins.oneInch.quote({
            chain: 'polygon', // The blockchain you want to use (eth/bsc/polygon)
            fromTokenAddress, // The token you want to swap
            toTokenAddress, // The token you want to receive
            amount: Moralis.Units.Token(fromAmount, fromDecimals),
        });
        console.log(quote);

       // const toAmount (, toDecimals)

    } catch (e) {
        document.querySelector('.js-quote-container').innerHTML = `
                <p>Unsuccessful conversion</p>
            `;
    }

}

async function formCancelled(event) {
    event.preventDefault();
    document.querySelector('.js-submit').setAttribute('disabled', '');
    document.querySelector('.js-cancel').setAttribute('disabled', '');
    $amountInput.value = '';
    $amountInput.setAttribute('disabled');
    delete $selectedToken.dataset.address;
    delete $selectedToken.dataset.decimals;
    delete $selectedToken.dataset.max;
    document.querySelector('.js-quote-container').innerHTML = '';
    document.querySelector('.js-amount-error').innerHTML = '';
}

document.querySelector('.js-submit').addEventListener('click', formSubmitted)
document.querySelector('.js-cancel').addEventListener('click', formCancelled)



// To Token dropdown preparation
async function getTop10Coins() {
    const response = await fetch('https://api.coinpaprika.com/v1/coins')
    const tokens = await response.json();

    return tokens
        .filter(token => token.rank <= 20 && token.rank >= 1)
        .map(token => token.symbol);
}

async function getTickerData(tickerList) {
    const tokens = await Moralis.Plugins.oneInch.getSupportedTokens({
        chain: 'polygon', // The blockchain you want to use (eth/bsc/polygon)
    });
    const tokenList = Object.values(tokens.tokens)

    return tokenList.filter(token => tickerList.includes(token.symbol));
}

function renderTokenDropdown(tokens) {
    const options = tokens.map(token => `
        <option value="${token.address}-${token.decimals}">
            ${token.name}
        </option>
    `).join('');
    document.querySelector('[name=to-token]').innerHTML = options;
}

getTop10Coins()
    .then(getTickerData)
    .then(renderTokenDropdown);```

@thecil I recently edited the code to include the submission of the quote request :ok_hand:

Hey @thecil !

Have you managed to have a look at my code/replicate the issue yet?

1 Like

I might need your index.html file too, im running your code with mine, and not reaching to the same issue that you have, my server is fresh new and just installed the 1inch plugin and it works as expected.

Please share your index.html.

Carlos Z

1 Like

Here’s my index.html:

<!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.0">
    <title>Moralis DEX</title>
    <script src="https://unpkg.com/moralis/dist/moralis.js"></script>

    <!--Bootstrap CSS should always be above 
    your own CSS to prevent it being overridden-->
    <!-- CSS only -->
    <link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css" rel="stylesheet"
        integrity="sha384-0evHe/X+R7YkIZDRvuzKMRqM+OrBnVFBL6DOitfPri4tjfHxaWutUpFmBp4vmVor" crossorigin="anonymous">
    <link rel="stylesheet" href="style.css">

</head>

<body>
    <div class="container">
        <div class="row">
            <div class="col-12 col-md-6 mb-2">
                <h1>MoralisSwap</h1>
            </div>
            <div class="col-12 col-md-6 d-flex align-items-center justify-content-md-center">
                <button id="btn-login" class="btn btn-success btn-sm">Moralis Login</button>
                <button id="btn-buy-crypto" class="btn btn-primary btn-sm" onclick="buyCrypto()">Buy Crypto</button>
                <button id="btn-logout" class="btn btn-danger btn-sm">Logout</button>
            </div>

        </div>
        
        <table class="table table-dark table-striped">
            <thead>
                <tr>
                    <th>#</th>
                    <th>Symbol</th>
                    <th>Amount</th>
                    <th>Action</th>
                </tr>
            </thead>
            <tbody class="js-token-balances"></tbody>
        </table>

        <form action="#" method="post" class="exchange-form">
            <div class="row">
                <div class="col-12 col-md-6">
                    <label>
                        <span class="js-from-token"></span>
                        Amount:
                        <input type="text" name="form-amount" class="js-from-amount" disabled />
                    </label>
                    <div class="js-amount-error error"></div>
                </div>
                <div class="col-12 col-md-6">
                    <label>
                        Swap to:
                        <select name="to-token"></select>
                    </label>
                </div>
            </div>
            <div class="row">
                <div class="col">
                    <button type="submit" class="js-submit btn btn-warning btn-sm" disabled>Get quote</button>
                    <button class="js-cancel btn btn-danger btn-sm" disabled>Cancel</button>
                </div>
            </div>
            </div>
            <div class="js-quote-container"></div>

        </form>
    </div>


    <!-- JavaScript Bundle with Popper -->
    <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/js/bootstrap.bundle.min.js"
        integrity="sha384-pprn3073KE6tl6bjs2QrFaJGz5/SUsLqktiwsUTF55Jfv3qYSDhgCecCxMW52nD2"
        crossorigin="anonymous"></script>
    <script src="./dex.js"></script>
</body>

</html>

That’s strange, idk why I run into this error :thinking:.

Codeline 52, error on the name, it should be from-amount.

method name should be POST (mayus).

This function, is missing event.preventDefault() at the start of its body. (thats why when you click on the get quote button, the web crash with HTTP ERROR 405, you are using the default method of the form (POST), instead of preventing it.

After this, your code should show the quote and you can continue to develop.

Carlos Z

1 Like

I want to thank you so much for taking the time to help me with this section of the course! :smile:

I was seriously wondering how to get past this bit and was felling very discouraged! You even showed me some errors that I didn’t know I had in my code!!!

Carlos, you don’t know how much this means to me! :pray:

Thank you once again for your help!

1 Like