API Endpoint URL - javascript

Basically, the weather API; Apixu changed everything to weatherstack recently, including their endpoints and I need help updating my twitter weather bot.
I did go through the documentation, changed to axios but I keep getting the "Cannot Read Property error"
My Old API Setup
const Twit = require('twit');
const config = require('./config');
const rp = require('request-promise-native');
async function setup(location) {
const options = {
url: "http://api.apixu.com/v1/current.json",
qs: {
key: API_KEY,
q: location
},
json: true
};
let result = await rp(options);
let condition = result.current.condition.text;
let tweetText = `The condition in ${location} is currently ${condition}!`;
console.log("TWEETING : ", tweetText);
sendTweet(tweetText)
}
According to their documentation, this is how it's supposed to be but I keep getting undefined errors.
const params = {
access_key: 'YOUR_ACCESS_KEY',
query: 'New York'
}
axios.get('https://api.weatherstack.com/current', {params})
.then(response => {
const apiResponse = response.data;
console.log(`Current temperature in ${apiResponse.location.name} is ${apiResponse.current.temperature}℃`);
}).catch(error => {
console.log(error);
});
The new Base URL: The new API requests start out with :
http://api.weatherstack.com/
documentation : https://weatherstack.com/quickstart
UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'c
ondition' of undefined
UnhandledPromiseRejectionWarning: Unhandled promise rejection. This
error originated either by throwing inside of an async function without a catch
block, or by rejecting a promise which was not handled with .catch(). (rejection
id: 1)

I would check the response.data.error object, if something goes wrong this will be populated. Funnily enough the http status code is still 200 for some error conditions.
axios.get('https://api.weatherstack.com/current', {params})
.then(response => {
if (!response.data.error) {
const apiResponse = response.data;
console.log(`Current temperature in ${apiResponse.location.name} is ${apiResponse.current.temperature}℃`);
} else {
console.log(`Response error: code: ${response.data.error.code}, info: ${response.data.error.info}`)
}
}).catch(error => {
console.error("An error occurred: ", error);
}
);
Using the free tier, I'm getting the following error with this request:
Response error: code: 105, info: Access Restricted - Your current Subscription Plan does not support HTTPS Encryption.
This is easily worked around by changing to http only (This will be less secure!):
axios.get('http://api.weatherstack.com/current', {params})
.then(response => {
if (!response.data.error) {
const apiResponse = response.data;
console.log(`Current temperature in ${apiResponse.location.name} is ${apiResponse.current.temperature}℃`);
} else {
console.log(`Response error: code: ${response.data.error.code}, info: ${response.data.error.info}`)
}
}).catch(error => {
console.error("An error occurred: ", error);
}
);

If you are using free version you need to use 'http' to work, i guess if you want to use 'https' it is premiun that you need to buy
Here is the simple example that i have used
http://api.weatherstack.com/current?access_key=0a82bdc4c6628b5f968dd500d30a8857&query=19.0760,-72.8777

Related

How to resolve parsing error: Unexpected reserved word 'await'

