I have a list of students, for each student, I have to access the address. I will get the student list in pagination. so I used the 'expand' operator to get all students. but I am not able to get the address for each student.
Student List
{
students: [
{
id: 1,
name: 'ABC'
},
{
id: 2,
name: 'XYZ'
}
],
nextPageToken: 'Aqw12'
}
Now using the student's id I have to fetch the address.
Here is my sample code to get the student's list with the rxjs expand operator.
const connection = this.searchStudent(nextPageToken).pipe(
expand((students: StudentsDto) => {
if (students.nextPageToken){
nextPageToken = students.nextPageToken;
return this.searchStudent(nextPageToken);
}else{
return new Observable as Observable<StudentsDto>;
}
})
);
const subscription = connection.subscribe({
next(response: StudentsDto) {
response.students.forEach(async (student: StudentDto) => {
console.log(student);
});
},
error(e) {
console.log(e)
},
complete() {
subscription.unsubscribe();
},
});
Now I am not able to get, what operator should I apply to get the address.
for address, I have implemented API in this.getAddress(studentId) function which return Observables.
Please help,
Thanks.
const connection = this.searchStudent(nextPageToken).pipe(
expand((response: StudentsDto) => {
if (response.nextPageToken){
nextPageToken = response.nextPageToken;
return this.searchStudent(nextPageToken);
}else{
return new Observable as Observable<StudentsDto>;
}
}),
mergeMap((response: StudentsDto) => {
return response.students.map(student => this.getAddress(student.id))
}),
mergeAll(),
);
const subscription = connection.subscribe({
next(response: AddressDto) {
// Perform/save operation on Address object
},
error(e) {
console.log(e)
},
complete() {
subscription.unsubscribe();
},
});
Related
Problem:When I try and send/store data in my database I get this error. Specifically, I am trying to create/save a classroom with student names.
Tech Used:
Prisma/Postgres connected to AWS RDS and Next.js, deployed on Vercel, etc.
Error Message
PrismaClientValidationError: Argument data.classrooms.upsert.0.create.students.connectOrCreate.0.create.school.connect of type schoolWhereUniqueInput needs at least one argument.
Argument data.classrooms.upsert.0.update.students.upsert.0.create.school.connect of type schoolWhereUniqueInput needs at least one argument.
at Document.validate (/var/task/node_modules/#prisma/client/runtime/index.js:29501:20)
at serializationFn (/var/task/node_modules/#prisma/client/runtime/index.js:33060:19)
at runInChildSpan (/var/task/node_modules/#prisma/client/runtime/index.js:22550:12)
at PrismaClient._executeRequest (/var/task/node_modules/#prisma/client/runtime/index.js:33067:31)
at async PrismaClient._request (/var/task/node_modules/#prisma/client/runtime/index.js:32994:16)
at async profile (/var/task/.next/server/pages/api/user/profile.js:175:27)
at async Object.apiResolver (/var/task/node_modules/next/dist/server/api-utils/node.js:366:9)
at async NextNodeServer.runApi (/var/task/node_modules/next/dist/server/next-server.js:481:9)
at async Object.fn (/var/task/node_modules/next/dist/server/next-server.js:735:37)
at async Router.execute (/var/task/node_modules/next/dist/server/router.js:247:36) {
clientVersion: '4.9.0'
}
DB Models with relationships: school (1 to many w/students); students (many to many with classrooms); teachers (one to many with students, many to many with classrooms)
Code/Prisma Query
export default async (req, res) => {
...
classroom.students.forEach((student) => {
const totalStudentPoints = student.rewardsRecieved.reduce(
(totalPoints, reward) => {
return totalPoints + reward.pointValue;
},
0
);
groups[student.group.name] += totalStudentPoints;
});
return { ...classroom, groupsTotalPoints: groups };
});
user.classrooms = newClassrooms;
res.json(user);
} else {
console.log("Could Not Find User");
res.status(401).json({
error: "Not authorized",
});
}
}
if (req.method === "PUT") {
const connectStudents = (shouldUpsert) => {
const students = req.body.students;
return students.map((student) => {
const UNSAFEHASH = md5(student.id);
const studentQuery: any = {
where: {
id: student.id,
},
create: {
id: student.id,
firstName: student.firstName,
lastName: student.lastName,
profilePicture: student.profilePicture,
userKey: UNSAFEHASH,
school: {
connect: {
id: req.body.schoolId,
},
},
group: {
connect: {
id: student.group.id,
},
},
},
};
if (shouldUpsert) {
studentQuery.update = {
firstName: student.firstName,
lastName: student.lastName,
profilePicture: student.profilePicture,
userKey: UNSAFEHASH,
group: {
connect: {
id: student.group.id,
},
},
};
}
return studentQuery;
});
};
try {
const user = await prisma.staff.update({
where: {
id: session.id,
},
data: {
firstName: req.body.firstName,
lastName: req.body.lastName,
classrooms: {
upsert: [
{
where: {
id: req.body.classId || "-1",
},
create: {
// id: req.body.classId,
name: req.body.className,
subject: req.body.classSubject,
students: {
connectOrCreate: connectStudents(false),
},
},
update: {
name: req.body.className,
subject: req.body.classSubject,
students: {
upsert: connectStudents(true),
},
},
},
],
},
},
});
Take a look at the PUT request and the prima.staff.update method more specifically. I was looking at the UPSERT I have there, but I can't figure out what's wrong.
I am getting this error ForeignKeyConstraintViolation { constraint: Index(\"Device\") } whenever i try to run following query.
const _CreatedConnectedToMobile = await Context.Database.ConnectedToMobile.create({ 'data': {} }) <-- creates entry in db with default values.
// Create mobile entry where i am trying to create entry in Account Table, with Connection to Device and ConnectedToMobile Table.
// Account, Device and ConnectedToMobile -> Mobile(Table) by foriegn key.
await Context.DataBase.mobile.create({
'data': {
'number': mobileNumber,
'Account': {
'create': {
'accountType': _accountType,
'activeAs': _accountType,
'accessPin': accessPin
}
},
'Device': {
'connectOrCreate': {
'where': { deviceUniqueId },
'create': { deviceUniqueId }
}
},
'ConnectedToMobile': {
'connect': {
'id': _CreatedConnectedToMobile.id
}
}
}
})
if i try to run serpratly everythings work fine but shortning it causes error why ?
await Context.DataBase.mobile.create({
'data': {
'number': mobileNumber,
'Account': {
'create': {
'accountType': _accountType,
'activeAs': _accountType,
'accessPin': accessPin
}
},
'Device': {
'connectOrCreate': {
'where': { deviceUniqueId }, // you search by unique Id
// when you create you send object of data
'create': { deviceUniqueId } // the issue here you send the unique Id but this object accept all fields in your schema model except the ID because Id will auto generate by id
}
},
'ConnectedToMobile': {
'connect': {
'id': _CreatedConnectedToMobile.id
}
}
}
})
I am trying to delete a post object from a user model, I hold these refrences to the post they have created, this is how I am trying to currently pull the post
userModel.findOneAndUpdate(
{ email: req.query.email, posts: req.query.postid },
// { $pull: { posts: req.query.postid } },
{ $pull: { posts : { number: mongoose.Types.ObjectId(req.query.postid) } }},
{ new: true },
function (error, user) {
if (error) {
res.json("error in /testing backend ===",error)
}
console.log(`Post id ===== ${req.query.postid}`);
console.log(`Email===== ${req.query.email}`);
console.log(`returning user====${user}`)
res.json('Successfully updated user');
}
);
this is how I have created the post
userModel.findOne({ email: req.body.author }, function(error, user) {
const locationURL = req.files.map((item) => item.location);
postModel.create({ ...req.body, image: locationURL }, (error, returnedDocuments) => {
if (error) {
throw new Error(error);
}
user.posts.push({ number: returnedDocuments._id, title: req.body.title, image: locationURL });
user.save((err) => {
console.log(err);
});
});
I originally had only 1 item pushed into the user model, but added a few more items, then I was having issues pulling the object, thanks for your help.
this is from my DB as to my posts array
For an array of objects, you can pull your desired document using the positional operator { "<array>.$" : value }.
{ $pull: { posts.$.number : req.query.postid }}
You can check out the docs on positional operators to learn more.
I'm new to GraphQL. I am wrapping a REST API wiht GraphQL, my problem is that I don't get the
ingredients of restaurant dishes (grandparents), just get the ingredients of a dish (parents) .This is my schema
type Restaurant{
id_restaurant: String
name: String
dishes:[Dish]
}
type Dish{
id_dish: String
name: String
ingredients:[Ingredient]
}
type Ingredient{
id_ingredient: String
name: String
}
type Query{
restaurants: [Restaurant]
dishes: [Dish]
ingredients: [Ingredient]
}
These are my resolvers
const mainURL = `https://my_apy_example`
const resolvers = {
Query: {
restaurants: () => { return fetch(`${mainURL}/restaurants`).then(res => res.json()) },
dishes: () => { return fetch(`${mainURL}/dishes`).then(res => res.json()) },
ingredients: () => { return fetch(`${mainURL}/ingredients`).then(res => res.json()) },
},
Restaurant: {
dishes: parent => {
const { id_restaurant } = parent
return fetch(`${mainURL}/dishes?id_restaurant=${id_restaurant}`).then(res => res.json())
},
},
Dish: {
ingredients: parent => {
const { id_dish } = parent
return fetch(`${mainURL}/ingredients?id_dish=${id_dish}`).then(res => res.json())
},
},
}
I assumed that the Dish resolver also resolved the dishes of Restaurant but I think I need other resolver for this, I was wrong.
This query doesn't show the ingredients
query{
restaurants{
name
dishes{
name
ingredients{
name
}
}
}
}
This query shows the ingredients
query{
dishes{
name
ingredients{
name
}
}
}
}
Any solution?
I am new to falcor data fetching framework. I tried with few example when I request for something like
model.get(["contacts", {0..2}, "name"])
.then(response => {
this.state.list = response.json.contacts;
this.setState(this.state);
});
at server side
let data = {
contacts: [
{name: "ABC"},
{name: "XYZ"},
{name: "PQR"}
]
};
let contactsRouter = Router.createClass([
{
route: 'contacts[{integers:contactIndexes}]',
get: (pathSet) => {
let results = [];
pathSet.contactIndexes.forEach(contactIndex => {
if (data.contacts.length > contactIndex) {
results.push({
path: ["contacts", contactIndex, "name"],
value: data.contacts[contactIndex].name
});
}
});
return results;
}
},
{
route: 'contacts.add',
call: (callPath, args) => {
var newContact = args[0];
data.contacts.push({name: newContact})
return [
{
path: ['contacts', data.contacts.length-1, 'name'],
value: newContact
},
{
path: ['contacts', 'length'],
value: data.contacts.length
}
]
}
}
]);
I'm getting data & able to do other operations too.
My question is I want to do same CRUD operations with MongoDB instead from
data.contacts
how i construct JSON Graph object data should come from database schema. hope my question is cleared.
The simplest way is to simply do a database query inside the route's get function:
{
route: 'contacts[{integers:contactIndexes}]',
get: (pathSet) => {
const data = db.get('myModel', (err, res) => {
return res
})
let results = [];
pathSet.contactIndexes.forEach(contactIndex => {
if (data.contacts.length > contactIndex) {
results.push({
path: ["contacts", contactIndex, "name"],
value: data.contacts[contactIndex].name
});
}
});
return results;
}
}
Made a simple repo using Falcor and CouchDB. It should be enough to understand how it should be done in MongoDB.