如何在 Python 中键入提示嵌套对象? [英] How can I type-hint a nested object in Python?
问题描述
我目前正在与 WSDL 进行集成,因此决定使用 Zeep 库与 Python 一起使用.
I'm currently doing a integration with WSDL, and such decided to go with Python using the Zeep library.
我正在尝试使用 mypy
对响应进行建模,以便它可以与 VSCode 的 Intellisense 配合使用,并且在我进行粗心的分配或修改时会给出一些提示.但是,当 WSDL 响应位于嵌套对象中时,我遇到了障碍,而且我无法找到对其进行类型提示的方法.
I'm trying to model the response with mypy
, so that it works with VSCode's Intellisense, as well as some giving me hints when I'm doing careless assignments or modifications. But I hit a roadblock when the WSDL responses is in a nested object, and I can't figure a way to type-hint it.
来自 WSDL 的示例响应:
Sample response from WSDL:
{
'result': {
'code': '1',
'description': 'Success',
'errorUUID': None
},
'accounts': {
'accounts': [
{
'accountId': 1,
'accountName': 'Ming',
'availableCredit': 1
}
]
}
}
我正在使用以下代码段进行类型提示:
I'm using the following snippet to type-hint:
class MethodResultType:
code: str
description: str
errorUUID: str
class AccountType:
accountId: int
accountName: str
availableCredit: float
class getAccounts:
result: MethodResultType
accounts: List[AccountType] # Attempt 1
accounts = TypedDict("accounts", {"accounts": List[AccountType]}) # Attempt 2
client = Client(os.getenv("API_URL"), wsse=user_name_token)
accountsResponse: getAccounts = client.service.getAccounts()
accounts = accountsResponse.accounts.accounts
# Attempt 1: "List[AccountType]" has no attribute "accounts"; maybe "count"?
# Attempt 2: "Type[accounts]" has no attribute "accounts"
对于尝试 1,原因很明显.但是在尝试了尝试 2 之后,我不知道如何继续了.我在这里错过了什么?
For Attempt 1, the reason is obvious. But after trying Attempt 2, I don't know how to proceed anymore. What am I missing here?
更新:按照@Avi Kaminetzky 的 answer,我尝试了以下 (游乐场):
Update: Following @Avi Kaminetzky's answer, I tried with following (playground):
from typing import List, TypedDict, Optional, Dict
class MethodResultType(TypedDict):
code: str
description: str
errorUUID: Optional[str]
class AccountType(TypedDict):
accountId: int
accountName: str
availableCredit: float
class getAccounts(TypedDict):
result: MethodResultType
accounts: Dict[str, List[AccountType]]
result: getAccounts = {
'result': {
'code': '1',
'description': 'Success',
'errorUUID': None
},
'accounts': {
'accounts': [
{
'accountId': 1,
'accountName': 'Ming',
'availableCredit': 1
}
]
}
}
print(result.result)
print(result.accounts)
但是我从 mypy 收到错误消息:
But I'm getting error message from mypy:
"getAccounts" has no attribute "result"
"getAccounts" has no attribute "accounts"
推荐答案
使用此 answer 作为参考,以下内容适用于我case(VSCode 中的智能感知,如果直接赋值给变量则不起作用):
Using this answer as reference, the following works for my case (Intellisense in VSCode, not working if directly assign into a variable):
更新:使用另一个 answer 作为参考,我已经更新了我的代码,以便能够以两种方式工作.(VSCode中的Intellisense,直接赋值给一个变量)
Update: Using another answer as reference, I have updated my code to be able to work both ways. (Intellisense in VSCode, directly assign into a variable)
class MethodResultType:
code: str
description: str
errorUUID: str
class AccountType:
accountId: int
accountName: str
availableCredit: float
class accounts:
accounts: List[AccountType]
class getAccounts:
def __init__(self):
self.accounts = accounts()
result: MethodResultType
@property
def accounts(self):
return self.accounts
client = Client(os.getenv("API_URL"), wsse=user_name_token)
# Getting real response from WSDL
accountsResponse: getAccounts = client.service.getAccounts()
# For testing using sample response
sampleResponse: getAccounts = getAccounts({
'result': {
'code': '1',
'description': 'Success',
'errorUUID': None
},
'accounts': {
'accounts': [
{
'accountId': 1,
'accountName': 'Ming',
'availableCredit': 1
}
]
}
})
这篇关于如何在 Python 中键入提示嵌套对象?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!