Hi I am trying to deploy my react native function to Firebase. The pre-conigured firebase function (helloWorld)seems to deploy correctly so I am definitely connected to Firebase. I am trying to deploy my own function which is the chatGPT API and followed the syntax of the initial pre-configured function. The function is a node environment which receives data and sends the data to the chatGPT API which is the completetion function below in the code. It seems that 'await' is already a reserved keyword so I have tried putting 'async' in multiple places but can't seem to deploy this to firebase
const functions = require("firebase-functions"); // Firebase initial function
const OpenAIApi = require("openai") // ChatGPT dependency
const Configuration = require("openai")// ChatGPT dependency
const configuration = new Configuration({
apiKey: process.env.OPENAI_API_KEY,
});
const openai = new OpenAIApi(configuration);
// // Create and deploy your first functions
// // https://firebase.google.com/docs/functions/get-started
//
exports.helloWorld = functions.https.onRequest((request, response) => {
functions.logger.info("Hello logs!", {structuredData: true});
response.send("Hello from Firebase!");
});
exports.firebasePromptReceiver = functions.https.onRequest((request, response) => {
if (!configuration.apiKey) {
res.status(500).json({
error: {
message:
'OpenAI API key not configured, please follow instructions in README.md',
},
});
return;
}
const prompt = request.body.prompt || '';
if (prompt.trim().length === 0) {
res.status(400).json({
error: {
message: 'Please enter a valid prompt',
},
});
return;
}
try {
const completion = await openai.createCompletion({ //ChatGPT API
model: 'text-davinci-003',
prompt: generatePrompt(prompt),
temperature: 0.9,
max_tokens: 2048,
});
response.status(200).json({result: completion.data.choices[0].text});
console.log(completion);
} catch (error) {
// Consider adjusting the error handling logic for your use case
if (error.response) {
console.error(error.response.status, error.response.data);
res.status(error.response.status).json(error.response.data);
} else {
console.error(`Error with OpenAI API request: ${error.message}`);
res.status(500).json({
error: {
message: 'An error occurred during your request.',
},
});
}
}
});
Please any help is greatly appreciated
functions.https.onRequest(async(request, response) => {..}
await operator sould be used in async function

React: TypeError Cannot read properties of undefined (reading '0')

I am working on a React App, and i'm trying to get some data using an axios GET request from my node backend.
the Api Endpoint i'm currently using that regard this problem is the following:
// NodeJS Backend
app.get('/v1/companys/user/:user_uuid', verify, (req, res) => { // GET - Company by User UUID
const selectQuery = 'SELECT * FROM companys WHERE uuid = (SELECT company_uuid FROM users WHERE uuid = ?)';
connection.query(selectQuery, [req.params.user_uuid], (err, results) => {
if(err) {
res.send(err)
} else if (results.length === 0) {
res.json({status: 404, message: 'Company not found'})
} else {
res.json({data: results})
}
});
});
This is my Front End:
// ReactJS FrontEnd
const companyLogo = userCompany ? userCompany.logo_url : null;
console.log(userCompany);
useEffect(() => {
const getUserCompany = async () => {
try {
await axios.get(process.env.REACT_APP_API_URL + 'companys/user/' + userUuid).then((response) => {
console.log("response "+ response);
let res = response.data.data[0];
console.log(res);
setUserCompany(res);
});
} catch (error) {
console.log(error);
}
};
getUserCompany();
}, [userUuid]);
There app works fine, but on the console the following error appear:
The object below the error is in fact the thing that i need (companyLogo)
I was wondering if someone know what am I doing wrong on my frontend to fix the TypeError.
Thanks for the help!
If you use optional chaining (?.) to catch possible null/undefined values, you'll most likely fix the issue.
So like this: let res = response.data.data?.[0];

Firestore Cloud Function returns undefined to client when I perform axios post operation

Good day, I am trying to process payment using Firestore Cloud Function and a payment Gateway called Yoco. My payment code works and returns an object of failure or success. When I do logger.log I can view the object but the problem is when I try returning the result to the Client. I keep getting undefined. My methods are async.
CLIENT SIDE
I want to response from server and update my UI
const handlePay = () => {
if (amount > 100) {
yoco.showPopup({
amountInCents: amount, // 2 decimal places begining from left
currency: "ZAR",
name: "Student Angel",
description: "Helping students deal with student debt",
callback: function (result) {
// This function returns a token that your server can use to capture a payment
if (result.error) {
const errorMessage = result.error.message;
alert("error occured: " + errorMessage);
} else {
paymentMethod({ token: result.id, amount: amount });
}
// In a real integration - you would now pass this chargeToken back to your
// server along with the order/basket that the customer has purchased.
},
});
} else {
toast.error(
"Due to high transaction charges, We can only process R100 and above. Thank you"
);
}
};
const paymentMethod = ({ token, amount }) => {
const handlePayments = httpsCallable(functions, "handlePayments");
handlePayments({ token, amount })
.then((result) => {
console.log(result);
})
.catch((result) => {
console.log(result);
});
};
THIS IS CLOUD FUNCTION
exports.handlePayments = functions.https.onCall(async (data, context) => {
// Using a testing key Not Production Key
const SECRET_KEY = "sk_test_5ca384cdyerp8kY188a435e95fbe";
// check auth state
if (!context.auth) {
throw new functions.https.HttpsError(
"unauthenticated",
"You are not authenticated"
);
}
const token = data.token;
const amount = data.amount;
await axios // I have tried this return await axios.post but nothing
.post(
"https://online.yoco.com/v1/charges/",
{
token: token,
amountInCents: amount,
currency: "ZAR",
},
{
headers: {
"X-Auth-Secret-Key": SECRET_KEY,
},
}
)
.then((res) => {
// res.status will contain the HTTP status code
// res.data will contain the response body
functions.logger.log(res);
return res;
})
.catch((error) => {
return error;
});
});
I removed the await on my axios call and replaced it with return. on my callbacks .then and catch instead of returning
return res
or
return error
I access the data property like this
return res.data
It also got rid of the Error I was getting in my cloud functions logs Maximum call stack size exceeded

Bot Framework V4 - TypeError: Cannot perform 'get' on a proxy that has been revoked

I am trying to make a rest query against a database that stores knowledge articles for users and returns an array of results based on what the user has searched for. Whenever I try to search I get:
"TypeError: Cannot perform 'get' on a proxy that has been revoked"
I have tried adding it to async as shown but I still keep getting the same error. Any idea what I am doing wrong?
const Response = async (turnContext) => {
if (turnContext.activity.value.choice === 'feedbackProvider') {
try {
const feedbackBody = turnContext.activity.value.feedbackBody;
const feedbackEmail = turnContext.activity.value.feedbackEmail;
storage.write(feedbackBody, feedbackEmail);
await turnContext.sendActivity(`Feedback Sent`);
} catch (err) {
console.log('fetch failed', err);
}
} else if (turnContext.activity.value.choice === 'issueRaiser') {
try {
const bugTitle = turnContext.activity.value.issueTitle;
const bugDesc = turnContext.activity.value.issueDescription;
const bugEmail = turnContext.activity.value.issueEmail;
const request = require('request');
request({
method: 'Post',
uri: `<uri>issues?title=${ bugTitle }&description=${ bugDesc } ${ bugEmail }&labels=bug`,
json: true,
headers: {
'Private-Token': '<token>'
}
});
turnContext.sendActivity(`Issue Raised`);
} catch (err) {
console.log('fetch failed', err);
}
} else if (turnContext.activity.value.choice === 'knowledgeBaseSearch') {
try {
const knowledgeBaseTopic = turnContext.activity.value.knowledgeBaseTopic;
request({
url: process.env.SN_KB_URL + knowledgeBaseTopic,
json: true,
auth: {
'username': process.env.Ticket_User,
'password': process.env.Ticket_Key
}
}, async (error, response, body) => {
try {
var stuff = [];
for (var i = 0, len = body.result.length; i < len; i++) {
stuff.push(
CardFactory.heroCard(body.result[i].short_description, ['imageUrl1'], [`${ process.env.SN_KB_Resp_URl }${ body.result[i].number }`])
);
}
let messageWithCarouselOfCards = MessageFactory.carousel(stuff);
await turnContext.sendActivity(messageWithCarouselOfCards);
} catch (err) {
console.log(error);
}
});
} catch (err) {
console.log('fetch failed', err);
}
}
};
Full Error Message:
TypeError: Cannot perform 'get' on a proxy that has been revoked
cardMiddleware.js:35
at Request.request [as _callback] (c:\Bots\sdk4-2\skills\cardMiddleware.js:35:45)
at Request.self.callback (c:\Bots\sdk4-2\node_modules\request\request.js:186:22)
at emitTwo (events.js:126:13)
at Request.emit (events.js:214:7)
at Request.<anonymous> (c:\Bots\sdk4-2\node_modules\request\request.js:1163:10)
at emitOne (events.js:116:13)
at Request.emit (events.js:211:7)
at IncomingMessage.<anonymous> (c:\Bots\sdk4-2\node_modules\request\request.js:1085:12)
at Object.onceWrapper (events.js:313:30)
at emitNone (events.js:111:20)
From my post on the forum I was informed that I was using a request module that did not support Promises, which I believe was causing my error. I've now began to use Axios for my request which is shown below;
try {
return await axios.get(process.env.SN_KB_URL + knowledgeBaseTopic, {
headers: {
auth: {
username: process.env.Ticket_User,
password: process.env.Ticket_Key
}
}
})
}
However now when I run the request I get a 401 'Unauthorised' error and I'm not sure what is wrong with my request.
This issue happened because I was using a request module that did not support promises. Changing my request module for one that did support promises (which I found out about by using this article) resolved the issue.
The answer for me was to double check I didn't miss any await usage that might be necessary. Turns out I called this.dialog.run(context, this.dialogState); without the await and that threw the same error. I found the answer on this Github issue
I spent a lot of time struggling with this issue. As other commenters have noted, the issue lies in the fact that the Lex Runtime is not promise-based, so you cannot await requests, which causes the proxy to be revoked.
Here is my solution:
async callLex(context) {
const params = {
botAlias: 'prod',
botName: 'botName',
userId: context.activity.from.id,
contentType: 'text/plain; charset=utf-8',
accept: 'text/plain; charset=utf-8',
inputStream: context.activity.text.trim()
}
let request = lexruntime.postContent(params)
await request.promise().then(
async response => {
console.log(response)
console.log('Success!')
await context.sendActivity(response.message)
},
err => {
console.log(err)
console.log('Error!')
})
}
Rather than directly invoke the request like "lexruntime.postContent(params, callback func)", I exclude the callback function and utilize the "promise" property of AWS.Request to send the request as a promise which enables me to use "await" and keeps the proxy open. See documentation here.
I'm going to put this here only because it's the first result that pops up when searching, although it doesn't directly relate to this issue.
There's a very easy way to use setTimeout() and avoid this error:
await new Promise(resolve => setTimeout(() => resolve(
turnContext.sendActivity('I was sent 5 seconds later')
), 5000));
In my scenario, we were trying to upload files from a Task Module (modal popup of teams) to the bot and in response the bot would give a first confirmation that the attachments are uploading. This activity would close the task module (as the bot must reply within 10 seconds or teams would resend the request). Now when the attachments were uploaded, we wanted to update the previously sent adaptive card with the list of the uploaded attachments. We achieved this using the proactive messaging feature of bot framework.
const conversationReference = TurnContext.getConversationReference(activity);
Promise.all(listOfPromises).then(() => {
await botAdapter.continueConversation(conversationReference, async turnContext => {
await turnContext.sendActivity('All attachments uploaded!');
});
}
Docs: https://learn.microsoft.com/en-us/azure/bot-service/bot-builder-howto-proactive-message?view=azure-bot-service-4.0&tabs=javascript
Check for lines that needs await inside any aync function. I hope that azure will point usto which file or line specifically but I have not figured it out until I looked at all my functions.
Okay, so this is indeed a very cryptic error message as the github thread here suggested .
But I found that I was not await ing in this block:
this.onMessage(async (context, next) => {.
const didBotWelcomedUser = await this.welcomedUserProperty.get(
context,
"false"
);
if (didBotWelcomedUser === false) {
// first time user is in chat
await this.sendWelcomeMessage(context); `<-------- await here was missing`
} else {
await this.sendSuggestedAction(context); `<-------- await here was missing`
}
await next();
});
this.onMembersAdded(async (context, next) => {
await this.sendWelcomeMessage(context);
await next();
});
}
I thought await.next() is enough. We all gotta learn this somehow... Hope you resolve yours.

"Unhandled rejection" error in Aurelia Fetch Client

I use Aurelia Fetch Client library to fetch JSON data from the backend server by the code:
getData() {
let httpClient = new HttpClient();
return httpClient.fetch('http://localhost:9220/get-data')
.then(response => response.json())
.then(data => return data);
}
}
And the metod getData() is called from the another code by the code:
dataService.getData().then(data => {
this.data = data;
}).catch(error => {
this.backendError = true;
});
As you can see I use here a catch statement and in case of error it's called, but I also see in the console an error message that comes from the library: "vendor-bundle.js:1395 Unhandled rejection TypeError: Failed to fetch". How can I get rid it?
I'm unsure if this is a bug with the Aurelia HTTP Fetch Client, but adding a responseError interceptor should remove the Unhandled Exception warning in the console.
let http = new HttpClient();
http.configure(config => {
config.withInterceptor({
response(response) {
return response;
},
responseError(error) {
return error;
}
})
});
This error may also come from the UseDeveloperExceptionPage middleware in a .NET Core API. This middleware strips all headers from the response which create CORS issues and causes the "TypeError: Failed to fetch" error you saw. Here is an example of my solution, which is described in full here.
.NET Core Middleware
private static Task HandleExceptionAsync(HttpContext context, Exception exception)
{
var code = HttpStatusCode.InternalServerError;
var result = JsonConvert.SerializeObject(new { error = "An internal server error has occurred." });
context.Response.ContentType = "application/json";
context.Response.StatusCode = (int)code;
return context.Response.WriteAsync(result);
}
Aurelia Interceptor
responseError(response: any): Promise<Response> {
if (response instanceof Response) {
return response.json().then((serverError: ServerError) => {
// Do something with the error here.
return Promise.reject<Response>(serverError.error);
});
}
}

Categories

Resources