Bitcoin Forum
March 19, 2024, 09:54:16 AM *
News: Latest Bitcoin Core release: 26.0 [Torrent]
 
   Home   Help Search Login Register More  
Pages: [1] 2 »  All
  Print  
Author Topic: Multiple Wallets, one computer (multiple accounts)  (Read 12069 times)
bytemaster (OP)
Hero Member
*****
Offline Offline

Activity: 770
Merit: 566

fractally


View Profile WWW
August 01, 2010, 08:14:29 PM
Last edit: October 25, 2010, 05:02:24 PM by satoshi
Merited by ABCbits (1)
 #1

I want to have multiple "accounts" with unique balances and to send and receive coins on a per-account basis.  The equiv. of having multiple wallets running at the same time.  

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins.  

https://fractally.com - the next generation of decentralized autonomous organizations (DAOs).
Activity + Trust + Earned Merit == The Most Recognized Users on Bitcointalk
Advertised sites are not endorsed by the Bitcoin Forum. They may be unsafe, untrustworthy, or illegal in your jurisdiction.
Insti
Sr. Member
****
Offline Offline

Activity: 294
Merit: 252


Firstbits: 1duzy


View Profile
August 01, 2010, 11:14:23 PM
 #2

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins. 

+1
lfm
Full Member
***
Offline Offline

Activity: 196
Merit: 104



View Profile
August 01, 2010, 11:24:57 PM
 #3

I want to have multiple "accounts" with unique balances and to send and receive coins on a per-account basis.  The equiv. of having multiple wallets running at the same time.   

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins. 

Would it help to use the attached messages you have when sending to an IP address? It should be easy to record a "sending ip address" in that case also.
bytemaster (OP)
Hero Member
*****
Offline Offline

Activity: 770
Merit: 566

fractally


View Profile WWW
August 02, 2010, 01:17:15 AM
 #4

Nope, I really need it on a per-receiving address so that it is easy to directly track the balances from customers paying me. 

https://fractally.com - the next generation of decentralized autonomous organizations (DAOs).
kwukduck
Legendary
*
Offline Offline

Activity: 1937
Merit: 1001


View Profile
September 22, 2010, 06:59:52 PM
 #5

It's something im missing too, it would be nice to have seperate 'accounts' with each it's own balance and transactions. One for personal use, one for business, etc.

14b8PdeWLqK3yi3PrNHMmCvSmvDEKEBh3E
lfm
Full Member
***
Offline Offline

Activity: 196
Merit: 104



View Profile
September 26, 2010, 08:24:11 AM
 #6

I want to have multiple "accounts" with unique balances and to send and receive coins on a per-account basis.  The equiv. of having multiple wallets running at the same time.   

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins. 

I guess one way to do this would be use the -datadir=<dir>  command line arg to specify a data directory (other than the default "$(HOME)/.bitcoin/"). You would only run the client on one directory at a time. (Note the directory is relative to the current directory for the SERVER bitcoind. Its safest to specify a fully qualified directory starting at the root.) Also of course the client does not need to be running  on any specific directory nor running at all to receive payments to addresses in any/all of the wallets.


nelisky
Legendary
*
Offline Offline

Activity: 1540
Merit: 1001


View Profile
September 26, 2010, 10:14:31 AM
 #7

I want to have multiple "accounts" with unique balances and to send and receive coins on a per-account basis.  The equiv. of having multiple wallets running at the same time.   

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins. 

I guess one way to do this would be use the -datadir=<dir>  command line arg to specify a data directory (other than the default "$(HOME)/.bitcoin/"). You would only run the client on one directory at a time. (Note the directory is relative to the current directory for the SERVER bitcoind. Its safest to specify a fully qualified directory starting at the root.) Also of course the client does not need to be running  on any specific directory nor running at all to receive payments to addresses in any/all of the wallets.




Yeah, I've been considering how to best go about this for the web services. Right now multiple services on the same machine run multiple clients bound to separate rpc ports. It works... to a point.

What I want is a separate wallet per user, and that scales pretty badly, so what I thought could be done is have multiple wallets in memory at the same time, based on some key (which would be the subdir inside the datadir for the wallet) and the rpc calls would take a -wallet= switch. I just don't know how many wallets I would be able to keep in memory at the same time, and I would loose the ability to move money instantly amongst them, but that's ok, I guess.

A slightly more scalable alternative would be to lazily load the wallets on demand. I know wallets keep a bunch of information, but maybe we could limit that to own addresses and transactions?

