[python/sdk] - Correctly handle outputs with properties named "values" (#6264)
Co-authored-by: Justin Van Patten <jvp@justinvp.com>
This commit is contained in:
parent
3a3b96de72
commit
f374b8a953
|
@ -6,6 +6,9 @@ CHANGELOG
|
|||
- [sdk/python] Gracefully handle monitor shutdown in the python runtime without exiting the process.
|
||||
[#6249](https://github.com/pulumi/pulumi/pull/6249)
|
||||
|
||||
- [sdk/python] Fix a bug in `contains_unknowns` where outputs with a property named "values" failed with a TypeError.
|
||||
[#6264](https://github.com/pulumi/pulumi/pull/6264)
|
||||
|
||||
## 2.20.0 (2021-02-03)
|
||||
|
||||
- [sdk/python] Fix `Output.from_input` to unwrap nested output values in input types (args classes), which addresses
|
||||
|
|
|
@ -33,7 +33,7 @@ from .. import _types
|
|||
|
||||
if TYPE_CHECKING:
|
||||
from ..output import Inputs, Input, Output
|
||||
from ..resource import Resource, CustomResource, ProviderResource
|
||||
from ..resource import Resource, ProviderResource
|
||||
from ..asset import FileAsset, RemoteAsset, StringAsset, FileArchive, RemoteArchive, AssetArchive
|
||||
|
||||
UNKNOWN = "04da6b54-80e4-46f7-96ec-b56ff0331ba9"
|
||||
|
@ -567,7 +567,7 @@ def contains_unknowns(val: Any) -> bool:
|
|||
if not any([x is val for x in stack]):
|
||||
stack.append(val)
|
||||
if isinstance(val, dict):
|
||||
return any([impl(x, stack) for x in val.values()])
|
||||
return any([impl(val[k], stack) for k in val])
|
||||
if isinstance(val, list):
|
||||
return any([impl(x, stack) for x in val])
|
||||
return False
|
||||
|
|
|
@ -36,18 +36,22 @@ class FakeCustomResource(CustomResource):
|
|||
self.__dict__["urn"] = Output.from_input(urn)
|
||||
self.__dict__["id"] = Output.from_input("id")
|
||||
|
||||
|
||||
class FakeComponentResource(ComponentResource):
|
||||
def __init__(self, urn):
|
||||
self.__dict__["urn"] = Output.from_input(urn)
|
||||
|
||||
|
||||
class MyCustomResource(CustomResource):
|
||||
def __init__(self, name: str, typ: Optional[str] = None, opts: Optional[ResourceOptions] = None):
|
||||
super(MyCustomResource, self).__init__(typ if typ is not None else "test:index:resource", name, None, opts)
|
||||
|
||||
|
||||
class MyComponentResource(ComponentResource):
|
||||
def __init__(self, name: str, typ: Optional[str] = None, opts: Optional[ResourceOptions] = None):
|
||||
super(MyComponentResource, self).__init__(typ if typ is not None else "test:index:component", name, None, opts)
|
||||
|
||||
|
||||
class MyResourceModule(ResourceModule):
|
||||
def version(self):
|
||||
return None
|
||||
|
@ -60,6 +64,7 @@ class MyResourceModule(ResourceModule):
|
|||
else:
|
||||
raise Exception(f"unknown resource type {typ}")
|
||||
|
||||
|
||||
class MyMocks(Mocks):
|
||||
def call(self, token, args, provider):
|
||||
raise Exception(f"unknown function {token}")
|
||||
|
@ -72,8 +77,24 @@ class MyMocks(Mocks):
|
|||
else:
|
||||
raise Exception(f"unknown resource type {typ}")
|
||||
|
||||
|
||||
@pulumi.output_type
|
||||
class MyOutputTypeDict(dict):
|
||||
|
||||
def __init__(self, values: list):
|
||||
pulumi.set(self, "values", values)
|
||||
|
||||
# Property with empty body.
|
||||
@property
|
||||
@pulumi.getter
|
||||
def values(self) -> str:
|
||||
"""Values docstring."""
|
||||
...
|
||||
|
||||
|
||||
def pulumi_test(coro):
|
||||
wrapped = pulumi.runtime.test(coro)
|
||||
|
||||
def wrapper(*args, **kwargs):
|
||||
settings.configure(settings.Settings())
|
||||
rpc._RESOURCE_PACKAGES.clear()
|
||||
|
@ -84,6 +105,7 @@ def pulumi_test(coro):
|
|||
|
||||
return wrapper
|
||||
|
||||
|
||||
class NextSerializationTests(unittest.TestCase):
|
||||
@pulumi_test
|
||||
async def test_list(self):
|
||||
|
@ -899,6 +921,12 @@ class NextSerializationTests(unittest.TestCase):
|
|||
self.assertTrue(await r.is_secret())
|
||||
self.assertEqual(await r.future(), "inner")
|
||||
|
||||
@pulumi_test
|
||||
async def test_dangerous_prop_output(self):
|
||||
out = self.create_output(MyOutputTypeDict(values=["foo", "bar"]), is_known=True)
|
||||
|
||||
self.assertTrue(await out.is_known())
|
||||
|
||||
@pulumi_test
|
||||
async def test_apply_unknown_output(self):
|
||||
out = self.create_output("foo", is_known=True)
|
||||
|
@ -1167,4 +1195,3 @@ class EnumSerializationTests(unittest.TestCase):
|
|||
one = FloatEnum.ZERO_POINT_ONE
|
||||
prop = await rpc.serialize_property(one, [])
|
||||
self.assertEqual(FloatEnum.ZERO_POINT_ONE, prop)
|
||||
|
||||
|
|
Loading…
Reference in a new issue