The Internet Computer provides a threshold signature API that allows any canister to use decentralised public-private key pairs. These keys can be used to sign messages for any system that uses compatible elliptic curves. Popular use cases are interacting with other blockchains such as Ethereum and Bitcoin. However, accessing this API requires developing a backend canister, which may be an unnecessary hurdle.
Objective
We would like to make a threshold signing service more accessible but keep it as secure as the canister API today. In particular:
Pure frontend web apps should be able to use threshold signatures. For example, a pure frontend app, served from an asset canister on the Internet Computer, should be able to interact with Ethereum smart contracts.
Off-chain and other-chain apps should be able to use the threshold signing APIs on the Internet Computer.
Proposal
We would like to create a canister that provides a threshold signing service, equivalent to the canister threshold API, as part of the core Internet Computer offering.
State
It is possible to implement the signing canister in a completely stateless manner, with no user data whatsoever. This is our preferred approach.
Technical challenges
Creating threshold signatures is computationally expensive. It therefore makes sense to charge callers a fee in cycles to cover this cost and deter DoS attacks.
A use case for this API is pure frontend apps. But ingress messages from a frontend app cannot have attached cycles, so a protocol such as ICRC-2 is needed to pay for the cycles.
The API should be very easy to use. If it is hard to use it takes one technical challenge away from developers and replaces it with another.
The implementation involves signatures, so must be made to cryptographic standards with good code quality and security audit. Any changes to the canister code must also be audited very carefully. This is not a canister that can casually be thrown up by anyone and be trusted.
Threshold signatures cannot be moved from one canister to another. Thus, the signing canister must remain in service indefinitely, or until a mechanism is implemented that allows moving threshold keys.
Maintenance
We expect that after an initial period of development, this canister will be very stable and require few updates. We did consider creating a “black-hole” canister with no controllers but:
In the event of a security flaw being discovered, we would be unable to repair a black-holed canister.
This canister is new. After deployment we may get feedback that some modification would greatly improve the utility of the canister. Due to the way threshold signatures work, we cannot migrate apps and users using one black-holed threshold signing canister to a newer and better black-holed threshold signing canister.
The code would, of course, be open source.
Purity vs usefulness
It would be possible to make a canister that implements raw cryptographic primitives only. However we feel that it should be made easy to perform common operations in a correct and safe manner. Our preferred policy is:
Provide utilities for very common operations, such as signing Ethereum transactions, in canister.
Create client-side libraries for less common operations.
Next steps
Determine whether such a canister would be useful to the community.
We have prototypes of the core technologies. These need to be assembled into a fully working technology demonstrator.
Libraries and code need to be published in a clean and accessible form and pass security review.
Note: The paid API library, in particular, is likely to have wider application. Any canister that wishes to offer a service for a fee could make use of that library.
Make a motion proposal to the NNS, requesting that the community accept putting the signer under NNS control.
ICP’s threshold protocols are one of its most unique and valuable propositions in my opinion and experience. Packaging them up and providing them to non-canister apps inside and outside of the ICP ecosystem could be a very valuable move.
A couple points that I think would help set this up for true success:
Make this an HTTP-first experience. There should be as little ICP-specific as possible when using these APIs. Just expose the functionality as a traditional HTTP API. This will lead to maximum compatibility and ease of use inside and outside of the ecosystem. Dealing with Candid and agents etc is a major barrier.
Accept payment through stablecoins on other chains. Please somehow just figure this out. Don’t expect anyone to purchase ICP or convert anything to cycles. Allow the simplest possible flow using USDC for example on Ethereum L1, L2s, Solana, etc.
I feel there’s an opportunity here to make a truly useful API across all of the blockchain industry.
Please don’t ruin the opportunity by making the whole experience ICP-specific and difficult to use. These barriers might be much larger than DFINITY generally expects.
If payment worked with stablecoins, it could actually provide upward pressure on the icp price as stablecoins purchase icp in the background (through DEXs?) before they are burned
As an example, imagine an Ethereum developer who wants to use these APIs. He’ll sign some kind of approve or something with his Ethereum wallet that has a USDC balance, and submit that through an HTTP API to the threshold service. The service will then pull those funds and decrement amounts with usage.
I started a library to handle payment called PAPI (Paid API). The payment type is a variant.
The first variant (the simplest to implement) handles payment by attached cycles. But this is only useful for inter canister calls.
The second variant handles payment via ICRC2, using an approval flow as you suggest. This handles payment via any ICRC-2 token, so it covers payment via ingress messages (the HTTP & off-chain/other-chain use case) with cycles or any other ICRC2 token. For example, ckUSDC.
The third variant is ICRC-2 again, but where payment is by a patron, not the caller. This covers the case where an application is paying on behalf of users.
I would be very open to adding more flows, tokens and standards. I can imagine a standardized endpoint to fetch a price list from a canister. That price list would include which tokens are accepted and which payment flows are supported. If you have specific use cases in mind, please reach out and we can find a protocol that works.
I would request that we can start with the simplest thing possible and expand on that, rather than waiting for protocol variants that cover every possible use case.
The paid API library isn’t clean and shipshape. Documenting the protocols, cleaning up the library and publishing is on my immediate roadmap.
What I was trying to emphasize with the payment piece is to not require ICRC tokens, allowing developers to sign/submit using only Ethereum/Solana/etc tools and processes.
A dev should be able to sign and send a transaction directly on Ethereum or directly to an HTTP API endpoint.
One can imagine a world that is pay with any token on any chain, receive any token on any chain, and pay gas or reverse gas with any token on any chain.
That would instantly make ICP indispensable to all crypto devs
Why is it this all needed? A canister needs threshold because it cannot hold secrets. An external user can (and must, even to sign the threshold request), so the external user can just sign whatever he wants to sign directly.
For sure there are some cases where an external key is the cleanest solution, in which case I would recommend doing that. Especially if you know the IC inside out, there are a lot of options. I have myself sometimes not seen what the problem is with some APIs because I know them too well and think “What’s so hard about that?”. Making the possible easier is a strong motivator here. We have a lot of tech that is not used to its full potential because it is inaccessible.
Let’s take the case of a pure front end application hosted on the IC. It requires an asset canister and an identity provider to log in (such as Internet Identity but not limited to that). Depending on the type of identity provider the client may indeed have a key in the form of a delegation. But that key is a short term key not well suited to interacting with say Ethereum. Whereas the IC has the logic to take that short term delegation and provide a long term key. And this makes it easier to work with other chains, regardless of choice of identity provider.
The codebase is approaching MVP status. We hope to have something we can present and formally hand over to NNS control sometime next week.
If you have use cases for the Chain Fusion Signer, please do reach out to make sure that we can support your use case.
The same applies to the paid API library. If you have an oracle, a canister hosting an AI model or any other API you would like to charge users for, PAPI should make this easy.
I expect that we will have quite a bit of iteration early on as we try to make this useful. Few things are as motivating as having users who get benefit from a tool!
Hello all. I am happy to announce that the PAPI (paid API) library has been vetted by our security team open sourced.
I will add more documentation on each of the payment flows in the coming weeks.
In discussions with potential users, I have found a great variety in requirements. If you have an API you would like to charge for, or that at least needs to cover its running costs, please reach out. If one of the existing flows does not cover your use case, perhaps we can add another.