Edward Tanguay
Edward Tanguay

Reputation: 193382

How can I get a timeOut to work inside the GraphQL root object?

In my GraphQL backend, the "employees" array is fetched and returned correctly even though it has to await its data, but the "slowEmployees" which contains a timeOut returns an empty array. How can I get "slowEmployees" to wait to return its data?

const root = {
    hello: () => {
        return 'hello world';
    },
    message: () => {
        return 'the message';
    },
    books: () => {
        return ['More About Linux', 'Bash Shell Scripting'];
    },
    employees: async () => {
        const rawEmployees = (
            await axios.get(
                'https://edwardtanguay.netlify.app/share/employees.json'
            )
        ).data;
        const employees = [];
        rawEmployees.forEach((rawEmployee) => {
            const employee = {
                firstName: rawEmployee.firstName,
                lastName: rawEmployee.lastName,
            };
            employees.push(employee);
        });
        return employees;
    },
    slowEmployees: () => {
        const employees = [];
        setTimeout(async () => {
            const rawEmployees = (
                await axios.get(
                    'https://edwardtanguay.netlify.app/share/employees.json'
                )
            ).data;
            rawEmployees.forEach((rawEmployee) => {
                const employee = {
                    firstName: rawEmployee.firstName,
                    lastName: rawEmployee.lastName,
                };
                employees.push(employee);
            });
        }, 2000);
        return employees;
    },
};

Upvotes: 0

Views: 101

Answers (1)

millhouse
millhouse

Reputation: 10007

You need to make setTimeout compatible with async/await - a very common problem.

If you create a "Promisified" setTimeout:

function timeout(ms) {
    return new Promise(resolve => setTimeout(resolve, ms));
}

... you can await it similarly to your regular employees endpoint:

...
slowEmployees: async () => {
    // Fetch raw data
    const rawEmployees = (
        await axios.get(
            'https://edwardtanguay.netlify.app/share/employees.json'
        )
    ).data;

    // Simulate being slow
    await timeout(2000);

    // Transform to required data shape and return
    return rawEmployees.map((rawEmployee) => {
        return {
            firstName: rawEmployee.firstName,
            lastName: rawEmployee.lastName,
        };
    });
},

Note I also changed your .forEach() + .push combination to a .map() - you're performing the transformation on each array element, with no side-effects, so it's a better semantic fit.

Upvotes: 3

Related Questions