The generic template and list template didn't work - facebook-messenger-bot

I'm following the facebook messenger develop QuickStart to create a Node.js project, and I improved it to work in quick reply. Then when I tried the Generic Template and List Template, but it didn't work.
As the following source code, when I input the work "generic" or "list", the messenger should reply me with the template messege. But there was nothing happened.
} else if (received_message.text === 'generic') {
console.log('generic in');
response = {
"attachment":{
"type":"template",
"payload":{
"template_type":"generic",
"elements":[
{
"title":"Welcome!",
"image_url":"http://webapplication120181023051009.azurewebsites.net/colorcar1.jpg",
"subtitle":"We have the right hat for everyone.",
"default_action": {
"type": "web_url",
"url": "https://www.taobao.com/",
"messenger_extensions": false,
"webview_height_ratio": "tall",
"fallback_url": "https://www.taobao.com/"
},
"buttons":[
{
"type":"web_url",
"url":"https://www.taobao.com/",
"title":"View Website"
},{
"type":"postback",
"title":"Start Chatting",
"payload":"DEVELOPER_DEFINED_PAYLOAD"
}
]
}
]
}
}
}
// Sends the response message
callSendAPI(sender_psid, response);
// Sends response messages via the Send API
function callSendAPI(sender_psid, response) {
// Construct the message body
let request_body = {
"recipient": {
"id": sender_psid
},
"message": response
}
console.log('PAGE_ACCESS_TOKEN:');
console.log(PAGE_ACCESS_TOKEN);
console.log('request body:');
console.log(request_body);
// Send the HTTP request to the Messenger Platform
request({
"uri": "https://graph.facebook.com/v2.6/me/messages?access_token=" + PAGE_ACCESS_TOKEN,
"qs": { "access_token": PAGE_ACCESS_TOKEN },
"method": "POST",
"json": request_body
}, (err, res, body) => {
if (!err) {
console.log('message sent!')
} else {
console.error("Unable to send message:" + err);
}
});
}

Sorry, I forgot to add the url into whiltelist.

Related

Problem sending POST body to the Firestore REST API

I want to create a new document in Firestore using the REST API.
Very good examples here using Axios to send the POST request with some fields:
https://www.jeansnyman.com/posts/google-firestore-rest-api-examples/
axios.post(
"https://firestore.googleapis.com/v1/projects/<PROJECTIDHERE>/databases/(default)/documents/<COLLECTIONNAME>",
{
fields: {
title: { stringValue: this.title },
category: { stringValue: this.category },
post: { stringValue: this.post },
summary: { stringValue: this.description },
published: { booleanValue: this.published },
created: { timestampValue: new Date() },
modified: { timestampValue: new Date() }
}
}
).then(res => { console.log("Post created") })
And an example here using Python Requests:
Using the Firestore REST API to Update a Document Field
(this is a PATCH request but the field formatting is the same as in a POST request)
import requests
import json
endpoint = "https://firestore.googleapis.com/v1/projects/[PROJECT_ID]/databases/(default)/documents/[COLLECTION]/[DOCUMENT_ID]?currentDocument.exists=true&updateMask.fieldPaths=[FIELD_1]"
body = {
"fields" : {
"[FIELD_1]" : {
"stringValue" : "random new value"
}
}
}
data = json.dumps(body)
headers = {"Authorization": "Bearer [AUTH_TOKEN]"}
print(requests.patch(endpoint, data=data, headers=headers).json())
I am using Google Apps Script UrlFetchApp.fetch to send my requests. I am able to use GET requests with no problems. For example, to get all the documents in a collection (in Google Apps Script):
function firestore_get_documents(){
var options = {
headers: { 'Authorization': 'Bearer ' + ScriptApp.getOAuthToken() },
method:'GET'
}
var response = UrlFetchApp.fetch('https://firestore.googleapis.com/v1/projects/<PROJECTIDHERE>/databases/(default)/documents/myCollection', options);
var parsed = JSON.parse(response.getContentText());
return parsed;
}
This works nicely. And changing 'method' to 'POST' creates a new document in myCollection as expected. Then I try to add a POST body with some fields (or just one field):
function firestore_create_new_document(){
var options = {
headers: { 'Authorization': 'Bearer ' + ScriptApp.getOAuthToken() },
method:'POST',
payload: {fields: { title: { stringValue: 'newTitle' } } }, // If you comment out this line, it works as expected
muteHttpExceptions:true
}
var response = UrlFetchApp.fetch('https://firestore.googleapis.com/v1/projects/<PROJECTIDHERE>/databases/(default)/documents/myCollection', options);
var contentText = response.getContentText();
var parsed = JSON.parse(response.getContentText());
return parsed;
}
I get the following errors:
code: 400 message: "Request contains an invalid argument."
status: "INVALID_ARGUMENT"
details[0][#type]: "type.googleapis.com/google.rpc.BadRequest"
details[0][fieldViolations][0][field]: "{title={stringValue=newTitle}}"
details[0][fieldViolations][0][description]: "Error expanding 'fields' parameter. Cannot find matching fields for path '{title={stringValue=newTitle}}'."
Documentation is available here:
https://firebase.google.com/docs/firestore/reference/rest/v1/projects.databases.documents/createDocument
https://firebase.google.com/docs/firestore/reference/rest/v1/projects.databases.documents#Document
The problem may be the formatting of my 'fields' object - I've tried several different formats from the documentation and examples
The problem may be that the fields don't exist yet? I think I should be able to create a new document with new fields
The problem may be with the way UrlFetchApp.fetch sends my JSON body. I have tried using payload = JSON.stringify(payload_object) and that doesn't work either.
I think UrlFetchApp is doing something slightly different than Axios or Python Requests - the body is getting sent differently, and not parsing as expected.
How about the following modification?
From:
var options = {
headers: { 'Authorization': 'Bearer ' + ScriptApp.getOAuthToken() },
method:'POST',
payload: {fields: { title: { stringValue: 'newTitle' } } }, // If you comment out this line, it works as expected
muteHttpExceptions:true
}
To:
var options = {
headers: { 'Authorization': 'Bearer ' + ScriptApp.getOAuthToken() },
method:'POST',
payload: JSON.stringify({fields: { title: { stringValue: 'newTitle' } } }),
contentType: "application/json",
muteHttpExceptions:true
}
When I tested above modified request, I could confirm that it worked. But if other error occurs, please tell me.
Reference:
Class UrlFetchApp

How to implement push notification in KaiOS app

I am trying to implement push notification in KaiOS app. I simply follow below links.
W3C Push API
Push API introduction
Service Worker Cookbook - Web Push Payload
After follow all links the push is working in browser but not in KaiOS app.
If anybody have any sample code or documents please share.
Any help will be appriciated.
1) First, add this permission in manifest.webapp
"permissions": {
"serviceWorker":{
"description": "required for handle push."
},
"push":{
"description": "New update push."
},
"desktop-notification": {
"description": "New content update notification for the user."
}
}
2) service worker file sw.js code
self.addEventListener('push', function(event) {
event.waitUntil(
self.registration.showNotification('My Push', {
body: 'Push Activated',
})
);
});
self.addEventListener('activate', e => {
self.clients.claim();
});
3) Add service worker on app start
registerSW : function() {
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('./sw.js').then(function(reg) {
console.log('Service Worker Registered!', reg);
reg.pushManager.getSubscription().then(function(sub) {
if (sub === null) {
} else {
console.log('Subscription object: ', sub);
}
});
}).catch(function(e) {
console.log('SW reg failed');
});
}
}
4) Call service worker by any dom element like button
registerServiceWorker: function() {
Notification.requestPermission().then(function(permission) {
if (permission === 'granted') {
if ('serviceWorker' in navigator) {
navigator.serviceWorker.ready.then(function(reg) {
reg.pushManager.subscribe({
userVisibleOnly: true
}).then(function(sub) {
console.log('Endpoint URL: ', sub.endpoint);
}).catch(function(e) {
if (Notification.permission === 'denied') {
console.warn('Permission for notifications was denied');
} else {
console.error('Unable to subscribe to push', e);
}
});
})
}
}
});
}
That's it.
I had same problem as this, but I followed this simple web push notification method,
https://medium.com/#seladir/how-to-implement-web-push-notifications-in-your-node-react-app-9bed79b53f34
as well as I fixed that issue and now It work properly. please don't forget to add permissions like below into the manifest.webapp file.
"permissions": {
"serviceworker": {
"description": "Needed for assocating service worker"
},
"desktop-notification": {
"description": "Needed for creating system notifications."
},
"notifications": {},
"push": {
"description": "Required for being updated with new goals in soccer matches"
},
"geolocation": {
"description": "Marking out user location"
},
"alarms": {
"description": "Scheduling alarms"
}
},
and as well as please refer this kaios documention for run the applicaion on kaios device.
https://developer.kaiostech.com/getting-started/build-your-first-hosted-app/pwa-to-hosted-app

