I am using Infura as a node for my DApp so I need to send raw transactions by signing them. These transactions can come from multiple users of an application so each user must sign and send a raw transaction to infura.

  • One solution would be take the private key as input from user during signup and securely store it somewhere for future transactions. This sounds like an insecure way and a lot of work.

  • Afaik the easiest and one of the safest ways to do this is get access to the account from metamask on the client instead of managing private keys of multiple users in my application.

If I'm using the second approach, I don't wanna put the logic of signing and doing transactions on the client, I need to transmit the private key to the server so that it will sign the transaction. How can I achieve this? Is there a safe solution to this?

  • Should I put all the blockchain logic in the client and update my database in the server code when successful? (I don't personally like this)
  • Most acceptable approach that I can think of is to sign the transaction using web3.personal.sign() on the client and then send the signed transaction to the server where the server calls web3.eth.sendSignedTransaction() to make the transaction.

How are the real DApps doing this with metamask integration?


I wanna rephrase this question since there is no straight forward anaswer here so far. The question would be:

What is the easiest way to sign transactions on user's behalf from the server without hardcoding their private keys? Any solution with or without Metamask would do.

  • Hopefully MetaMask doesn't allow you access to the user's private key. (That's basically the point of MetaMask, to protect me from a website asking for that.) Why don't you want to just send the transaction from the client? That's definitely the typical path.
    – user19510
    Mar 16, 2019 at 23:12
  • Well I want the server to be the API for calling the contracts which makes more sense as there would be a lot of code to do validation, make transaction and save the results in a database etc. If I separate contract calling and saving to db between client and server it becomes a tightly coupled system. I understand what you say but is there any way I can stick to making transactions on server but by using metamask?
    – socket_var
    Mar 17, 2019 at 0:49
  • I am just a beginner so I'm not sure but, can I use personal.sign() to sign the transaction in the client, send it in the request body to the server and send the raw transaction from the server. Would that work ?
    – socket_var
    Mar 17, 2019 at 0:51
  • You would want eth_signTransaction, but it looks like MetaMask doesn't support that: github.com/MetaMask/metamask-extension/issues/3475.
    – user19510
    Mar 17, 2019 at 0:56
  • Depending on what you're doing, you might be able to get by with signing non-transactions and then making transactions that use those signed messages yourself (but then you'll be paying for gas).
    – user19510
    Mar 17, 2019 at 0:57


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Browse other questions tagged or ask your own question.