Satoshi: are you planning on doing any of this? As I'm not familiar with this part of the code, it would suck to spend a week trying to figure out the best way to do this and then you pushing the perfect implementation to svn Smiley
jimbobway
Legendary
*
Offline Offline

Activity: 1304
Merit: 1014



View Profile
September 27, 2010, 03:53:38 AM
 #8

Can you just create a new windows user and log in with that user?  Bitcoin creates a directory per windows user, I think.
theymos
Administrator
Legendary
*
Offline Offline

Activity: 5138
Merit: 12565


View Profile
September 27, 2010, 04:34:04 AM
 #9

You could create an additional database file with public keys associated with usernames/passwords. Creating an address logs the resulting public key to the new database (in addition to wallet.dat); CreateTransaction is modified to only select coins from those addresses associated with the account; the various "list transactions" commands are modified to only tally/show transactions to addresses associated with the account; new commands are added to transfer keys from one account to another. You could make it possible to transfer funds (without the keys) from one account to another without a real transaction, but this would involve much more complexity.

Implementation wouldn't be too difficult, I think (if you don't have to deal with the UI). The worst part would be dealing with the new database file and figuring out how to replace the existing authentication with your own stuff.

1NXYoJ5xU91Jp83XfVMHwwTUyZFK64BoAD
throughput
Full Member
***
Offline Offline

Activity: 158
Merit: 100


View Profile
September 27, 2010, 01:48:18 PM
 #10

Satoshi: are you planning on doing any of this? As I'm not familiar with this part of the code, it would suck to spend a week trying to figure out the best way to do this and then you pushing the perfect implementation to svn Smiley

I'm sure, Satoshi should better plan documenting the protocol as a standard, so we will have interoperable implementations,
free from his dictatorship and tyranny. That is solely my own opinion.

For the techical issue discussed: It is clear, that the "node" instance, that holds the blocks database, connects to the network,
exchanges data with peers and with users, is architecturally independent from the "wallet" instance(s).
Wallet(s) may be viewed as peer(s), that request the block data and publish transactions/blocks, like network peers do now.

So it is feasible to have "block chain" daemon, that will cache block database on disk and may also act as an intermediary
between the local users and "the network", so it will have no secret keys at all, no sensitive information.
And the local "wallets" will have no networking part, no network interoperability problems, except for connecting to the daemon. So there will be no "bind to port 8XXX" issue.
They will be free from the P2P stuff, will only work in a client-server paradigm, will trust the server for executing their requests, but will not trust the server with any secret information.
And so, they may be as simple, as system-on-a-chip cards, capable of iterating through the blocks/transactions list, but not required to store it. The block chain database may also return narrow results, parameterised by the list of public keys, like "getreceivedbyaddr" does now.

Generation should happen at admin's local wallet, not at the networking node. That means "wallets" will be permitted to publish not only transactions, but solved blocks too.

For current codebase this is a major refactoring, I'm sure Satoshi will veto on it, and he may have his own merits.
So the only hope is the alternative implementations, that aren't possible without the standard.
nelisky
Legendary
*
Offline Offline

Activity: 1540
Merit: 1001


View Profile
September 27, 2010, 01:56:05 PM
 #11

Satoshi: are you planning on doing any of this? As I'm not familiar with this part of the code, it would suck to spend a week trying to figure out the best way to do this and then you pushing the perfect implementation to svn Smiley

I'm sure, Satoshi should better plan documenting the protocol as a standard, so we will have interoperable implementations,
free from his dictatorship and tyranny. That is solely my own opinion.

For the techical issue discussed: It is clear, that the "node" instance, that holds the blocks database, connects to the network,
exchanges data with peers and with users, is architecturally independent from the "wallet" instance(s).
Wallet(s) may be viewed as peer(s), that request the block data and publish transactions/blocks, like network peers do now.

So it is feasible to have "block chain" daemon, that will cache block database on disk and may also act as an intermediary
between the local users and "the network", so it will have no secret keys at all, no sensitive information.
And the local "wallets" will have no networking part, no network interoperability problems, except for connecting to the daemon. So there will be no "bind to port 8XXX" issue.
They will be free from the P2P stuff, will only work in a client-server paradigm, will trust the server for executing their requests, but will not trust the server with any secret information.
And so, they may be as simple, as system-on-a-chip cards, capable of iterating through the blocks/transactions list, but not required to store it. The block chain database may also return narrow results, parameterised by the list of public keys, like "getreceivedbyaddr" does now.

Generation should happen at admin's local wallet, not at the networking node. That means "wallets" will be permitted to publish not only transactions, but solved blocks too.

For current codebase this is a major refactoring, I'm sure Satoshi will veto on it, and he may have his own merits.
So the only hope is the alternative implementations, that aren't possible without the standard.


