1

I'm new to AWS including Lambda (and stack over flow for that matter so go easy on me please). I want to be able to get data requests from https://rapidapi.com/api-sports/api/api-football and post the results to my S3 or Dynamo DB instances.

I've attempted creating an AWS Lambda URL function which only succeeds in returning null results. I have tried looking for a straight forward explanation of how to achieve this but im a bit stumped.

So i created a test Lambda URL function by copying the API code supplied by Rapid API (node JS fetch). I pasted it under this line of code export const handler = async(event) => {

So i ended up with this code

export const handler = async(event) => {

const options = {
  method: 'GET',
  headers: {
    'X-RapidAPI-Host': 'api-football-v1.p.rapidapi.com',
    'X-RapidAPI-Key': 'MY API KEY',
    Authorization: 'Basic Og=='
  }
};

fetch('https://api-football-v1.p.rapidapi.com/v3/players?team=42&season=2022&search=saka', options)
  .then(response => response.json())
  .then(response => console.log(response))
  .catch(err => console.error(err))};

I also added the JSON schema provided by rapid API

I run the test in AWS and it says its succeeded but i get the below message and it returns null.

Test Event Name JSON

Response null

Function Logs START RequestId: bfb5ddd4-56f8-466a-b3c1-7ed89f3edc2b Version:
$LATEST 2022-11-24T16:07:33.622Z
203cdbbc-a661-4256-91bb-2ada34d53042
ERROR TypeError: fetch failed at Object.fetch (node:internal/deps/undici/undici:11118:11) at process.processTicksAndRejections (node:internal/process/task_queues:95:5) { cause: ConnectTimeoutError: Connect Timeout Error at onConnectTimeout (node:internal/deps/undici/undici:6625:28) at node:internal/deps/undici/undici:6583:50 at Immediate._onImmediate (node:internal/deps/undici/undici:6614:13) at process.processImmediate (node:internal/timers:471:21) { code: 'UND_ERR_CONNECT_TIMEOUT' } } END RequestId: bfb5ddd4-56f8-466a-b3c1-7ed89f3edc2b REPORT RequestId: bfb5ddd4-56f8-466a-b3c1-7ed89f3edc2b Duration: 194.65 ms Billed Duration: 195 ms Memory Size: 128 MB Max Memory Used: 73 MB

Request ID bfb5ddd4-56f8-466a-b3c1-7ed89f3edc2b

Would anyone know what im doing wrong or be able to point me in the right direction?

John Rotenstein
  • 241,921
  • 22
  • 380
  • 470
Bully82
  • 11
  • 3
  • Your posted code is incomplete, but it doesn't include any return statement. – jarmod Nov 24 '22 at 20:23
  • Related to the timeout issue, did you configure the Lambda function in VPC? If you did, then don't (unless you know what you're doing). – jarmod Nov 24 '22 at 20:30
  • right ok re the return statement what would that look like? is it provided by rapid api along with the get statement? – Bully82 Nov 25 '22 at 07:45
  • re the VPC - no i didnt go near that - as i clearly dont know what im doing properly :) – Bully82 Nov 25 '22 at 07:46
  • You seem to be using undici. Have you tried this with other HTTP clients such as Axios and node-fetch? – jarmod Nov 25 '22 at 15:53
  • i shall try each of those code snippets and see what happens. – Bully82 Nov 25 '22 at 18:06

1 Answers1

0

Firstly it's unclear what AWS Node.js runtime you are using (likely v18 at the time of writing), or is it some other version? Let's assume v18 for now.

Node supports CommonJS, and does not support the ESM / ES6 'export' syntax without an experimental flag, so for simplicity to get to the meat of the problem, you should use module.exports for now (though do learn about the ecosystems around both styles as you have time!).

Thus the code to paste into AWS Lambda becomes more like:

const handler = async(event) => {
 // more code here
}

module.exports = {
  handler,
}

But that's not what you probably wanted, as when I test it in AWS Lambda, it returns for me a bit like for you, with no additional output:

Response
null

Why? Well there's a clue is in the stack trace in your UND_ERR_CONNECT_TIMEOUT which I know happens to be findable in the Node.JS docs source as being socket is destroyed due to connect timeout. but unlike elm, it's not really helpful either. Perhaps it's helpful to identify it's in the Promise syntax, and so consider avoiding promises and callbacks, until you need them (e.g. advanced concurrency like Promise.allSettled or legacy callback-only APIs).

So ... a more useful version would return await the results:

const handler = async(event) => {
  const options = {
    method: 'GET',
    headers: {
      'X-RapidAPI-Host': 'api-football-v1.p.rapidapi.com',
      'X-RapidAPI-Key': 'MY API KEY',
      Authorization: 'Basic Og=='
    }
  };
  
  try {
    const fetched = await fetch('https://api-football-v1.p.rapidapi.com/v3/players?team=42&season=2022&search=saka', options);
    return await fetched.json();
  } catch (err) {
    console.error(err);
  }
}

module.exports = {
  handler,
}

Which for me yields something that tells me of course 'MY API KEY' would need to be changed, though should be pretty close to what you're looking for.

Response
{
  "message": "You are not subscribed to this API."
}
pzrq
  • 1,626
  • 1
  • 18
  • 24