I have the following answer from sync :
When i use the google home mini or simulator and say set the fan to low, I receive that device doesnt support that. Can anybody help me ? Documentation seems the problem
{
id: '123',
type: 'action.devices.types.FAN',
traits: [
'action.devices.traits.FanSpeed',
'action.devices.traits.OnOff'
],
name: {
defaultNames: ['Sirius Cybernetics Corporation 33321'],
name: 'Fan',
nicknames: ['wall fan']
},
willReportState: true,
attributes: {
availableFanSpeeds: {
speeds: [{
speed_name: 'Low',
speed_values: [{
speed_synonym: ['low', 'slow'],
lang: 'en'
}, {
speed_synonym: ['low', 'slow'],
lang: 'de'
}]
}, {
speed_name: 'High',
speed_values: [{
speed_synonym: ['high'],
lang: 'en'
}, {
speed_synonym: ['high'],
lang: 'de'
}]
}],
},
reversible: true
},
deviceInfo: {
manufacturer: 'Sirius Cybernetics Corporation',
model: '492134',
hwVersion: '3.2',
swVersion: '11.4'
},
}
EDIT:
I forgot to say that on off work well..
You are missing the attribute 'ordered' See below
attributes: {
availableFanSpeeds: {
speeds: [{
speed_name: 'Low',
speed_values: [{
speed_synonym: ['low', 'slow'],
lang: 'en'
}, {
speed_synonym: ['low', 'slow'],
lang: 'de'
}]
}, {
speed_name: 'High',
speed_values: [{
speed_synonym: ['high'],
lang: 'en'
}, {
speed_synonym: ['high'],
lang: 'de'
}]
}],
'ordered':true
},
reversible: true
}
Related
I've been trying to get my Google Actions Smart Home (nodejs) working in AWS lambda. However it isn't working. Whenever I connect it on the Google Home app, I just get a message of "Couldn't update the setting...". I've already configured the API gateway correctly and set the Handler to "index.smarthome" as shown in the below image link. Why isn't it working, and how can I get my lambda google action smart home working?
Image Link
My firebase version is working though (modified from the washing machine example at https://codelabs.developers.google.com/codelabs/smarthome-washer/#2).
const functions = require('firebase-functions');
const {smarthome} = require('actions-on-google');
const app = smarthome();
app.onSync(body => {
return {
requestId: 'ff36a3cc-ec34-11e6-b1a0-64510650abcf',
payload: {
agentUserId: '123',
devices: [{
id: 'washer',
type: 'action.devices.types.WASHER',
traits: [
'action.devices.traits.OnOff',
'action.devices.traits.StartStop',
'action.devices.traits.RunCycle',
'action.devices.traits.Modes',
'action.devices.traits.Toggles',
],
name: {
defaultNames: ['My Washer'],
name: 'Washer',
nicknames: ['Washer']
},
deviceInfo: {
manufacturer: 'Acme Co',
model: 'acme-washer',
hwVersion: '1.0',
swVersion: '1.0.1'
},
attributes: {
pausable: true,
availableModes: [{
name: 'load',
name_values: [{
name_synonym: ['load'],
lang: 'en'
}],
settings: [{
setting_name: 'small',
setting_values: [{
setting_synonym: ['small'],
lang: 'en'
}]
}, {
setting_name: 'large',
setting_values: [{
setting_synonym: ['large'],
lang: 'en'
}]
}],
ordered: true
}],
availableToggles: [{
name: 'Turbo',
name_values: [{
name_synonym: ['turbo'],
lang: 'en'
}]
}]
}
}]
}
};
});
app.onExecute((body) => {
const {requestId} = body;
const payload = {
commands: [{
ids: [],
status: 'SUCCESS',
states: {
online: true,
},
}],
};
for (const input of body.inputs) {
for (const command of input.payload.commands) {
for (const device of command.devices) {
const deviceId = device.id;
payload.commands[0].ids.push(deviceId);
for (const execution of command.execution) {
const execCommand = execution.command;
const {params} = execution;
switch (execCommand) {
case 'action.devices.commands.OnOff':
payload.commands[0].states.on = params.on;
break;
case 'action.devices.commands.StartStop':
payload.commands[0].states.isRunning = params.start;
break;
case 'action.devices.commands.PauseUnpause':
payload.commands[0].states.isPaused = params.pause;
break;
case 'action.devices.commands.SetModes':
break;
case 'action.devices.commands.SetToggles':
break;
}
}
}
}
}
return {
requestId: requestId,
payload: payload,
};
});
exports.smarthome = functions.https.onRequest(app);
And here is the code that I used in my AWS lambda function. I referenced https://github.com/actions-on-google/actions-on-google-nodejs & creating dialogflow v2 project with serverless to make it lambda compatible. The main difference between the lambda and firebase versions is the "exports.smarthome" code.
const {smarthome} = require('actions-on-google');
const app = smarthome();
app.onSync(body => {
return {
requestId: 'ff36a3cc-ec34-11e6-b1a0-64510650abcf',
payload: {
agentUserId: '123',
devices: [{
id: 'washer',
type: 'action.devices.types.WASHER',
traits: [
'action.devices.traits.OnOff',
'action.devices.traits.StartStop',
'action.devices.traits.RunCycle',
'action.devices.traits.Modes',
'action.devices.traits.Toggles',
],
name: {
defaultNames: ['My Washer'],
name: 'Washer',
nicknames: ['Washer']
},
deviceInfo: {
manufacturer: 'Acme Co',
model: 'acme-washer',
hwVersion: '1.0',
swVersion: '1.0.1'
},
attributes: {
pausable: true,
availableModes: [{
name: 'load',
name_values: [{
name_synonym: ['load'],
lang: 'en'
}],
settings: [{
setting_name: 'small',
setting_values: [{
setting_synonym: ['small'],
lang: 'en'
}]
}, {
setting_name: 'large',
setting_values: [{
setting_synonym: ['large'],
lang: 'en'
}]
}],
ordered: true
}],
availableToggles: [{
name: 'Turbo',
name_values: [{
name_synonym: ['turbo'],
lang: 'en'
}]
}]
}
}]
}
};
});
app.onExecute((body) => {
const {requestId} = body;
const payload = {
commands: [{
ids: [],
status: 'SUCCESS',
states: {
online: true,
},
}],
};
for (const input of body.inputs) {
for (const command of input.payload.commands) {
for (const device of command.devices) {
const deviceId = device.id;
payload.commands[0].ids.push(deviceId);
for (const execution of command.execution) {
const execCommand = execution.command;
const {params} = execution;
switch (execCommand) {
case 'action.devices.commands.OnOff':
payload.commands[0].states.on = params.on;
break;
case 'action.devices.commands.StartStop':
payload.commands[0].states.isRunning = params.start;
break;
case 'action.devices.commands.PauseUnpause':
payload.commands[0].states.isPaused = params.pause;
break;
case 'action.devices.commands.SetModes':
break;
case 'action.devices.commands.SetToggles':
break;
}
}
}
}
}
return {
requestId: requestId,
payload: payload,
};
});
exports.smarthome = function(event, context, callback) {
app.handler(event, {})
.then((res) => {
if (res.status != 200) {
callback(null, {
"fulfillmentText": `I got status code: ${res.status}`
});
} else {
callback(null, res.body);
}
}).catch((e) => {
callback(null, {
"fulfillmentText": `There was an error\n${e}`
});
});
};
Check your AWS CloudWatch logs and see what happens when the lambda is called. You can print to stdout in your lambda and have it show up in these logs.
Along with your Cloudwatch logs, you could also have a look at your Stackdriver logs.
I use mongoose. I tried to add models in
ProductController.js:
const student = require('../models/studentModel');.populate('student_list')
but I still get the same result.
productModel.js
{
lectureProductId: {
type: mongoose.Schema.Types.ObjectId,
ref: 'Lecture',
}
}
lectureModel.js
{
task_list: [{
type: mongoose.Schema.Types.ObjectId,
ref: 'task'
}],
student_list: [{
type: mongoose.Schema.Types.ObjectId,
ref: 'student'
}],
teacher: {
type: mongoose.Schema.Types.ObjectId,
ref: 'teacher', required: true,
},
}
productController.js
productModel.find()
.populate('lectureProductId')
.populate('taskProductId')
.then(product => {
res.json({
status: 'success',
message: 'products retrieved successfully',
data: product
});
})
lectureController.js
lectureModel.find()
.populate('teacher')
.populate('task_list')
.populate('student_list')
.then(lecture => {
res.json({
status: 'success',
message: 'Lectures retrieved successfully',
data: lecture,
});
})
When I send request I see :
"lectureProductId": {
"keywords": [ "MATLAB", "BİSECTİON", "NEWTON-RAHSON" ],
"task_list": [ "5d26d617454d23000665421c", "5d26d617454d230006654217", "5d26d617454d23000665421b", "5d26d617454d23000665421a", "5d26d617454d230006654218" ],
"student_list": [ "5d26d615454d230006654206", "5d26d615454d230006654207", "5d26d615454d230006654208", "5d26d615454d23000665420c", "5d26d615454d23000665420d", "5d26d616454d23000665420e", "5d26d616454d23000665420f" ],
"_id": "5d26d617454d230006654221",
"name": "Numerical Analysis",
"programmingLanguages": "MATLAB",
"description": "MATLAB for easy level",
"teacher": "5d26d616454d230006654215", "__v": 0
}
How can I see student_list with other fields?
"student_list": [
"5d26d615454d230006654206",
"5d26d615454d230006654207",
"5d26d615454d230006654208",
"5d26d615454d23000665420c",
"5d26d615454d23000665420d",
"5d26d616454d23000665420e",
"5d26d616454d23000665420f"
]
productModel
.find()
.populate({
path: 'lectureProductId',
model: 'lecture',
populate: { path: 'task_list' },
})
This is answer for my question.
productModel
.find()
.populate({
path: 'id with ref',
model: 'childs model',
populate: { path: 'id with ref in childs model' },
})
I have seen this asked several times, but I haven't found a solution that has worked. I am trying to query a MongoDB using Mongoose .findById and am not getting the expected results. find({id: "..."}) is also not returning anything.
Using find without any parameters displays all of the expected results including id key-value pairs, but I cannot use the id value in the query.
Using mongoose: 5.4.9
const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost/mongo-exercises', { useNewUrlParser: true });
const courseSchema = new mongoose.Schema({
name: String,
author: String,
tags: [String],
date: { type: Date, default: Date.now },
isPublished: Boolean,
price: Number
});
const Course = mongoose.model('Course', courseSchema);
async function getCourses() {
return await Course
.find()
}
async function run() {
const result = await getCourses();
console.log(result);
}
run();
//Return
[ { tags: [ 'react', 'frontend' ],
_id: 5a68fdf95db93f6477053ddd,
date: 2018-01-24T21:43:21.589Z,
name: 'React Course',
author: 'Mosh',
isPublished: false,
__v: 0 },
{ tags: [ 'aspnet', 'backend' ],
_id: 5a68fde3f09ad7646ddec17e,
date: 2018-01-24T21:42:59.605Z,
name: 'ASP.NET MVC Course',
author: 'Mosh',
isPublished: true,
price: 15,
__v: 0 },
{ tags: [ 'node', 'backend' ],
_id: 5a68fe2142ae6a6482c4c9cb,
date: 2018-01-24T21:44:01.075Z,
name: 'Node.js Course by Jack',
author: 'Jack',
isPublished: true,
price: 12,
__v: 0 },
{ tags: [ 'node', 'backend' ],
_id: 5a68fdd7bee8ea64649c2777,
date: 2018-01-24T21:42:47.912Z,
name: 'Node.js Course',
author: 'Mosh',
isPublished: true,
price: 20,
__v: 0 },
{ tags: [ 'node', 'backend' ],
_id: 5a68ff090c553064a218a547,
date: 2018-01-24T21:47:53.128Z,
name: 'Node.js Course by Mary',
author: 'Mary',
isPublished: false,
price: 12,
__v: 0 },
{ tags: [ 'angular', 'frontend' ],
_id: 5a6900fff467be65019a9001,
date: 2018-01-24T21:56:15.353Z,
name: 'Angular Course',
author: 'Mosh',
isPublished: true,
price: 15,
__v: 0 },
{ tags: [ 'express', 'backend' ],
_id: 5a68fdc3615eda645bc6bdec,
date: 2018-01-24T21:42:27.388Z,
name: 'Express.js Course',
author: 'Mosh',
isPublished: true,
price: 10,
__v: 0 } ]
That code verifies I'm connected to the correct database and retrieving real ids. When I modify the getCourses function as shown below, I get null or an empty array depending on whether I use findById or find({id: "..."}).
async function getCourses() {
return await Course
.findById('5a68fdf95db93f6477053ddd')
}
//null
async function getCourses() {
return await Course
.find({ id: '5a68fdf95db93f6477053ddd' })
}
// []
async function getCourses() {
return await Course
.find({ _id: '5a68fdf95db93f6477053ddd' })
}
// []
Any help would be greatly appreciated. Thank you!
EDIT: Showing full find() response.
Upon our discussion as your importing the data from JSON file, So its inserting the _id as string, While finding the document by _id, moognoose automatically converting string to Object.
// Original JSON
{
"_id": "5a68fde3f09ad7646ddec17e",
"tags": [
"aspnet",
"backend"
],
"date": "2018-01-24T21:42:59.605Z",
"name": "ASP.NET MVC Course",
"author": "Mosh",
"isPublished": true,
"price": 15,
"__v": 0
}
Solution 1 :
To insert the _id as in the JSON, change your _id field with $oid as below,
{
"_id": { "$oid": "5a68fde3f09ad7646ddec17e" },
"tags": [
"aspnet",
"backend"
],
"date": "2018-01-24T21:42:59.605Z",
"name": "ASP.NET MVC Course",
"author": "Mosh",
"isPublished": true,
"price": 15,
"__v": 0
}
Solution 2 :
Remove _id from your JSON, MongoDB will generate a _id automatically
{
"tags": [
"aspnet",
"backend"
],
"date": "2018-01-24T21:42:59.605Z",
"name": "ASP.NET MVC Course",
"author": "Mosh",
"isPublished": true,
"price": 15,
"__v": 0
}
Given the architecture below, is there a way that I can query the people collection based on the searchable columns and get back an object such as this?
organization with people: {
_id: "13efdsf31r23rwes"
name: "Name",
wp_slug: "/wordpress-slug/",
type: "Cemetary",
file_name: "something.csv",
columns: [
{ label: "Maiden Name", name: "maiden_name", hidden: false },
{ label: "First Name", name: "first_name", hidden: false },
{ label: "First Pet", name: "first_pet", hidden: true },
],
people: [
{
_id: "13okekdsf12313",
"organization_id": 13efdsf31r23rwes,
"maiden_name": "Gilomen",
"surname": "Black",
"first_name": "Maria",
"first_pet": "Bud the Dog",
"searchable_columns": {
"surname": ["Black", "Gilomen"],
"given": ["Maria"],
}
},
{
_id: "1231sdf1313ewfd",
"organization_id": 13efdsf31r23rwes,
"maiden_name": "Portland",
"surname": "Smith",
"first_name": "Rose",
"first_pet": "Max the Dog",
"searchable_columns": {
"surname": ["Smith", "Portland"],
"given": ["Rose"],
}
},
]
}
Current architecture:
organization document example: {
_id: "13efdsf31r23rwes"
name: "Name",
wp_slug: "/wordpress-slug/",
type: "Cemetary",
file_name: "something.csv",
columns: [
{ label: "Maiden Name", name: "maiden_name", hidden: false },
{ label: "First Name", name: "first_name", hidden: false },
{ label: "First Pet", name: "first_pet", hidden: true },
],
}
people collection: [
{
_id: "13okekdsf12313",
"organization_id": 13efdsf31r23rwes,
"maiden_name": "Gilomen",
"surname": "Black",
"first_name": "Maria",
"first_pet": "Bud the Dog",
"searchable_columns": {
"surname": ["Black", "Gilomen"],
"given": ["Maria"],
}
},
{
_id: "1231sdf1313ewfd",
"organization_id": 13efdsf31r23rwes,
"maiden_name": "Portland",
"surname": "Smith",
"first_name": "Rose",
"first_pet": "Max the Dog",
"searchable_columns": {
"surname": ["Smith", "Portland"],
"given": ["Rose"],
}
},
]
Unfortunately we have hit the 16M document limit when they are stored as a combined document, so I need to do this workaround. Is this possible to do with a straight MongoDB query, or is there no other way than to query twice? There are about 5 million records of people and 500+ organizations. Any help would be appreciated, especially if shown in MongoPHP format.
I was able to workaround the size limitation. Using the "desired structure", I split the intended document into multiple documents of a size under 16M. Using an aggregate query, I was able to combine all of the splits back together.
$documents_with_results = $db->organization_data->aggregate(array(
array( '$match' => $search_column_query),
array( '$unwind' => '$p' ),
array( '$match' => $search_column_query),
array( '$group' => array(
'_id' => '$_id',
'name' => array( '$first' => '$n' ),
'slug' => array( '$first' => '$ws' ),
'people' => array( '$push' => '$p' )
))
));
I am using the Sencha Touch 2.0 KitchenSink example to try to learn some of the basics. I am getting stuck on chained selectfields though.
I am going off the tutorial here but with the different setup I am being thrown off. The code below runs perfectly in the Forms.js file in kitchensink, but I am missing on the actual chainedselect part of it.
EDIT: What I am asking is how to make chained selectfields. I have the datastores and the selectfields in the example code, but not a working chained selectfield from first to second.
Ext.regModel('First', {
idProperty: 'FirstID',
fields: [{
name: 'FirstID',
type: 'int'
}, {
name: 'FirstName',
type: 'string'
}]
});
Ext.regModel('Second', {
idProperty: 'SecondID',
fields: [{
name: 'SecondID',
type: 'int'
},{
name: 'FirstID',
type: 'int'
}, {
name: 'SecondName',
type: 'string'
}]
});
var firstStore = new Ext.data.Store({
model: 'First',
data: [{
FirstID: 1,
FirstName: 'Kenworth'
}, {
FirstID: 2,
FirstName: 'Peterbilt'
}],
autoLoad: true
});
var secondStore = new Ext.data.Store({
model: 'First',
data: [{
SecondID: 1,
FirstID: 1,
SecondName: 'T800'
}, {
SecondID: 2,
FirstID: 1,
SecondName: 'T700'
}, {
SecondID: 3,
FirstID: 1,
SecondName: 'T660'
}, {
SecondID: 4,
FirstID: 1,
SecondName: 'T470'
}],
autoLoad: true
});
Ext.define('Kitchensink.view.Forms', {
extend: 'Ext.tab.Panel',
requires: [
'Ext.form.Panel',
'Ext.form.FieldSet',
'Ext.field.Number',
'Ext.field.Spinner',
'Ext.field.DatePicker',
'Ext.field.Select',
'Ext.field.Hidden'
],
config: {
activeItem: 0,
tabBar: {
// docked: 'bottom',
ui: 'dark',
layout: {
pack: 'center'
}
},
items: [
{
title: 'Basic',
xtype: 'formpanel',
id: 'basicform',
iconCls: 'refresh',
items: [
{
xtype: 'fieldset',
title: 'Enter Data',
instructions: 'Please enter the information above.',
defaults: {
labelWidth: '35%'
},
items: [
{
xtype: 'selectfield',
name: 'firstfield',
label: 'First',
store: firstStore,
displayField: 'FirstName',
valueField: 'FirstID'
}, {
xtype: 'selectfield',
name: 'secondfield',
label: 'Second',
store: secondStore,
displayField: 'SecondName',
valueField: 'SecondID'
}
]
}
]
}
]
},
onFirstChange: function(selectField, value){
var secondSelectField = this.items.get(1);
secondSelectField.store.clearFilter(); // remove the previous filter
// Apply the selected Country's ID as the new Filter
secondSelectField.store.filter('FirstID', value);
// Select the first City in the List if there is one, otherwise set the value to an empty string
var firstValue = secondSelectField.store.getAt(0);
if(firstValue){
secondSelectField.setValue(firstValue.data.SecondID);
} else {
secondSelectField.setValue('');
}
}
});