Well put, the standard is certainly needed to move this into mainstream, and source code as documentation sucks. But that is slightly longer, more important goal, not one I will hold off on projects for. I'm sure you agree the standard definition alone will take a good amount of time, especially when people look at it and start saying what if, or wouldn't it be better if... Then we still have to develop standards compliant clients.

I'm not saying that effort isn't worth it, much the opposite, it's mandatory for the immediate future. This hack jobs we do are actually a great way to get to know how things are being done, thus gathering any knowledge to help in describing the protocol Smiley
Gavin Andresen
Legendary
*
qt
Offline Offline

Activity: 1652
Merit: 2164


Chief Scientist


View Profile WWW
September 27, 2010, 03:14:55 PM
Merited by ABCbits (3)
 #12

The "label" mechanism (setlabel / getreceivedbylabel) is supposed to meet this need, but only solves part of the problem.

If the API was extended as I describe below, would it solve the same problems as having multiple wallets?

Proposal:

+ new send method: send TO a given bitcoin address specifically FROM the bitcoins sent to <label>
  (change generated would be automatically tagged with <label>)
+ add optional [label] param to getbalance.
+ new method: listsentbylabel
  (returns array of [ "address" : "bcaddresssentto", "amount" : x.yz, "confirmations": n ])

Each customer "account" would be a bitcoin <label>.  Account handling would look like:

Create account / create new address for account:
  getnewaddress [account_id_label]
   ... tell user "fund your account by sending coins to {the address returned}"

Customer withdraws/spends:
  sendfrom [account_id_label] [address] [amount]
   (FAILS if balance for that account too low)

Show customer their balance:
  getbalance [account_id_label]

Show customer their transactions in/out
  listreceivedbylabel [account_id_label]
  listsentbylabel [account_id_label]

---------

Seems to me this would be a much better direction to go in, rather than having separate wallet.dat files for each customer.  At the very least, backing up thousands of customer's wallet files would be inefficient and error-prone, and constantly switching between them would also be incredibly inefficient.


How often do you get the chance to work on a potentially world-changing project?
nelisky
Legendary
*
Offline Offline

Activity: 1540
Merit: 1001


View Profile
September 27, 2010, 03:33:59 PM
 #13

The "label" mechanism (setlabel / getreceivedbylabel) is supposed to meet this need, but only solves part of the problem.

If the API was extended as I describe below, would it solve the same problems as having multiple wallets?

Proposal:

+ new send method: send TO a given bitcoin address specifically FROM the bitcoins sent to <label>
  (change generated would be automatically tagged with <label>)
+ add optional [label] param to getbalance.
+ new method: listsentbylabel
  (returns array of [ "address" : "bcaddresssentto", "amount" : x.yz, "confirmations": n ])

Each customer "account" would be a bitcoin <label>.  Account handling would look like:

Create account / create new address for account:
  getnewaddress [account_id_label]
   ... tell user "fund your account by sending coins to {the address returned}"

Customer withdraws/spends:
  sendfrom [account_id_label] [address] [amount]
   (FAILS if balance for that account too low)

Show customer their balance:
  getbalance [account_id_label]

Show customer their transactions in/out
  listreceivedbylabel [account_id_label]
  listsentbylabel [account_id_label]

---------

Seems to me this would be a much better direction to go in, rather than having separate wallet.dat files for each customer.  At the very least, backing up thousands of customer's wallet files would be inefficient and error-prone, and constantly switching between them would also be incredibly inefficient.



That is a much better approach, agreed. Assuming one label spans multiple addresses, so a client can accept transactions from an imported priv key (this being discussed on another thread), it seems to fit my needs perfectly, with only one small caveat which is internal transfers; say I use this approach for the lottery users (though that is not my use case, I actually would be more about site separation than user separation, but still):
- Each account has on inbound address, annotated with the login label
- Every time a user withdraws, I use the sendfrom mechanism you describe
- The user hits the jackpot, but the prize is actually held in multiple users' accounts so
  a) I need to, when users buy tickets, move the amount to a separate address (forces external transaction, sucks)
  b) I leave coins where they are, and then on payout I make a normal sendtoaddress (both external transaction and breaks the label accounting logic)
  c) I leave coins where they are, payouts do nothing to the wallet, withdrawals do as many transactions as needed from each user account (what a nightmare!)

I don't see any good option here, and the best one, if I'm doing external transactions anyway, is a). I can trust these transactions with 0 blocks confirmed, because I'm both the sender and the recipient, and this would keep the accounts/labels in check, which serves as a great verification to the overall balances. Can you think of any alternative?
Gavin Andresen
Legendary
*
qt
Offline Offline

