首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >在Create方法中无法识别的扩展值

在Create方法中无法识别的扩展值
EN

Stack Overflow用户
提问于 2022-05-06 22:55:39
回答 2查看 49关注 0票数 0

Deno具有全局可用的sessionStorage,这就是我正在使用的内存数据库。

我正在研究一种方法,在sessionStorage创建一个新的博物馆。但是,问题是,我的创建方法只有当我的博物馆类型不扩展记录时才有效。

这是我喜欢的类型:

代码语言:javascript
复制
// I want my Museum type to extend the Record type for the extra type safety
interface Museum extends Record<string, unknown> {
  id: string
  name: string
  description: string
  location: {
    lat: number
    lng: number
  }
  createdAt: Date
  updatedAt?: Date
}

// I'm testing two different NewMuseum types
type NewMuseum = Omit<Museum, "id" | "createdAt" | "updatedAt">
// type NewMuseum = Partial<Museum>

这是我的班级:

代码语言:javascript
复制
export class Repository {
  
  async getList(): Promise<Museum[]> {
    return JSON.parse(sessionStorage.getItem('museums') || '[]') as Museum[]
  }

  async create(museum: NewMuseum): Promise<Museum> {
    const museumList = await this.getList()
    const newMuseum = {
      id: crypto.randomUUID(),
      ...museum,
      createdAt: new Date(),
    }
    museumList.push(newMuseum)
    sessionStorage.setItem('museums', JSON.stringify(museumList))
    
    return newMuseum
  }
}

当我去传播新博物馆的价值时,linter在newMuseum上捕捉到了museumList.push(newMuseum)线上的一个错误。

代码语言:javascript
复制
Argument of type '{ createdAt: Date; id: string; }' is not assignable to parameter of type 'Museum'.deno-ts(2345)

newMuseum没有认识到我在其中传播的价值观。相反,newMuseum应该如下所示:

代码语言:javascript
复制
const newMuseum: {
    createdAt: Date;
    name: string;
    description: string;
    location: {
        lat: number;
        lng: number;
    };
    id: string;
}

如何让newMuseum识别价差值?我是否应该尝试用部分实用程序类型来解决这个问题,而不是忽略呢?

EN

回答 2

Stack Overflow用户

发布于 2022-05-06 23:18:36

把这个newMuseum物体作为博物馆就是其中的诀窍。以下是更新的解决方案:

代码语言:javascript
复制
export class Repository {
  
  async getList(): Promise<Museum[]> {
    return JSON.parse(sessionStorage.getItem('museums') || '[]') as Museum[]
  }

  async create(museum: NewMuseum): Promise<Museum> {
    const museumList = await this.getList()
    const newMuseum = {
      ...museum,
      id: crypto.randomUUID(),
      createdAt: new Date(),
    } as Museum
    museumList.push(newMuseum)
    sessionStorage.setItem('museums', JSON.stringify(museumList))
    
    return newMuseum
  }
}

类型记录并不真正知道spread操作符的类型,所以它假设它不兼容。博物馆告诉打字员“别担心,我相信这是对的。”

对德诺的不和大声呼喊救命!

票数 0
EN

Stack Overflow用户

发布于 2022-05-07 00:04:04

由于NewMuseum不包含这些值,所以您希望在扩展操作中被识别的值不在那里。Omit导致更改了一组键:

代码语言:javascript
复制
type NewMuseum = Omit<Museum, "id" | "createdAt" | "updatedAt">;

决意

代码语言:javascript
复制
type NewMuseum = {
    [x: string]: unknown;
    [x: number]: unknown;
}

而不是

代码语言:javascript
复制
interface NewMuseum extends Record<string, unknown> {
  name: string;
  description: string;
  location: {
    lat: number;
    lng: number;
  };
}

因此,在尝试传播NewMuseum之前,这些键的类型信息已经丢失。

您可以考虑通过像Omit这样的实用程序来组合您的类型,而不是计算类型。

例如:

代码语言:javascript
复制
type MuseumData = Record<string, unknown> & {
  name: string;
  description: string;
  location: {
    lat: number;
    lng: number;
  };
};

type MuseumMetadata = {
  id: string;
  createdAt: Date;
  updatedAt?: Date;
};

type Museum = MuseumData & MuseumMetadata;

type NewMuseum = MuseumData;
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72148135

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档