Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Receiving Promise {<pending>} back from .then()

I have an API call in api.js:

 export const getGraphData = (domain, userId, testId) => {
   return axios({
     url: `${domain}/api/${c.embedConfig.apiVersion}/member/${userId}/utests/${testId}`,
     method: 'get',
   });
 };

I have a React helper that takes that data and transforms it.

import { getGraphData } from './api';

const dataObj = (domain, userId, testId) => {

  const steps = getGraphData(domain, userId, testId)
  .then((result) => {
    return result.attributes;
  });

  console.log(steps);

  // const steps = test.get('steps');
  const expr = /select/;

  // build array of steps that we have results in
  const resultsSteps = [];

  steps.forEach((step) => {
    // check for types that contain 'select', and add them to array
    if (expr.test(step.get('type'))) {
      resultsSteps.push(step);
    }
  });

  const newResultsSteps = [];

  resultsSteps.forEach((item, i) => {
    const newMapStep = new Map();
    const itemDescription = item.get('description');
    const itemId = item.get('id');
    const itemOptions = item.get('options');
    const itemAnswers = item.get('userAnswers');
    const newOptArray = [];
    itemOptions.forEach((element) => {
      const optionsMap = new Map();
      let elemName = element.get('value');
      if (!element.get('value')) { elemName = element.get('caption'); }
      const elemPosition = element.get('position');
      const elemCount = element.get('count');

      optionsMap.name = elemName;
      optionsMap.position = elemPosition;
      optionsMap.value = elemCount;
      newOptArray.push(optionsMap);
    });
    newMapStep.chartType = 'horizontalBar';
    newMapStep.description = itemDescription;
    newMapStep.featured = 'false';
    newMapStep.detailUrl = '';
    newMapStep.featuredStepIndex = i + 1;
    newMapStep.id = itemId;
    newMapStep.isValid = 'false';
    newMapStep.type = 'results';
    const listForNewOptArray = List(newOptArray);
    newMapStep.data = listForNewOptArray;
    newMapStep.userAnswers = itemAnswers;
    newResultsSteps.push(newMapStep);
  });

  return newResultsSteps;
};

export default dataObj;

The issue is steps, when logged outside the .then() returns a Promise {<pending>}. If I log results.attributes inside the .then(), I see the data fully returned.

like image 943
TWLATL Avatar asked Feb 13 '18 13:02

TWLATL


People also ask

How do I resolve a promise pending issue?

The promise will always log pending as long as its results are not resolved yet. You must call . then on the promise to capture the results regardless of the promise state (resolved or still pending): Promises are forward direction only; You can only resolve them once.

How do I resolve promises before returning?

You can use the async/await syntax or call the . then() method on a promise to wait for it to resolve. Inside of functions marked with the async keyword, you can use await to wait for the promises to resolve before continuing to the next line of the function.

What does promise () method do?

The . promise() method returns a dynamically generated Promise that is resolved once all actions of a certain type bound to the collection, queued or not, have ended. By default, type is "fx" , which means the returned Promise is resolved when all animations of the selected elements have completed.

Can I return a promise in a then?

The then method returns a new Promise , which allows for method chaining. If the function passed as handler to then returns a Promise , an equivalent Promise will be exposed to the subsequent then in the method chain. The below snippet simulates asynchronous code with the setTimeout function.


1 Answers

You need to wait until your async call is resolved. You can do this by chaining on another then:

getGraphData(domain, userId, testId)
  .then((result) => {
    return result.attributes;
  })
  .then(steps => {
     // put the rest of your method here
  });

You can also look at async/await if your platform supports it which would allow code closer to your original

const steps = await getGraphData(domain, userId, testId)
  .then((result) => {
    return result.attributes;
  });

// can use steps here
like image 159
Jamiec Avatar answered Oct 14 '22 08:10

Jamiec