没有 opts 的 JSData 加载关系
JSData load relations without opts
当通过映射器急切加载关系时,opts
参数会传递给加载的关系。在我的例子中,这打破了 api 。例如:
storyMapper.findAll({ title: 'foobar' }, { with: ['user'] });
这导致两个请求:
GET /stories?title=foobar
GET /users?title=foobar
我可能遗漏了一些东西,但我希望使用定义的关系,以便首先加载故事,它是 userId
字段读取,第二个查询类似于
GET /users/<the id>
或至少
GET /users?where=<id in <the id>>
所以我的问题是;我可以改变它的行为还是我需要在每个故事加载后使用 loadRelations
?
代码示例:
// user schema
import { Schema } from 'js-data';
export const user = new Schema({
$schema: 'http://json-schema.org/draft-04/schema#',
title: 'User',
description: 'Schema for User records',
type: 'object',
properties: {
_id: { type: 'string' },
username: { type: 'string' },
email: { type: 'string' },
password: { type: 'string' },
},
required: ['username', 'email', 'password'],
});
// story schema
import { Schema } from 'js-data';
export const story = new Schema({
$schema: 'http://json-schema.org/draft-04/schema#',
title: 'Story',
description: 'Schema for Story records',
type: 'object',
properties: {
_id: { type: 'string' },
title: { type: 'string', default: '' },
userId: { type: ['string', 'null'] },
username: { type: ['string', 'null'] },
},
required: ['title'],
});
// user mapper
this.store.defineMapper('user', {
mapperClass: ObservableMapper,
recordClass: User,
endpoint: 'users',
idAttribute: '_id',
schema: schemas.user,
relations: relations.user,
})
// story mapper
this.store.defineMapper('story', {
mapperClass: ObservableMapper,
recordClass: Story,
endpoint: 'storys',
idAttribute: '_id',
schema: schemas.story,
relations: relations.story,
})
// user relations
export const user = {
hasMany: {
world: {
foreignKey: 'userId',
localField: 'worlds',
},
},
};
// story relations
export const world = {
belongsTo: {
user: {
foreignKey: 'userId',
localField: 'user',
},
},
};
从 GET /stories?title=foobar
返回的示例数据:
{
"_id": "546e53dcedee82d542000003",
"userId": "526e8617964fd22d2b000001",
"username": "Someone",
"title": "Lorem Ipsum"
}
你错过了 User-Story 关系的另一面:
// user relations
export const user = {
hasMany: {
story: {
foreignKey: 'userId',
localField: 'stories'
},
world: {
foreignKey: 'userId',
localField: 'worlds'
}
}
};
现在,当您实际发出请求时,您有两个选择:
选项 1 - 多个请求
这需要您的服务器理解 "where" 查询字符串参数:
store.findAll('story', { title: 'foobar' }, { with: ['user'] })
这里有一个 plunker 演示:https://plnkr.co/edit/UCFJNg?p=preview
plunker 示例提出两个请求:
GET /stories?title=foobar
GET /users?title=foobar&where={"_id":{"in":[123,234]}}
选项 2 - 单个请求
这需要您的服务器理解 "with" 查询字符串参数:
store.findAll('story', { title: 'foobar' }, { params: { with: ['user'] } })
这里有一个 plunker 演示:https://plnkr.co/edit/M6quP4?p=preview
plunker 示例仅发出一个请求,并期望用户嵌入到服务器响应的故事中:
GET /stories?with=user&title=foobar
备注
这是 HTTP 适配器的一个怪癖。对于所有其他适配器,使用 with
选项会如您所愿,您不必乱用 params
选项。
当通过映射器急切加载关系时,opts
参数会传递给加载的关系。在我的例子中,这打破了 api 。例如:
storyMapper.findAll({ title: 'foobar' }, { with: ['user'] });
这导致两个请求:
GET /stories?title=foobar
GET /users?title=foobar
我可能遗漏了一些东西,但我希望使用定义的关系,以便首先加载故事,它是 userId
字段读取,第二个查询类似于
GET /users/<the id>
或至少
GET /users?where=<id in <the id>>
所以我的问题是;我可以改变它的行为还是我需要在每个故事加载后使用 loadRelations
?
代码示例:
// user schema
import { Schema } from 'js-data';
export const user = new Schema({
$schema: 'http://json-schema.org/draft-04/schema#',
title: 'User',
description: 'Schema for User records',
type: 'object',
properties: {
_id: { type: 'string' },
username: { type: 'string' },
email: { type: 'string' },
password: { type: 'string' },
},
required: ['username', 'email', 'password'],
});
// story schema
import { Schema } from 'js-data';
export const story = new Schema({
$schema: 'http://json-schema.org/draft-04/schema#',
title: 'Story',
description: 'Schema for Story records',
type: 'object',
properties: {
_id: { type: 'string' },
title: { type: 'string', default: '' },
userId: { type: ['string', 'null'] },
username: { type: ['string', 'null'] },
},
required: ['title'],
});
// user mapper
this.store.defineMapper('user', {
mapperClass: ObservableMapper,
recordClass: User,
endpoint: 'users',
idAttribute: '_id',
schema: schemas.user,
relations: relations.user,
})
// story mapper
this.store.defineMapper('story', {
mapperClass: ObservableMapper,
recordClass: Story,
endpoint: 'storys',
idAttribute: '_id',
schema: schemas.story,
relations: relations.story,
})
// user relations
export const user = {
hasMany: {
world: {
foreignKey: 'userId',
localField: 'worlds',
},
},
};
// story relations
export const world = {
belongsTo: {
user: {
foreignKey: 'userId',
localField: 'user',
},
},
};
从 GET /stories?title=foobar
返回的示例数据:
{
"_id": "546e53dcedee82d542000003",
"userId": "526e8617964fd22d2b000001",
"username": "Someone",
"title": "Lorem Ipsum"
}
你错过了 User-Story 关系的另一面:
// user relations
export const user = {
hasMany: {
story: {
foreignKey: 'userId',
localField: 'stories'
},
world: {
foreignKey: 'userId',
localField: 'worlds'
}
}
};
现在,当您实际发出请求时,您有两个选择:
选项 1 - 多个请求
这需要您的服务器理解 "where" 查询字符串参数:
store.findAll('story', { title: 'foobar' }, { with: ['user'] })
这里有一个 plunker 演示:https://plnkr.co/edit/UCFJNg?p=preview
plunker 示例提出两个请求:
GET /stories?title=foobar
GET /users?title=foobar&where={"_id":{"in":[123,234]}}
选项 2 - 单个请求
这需要您的服务器理解 "with" 查询字符串参数:
store.findAll('story', { title: 'foobar' }, { params: { with: ['user'] } })
这里有一个 plunker 演示:https://plnkr.co/edit/M6quP4?p=preview
plunker 示例仅发出一个请求,并期望用户嵌入到服务器响应的故事中:
GET /stories?with=user&title=foobar
备注
这是 HTTP 适配器的一个怪癖。对于所有其他适配器,使用 with
选项会如您所愿,您不必乱用 params
选项。