Need to get data from fixture JSON - node.js

I am struggling hard since yesterday getting the data from JSON, I don't understand why the fixture is not accessible. When I tried to get the ID, it gives me an error saying id isn't defined.
This gives me an error saying ID is not defined:
res.send(data.response["fixture"].id)
This code returns nothing:
res.send(data.response.fixture);
This code gives me the JSON data:
res.send(data.response
My JSON data:
// 20220714200426
// http://localhost:9090/
[
{
"fixture": {
"id": 822924,
"referee": "Jhon Alexander Hinestroza Romana, Colombia",
"timezone": "UTC",
"date": "2022-07-15T01:10:00+00:00",
"timestamp": 1657847400,
"periods": {
"first": 1657847400,
"second": 1657851000
},
"venue": {
"id": 375,
"name": "Estadio Manuel Murillo Toro",
"city": "Ibagué"
},
"status": {
"long": "Second Half",
"short": "2H",
"elapsed": 90
}
},
"league": {
"id": 239,
"name": "Primera A",
"country": "Colombia",
"logo": "https://media.api-sports.io/football/leagues/239.png",
"flag": "https://media.api-sports.io/flags/co.svg",
"season": 2022,
"round": "Clausura - 2"
},
"teams": {
"home": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png",
"winner": true
},
"away": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png",
"winner": false
}
},
"goals": {
"home": 2,
"away": 0
},
"score": {
"halftime": {
"home": 0,
"away": 0
},
"fulltime": {
"home": null,
"away": null
},
"extratime": {
"home": null,
"away": null
},
"penalty": {
"home": null,
"away": null
}
},
"events": [
{
"time": {
"elapsed": 1,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 13398,
"name": "Y. Congo"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 26,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 13592,
"name": "T. Gutierrez"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 27,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 13304,
"name": "B. Rovira"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 40,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 13592,
"name": "T. Gutierrez"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Red Card",
"comments": null
},
{
"time": {
"elapsed": 56,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": null,
"name": "O. Acosta"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 59,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 283830,
"name": "L. Riascos"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 61,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 13348,
"name": "L. Miranda"
},
"assist": {
"id": null,
"name": null
},
"type": "Var",
"detail": "Goal Disallowed - offside",
"comments": null
},
{
"time": {
"elapsed": 64,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 10328,
"name": "Y. Gonzalez"
},
"assist": {
"id": null,
"name": "O. Acosta"
},
"type": "subst",
"detail": "Substitution 1",
"comments": null
},
{
"time": {
"elapsed": 66,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 6632,
"name": "A. Renteria"
},
"assist": {
"id": 13348,
"name": "L. Miranda"
},
"type": "subst",
"detail": "Substitution 1",
"comments": null
},
{
"time": {
"elapsed": 69,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 13596,
"name": "M. Rangel"
},
"assist": {
"id": 13298,
"name": "J. Lucumi"
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
},
{
"time": {
"elapsed": 70,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 59887,
"name": "A. Gutierrez"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 72,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 13298,
"name": "J. Lucumi"
},
"assist": {
"id": 6632,
"name": "A. Renteria"
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
},
{
"time": {
"elapsed": 78,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 31691,
"name": "A. Vuletich"
},
"assist": {
"id": 51135,
"name": "H. Mosquera"
},
"type": "subst",
"detail": "Substitution 2",
"comments": null
},
{
"time": {
"elapsed": 78,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 200150,
"name": "J. C. Caldera Alvis"
},
"assist": {
"id": 51165,
"name": "A. Rodriguez"
},
"type": "subst",
"detail": "Substitution 3",
"comments": null
},
{
"time": {
"elapsed": 82,
"extra": null
},
"team": {
"id": 1127,
"name": "Deportivo Cali",
"logo": "https://media.api-sports.io/football/teams/1127.png"
},
"player": {
"id": 200150,
"name": "J. C. Caldera Alvis"
},
"assist": {
"id": null,
"name": null
},
"type": "Card",
"detail": "Yellow Card",
"comments": null
},
{
"time": {
"elapsed": 84,
"extra": null
},
"team": {
"id": 1142,
"name": "Deportes Tolima",
"logo": "https://media.api-sports.io/football/teams/1142.png"
},
"player": {
"id": 59758,
"name": "A. Melendez"
},
"assist": {
"id": 35757,
"name": "Y. Orozco"
},
"type": "subst",
"detail": "Substitution 2",
"comments": null
}
]
},
{
"fixture": {
"id": 896998,
"referee": null,
"timezone": "UTC",
"date": "2022-07-15T02:00:00+00:00",
"timestamp": 1657850400,
"periods": {
"first": 1657850400,
"second": 1657854000
},
"venue": {
"id": 1087,
"name": "Estadio Universitario de Nuevo León",
"city": "San Nicolás de los Garza"
},
"status": {
"long": "Second Half",
"short": "2H",
"elapsed": 46
}
},
"league": {
"id": 927,
"name": "World Cup - Women - Qualification Concacaf",
"country": "World",
"logo": "https://media.api-sports.io/football/leagues/927.png",
"flag": null,
"season": 2022,
"round": "Semi-finals"
},
"teams": {
"home": {
"id": 1717,
"name": "Canada W",
"logo": "https://media.api-sports.io/football/teams/1717.png",
"winner": true
},
"away": {
"id": 1785,
"name": "Jamaica W",
"logo": "https://media.api-sports.io/football/teams/1785.png",
"winner": false
}
},
"goals": {
"home": 1,
"away": 0
},
"score": {
"halftime": {
"home": 1,
"away": 0
},
"fulltime": {
"home": null,
"away": null
},
"extratime": {
"home": null,
"away": null
},
"penalty": {
"home": null,
"away": null
}
},
"events": [
{
"time": {
"elapsed": 10,
"extra": null
},
"team": {
"id": 1785,
"name": "Jamaica W",
"logo": "https://media.api-sports.io/football/teams/1785.png"
},
"player": {
"id": null,
"name": "C. Swaby"
},
"assist": {
"id": null,
"name": "J. C. Pelaia-Hylton"
},
"type": "subst",
"detail": "Substitution 1",
"comments": null
},
{
"time": {
"elapsed": 18,
"extra": null
},
"team": {
"id": 1717,
"name": "Canada W",
"logo": "https://media.api-sports.io/football/teams/1717.png"
},
"player": {
"id": null,
"name": "J. Fleming"
},
"assist": {
"id": null,
"name": null
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
}
]
},
{
"fixture": {
"id": 868553,
"referee": null,
"timezone": "UTC",
"date": "2022-07-15T02:05:00+00:00",
"timestamp": 1657850700,
"periods": {
"first": 1657850700,
"second": null
},
"venue": {
"id": 1844,
"name": "Estadio Olímpico Carlos Iturralde Rivero",
"city": "Mérida"
},
"status": {
"long": "Halftime",
"short": "HT",
"elapsed": 45
}
},
"league": {
"id": 263,
"name": "Ascenso MX",
"country": "Mexico",
"logo": "https://media.api-sports.io/football/leagues/263.png",
"flag": "https://media.api-sports.io/flags/mx.svg",
"season": 2022,
"round": "Apertura - 3"
},
"teams": {
"home": {
"id": 2311,
"name": "Venados FC",
"logo": "https://media.api-sports.io/football/teams/2311.png",
"winner": true
},
"away": {
"id": 2308,
"name": "Celaya",
"logo": "https://media.api-sports.io/football/teams/2308.png",
"winner": false
}
},
"goals": {
"home": 2,
"away": 1
},
"score": {
"halftime": {
"home": 2,
"away": 1
},
"fulltime": {
"home": null,
"away": null
},
"extratime": {
"home": null,
"away": null
},
"penalty": {
"home": null,
"away": null
}
},
"events": [
{
"time": {
"elapsed": 11,
"extra": null
},
"team": {
"id": 2308,
"name": "Celaya",
"logo": "https://media.api-sports.io/football/teams/2308.png"
},
"player": {
"id": null,
"name": "D. Gonzalez"
},
"assist": {
"id": null,
"name": null
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
},
{
"time": {
"elapsed": 17,
"extra": null
},
"team": {
"id": 2311,
"name": "Venados FC",
"logo": "https://media.api-sports.io/football/teams/2311.png"
},
"player": {
"id": null,
"name": "M. Perez"
},
"assist": {
"id": null,
"name": null
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
},
{
"time": {
"elapsed": 36,
"extra": null
},
"team": {
"id": 2311,
"name": "Venados FC",
"logo": "https://media.api-sports.io/football/teams/2311.png"
},
"player": {
"id": 36091,
"name": "M. Perez"
},
"assist": {
"id": null,
"name": null
},
"type": "Goal",
"detail": "Normal Goal",
"comments": null
}
]
}
]
My Node.js code:
const express = require('express');
const Router = express.Router();//router will be used now to route
require('dotenv').config();
const fetch = require('cross-fetch');
const axios = require('axios');
const request = require('request');
const endpoint = 'fixtures';
Router.get('/', (req, res) => {
var options = {
method: 'GET',
url: `https://v3.football.api-sports.io/${endpoint}`,
qs: {live: 'all'},
headers: {
'x-rapidapi-host': 'v3.football.api-sports.io',
'x-rapidapi-key': `${process.env.API_KEY}`
}
};
request(options, function (error, resp, body) {
if (error) throw new Error(error);
const data = JSON.parse(body);
res.send(data.response);
});
})
module.exports = Router;
What I want is to access fixture ID and all other keys as well but I am not able to reach the fixture. Can anyone able to guide me on what's wrong I am doing?

From the json data response body above, data.response is an array of objects of multiple fixtures. So, data.response.fixture would always return undefined. To access a particular fixture, depending on what you want to do to with, you'd have to access the index of the response first. As such:
console.log(data.response[0].fixture)
this should return:
"fixture": {
"id": 822924,
"referee": "Jhon Alexander Hinestroza Romana, Colombia",
"timezone": "UTC",
"date": "2022-07-15T01:10:00+00:00",
"timestamp": 1657847400,
"periods": {
"first": 1657847400,
"second": 1657851000
},
"venue": {
"id": 375,
"name": "Estadio Manuel Murillo Toro",
"city": "Ibagué"
},
"status": {
"long": "Second Half",
"short": "2H",
"elapsed": 90
}
}
To access its id:
console.log(data.response[0].fixture.id)
The important thing is to access the properties through the array index of the element you want.

Related

How do I send customer data from twilio to stripe?

I'm using Twilio to allow my customers to pay automatically over the phone via to stripe. I followed this tutorial: Is there a way to enter dollars/cents via DTMF?
The issue I'm running into is how do I send the "phone number" as a "customer" into stripe? The reason I want this is to be able to see who bought what and how many times etc. Currently, they are all coming into stripe as unknown/guest.
My only success has been (I'm using the studio) entering {{trigger.call.From}} into the "payment description". That still doesn't solve the issue fully though.
Any help would be greatly appreciated!
Here is my flow code:
{
"description": "A New Flow",
"states": [
{
"name": "Trigger",
"type": "trigger",
"transitions": [
{
"next": "received_message_forward",
"event": "incomingMessage"
},
{
"next": "gather_1",
"event": "incomingCall"
},
{
"event": "incomingConversationMessage"
},
{
"event": "incomingRequest"
},
{
"event": "incomingParent"
}
],
"properties": {
"offset": {
"x": 0,
"y": 0
}
}
},
{
"name": "gather_1",
"type": "gather-input-on-call",
"transitions": [
{
"next": "function_1",
"event": "keypress"
},
{
"event": "speech"
},
{
"next": "gather_1",
"event": "timeout"
}
],
"properties": {
"voice": "man",
"speech_timeout": "auto",
"offset": {
"x": 30,
"y": 270
},
"loop": 1,
"finish_on_key": "#",
"say": "Welcome and thank you for calling the donation line. Please enter the amount you wish to donate, then press pound. To enter with cents use the star key. for example to enter $18.50, press one eight star five zero.",
"language": "en-US",
"stop_gather": true,
"gather_language": "en",
"profanity_filter": "true",
"timeout": 5
}
},
{
"name": "function_1",
"type": "run-function",
"transitions": [
{
"next": "confirm_donation_amount",
"event": "success"
},
{
"event": "fail"
}
],
"properties": {
"offset": {
"x": -60,
"y": 530
},
"parameters": [
{
"value": "{{widgets.gather_1.Digits}}",
"key": "amount"
}
],
"url": "https://sand-pointer-5043.twil.io/pay_from_exchange"
}
},
{
"name": "say_play_2",
"type": "say-play",
"transitions": [
{
"event": "audioComplete"
}
],
"properties": {
"voice": "man",
"offset": {
"x": -60,
"y": 840
},
"loop": 1,
"say": "You entered ${{widgets.function_1.body}}",
"language": "en-US"
}
},
{
"name": "pay_1",
"type": "capture-payments",
"transitions": [
{
"next": "say_play_3",
"event": "success"
},
{
"next": "say_play_4",
"event": "maxFailedAttempts"
},
{
"next": "say_play_4",
"event": "providerError"
},
{
"next": "say_play_4",
"event": "payInterrupted"
},
{
"next": "say_play_4",
"event": "hangup"
},
{
"next": "say_play_4",
"event": "validationError"
}
],
"properties": {
"security_code": true,
"offset": {
"x": -70,
"y": 1140
},
"max_attempts": 2,
"payment_connector": "",
"payment_amount": "{{widgets.function_1.body}}",
"description": "{{trigger.call.From}} via Twilio",
"currency": "usd",
"language": "en-US",
"postal_code": "false",
"payment_token_type": "reusable",
"timeout": 5,
"valid_card_types": [
"visa",
"master-card",
"amex",
"discover"
]
}
},
{
"name": "say_play_3",
"type": "say-play",
"transitions": [
{
"next": "send_success_message_1",
"event": "audioComplete"
}
],
"properties": {
"voice": "man",
"offset": {
"x": -185,
"y": 1433
},
"loop": 1,
"say": "Your donation of ${{widgets.function_1.body}} was successful, Thank you.",
"language": "en-US"
}
},
{
"name": "say_play_4",
"type": "say-play",
"transitions": [
{
"next": "send_fail_message_1",
"event": "audioComplete"
}
],
"properties": {
"voice": "man",
"offset": {
"x": 190,
"y": 1456
},
"loop": 1,
"say": "There was an error with your donation. Please verify your details and call back to try again. Thanks!",
"language": "en-US"
}
},
{
"name": "send_success_message_1",
"type": "send-message",
"transitions": [
{
"event": "sent"
},
{
"event": "failed"
}
],
"properties": {
"offset": {
"x": -100,
"y": 1700
},
"service": "{{trigger.message.InstanceSid}}",
"channel": "{{trigger.message.ChannelSid}}",
"from": "{{flow.channel.address}}",
"to": "{{contact.channel.address}}",
"body": "Your donation of ${{widgets.function_1.body}} was successful, Thank you!."
}
},
{
"name": "send_fail_message_1",
"type": "send-message",
"transitions": [
{
"event": "sent"
},
{
"event": "failed"
}
],
"properties": {
"offset": {
"x": 250,
"y": 1700
},
"service": "{{trigger.message.InstanceSid}}",
"channel": "{{trigger.message.ChannelSid}}",
"from": "{{flow.channel.address}}",
"to": "{{contact.channel.address}}",
"body": "There was an error with your donation. Please verify your details and call back to try again. Thanks!"
}
},
{
"name": "confirm_donation_amount",
"type": "gather-input-on-call",
"transitions": [
{
"next": "split_2",
"event": "keypress"
},
{
"event": "speech"
},
{
"next": "confirm_donation_amount",
"event": "timeout"
}
],
"properties": {
"number_of_digits": 1,
"speech_timeout": "auto",
"offset": {
"x": 420,
"y": 530
},
"loop": 1,
"finish_on_key": "#",
"say": "You entered ${{widgets.function_1.body}}. Press 1 to confirm, or press 2 to enter a different amount.",
"stop_gather": true,
"gather_language": "en",
"profanity_filter": "true",
"timeout": 5
}
},
{
"name": "split_2",
"type": "split-based-on",
"transitions": [
{
"next": "confirm_donation_amount",
"event": "noMatch"
},
{
"next": "pay_1",
"event": "match",
"conditions": [
{
"friendly_name": "If value equal_to 1",
"arguments": [
"{{widgets.confirm_donation_amount.Digits}}"
],
"type": "equal_to",
"value": "1"
}
]
},
{
"next": "gather_1",
"event": "match",
"conditions": [
{
"friendly_name": "If value equal_to 2",
"arguments": [
"{{widgets.confirm_donation_amount.Digits}}"
],
"type": "equal_to",
"value": "2"
}
]
}
],
"properties": {
"input": "{{widgets.confirm_donation_amount.Digits}}",
"offset": {
"x": 430,
"y": 800
}
}
},
{
"name": "received_message_forward",
"type": "send-message",
"transitions": [
{
"event": "sent"
},
{
"event": "failed"
}
],
"properties": {
"offset": {
"x": -300,
"y": 250
},
"service": "{{trigger.message.InstanceSid}}",
"channel": "{{trigger.message.ChannelSid}}",
"from": "{{flow.channel.address}}",
"to": "{{contact.channel.address}}",
"body": "Thanks for texting the Donation line. To donate, please call us on this same number. We do not accept donations via text."
}
}
],
"initial_state": "Trigger",
"flags": {
"allow_concurrent_calls": true
}
}
Here is the function:
exports.handler = function(context, event, callback) {
const amount = event.amount;
const convert = amount.replace('*', '.');
callback(null, convert);
};

Mongoose pluck document array

I have a document like this:
I have a schema design like this, I'm using mongoose-paginate-v2:
const options = {
select: 'files',
lean: true,
offset,
limit
};
const data = Message.paginate(
{ conversation_id: conversationId, 'files.category': { "$in" : category } },
options,
);
return data;
This is my response data:
[
{
"_id": "628472b3ef39fbb8bb655317",
"files": [
{
"src": "U21102500080/2022/5/images/1652847282675-pexels_02.jpeg",
"name": "pexels_02.jpeg",
"extension": "jpeg",
"size": 25708,
"category": "image",
"_id": "628472b3ef39fbb8bb655318"
},
{
"src": "U21102500080/2022/5/images/1652847282704-pexels_03.jpeg",
"name": "pexels_03.jpeg",
"extension": "jpeg",
"size": 107748,
"category": "image",
"_id": "628472b3ef39fbb8bb655319"
},
{
"src": "U21102500080/2022/5/images/1652847282704-pexels_01.jpeg.jpeg",
"name": "pexels_01.jpeg.jpeg",
"extension": "jpeg",
"size": 22364,
"category": "image",
"_id": "628472b3ef39fbb8bb65531a"
}
],
"id": "628472b3ef39fbb8bb655317"
},
{
"_id": "628702c293b660628e95124d",
"files": [
{
"src": "c6ed8c14-bcec-4739-bdf2-2392c7d15318/2022/5/images/1653015230055-pexels-photo-11427585.jpeg",
"name": "pexels-photo-11427585.jpeg",
"extension": "jpeg",
"size": 17000,
"category": "image",
"_id": "628702c293b660628e95124e"
},
{
"src": "c6ed8c14-bcec-4739-bdf2-2392c7d15318/2022/5/images/1653015230098-chen-sithyfong-1fSRYz5QpSE-unsplash.jpeg",
"name": "chen-sithyfong-1fSRYz5QpSE-unsplash.jpeg",
"extension": "jpeg",
"size": 174722,
"category": "image",
"_id": "628702c293b660628e95124f"
},
{
"src": "c6ed8c14-bcec-4739-bdf2-2392c7d15318/2022/5/images/1653015230098-screen-post-EC5kTElGfNs-unsplash.jpeg",
"name": "screen-post-EC5kTElGfNs-unsplash.jpeg",
"extension": "jpeg",
"size": 160266,
"category": "image",
"_id": "628702c293b660628e951250"
}
],
"id": "628702c293b660628e95124d"
},
{
"_id": "628702fa93b660628e951275",
"files": [
{
"src": "U21102500080/2022/5/images/1653015288963-2022-01-26 16.58.29.jpg",
"name": "2022-01-26 16.58.29.jpg",
"extension": "jpg",
"size": 34576,
"category": "image",
"_id": "628702fa93b660628e951276"
},
{
"src": "U21102500080/2022/5/images/1653015288968-2022-01-26 16.58.20.jpg",
"name": "2022-01-26 16.58.20.jpg",
"extension": "jpg",
"size": 31982,
"category": "image",
"_id": "628702fa93b660628e951277"
},
{
"src": "U21102500080/2022/5/images/1653015288968-2022-01-26 16.58.24.jpg",
"name": "2022-01-26 16.58.24.jpg",
"extension": "jpg",
"size": 119198,
"category": "image",
"_id": "628702fa93b660628e951278"
}
],
"id": "628702fa93b660628e951275"
},
]
But I want this response data:
[
{
"src": "",
"name": "",
"extension": "",
"size": 0,
"category": "",
"_id": "628472b3ef39fbb8bb655318"
},
{
"src": "",
"name": "",
"extension": "",
"size": 0,
"category": "",
"_id": "628472b3ef39fbb8bb655319"
},
{
"src": "",
"name": "",
"extension": "",
"size": 0,
"category": "",
"_id": "628472b3ef39fbb8bb65531a"
},
{
"src": "",
"name": "",
"extension": "",
"size": 0,
"category": "",
"_id": "628702c293b660628e95124e"
}
]
const options = {
select: 'files',
lean: true,
offset,
limit
};
let data = Message.paginate(
{ conversation_id: conversationId, 'files.category': { "$in" : category } },
options,
);
data = data.reduce((prev,curr) => [...prev.files, ...curr.files], [] )
return data;

Shopware6 API integrity constraints on nested entities

Tested on Shopware 6.3.5.1:
I'm trying to create a product via API together with its parent. That is necessary, because I can only iterate over variants in the other system.
As far as I can tell there's no conflict with the IDs or duplicates. Neither the product nor its parent already exist.
But when I do this:
POST https://somedomain.de/api/v3/_action/sync
Content-Type: application/json
Accept: application/json
Authorization: Bearer {{auth_token}}
{
"7508d64f832fb06b8f82f78963b280ab": {
"action": "upsert",
"entity": "product",
"payload": [
{
"id": "7508d64f832fb06b8f82f78963b280ab",
"__code": "1111111189",
"stock": 99,
"taxId": "d390c2f211144543845dbf76fa69d17a",
"cmsPageId": null,
"deliveryTimeId": null,
"manufacturerId": null,
"visibilities": [
{
"id": "e24f994426246015347bba784ac69a97",
"productId": "7508d64f832fb06b8f82f78963b280ab",
"salesChannelId": "8e7c11e2540b4c71b521d5a59920e142",
"visibility": 30
}
],
"unitId": null,
"price": [
{
"currencyId": "b7d2554b0ce847cd82f3ac9bd1c0dfca",
"net": 25,
"gross": 29.75,
"linked": true
}
],
"productNumber": "1111111189",
"coverId": null,
"translations": {
"ce1df85b5f1c4eedbc532cbd34c57df6": {
"name": "Converse black",
"description": "Converse black"
},
"2fbb5fe2e29a4d70aa5854ce7ce3e20b": {
"name": "Converse black",
"description": "Converse black"
}
},
"categories": [
{
"id": "e90cf50735a0d6f69b2dbf599caa4954"
},
{
"id": "a5b4753f41c8f4bedba1bf5954c961cb"
}
],
"properties": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
],
"media": [
{
"id": "cb9a886400616c215a588b13cb7c662b",
"mediaId": "a7aabb5ff4dc3c99ba45724ec7477ffe"
}
],
"parent": {
"id": "7a788255eab96bf51002829b3a6becf2",
"__code": "1111111189",
"stock": 99,
"taxId": "d390c2f211144543845dbf76fa69d17a",
"cmsPageId": null,
"deliveryTimeId": null,
"manufacturerId": null,
"visibilities": [
{
"id": "8d5a7e2b2c02986a924eaf3d9504413c",
"productId": "7a788255eab96bf51002829b3a6becf2",
"salesChannelId": "8e7c11e2540b4c71b521d5a59920e142",
"visibility": 30
}
],
"unitId": null,
"price": [
{
"currencyId": "b7d2554b0ce847cd82f3ac9bd1c0dfca",
"net": 25,
"gross": 29.75,
"linked": true
}
],
"productNumber": "converseblack",
"coverId": null,
"translations": {
"ce1df85b5f1c4eedbc532cbd34c57df6": {
"name": "Converse black",
"description": "Converse black"
},
"2fbb5fe2e29a4d70aa5854ce7ce3e20b": {
"name": "Converse black",
"description": "Converse black"
}
},
"categories": [
{
"id": "e90cf50735a0d6f69b2dbf599caa4954"
},
{
"id": "a5b4753f41c8f4bedba1bf5954c961cb"
}
],
"properties": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
],
"media": [
{
"id": "cb9a886400616c215a588b13cb7c662b",
"mediaId": "a7aabb5ff4dc3c99ba45724ec7477ffe"
}
],
"configuratorSettings": [
{
"optionId": "a01a0380ca3c61428c26a231f0e49a09",
"id": "db3787abb8d6372e1997c144031ef1e2"
}
]
},
"parentId": "7a788255eab96bf51002829b3a6becf2",
"options": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
]
}
]
}
}
I get as a response that the integrity constraint productId X saleschannelId in visibilities gets violated:
{
"success": false,
"data": {
"7508d64f832fb06b8f82f78963b280ab": {
"result": [
{
"entities": [],
"errors": [
{
"code": "0",
"status": "500",
"title": "Internal Server Error",
"detail": "An exception occurred while executing 'INSERT INTO `product_visibility` (`id`, `product_id`, `product_version_id`, `sales_channel_id`, `visibility`, `created_at`) VALUES (?, ?, ?, ?, ?, ?)' with params [\"\\x8d\\x5a\\x7e\\x2b\\x2c\\x02\\x98\\x6a\\x92\\x4e\\xaf\\x3d\\x95\\x04\\x41\\x3c\", \"\\x7a\\x78\\x82\\x55\\xea\\xb9\\x6b\\xf5\\x10\\x02\\x82\\x9b\\x3a\\x6b\\xec\\xf2\", \"\\x0f\\xa9\\x1c\\xe3\\xe9\\x6a\\x4b\\xc2\\xbe\\x4b\\xd9\\xce\\x75\\x2c\\x34\\x25\", \"\\x8e\\x7c\\x11\\xe2\\x54\\x0b\\x4c\\x71\\xb5\\x21\\xd5\\xa5\\x99\\x20\\xe1\\x42\", 30, \"2021-02-22 11:36:18.099\"]:\n\nSQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry 'zx\\x82U\\xEA\\xB9k\\xF5\\x10\\x02\\x82\\x9B:k\\xEC\\xF2-\\x0F\\xA9\\x1C\\x...' for key 'uniq.product_id__sales_channel_id'"
}
]
}
],
"extensions": []
}
},
"extensions": []
}
I just figured out, that it's possible to extract the nested entities into separate actions (that works):
{
"7508d64f832fb06b8f82f78963b280ab": {
"action": "upsert",
"entity": "product",
"payload": [
{
"id": "7508d64f832fb06b8f82f78963b280ab",
"__code": "1111111189",
"stock": 99,
"taxId": "d390c2f211144543845dbf76fa69d17a",
"cmsPageId": null,
"deliveryTimeId": null,
"manufacturerId": null,
"unitId": null,
"price": [
{
"currencyId": "b7d2554b0ce847cd82f3ac9bd1c0dfca",
"net": 25,
"gross": 29.75,
"linked": true
}
],
"productNumber": "1111111189",
"coverId": null,
"translations": {
"ce1df85b5f1c4eedbc532cbd34c57df6": {
"name": "Converse black",
"description": "Converse black"
},
"2fbb5fe2e29a4d70aa5854ce7ce3e20b": {
"name": "Converse black",
"description": "Converse black"
}
},
"categories": [
{
"id": "e90cf50735a0d6f69b2dbf599caa4954"
},
{
"id": "a5b4753f41c8f4bedba1bf5954c961cb"
}
],
"properties": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
],
"media": [
{
"id": "cb9a886400616c215a588b13cb7c662b",
"mediaId": "a7aabb5ff4dc3c99ba45724ec7477ffe"
}
],
"parent": {
"id": "7a788255eab96bf51002829b3a6becf2",
"__code": "1111111189",
"stock": 99,
"taxId": "d390c2f211144543845dbf76fa69d17a",
"cmsPageId": null,
"deliveryTimeId": null,
"manufacturerId": null,
"unitId": null,
"price": [
{
"currencyId": "b7d2554b0ce847cd82f3ac9bd1c0dfca",
"net": 25,
"gross": 29.75,
"linked": true
}
],
"productNumber": "converseblack",
"coverId": null,
"translations": {
"ce1df85b5f1c4eedbc532cbd34c57df6": {
"name": "Converse black",
"description": "Converse black"
},
"2fbb5fe2e29a4d70aa5854ce7ce3e20b": {
"name": "Converse black",
"description": "Converse black"
}
},
"categories": [
{
"id": "e90cf50735a0d6f69b2dbf599caa4954"
},
{
"id": "a5b4753f41c8f4bedba1bf5954c961cb"
}
],
"properties": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
],
"media": [
{
"id": "cb9a886400616c215a588b13cb7c662b",
"mediaId": "a7aabb5ff4dc3c99ba45724ec7477ffe"
}
],
"configuratorSettings": [
{
"optionId": "a01a0380ca3c61428c26a231f0e49a09",
"id": "db3787abb8d6372e1997c144031ef1e2"
}
]
},
"parentId": "7a788255eab96bf51002829b3a6becf2",
"options": [
{
"id": "a01a0380ca3c61428c26a231f0e49a09"
}
]
}
]
},
"e24f994426246015347bba784ac69a97": {
"action": "upsert",
"entity": "product_visibility",
"payload": [
{
"id": "e24f994426246015347bba784ac69a97",
"productId": "7508d64f832fb06b8f82f78963b280ab",
"salesChannelId": "8e7c11e2540b4c71b521d5a59920e142",
"visibility": 30
}
]
},
"8d5a7e2b2c02986a924eaf3d9504413c": {
"action": "upsert",
"entity": "product_visibility",
"payload": [
{
"id": "8d5a7e2b2c02986a924eaf3d9504413c",
"productId": "7a788255eab96bf51002829b3a6becf2",
"salesChannelId": "8e7c11e2540b4c71b521d5a59920e142",
"visibility": 30
}
]
}
}

Why Does Calling Expand and Select on a PUT result in LESS information being returned - Acumatica REST API

In the example for Acumatica: "Lesson 2.1: Updating a Customer Account" the sample code will update the customer's Contact info, based on retrieving it by the email address. It expands the MainContact and selects CustomerID and CustomerClass:
https://localhost/MyStoreInstance/entity/Default/18.200.001/Customer?$filter=MainContact/Email eq 'info#jevy-comp.con'&$expand=MainContact&$select=CustomerID,CustomerClass
The values that are returned include CustomerID, CustomerClass PLUS a fully loaded BillingContact record, comprising 2150 Bytes of data like this:
{
"id": "0b88d208-297a-4b81-a20c-39d27bace10a",
"rowNumber": 1,
"note": "",
"BillingContact": {
"id": "e1133b8a-fca9-4885-8e4c-09a85808f025",
"rowNumber": 1,
"note": null,
"Activities": [],
"Address": {
"id": "4f1719aa-6eb0-4551-a143-ad2139e135aa",
"rowNumber": 1,
"note": null,
"AddressLine1": {
"value": "1000 Pennsylvania Ave"
},
"AddressLine2": {},
"City": {
"value": "San Francisco"
},
"Country": {
"value": "US"
},
"PostalCode": {
"value": "94107-3479"
},
"State": {
"value": "CA"
},
"custom": {},
"files": []
},
"Attention": {
"value": "Mister. Jack Green"
},
"Attributes": [],
"Campaigns": [],
"Cases": [],
"ContactID": {
"value": 12417
},
"DisplayName": {
"value": "Jevy Computers"
},
"Duplicates": [],
"Email": {
"value": "green#jevy-comp.con"
},
"Fax": {},
"FirstName": {},
"JobTitle": {
"value": ""
},
"LastName": {},
"MarketingLists": [],
"MiddleName": {},
"Notifications": [],
"Opportunities": [],
"Phone1": {
"value": "+1 (777) 380-0089"
},
"Phone1Type": {
"value": "Business 1"
},
"Phone2": {},
"Phone2Type": {
"value": "Business 2"
},
"Relations": [],
"Title": {},
"UserInfo": null,
"WebSite": {},
"custom": {},
"files": []
},
"BillingContactSameAsMain": {
"value": false
},
"CustomerClass": {
"value": "INTL"
},
"CustomerID": {
"value": "C000000003"
},
"custom": {},
"files": []
}
However, when I explicitly ask for BillingContact to be Expanded, I get LESS information than I get when I omit it from the EXPAND command altogether. (I get 1235 bytes in return.)
{
"id": "0b88d208-297a-4b81-a20c-39d27bace10a",
"rowNumber": 1,
"note": "",
"BillingContact": {
"id": "e1133b8a-fca9-4885-8e4c-09a85808f025",
"rowNumber": 1,
"note": null,
"Attention": {
"value": "Mr. Jack Green"
},
"ContactID": {
"value": 12417
},
"DisplayName": {
"value": "Jevy Computers"
},
"Email": {
"value": "green#jevy-comp.con"
},
"Fax": {},
"FirstName": {},
"JobTitle": {
"value": ""
},
"LastName": {},
"MiddleName": {},
"Phone1": {
"value": "+1 (777) 380-0089"
},
"Phone1Type": {
"value": "Business 1"
},
"Phone2": {},
"Phone2Type": {
"value": "Business 2"
},
"Title": {},
"WebSite": {},
"custom": {},
"files": []
},
"BillingContactSameAsMain": {
"value": false
},
"CustomerClass": {
"value": "INTL"
},
"CustomerID": {
"value": "C000000003"
},
"custom": {},
"files": []
}
Clearly I do not understand how the expand command is operating in a PUT. Can anyone explain it to me?
Why does including BillingContact in the expand command give me less BillingContact information?
When you execute a Put request, Acumatica automatically add expands for the entities your are touching, including subentities, so you see Address under BillingContact.
When you add expand on the billing contact, it overrides the default expands and you do not see Address any more.
To get Address in the result, you add another expand : BillingContact/Address
Same applies to all other entities

create contact from node.js to mautic uisng Mautic rest api

I am using mautic-node npm module for contacting mautic REST API from node.js.My aim is to create a contact from my app in mautic dashboard using mautic REST API,but i am facing issue in creating contact from node.js.Please help me to figure out this.
var mautic = require('mautic-api-node');
var request = require('request');
var config = require('../config/config.js');
var request = require('request');
exports.saveContact = (req, res) => {
queryParameters = JSON.stringify(req.body);
var username = "mauticUsername";
var password = "mauticPassword";
var auth = "Basic " + new Buffer.from(username + ":" +
password).toString("base64");
var options = {
url: 'https://mautic-url/api/contacts/new',
method: "POST",
form: queryParameters,
headers: {
"Authorization": auth
}
};
request(options, (error, response, body) => {
if (error) console.log(error);
console.log("Body", body);
})
}
I am passing this request body to backend:-
{
"firstname":"firstname",
"ipAddress":"Ipaddress",
"lastname":"lastname",
"email":"email"
}
when i run this code i am getting this response
Body {
"contact": {
"isPublished": true,
"dateAdded": "2019-06-08T10:06:25+00:00",
"dateModified": null,
"createdBy": 1,
"createdByUser": "username",
"modifiedBy": null,
"modifiedByUser": null,
"id": 1277,
"points": 0,
"color": null,
"fields": {
"core": {
"title": {
"id": 1,
"group": "core",
"label": "Title",
"alias": "title",
"type": "lookup",
"value": null
},
"firstname": {
"id": 2,
"group": "core",
"label": "First Name",
"alias": "firstname",
"type": "text",
"value": null
},
"lastname": {
"id": 3,
"group": "core",
"label": "Last Name",
"alias": "lastname",
"type": "text",
"value": null
},
"company": {
"id": 4,
"group": "core",
"label": "Primary company",
"alias": "company",
"type": "text",
"value": null
},
"position": {
"id": 5,
"group": "core",
"label": "Position",
"alias": "position",
"type": "text",
"value": null
},
"email": {
"id": 6,
"group": "core",
"label": "Email",
"alias": "email",
"type": "email",
"value": null
},
"mobile": {
"id": 7,
"group": "core",
"label": "Mobile",
"alias": "mobile",
"type": "tel",
"value": null
},
"phone": {
"id": 8,
"group": "core",
"label": "Phone",
"alias": "phone",
"type": "tel",
"value": null
},
"points": {
"id": 9,
"group": "core",
"label": "Points",
"alias": "points",
"type": "number",
"value": null
},
"fax": {
"id": 10,
"group": "core",
"label": "Fax",
"alias": "fax",
"type": "tel",
"value": null
},
"address1": {
"id": 11,
"group": "core",
"label": "Address Line 1",
"alias": "address1",
"type": "text",
"value": null
},
"address2": {
"id": 12,
"group": "core",
"label": "Address Line 2",
"alias": "address2",
"type": "text",
"value": null
},
"city": {
"id": 13,
"group": "core",
"label": "City",
"alias": "city",
"type": "text",
"value": null
},
"state": {
"id": 14,
"group": "core",
"label": "State",
"alias": "state",
"type": "region",
"value": null
},
"zipcode": {
"id": 15,
"group": "core",
"label": "Zip Code",
"alias": "zipcode",
"type": "text",
"value": null
},
"country": {
"id": 16,
"group": "core",
"label": "Country",
"alias": "country",
"type": "country",
"value": null
},
"preferred_locale": {
"id": 17,
"group": "core",
"label": "Preferred Locale",
"alias": "preferred_locale",
"type": "locale",
"value": null
},
"timezone": {
"id": 18,
"group": "core",
"label": "mautic.lead.field.timezone",
"alias": "timezone",
"type": "timezone",
"value": null
},
"last_active": {
"id": 19,
"group": "core",
"label": "Date Last Active",
"alias": "last_active",
"type": "datetime",
"value": null
},
"attribution_date": {
"id": 20,
"group": "core",
"label": "Attribution Date",
"alias": "attribution_date",
"type": "datetime",
"value": null
},
"attribution": {
"id": 21,
"group": "core",
"label": "Attribution",
"alias": "attribution",
"type": "number",
"value": null
},
"website": {
"id": 22,
"group": "core",
"label": "Website",
"alias": "website",
"type": "url",
"value": null
}
},
"social": {
"facebook": {
"id": 23,
"group": "social",
"label": "Facebook",
"alias": "facebook",
"type": "text",
"value": null
},
"foursquare": {
"id": 24,
"group": "social",
"label": "Foursquare",
"alias": "foursquare",
"type": "text",
"value": null
},
"googleplus": {
"id": 25,
"group": "social",
"label": "Google+",
"alias": "googleplus",
"type": "text",
"value": null
},
"instagram": {
"id": 26,
"group": "social",
"label": "Instagram",
"alias": "instagram",
"type": "text",
"value": null
},
"linkedin": {
"id": 27,
"group": "social",
"label": "LinkedIn",
"alias": "linkedin",
"type": "text",
"value": null
},
"skype": {
"id": 28,
"group": "social",
"label": "Skype",
"alias": "skype",
"type": "text",
"value": null
},
"twitter": {
"id": 29,
"group": "social",
"label": "Twitter",
"alias": "twitter",
"type": "text",
"value": null
}
},
"personal": [],
"professional": [],
"all": {
"id": 1277,
"title": null,
"firstname": null,
"lastname": null,
"company": null,
"position": null,
"email": null,
"mobile": null,
"phone": null,
"points": null,
"fax": null,
"address1": null,
"address2": null,
"city": null,
"state": null,
"zipcode": null,
"country": null,
"preferred_locale": null,
"timezone": null,
"last_active": null,
"attribution_date": null,
"attribution": null,
"website": null,
"facebook": null,
"foursquare": null,
"googleplus": null,
"instagram": null,
"linkedin": null,
"skype": null,
"twitter": null
}
},
"lastActive": null,
"owner": null,
"ipAddresses": [],
"tags": [],
"utmtags": null,
"stage": null,
"dateIdentified": null,
"preferredProfileImage": null,
"doNotContact": [],
"frequencyRules": []
}
}
This is the response of GET contacts API i guess so i am confused why i am getting GET API response while doing POST request to contact API please help me to figure out this issue.
As you can see in the picture, when you create a new contact along with response status code it returns the properties as well which are similar to "Get Contact" request(as you will get when you get contact by id). So I think as long as your new contact is being created in mautic you shouldn't be worried.

Resources