UX for Setting Subnode Owners - Onboarding Process

I’m baking subdomain issuance [setSubnodeOwner] into the onboarding process of our mobile wallet app. We’re currently thinking about what’s the best way to do this from a usability perspective.

I’d like to open up the discussion on this topic so we can gather ideas from the community that will help improve wallet usability for other upcoming projects as well.

Initial thoughts

Generally speaking, our servers will receive a request from the mobile client upon wallet creation, and it will do a setSubnodeOwner with the user’s newly created wallet address as the owner.

To speed up the process, we’re thinking of automatically assigning a random, readable subdomain label to start with. The user will have the option to change their “username” (i.e. label) later in Settings.

User’s POV

The setSubnodeOwner process will likely be the last step of the onboarding process. Acting as the user, I would expect to see some sort of loading screen animation with text like “We’re setting up your wallet…”, and once the setSubnodeOwner transaction is mined, the loading animations will disappear, and the user will be sent to their main wallet screen.

My only worry about this approach is the possibility of long wait times for new blocks.

Perhaps this process can happen asynchronously so that the user can use the app right away. They may see the hexidecimal address at first, but it will eventually resolve to the subdomain once the tx is mined.

Other considerations

Are there any other transactions that need to be called in addition to setSubnodeOwner?

Does the user need to call setResolver on their newly acquired subnode? If so, how will this affect the onboarding process if their wallet is brand new and it doesn’t have any ether to pay for the gas?

Any other feedback or guidance on this would be super helpful.

That seems reasonable.

Yes, for a fully set up name, you need to:

  1. Create the name with setSubdomainOwner.
  2. Set a resolver with setResolver.
  3. Set an address with setAddr on the resolver (unless you use a special resolver that, eg, resolves all names to their owners).

I’d suggest writing a simple ‘registrar’ contract to own your ENS name, which can do all three of these operations for your user in a single transaction.

1 Like

Thanks @nickjohnson. I’ve been looking at the docs on Writing a Registrar.

So far this is my understanding of how to set this up:

  1. Write a simple FIFS registrar contract with the minimum amount of functionality required to issue and resolve subdomains.
  2. Deploy the FIFS registrar contract.
  3. Instantiate with FIFSRegistrar(address ensAddr, bytes32 node), where ensAddr is the address of the ENS registry, and node is the nameHash("mywallet.eth").
  4. Transfer ownership of "mywallet.eth" to the FIFS registrar contract. (?)
  5. User creates a new wallet. The mobile client informs our server to issue a new subdomain.
  6. The FIFS registrar performs the three necessary operations to issue a subdomain on behalf of a new user. (?)

I am having a hard time wrapping my head around the FIFS registrar contract owning the parent name. What are the benefits in transferring ownership of my parent name to the registrar contract rather than directly retaining ownership of it?

Thanks for your help with this.

That’s right.

You have to transfer ownership to the FIFS registrar, because that’s the only way it has permission to create subdomains. You can, if you wish, retain ownership of the registration in the .eth registrar contract - but doing so will allow you to reclaim ownership of the name, which means you could take domains off your users.

You have to transfer ownership to the FIFS registrar, because that’s the only way it has permission to create subdomains.

OK that’s what I figured, but I was a little confused by the code in the example registrar. In the FIFSRegistrar contract, the register function contains the following lines:

var currentOwner = ens.owner(node);

if (currentOwner != 0 && currentOwner != msg.sender) throw;

This assumes that the msg.sender is the owner of the name in the registry. I may be wrong here, but the contract cannot ever be msg.sender, correct? (unless there is a way that a contract can call itself). If so, I guess this just comes down to needing a FIFS registrar with custom logic that fits our use case.

You can, if you wish, retain ownership of the registration in the .eth registrar contract - but doing so will allow you to reclaim ownership of the name, which means you could take domains off your users.

Gotcha. So once both types of ownerships are transferred to the contract, it’ll own the name indefinitely. I will have to transfer ownership of the name AND ownership of the registration to the contract if I want to mitigate that potential attack vector.

Bear in mind that a simple FIFS registrar would be open to front running.

If you are okay with paying the costs to set up the wallet for your user I’d recommend your servers create the subname, assign the resolver and set the address themselves. Then you can transfer ownership of it to the user.

Alternatively write your own registrar that has a two-phase registration (similar to the new .eth registrar) and get it to do the work of assigning the resolver and setting addresses in the second phase.

Yes - the FIFS registrar itself has to own the name in order to create subdomains of it. That’s what this check establishes.

You need to transfer ownership of the name to the registrar for it to operate correctly. It doesn’t need to own the registration - but if you want to guarantee to your users that you can’t reassign their names, the registration has to be out of your control. As a simple solution, you could transfer ownership to 0x0.

Also, if you’re going to be doing registrations using your own backend code, you can make a registrar that allows only your account to register new names. That way, you can exercise whatever control over registrations that you wish.