我为ASP.NET MVC结构写了类似的基础,并在github(express-mvc)上发布了。一切正常,但我无法在body
对象内强制转换request
以适应任何接口。
这正是我想要的:
export default interface Post {
title: string
body: string
}
import Post from '@models/user'
router.post("/post", (req: Request, res: Response) => {
const Model: Post = req.body
})
但是在运行时没有接口,因为JavaScript没有接口。当我使用它时,将以JavaScript输出
const Model;
Model = req.body
那样的话,它将接口的非成员属性分配给我的变量。
简而言之,我想在Model
变量中知道接口的属性。
我正在使用解构技术暂时解决该项目中的问题
import Post from '@models/user'
router.post("/post", (req: Request, res: Response) => {
const { title, body }: Post = req.body
const Model: Post = <Post>{
title,
body
};
})
您有什么建议
function castByBody<Model>(source: {}, modelProperties: any[]): Partial<Model> {
const post: Partial<Model> = {};
for (const key of modelProperties) {
post[key] = source[key];
}
return post;
}
class User {
public first_name: string = null
public username: string = null
public email: string = null
public password: string = null
public age: number = null
}
let user = new User() // create new instance
let userProperties: any[] = Object.getOwnPropertyNames(user) // get all properties from instance
const reqBody = {
first_name: "afulsamet",
username: "aful",
email: "afulsamet@gmail.com",
password: "333222233",
title: "member",
age: 18
} // user instance does not have title property
const model: Partial<User> = castByBody<User>(reqBody, userProperties);
console.log(model)
输出将与控制台中的一样
{
age: 18
email: "afulsamet@gmail.com"
first_name: "afulsamet"
password: "333222233"
username: "aful"
}
答案 0 :(得分:2)
那样的话,它将接口的非成员属性分配给我的变量。
如果您不希望这样做,则不能使用强制转换(它不是真正的强制转换,在TypeScript中称为 type assertion )。您必须创建一个新对象。
您可以通过解构来实现此目的,尽管您可以通过更快地(在参数列表中)使其变得不那么笨拙,并且不需要其类型断言,但TypeScript会看到您分配的是可以接受的:
router.post("/post", ({body: { title, body }}, res: Response) => {
const Model: Post = {
title,
body
};
})
根据类型信息自动执行此操作(无需键入title
和body
)将需要TypeScript提供运行时类型信息,currently outside TypeScript's goals(尽管这通常是-要求的功能)。
当然,不必破坏结构。您可能有一个属性名称数组(TypeScript不会给您提供),可能在类型旁边定义了该属性名称,并使用了它:
const PostKeys = ["title", "body"];
然后
router.post("/post", ({body}, res: Response) => {
const Model: {} as Post;
for (const key of PostKeys) {
Model[key] = body[key];
}
})
也许甚至使它成为可重用的功能
function createPost(source: any): Post {
const post: {} as Post;
for (const key of PostKeys) {
post[key] = source[key];
}
return post;
}
然后
router.post("/post", ({body}, res: Response) => {
const Model: createPost(body);
})