Activity: 1652
Merit: 2164


Chief Scientist


View Profile WWW
September 27, 2010, 05:10:33 PM
 #14

Separate "accounts" (addresses with labels) to accumulate Jackpots is the right idea.  Users buy tickets, bitcoins are moved to the appropriate Jackpot account.  When a Jackpot is won, transactions flow out of its account back to whoever won.

How often do you get the chance to work on a potentially world-changing project?
nelisky
Legendary
*
Offline Offline

Activity: 1540
Merit: 1001


View Profile
September 27, 2010, 05:16:18 PM
 #15

Separate "accounts" (addresses with labels) to accumulate Jackpots is the right idea.  Users buy tickets, bitcoins are moved to the appropriate Jackpot account.  When a Jackpot is won, transactions flow out of its account back to whoever won.


Yeah, it is quite obvious. I suffer for over optimization obsession syndrome Smiley I feel that as data flows only inside the application there's no need to register transactions and put that 'extra load' on the system, but quite frankly the extra load is perfectly ignorable, and the transactions help keep everything tidy. Are you planning to do anything on this regard? I'm sure I can find my way around to do it myself, it will just take time, but I don't want to duplicate any work though.
satoshi
Founder
Sr. Member
*
qt
Offline Offline

Activity: 364
Merit: 6610


View Profile
October 24, 2010, 07:17:51 PM
 #16

I have the beginning of something like this.  It's mostly like what Gavin described.

Some more rpc interface:

move <fromaccount> <toaccount> <amount>
   Move from one internal account to another.  I think blank account name ("") will be your default account.  If you sell something to a user, you could do move "theiraccount" "" 123.45.
   Is "move" the best name for this?  I shied away from "transfer" because that sounds too close to sending a transaction.

I'm thinking a new function getaccountaddress instead of overloading getnewaddress:

getaccountaddress <account>
   Gives you an address allocated from getnewaddress <account>.  It'll keep giving the same address until something is received on the address, then it allocates a new address.  (It automatically does what the sample code I posted some time ago did)

Would these commands make it possible in simple cases to implement your website without needing a database of your own?
grondilu
Legendary
*
Offline Offline

Activity: 1288
Merit: 1076


View Profile
October 24, 2010, 07:29:24 PM
 #17

Wouldn't it be much simpler to be able to run several instances of bitcoin, each of them running on a specific "wallet.dat" file ?

I mean, we would just add a --wallet long option to the client/server app.  The name of your account would be the name of your wallet file.

SmokeTooMuch
Legendary
*
Offline Offline

Activity: 860
Merit: 1021


View Profile
October 24, 2010, 08:58:32 PM
 #18

I want to have multiple "accounts" with unique balances and to send and receive coins on a per-account basis.  The equiv. of having multiple wallets running at the same time.   

It would help to simply list the balance for each 'receiving address' and to specify a 'source' address when sending coins. 
use -datadir and change the port on the source code and then use a different dir and port for every bitcoin instance

Date Registered: 2009-12-10 | I'm using GPG, pm me for my public key. | Bitcoin on Reddit: https://www.reddit.com/r/btc
satoshi
Founder
Sr. Member
*
qt
Offline Offline

Activity: 364
Merit: 6610


View Profile
October 25, 2010, 04:53:53 PM
 #19

Here's some pseudocode of how you would use the account based commands.  It sure makes website integration a lot easier.

print "send to " + getaccountaddress(username) + " to fund your account"
print "balance: " + getbalance(username, 0)
print "available balance: " + getbalance(username, 6)

// if you make a sale, move the money out of their account
move(username, "", amount, 6)

// withdrawal
sendfrom(username, bitcoinaddress, amount, 6)
jgarzik
Legendary
*
qt
Offline Offline

Activity: 1596
Merit: 1091


View Profile
October 25, 2010, 05:18:58 PM
 #20


Why try so hard to prevent running multiple instances of bitcoin?

It is a valid use case to separate bitcoin processes for separate users using SElinux MAC protection, a protection far stronger than anything that can be coded into a shared user process.

Jeff Garzik, Bloq CEO, former bitcoin core dev team; opinions are my own.
Visit bloq.com / metronome.io
Donations / tip jar: 1BrufViLKnSWtuWGkryPsKsxonV2NQ7Tcj
Pages: [1] 2 »  All
  Print  
 
Jump to:  

Powered by MySQL Powered by PHP Powered by SMF 1.1.19 | SMF © 2006-2009, Simple Machines Valid XHTML 1.0! Valid CSS!