Download or view file using google firebase cloud function

What I'm trying to do:
Generate invoice using a third party lib.
Download/View invoice
My code
let createPdf = functions.https.onRequest(async (request, response) => {
// more code here
if (download == 'true') {
return response.status(200).download(__dirname + "/docs/" + newFileName, newFileName, (err) => {
if (err) {
console.log(err.message);
} else {
console.log("Downloaded:", filename)
}
})
} else {
var options = {
root: __dirname,
dotfiles: 'deny',
headers: {
'x-timestamp': Date.now(),
'x-sent': true
}
};
return response.status(200).sendFile("/docs/" + newFileName, options, (err) => {
if (err) {
console.log(err);
} else {
console.log('Sent:', filename);
}
});
}
});
The error
{
"error": {
"code": 500,
"status": "INTERNAL",
"message": "function crashed",
"errors": [
"socket hang up"
]
}
}
Note:
When I return a simple string instead of the file it works.
Use express request and response objects to send a file.
Read this documentation: using_express_request_and_response_objects
And don't forget to use absolute path when using sendFile

botkit middleware - How to use sendToWatson to update context?

I use https://github.com/watson-developer-cloud/botkit-middleware#implementing-app-actions as my reference.
The context in my conversation does not update.
Here is my bot-facebook.js.
function checkBalance(context, callback) {
var contextDelta = {
user_name: 'Henrietta',
fname: 'Pewdiepie'
};
callback(null, context);
}
var checkBalanceAsync = Promise.promisify(checkBalance);
var processWatsonResponse = function (bot, message) {
if (message.watsonError) {
console.log(message.watsonError);
return bot.reply(message, "I'm sorry, but for technical reasons I can't respond to your message");
}
if (typeof message.watsonData.output !== 'undefined') {
//send "Please wait" to users
bot.reply(message, message.watsonData.output.text.join('\n'));
if (message.watsonData.output.action === 'check_balance') {
var newMessage = clone(message);
newMessage.text = 'check new name';
checkBalanceAsync(message.watsonData.context).then(function (contextDelta) {
console.log("contextDelta: " + JSON.stringify(contextDelta));
return watsonMiddleware.sendToWatsonAsync(bot, newMessage, contextDelta);
}).catch(function (error) {
newMessage.watsonError = error;
}).then(function () {
return processWatsonResponse(bot, newMessage);
});
}
}
};
controller.on('message_received', processWatsonResponse);
The JSON editor of welcome node in my watson conversation.
{
"context": {
"fname": "",
"user_name": ""
},
"output": {
"text": {
"values": [
"Good day :) My name is Doug and I am a chatbot."
],
"selection_policy": "random"
},
"action": "check_balance"
}
}
I have tried multiple ways I could imagine.
Do I need to do something like fname: <?contextDelta.fname?> in the json editor?
You aren't checking context in your dialog.
Context object in JSON editor is used to store captured data in context,
so your node actually empties context variable.
Probably you need to remove that context initialization from your dialog,
To see value of context variable, you have to use it in the output
"Good day, $fname :) My name is Doug and I am a chatbot."

how to detect invalid route and show 404 error in hapi js?

I want to show a 404 view page when user is trying to access the invalid route which is not defined. for example if i am trying to access /myData then it should redirect to /404.
server.js
server.route(routes);
routes.js
module.exports =[
{
path:'/',
method:'GET',
handler:function(request, reply) {
reply.view('index').unstate('token');
}
},
{
path:'/login',
method:'GET',
handler:function(request, reply) {
reply.view('login');
}
},
{
path:'/login',
method:'POST',
handler:handlers.loginHandler,
config: {
state: {
parse: true, // parse and store in request.state
failAction: 'error' // may also be 'ignore' or 'log'
}
}
},
{
path:'/register',
method:'GET',
handler:function(request, reply) {
reply.view('register');
}
}];
You can decide based on the response of the server like this
server.ext({
type: 'onPreResponse',
method(request, reply) {
if (request.response.output.statusCode == 404) {
//serve your page here
}
reply.continue();
},
});

Resources