用户在使用 Sequelize 之前是否喜欢 post
Has the user liked the post before or not using Sequelize
目前,当用户喜欢 post 时,该喜欢的记录会添加到我的喜欢 table 中,其中包含用户 ID 和 postId。
现在,当用户查看 post 时,我想确定他们之前是否喜欢 post。我明白要这样做,我需要在调用 post 信息时在 get 请求中确定这一点。
当我要求 post 信息时,我需要检查 Likes table 以获取当前用户的 userId 和当前 postId 的记录 post。如果存在,那么我需要 return 一个名为 isLiked 的参数并将其设置为 true,如果不存在,则 isLiked=false。
这是我的 Post 模型:
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true,
},
title: {
type: Sequelize.STRING,
},
userId: {
type: Sequelize.INTEGER,
},
likesCount:{
type:Sequelize.INTEGER,
defaultValue:0,
validate: {
min: 0,
}
},
这是我的点赞模型:
id: {
allowNull: false,
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER,
},
PostId: {
type: Sequelize.INTEGER,
references: {
model: "Post",
key: "id",
},
},
userId: {
type: Sequelize.INTEGER,
references: {
model: "User",
key: "id",
},
},
这是我的用户模型:
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true,
},
name: {
type: Sequelize.STRING,
},
这是我的联想:
User.hasMany(Post, { foreignKey: "userId" });
Post.belongsTo(User, { foreignKey: "userId" });
Post.hasMany(Likes, { foreignKey: "PostId", targetKey: "id" });
Likes.belongsTo(Post, { foreignKey: "PostId", targetKey: "id" });
User.hasMany(Likes, { foreignKey: "userId", targetKey: "id" });
Likes.belongsTo(User, { foreignKey: "userId", targetKey: "id" });
更新
我一直在研究并发现,因为我正在使用 JWT 中间件来签署我的用户令牌,并且我目前正在检查当前用户是否有类似 table 的任何记录,我尝试了以下但有人可以告诉我这种方法是否正确吗?
router.get("/", async (req, res) => {
const posts = await Post.findAll({
order: [["createdAt", "DESC"]],
include: [
{ model: Post_Image, attributes: ["id", "images"] },
{ model: Likes, attributes: ["id", "PostId", "userId"] },
],
});
if (!posts) return res.status(404).send();
const baseUrl = config.get("assetsBaseUrl");
const plainPosts = posts.map((x) => x.get({ plain: true }));
const resultPosts = [];
for (const post of plainPosts) {
let isLiked = false;
let like = await Likes.findOne({
where: {
[Op.and]: [{ PostId: post.id) }, { userId:
req.user.id }],
},
});
if (like) isLiked = true;
const { Post_Images, ...postAttributes } = post;
const IMAGES = Post_Images.map((postImage) => ({
url: `${baseUrl}${postImage.images}_full.jpg`,
thumbnailUrl: `${baseUrl}${postImage.images}_thumb.jpg`,
}));
resultPosts.push({ ...postAttributes, images: IMAGES, isLiked
});
}
res.send( resultPosts );
});
除非您想覆盖某些内容,否则您不需要指定所有字段,否则 Sequelize 可以为您生成大部分列。
const User = sequelize.define(
'user',
{
name: {
type: Sequelize.STRING,
},
},
{ /* options */ }
);
const Post = sequelize.define(
'post',
{
title: {
type: Sequelize.STRING,
},
},
{ /* options */ }
);
// the join table so you can reference it, but doesn't need any columns including primary key (unless you want to a "super join")
const Likes = sequelize.define(
'likes',
{}, // no columns here
{ /* options */ }
);
创建模型之间的关联将自动创建大部分外键字段。在 Likes
关系上使用 through
关键字使其成为多对多关系。
// Users can have many Posts
User.hasMany(Post);
// Posts belong to one User
Post.belongsTo(User);
// Users can like more than one Post through the `likes` join table
User.hasMany(Post, { as: 'likes', through: 'likes' });
// Posts can be liked by more than one User through the `likes` join table
Post.hasMany(User, { as: 'likes', through: 'likes' });
不需要存储点赞数,因为可以通过join table.
汇总
// Get the 'likes' count for a Post, instead of saving it on the post
const posts = await Post.findAll({
attributes: {
include: [
[sequelize.fn('COUNT', sequelize.col('likes.userId')), 'likesCount'],
],
},
include: [
{
model: User,
as: 'likes',
though: 'likes',
attributes: [],
required: false,
},
],
});
// `posts` will be an array of Post instances that have a likesCount property
posts.forEach((post) => {
console.log(`The post ${post.title} has ${post.likesCount} likes.`);
});
对于个人(或多个)Post,您可以通过 post 获得喜欢它的用户列表(或使用 Like
模型及其关系) .
// Get the user 'likes' for a Post
const post = await Post.findByPk(postId, {
include: [
{
model: User,
as: 'likes',
though: 'likes',
required: false,
},
],
});
post.likes.forEach((like) => {
console.log(`The user ${like.name} has liked the post ${post.title}.`);
});
你不需要再次请求Like
,你已经得到了所有post的赞:
for (const post of plainPosts) {
// check if we have any like among posts' likes that is made by a certain user
const isLiked = post.Likes.some(x => x.userId === req.user.id);
const { Post_Images, ...postAttributes } = post;
...
目前,当用户喜欢 post 时,该喜欢的记录会添加到我的喜欢 table 中,其中包含用户 ID 和 postId。
现在,当用户查看 post 时,我想确定他们之前是否喜欢 post。我明白要这样做,我需要在调用 post 信息时在 get 请求中确定这一点。
当我要求 post 信息时,我需要检查 Likes table 以获取当前用户的 userId 和当前 postId 的记录 post。如果存在,那么我需要 return 一个名为 isLiked 的参数并将其设置为 true,如果不存在,则 isLiked=false。
这是我的 Post 模型:
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true,
},
title: {
type: Sequelize.STRING,
},
userId: {
type: Sequelize.INTEGER,
},
likesCount:{
type:Sequelize.INTEGER,
defaultValue:0,
validate: {
min: 0,
}
},
这是我的点赞模型:
id: {
allowNull: false,
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER,
},
PostId: {
type: Sequelize.INTEGER,
references: {
model: "Post",
key: "id",
},
},
userId: {
type: Sequelize.INTEGER,
references: {
model: "User",
key: "id",
},
},
这是我的用户模型:
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true,
},
name: {
type: Sequelize.STRING,
},
这是我的联想:
User.hasMany(Post, { foreignKey: "userId" });
Post.belongsTo(User, { foreignKey: "userId" });
Post.hasMany(Likes, { foreignKey: "PostId", targetKey: "id" });
Likes.belongsTo(Post, { foreignKey: "PostId", targetKey: "id" });
User.hasMany(Likes, { foreignKey: "userId", targetKey: "id" });
Likes.belongsTo(User, { foreignKey: "userId", targetKey: "id" });
更新
我一直在研究并发现,因为我正在使用 JWT 中间件来签署我的用户令牌,并且我目前正在检查当前用户是否有类似 table 的任何记录,我尝试了以下但有人可以告诉我这种方法是否正确吗?
router.get("/", async (req, res) => {
const posts = await Post.findAll({
order: [["createdAt", "DESC"]],
include: [
{ model: Post_Image, attributes: ["id", "images"] },
{ model: Likes, attributes: ["id", "PostId", "userId"] },
],
});
if (!posts) return res.status(404).send();
const baseUrl = config.get("assetsBaseUrl");
const plainPosts = posts.map((x) => x.get({ plain: true }));
const resultPosts = [];
for (const post of plainPosts) {
let isLiked = false;
let like = await Likes.findOne({
where: {
[Op.and]: [{ PostId: post.id) }, { userId:
req.user.id }],
},
});
if (like) isLiked = true;
const { Post_Images, ...postAttributes } = post;
const IMAGES = Post_Images.map((postImage) => ({
url: `${baseUrl}${postImage.images}_full.jpg`,
thumbnailUrl: `${baseUrl}${postImage.images}_thumb.jpg`,
}));
resultPosts.push({ ...postAttributes, images: IMAGES, isLiked
});
}
res.send( resultPosts );
});
除非您想覆盖某些内容,否则您不需要指定所有字段,否则 Sequelize 可以为您生成大部分列。
const User = sequelize.define(
'user',
{
name: {
type: Sequelize.STRING,
},
},
{ /* options */ }
);
const Post = sequelize.define(
'post',
{
title: {
type: Sequelize.STRING,
},
},
{ /* options */ }
);
// the join table so you can reference it, but doesn't need any columns including primary key (unless you want to a "super join")
const Likes = sequelize.define(
'likes',
{}, // no columns here
{ /* options */ }
);
创建模型之间的关联将自动创建大部分外键字段。在 Likes
关系上使用 through
关键字使其成为多对多关系。
// Users can have many Posts
User.hasMany(Post);
// Posts belong to one User
Post.belongsTo(User);
// Users can like more than one Post through the `likes` join table
User.hasMany(Post, { as: 'likes', through: 'likes' });
// Posts can be liked by more than one User through the `likes` join table
Post.hasMany(User, { as: 'likes', through: 'likes' });
不需要存储点赞数,因为可以通过join table.
汇总// Get the 'likes' count for a Post, instead of saving it on the post
const posts = await Post.findAll({
attributes: {
include: [
[sequelize.fn('COUNT', sequelize.col('likes.userId')), 'likesCount'],
],
},
include: [
{
model: User,
as: 'likes',
though: 'likes',
attributes: [],
required: false,
},
],
});
// `posts` will be an array of Post instances that have a likesCount property
posts.forEach((post) => {
console.log(`The post ${post.title} has ${post.likesCount} likes.`);
});
对于个人(或多个)Post,您可以通过 post 获得喜欢它的用户列表(或使用 Like
模型及其关系) .
// Get the user 'likes' for a Post
const post = await Post.findByPk(postId, {
include: [
{
model: User,
as: 'likes',
though: 'likes',
required: false,
},
],
});
post.likes.forEach((like) => {
console.log(`The user ${like.name} has liked the post ${post.title}.`);
});
你不需要再次请求Like
,你已经得到了所有post的赞:
for (const post of plainPosts) {
// check if we have any like among posts' likes that is made by a certain user
const isLiked = post.Likes.some(x => x.userId === req.user.id);
const { Post_Images, ...postAttributes } = post;
...