IPFS Kubo Gateway Using Gateway.NoFetch Breaks IPNS Resolution

I’ve been messing around with hosting my own public gateway to serve a static website. For now that’s just a hello world skeleton exported from Wordpress.

I’ve gone through the steps of dns linking a domain to my /ipns/somelongkeystring record, note that it’s not the plain ipfs CID. Additionally I setup a custom domain with a CNAME record pointing to the public gateway. This is currently setup as follows:

blog.labadappt.com

The guide I followed to set up my gateway can be found here: The complete guide to hosting a public IPFS gateway · GitHub

I was hoping to be able to leverage the Gateway.Nofetch config option in the kubo settings to block any other content than what I’ve pinned to my node.

However this doesn’t seem to be working as expected. What I expected was with my setup described as above be able to resolve my ipns name as expected after Nofetch is set to true. What happens however is that:

When I navigate to: blog.labadappt.com
I get: 500 Internal Server Error: failed to resolve /ipns/blog.labadappt.com/: could not resolve name

However I know that the content is in fact available because:

When I manually navigate to the raw CID my ipns key resolves to: https://bafybeih46b5zzr5heryxkpwc3xhfvatsbtwqhhqd2z5ndsybfu2kfnijiq.ipfs.labadappt.com/
I get the expected static wordpress site.

I also know that Nofetch is working to block other content because:

When I try the CID for the docs site: https://bafybeiadyn53lx6q2at3ml6cbo3xirhhzwawxjlw3u6irajqmoi45lh7hy.ipfs.labadappt.com/
I get : 500 Internal Server Error: failed to resolve /ipfs/bafybeiadyn53lx6q2at3ml6cbo3xirhhzwawxjlw3u6irajqmoi45lh7hy/: block was not found locally (offline): ipld: could not find bafybeiadyn53lx6q2at3ml6cbo3xirhhzwawxjlw3u6irajqmoi45lh7hy

What is especially curious though is:

When I try: https://docs-ipfs-tech.ipns.labadappt.com/
I get: 500 Internal Server Error: failed to resolve /ipns/docs.ipfs.tech/: block was not found locally (offline): ipld: could not find QmNbLpTNxxdRkqawvDB1RKgnctsuxEkZ1hM4LR623U2E7w

So it did make a successful attempt to resolve docs.ipfs.tech, and got blocked by Nofetch when attempting to retrieve it. Unlike my blog.labadappt.com which just failed to resolve the CID all together.

At this point I should note that my Gateway node isn’t holding the key used to sign the IPNS record. The content is pinned, and over ssh I can still ipfs name resolve blog.labadappt.com correctly without the signing node online. The signing node published the IPNS record using the command ipfs name publish --key=labadappt -t=8760h --ttl=8760h --allow-offline=true /ipfs/QmfN28hoT1wLv3qGvLCtzyrWg1BDPmcZigRw36MDiqVr75 with the intent that the node could be offline for a year and the record would still be valid.

This lead me to inspect my record with ipfs name inspect and got "Validation":{"Valid":false,"Reason":"public key is not embedded in peer ID","Name":"k2k4r8ppytrro2mnn9b7lw4u95ddtm4zhs3zh7jhc9of7d030ilcmclg"}. But it still otherwise resolves, and I will stress that blog.labadappt.com does resolve properly when NoFetch is disabled. So I don’t think that’s the problem, but thought it worth mentioning to be thorough (and I would also be curious what this means, bonus points).

Upon further inspecting the difference between my blog.labadappt.com and docs.ipfs.tech I noticed that the IPFS docs records have a CNAME pointing back to it’s own TXT record. Additionally the docs.ipfs.tech TXT record points to a normal /ipfs/<CID> path. Does the NoFetch behavior only resolve DNSlinks to IPFS CIDs, but won’t resolve an actual /ipns/somepublickey, or is the CNAME needed for some reason?

Or am I missing something else entirely which I need to do to enable the IPNS name resolution with NoFetch enabled?

Edit: The more I think about it the more I think it’s that NoFetch creates a more literal ‘offline’ sort of behavior. When looking at this line from the Kubo repo and seeing that NoFetch triggers something called OfflineUnixFSPathResolver I’m getting the feeling it took offline quite literally and doesn’t even try to resolve an ipns path because that would involve asking the wider network. But this doesn’t seem to be intentional because I do have the correct CID in my local repo. Is this worth an issue on GitHub?

Gateway.Nofetch prevents from fetching data that is not on the node, but the gateway can still serve unpinned data. There is a similar option Reprovider.Strategy which tells the node to only reprovide things that are pinned, but that’s only on the network and does not affect the gateway as I understand it.

It’s difficult to debug the problem without code because you have multiple layers of resolution:

  1. first layer is dnslink
  2. dnslink resolves to ipns
  3. ipns resolves to cid

I suggest you first try to set the dnslink to the cid. If this fails, there is a problem with your dnslink. Otherwise there is more likely a problem with the ipns resolution. This resolution can be very slow (>1 min) sometimes and I do not totally understand why. In fact this is what I was looking for when I stumbled upon your post.