Introduce the `PredicateId` Type to the std-lib
We currently support the following blockchain types:
-
ContractId -
Address
This allows for developers using Sway to differentiate between the blockchain types they are interacting with when writing contracts for type-saftey. However, Fuel supports one additional type; the Predicate.
The following proposes the introduction of the PredicateId type based on the existing Address and ContractId types to enhance type-saftey:
/// The `PredicateId` type, a struct wrapper around the inner `b256` value.
pub struct PredicateId {
/// The underlying raw `b256` data of the predicate.
value: b256,
}
The PredicateId type would also be added to the Identity type and the predicate_id() function would return a PredicateId:
pub enum Identity {
Address: Address,
ContractId: ContractId,
PredicateId: PredicateId,
}
pub fn predicate_id() -> PredicateId { ... }
It is important to note that while internally there is no difference between an address and a predicate, this is abstracted away from the Sway developer. Their focus should be on contract security and not particularly the inner workings of the Fuel VM. The PredicateId further enhances type-saftey for the same reason Address and ContractId were introduced.
We currently suggest Predicates to be treated as an Address in Sway however, this introduces limits if developers would like to create different behaviors for the two cases if an address is known to be a predicate. For example, in a match statement of an Identity type we are currently limited to ContractId or Address. There is no current method of handling a known predicate address differently than an Address. This would be particularly helpful in predicate factories, predicate based order books, and predicate based wallets where Sway developers are frequently interacting with predicates for enhanced type-saftey.
This proposal will introduce breaking changes in the SDK, as the predicate type would need to be added to the Identity type and handled accordingly.
I'm still a bit unsure of whether this makes sense, I can see it adding a bit of friction for all the applications that don't need to differentiate between Addresses and Predicates, and could potentially increase code size if match statements need to handle both now.
One alternative would be to keep Identity as Address + Contract, and have a separate struct that is Address, Contract & Predicate.
Overall, we should probably gather some opinions from developers internally and externally about whether this would be helpful, neutral, or confusing.
Introducing PredicateId as an alias for Address might be a nice solution here.
An external discussion has led to the conclusion that rather than introducing the PredicateId type, all semantic naming should refer to the "Predicate Address" rather than id or root. This allows for the Address type to cover both cases and does not introduce any breaking changes.
This issue will be closed by https://github.com/FuelLabs/sway/pull/5596
Closed by https://github.com/FuelLabs/sway/pull/5596