我正在使用具有以下结构的界面:
awk 'BEGIN{FS=OFS=","}!/dfg/{$2="00070"}1' file
abc,00070,india
dfg,78910,china
abc,00070,japan
abc,00070,australia
现在,我想创建一个允许任何键的对象,但是该值始终为interface IAsset {
file: string,
type: number
}
类型:
IAsset
我通过实现一种新类型尝试了this answer中概述的方法:
const list = {
bike: {
file: "./meshes/bike.fbx",
type: 0,
},
sky: {
file: "./textures/sky.jpg",
type: 1,
style: "red" // <-- should yield error
}
};
但是我不想使用字符串访问我的元素,例如type AssetList{[key: string], IAsset}
,因为那样的话我可以请求不存在的元素,例如list["bike"]
而不会出错(而且,我也会丢失自动完成功能)。
如何告诉TypeScript该对象中的每个值应为list["apple"]
类型,而没有基于字符串的访问器?
答案 0 :(得分:2)
没有任何一种类型可以表示您要查找的内容:具有已知键的对象类型,其所有属性值均为AWSTemplateFormatVersion : '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: add docs directly from s3
Parameters:
Environment:
Type: String
Default: staging
DocumentMetadataBucketName:
Type: String
DocumentSourceBucketName:
Type: String
DocumentMetadataBucketArn:
Type: String
DocumentSourceBucketArn:
Type: String
Resources:
UploaddirectFunction:
Type: AWS::Serverless::Function
Properties:
FunctionName: !Sub leopro-uploaddirect-function-${Environment}
Handler: uploaddirect.handler
Runtime: nodejs10.x
Timeout: 300
Role: !GetAtt UploaddirectExecutionRole.Arn
Environment:
Variables:
DOCUMENT_METADATA_BUCKET: !Ref DocumentMetadataBucketName
DOCUMENT_SOURCE_BUCKET: !Ref DocumentSourceBucketName
CodeUri: .
UploaddirectExecutionRole:
Type: AWS::IAM::Role
Properties:
RoleName: !Sub leopro-uploaddirect-exec-role-${Environment}
ManagedPolicyArns:
- "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole"
Policies:
-
PolicyName: !Sub leopro-uploaddirect-access-s3-${Environment}
PolicyDocument:
Version: "2012-10-17"
Statement:
-
Effect: "Allow"
Action:
- "s3:GetObject"
- "s3:PutObject"
Resource: 'arn:aws:s3:::*/*'
Statement:
-
Effect: "Allow"
Action:
- "s3:*"
Resource: '*'
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
-
Effect: "Allow"
Principal:
Service:
- "lambda.amazonaws.com"
Action:
- "sts:AssumeRole"
UploaddirectBucket:
Type: AWS::S3::Bucket
Properties:
BucketName: !Sub leopro-uploaddirect-dropbox-bucket-${Environment}
NotificationConfiguration:
LambdaConfigurations:
-
Event: 's3:ObjectCreated:*'
Function: !GetAtt UploaddirectFunction.Arn
UploaddirectBucketPolicy:
Type: AWS::S3::BucketPolicy
Properties:
Bucket: !Ref UploaddirectBucket
PolicyDocument:
Statement:
-
Action:
- "s3:GetObject"
Effect: "Allow"
Resource: !Sub "arn:aws:s3:::leopro-uploaddirect-dropbox-bucket-${Environment}/*"
Principal: "*"
InvokeFromS3Permission:
Type: AWS::Lambda::Permission
Properties:
FunctionName: !GetAtt UploaddirectFunction.Arn
Action: "lambda:InvokeFunction"
Principal: "s3.amazonaws.com"
SourceArn: !Join [ "", [ "arn:aws:s3:::", !Sub "leopro-uploaddirect-dropbox-bucket-${Environment}" ] ]
类型。但是,您可以根据键集IAsset
将其表示为generic类型AssetList<K>
,例如:
K
然后您可以编写type AssetList<K extends PropertyKey> = Record<K, IAsset>;
,但是假设您希望编译器为您推断键,则可以使用辅助函数代替类型注释:
const list: AssertList<"bike"|"sky"> = {...}
并像这样使用它:
const asAssetList = <K extends PropertyKey>(a: AssetList<K>) => a;
如果不注释掉const list = asAssetList({
bike: {
file: "./meshes/bike.fbx",
type: 0,
},
sky: {
file: "./textures/sky.jpg",
type: 1,
// style: "red" // excess property warning here
}
});
,您会得到一个excess property warning的期望值。
然后style: "red"
会确切记住它拥有的键:
list
好的,希望能有所帮助;祝你好运!
答案 1 :(得分:0)
经过一番摸索,我发现Record
方法有点令人费解,而且过于抽象,无法完全掌握。此外,将此变量导入其他文件需要一个怪异的Record<"bike"|"sky", IAsset>
接口,每次我需要添加一个以上元素时,该接口都难以声明和更新。
相反,我只是创建了一个类,并将每个属性声明为其自己的IAsset
类型。现在,我可以轻松地将AssetListClass
与AssetList
一起导入其他文件。
interface IAsset {
file: string,
type: number
}
export class AssetListClass {
bike: IAsset = {
file: "meshes/bike.fbx",
type: 0
};
sky: IAsset = {
file: "./textures/sky.jpg",
type: 1,
}
}
export const AssetList = new AssetListClass();