Cloudkit JS query filterby recordName gives error - cloudkit

Working on a website in which I pass a recordName to a second page via the URL. I see the correct parse of the recordName {data} and then attempt to use it for a query with a filterBy as follows:
var query = { recordType: 'Events',
filterBy: [{
fieldName: 'recordName',
comparator: 'EQUALS',
fieldValue: {value: [{data}]
}
}]
};
return publicDB.performQuery(query).then(function (response) {
if(response.hasErrors) {
console.error(response.errors[0]);
return;
}
var records = response.records;
var numberOfRecords = records.length;
if (numberOfRecords === 0) {
console.error('No matching items');
return;
}
self.events(records);
This approach and other attempts to specify the fieldName as recordName all produce the same error message:
ckErrorCode:"NOT_FOUND"
extensionErrorCode:undefined
reason:"ObjectNotFoundException: no such field recordName"
recordName:undefined
redirectURL:undefined
retryAfter:undefined
serverErrorCode:"NOT_FOUND"
subscriptionID:undefined
uuid:"7ff93475-a22c-4ae2-859f-4a219e0253b1"
zoneID:undefined
message:"ObjectNotFoundException: no such field recordName"
This seems really odd, but perhaps it's something obvious that is easily fixed.
Any suggestions are appreciated.

recordName is a system field and below is how you should query for those:
var query = {
recordType: 'Events',
filterBy: [{
comparator: 'EQUALS',
systemFieldName: 'recordName',
fieldValue: {
value: 'the-name-of-the-record'
}
}]
}
Due to a known bug, you have to add an additional wrapper around recordName:
var query = {
recordType: 'Events,
filterBy: [{
comparator: 'EQUALS',
systemFieldName: 'recordName',
fieldValue: {
value: {
recordName: 'the-name-of-the-record'
}
}
}]
}

Related

Graphql apollo playground - how to add array of strings

tldr: How do I write a mutation in GraphQL playground to add an array of strings when creating a new record in the database
I'm using a MongoDB database for an application. I always have trouble finding documentation for how to write queries and mutations in GraphQL apollo playground. In this example, let's take an example of an athlete. An athlete can win many awards. The awards are just an array of strings. I will use a simple model as an example...
const playerSchema = new Schema({
playerName: {
type: String,
required: true,
},
awards: [{
type: String,
}]
})
const Player = model('Player', playerSchema)
module.exports = Player;
Here is my typeDef for this model with Queries and Mutations
const typeDefs = gql`
type Player{
playerName: String!
awards: [String]
}
type Query {
players: [Player!]
}
type typeDefs {
addPlayer:(playerName: String!, awards:[String]
}
}`;
module.exports = typeDefs;
Here is my resolvers for this model
const resolvers = {
Query: {
players: async () => {
return await Player.find(populate('player');
}
Mutation: {
addPlayer: async( parent, {playerName, awards}) => {
return await Player.create({playerName, awards})
}
}
module.exports = resolvers;
Now, I start the server and go to GraphQL playground in the browser. I cannot add an array of strings for the awards. How do I write this query in GraphQL playground? Here is an example of my best attempt:
mutation addPlayer($playerName: String!, $awards:[String]){
addPlayer(playerName:$playerName, awards:$awards){
playerName
awards
}
}
and finally my query variables for this mutation
{
"playerName": "Michael Jordan",
"awards": ["Most Valuable Player", "Rookie of the Year", "Scoring Champion"]
}
If I run a query in GraphQL to see what players exist in the database:
query players{
players{
playerName
awards
}
}
This is the results. Why is the 'awards' array empty??
{
"data": {
"players": [
{
"playerName": "Michael Jordan",
"awards": [], //EMPTY ARRAY HERE, WHY?
}
]
}
}

The method findOneAndUpdate change the id of my element in a array

I'm working with mongoDB, mongoose and graphQL. I'm trying to make an update in my DB.
I'm doing an update in an array called phones, the changes work perfectly, the only problem is that when the update ends, the value of the objectId changes.
// Models -> Schema Organization
const organizationSchema = new mongoose.Schema({
name: String,
address: String,
phones: [
{
number: Number,
prefix: Number
}
],
email: String
})
// Types -> Organization
type Response {
success: Boolean!
token: String
errors: [Error]
}
type Error {
path: String!
message: String!
}
input iOrganization {
_id: ID
arrID: ID
address: String
email: String
number: Int
prefix: Int
name: String
}
type Mutation {
updateOrgGeneric(iOrg: iOrganization): Response!
}
// Resolvers -> Organization (1st way)
Mutation: {
updateOrgGeneric: (parent, args, {models}) => {
return models.Organization.findOneAndUpdate(
{ "_id": args.iOrg._id, "phones._id": args.iOrg.arrID },
{ $set: { "phones.$": { number: args.iOrg.number, prefix: args.iOrg.prefix }} },
{new: true}
)
.then((resp) => {
console.log(resp);
return {
success: true,
errors: []
}
})
.catch((error) => {
return {
success: false,
errors: error
};
})
},
}
// Resolvers -> Organization (2nd way)
Mutation: {
updateOrgGeneric: (parent, args, {models}) => {
return models.Organization.findOneAndUpdate(
{ "_id": args.iOrg._id },
{ $set: { "phones.$[arr]": { number: args.iOrg.number, prefix: args.iOrg.prefix }} },
{new: true}
{ arrayFilters:[{ "arr._id": mongoose.Types.ObjectId(args.iOrg.arrID) }], new: true}
)
.then((resp) => {
console.log(resp);
return {
success: true,
errors: []
}
})
.catch((error) => {
return {
success: false,
errors: error
};
})
}
}
// Playground (http://localhost:5000/graphql)
mutation {
updateOrgGeneric(
iOrg: {
_id: "5bdbee1b794b972bc8562aeb"
arrID: "5bdcea7cae88be098c020b19"
number: 85239,
prefix: 862
}
){
success
errors {
path
message
}
}
}
Both _id, as arrID, exist in the BD.
In the playground example the initial arrID was: _id:ObjectId("5bdcea7cae88be098c020b19"), but after the update is another, example: _id:ObjectId("5bdcec0a2ab78533b4bd1d98"). What am I doing wrong?
Thank you!
Mongodb is a nosql database which means that every object in the database should consist of an Id and revision values. Once an update occurs the revision value changes as part of the update process to implement the changes made to the data object. Since your data object don't have the revision value then the id value changes. Because it is unique. Now I'm no expert with mongo but you should check the docs on how to persist data objects and change accordingly
In case anyone lands here (despite this being old post), the problem probably lies in trying to update the entire phones object, of which the overwritten _id is a part. Since there's a model defined for phonesin mongoose, it will try to create a new _id any time an entire new phones object is created.
Someone who wanted to keep the same id would need to $set only the fields they want to change, rather than the entire object. So
{ $set: { "phones.$[arr]": { number: args.iOrg.number, prefix: args.iOrg.prefix }} }
could be changed to
{ $set: { "phones.$[arr].number": args.iOrg.number, "phones.$[arr].prefix": args.iOrg.prefix } }

MongoDB Document Validation in Meteor?

How would one approach doing this (https://docs.mongodb.com/v3.2/core/document-validation/):
db.createCollection( "contacts",
{ validator: { $or:
[
{ phone: { $type: "string" } },
{ email: { $regex: /#mongodb\.com$/ } },
{ status: { $in: [ "Unknown", "Incomplete" ] } }
]
}
} )
In this:
// database.js
import { Mongo } from 'meteor/mongo';
export const Test = new Mongo.Collection('Test');
Thanks
you first need to define your schema in meteor.
Lists.schema = new SimpleSchema({
name: {type: String},
incompleteCount: {type: Number, defaultValue: 0},
userId: {type: String, regEx: SimpleSchema.RegEx.Id, optional: true}
});
This example defines a schema with a few simple rules:
We specify that the name field of a list is required and must be a
string.
We specify the incompleteCount is a number, which on insertion is
set to 0 if not otherwise specified.
We specify that the userId, which is optional, must be a string that
looks like the ID of a user document.
It’s pretty straightforward to validate a document with a schema. We can write:
const list = {
name: 'My list',
incompleteCount: 3
};
Lists.schema.validate(list);
In this case, as the list is valid according to the schema, the validate() line will run without problems. If however, we wrote:
const list = {
name: 'My list',
incompleteCount: 3,
madeUpField: 'this should not be here'
};
Lists.schema.validate(list);
Then the validate() call will throw a ValidationError which contains details about what is wrong with the list document.

Waterline: How to perform IN queries if attribute is a collection?

In the docs of waterline it is stated that this is the way to perform a IN query on a model:
Model.find({
name : ['Walter', 'Skyler']
});
And this the way to perform an OR query on a model:
Model.find({
or : [
{ name: 'walter' },
{ occupation: 'teacher' }
]
})
My problem now is that i need a combination of those two, and to make it even more complicated, one of the attributes i have to use is a collection.
So what i tried is this, but it doesn't seem to work:
Product.find({
or : [
{ createdBy: userIds },
{ likes: userIds }
]
})
Note: userIds is an array of id's from a user model.
The (simplified) product model looks likes this:
module.exports = {
attributes: {
name: 'string',
description: 'string',
createdBy: {
model: 'User'
},
brand: {
model: 'Brand',
},
likes: {
collection: 'User',
}
}
}
The query works when I only include createdBy, so it seems to be a problem with the collection attribute.
Is this somehow possible?
Thank you for your input.
UPDATE:
I think this is only possible with native() queries.
The way I understand it something like this should work.
Product.native(function(err, products){
if(err) return res.serverError(err);
products.find({"likes": { $elemMatch: { _id: { $in: userIds}}}}).toArray(function(err, results){
if (err){
console.log('ERROR', err);
}
else {
console.log("found products: " + results.length);
console.log(results);
return res.ok(results);
}
});
});
Unfortunately, it doesn't. The returned results is always an empty array.

null results of search by _id in mongoose

I'm getting [] res in mongoose find by {parentId: cat._id}
var ObjectId = Schema.ObjectId;
var CategorySchema = new Schema({
name: String,
slug: String,
parentId: {type: ObjectId, required: false},
ancestors: {
type: [{
_id: ObjectId,
name: String,
slug: String
}], required: false
}
});
CategorySchema.statics.getNested = function(parentSlug,cb){
this.findOne({slug:parentSlug},function(err,cat){
if (err) {
cb(err);
} else {
this.find({parentId: cat._id},function(err, cats){
console.log(cats);
if (err){
cb(err);
} else {
cb(null,cats);
}
});
}
});
};
I tried {parentId: ObjectId(cat._id)} but this did not work too // ObjectId(cat._id) -> undefined
How do I search mongoose by _id?
UPDATE!
The query
Category.find({parentId:'5634eeb38a33a59c1dffa6ee'}, function(err,res){
console.log(res);
});
is working fine but how?
It should be {parentId: mongoose.Types.ObjectId(cat._id)}
You have incorrect ObjectId type in your schema, you should use Schema.Types.ObjectId instead of Schema.ObjectId because they return different values:
http://mongoosejs.com/docs/api.html#schema-objectid-js
http://mongoosejs.com/docs/api.html#types-objectid-js
If you replace your ObjectId definition to the following
var ObjectId = Schema.Types.ObjectId;
your code should work correctly.