Description
Issue to be solved
Currently, the contract update validator prevents removing type declarations from a contract, to prevent it from getting re-added with a different structure. However, it would be useful to have a way to remove type definitions and force users of those contracts to start using a new type instead. This could be even more useful with cadence 1.0.
Suggested Solution
Suggestion I:
One possible solution is to introduce a pragma to tombstone a type definition. e.g: #removedType(T)
.
One can remove a type and add this pragma to indicate that this type was removed. It will prevent re-adding a new type with the same name in future. The pragma itself is not removable once it is aded.
Cons:
- The problem with just removing a type is that, any stored value belongs to this type would become unusable. This does not cause any harm to the network though (which was the original intention of preventing type removals).
- How would migrations handle these missing types?
Suggestion II:
Alternatively, it is possible to provide a way to remove and replace a type with another, particularly during the Cadence 1.0 upgrades. e.g: #replacedType(T, R)
, where R
is the new type to replace with. Similar to the suggested removedType
pragma, this will prevent any re-additions of a new type with the same name.
- During the state migrations, all usages of
T
would be replaced with typeR
, including static types of values, conformances, etc. - This is in a way, providing the user also the ability to define type-change rules similar to what we have done for the system contracts.
- Migrations will first have to collect all these replacements pairs first, before do the actual migrations
This would be only supported if T
and R
satisfy particular conditions, such as:
T
andR
has to be of the same kind. i.e: both are resources / both are resource-interfaces / etc.- The new type
R
should have at-most the set of fields as the old typeT
. It's ok to have less number of fields, but no any additional fields. The filed names and types of the fields should be the same. (This is similar to the existing field update restrictions during contract updates). - So this is basically similar to allowing renaming a type (in addition to what is already supported in existing contract updates)
- Anything else??