ownercredit

Ownercredit implements some concepts for a wealth-backed currency system


Keywords
ownercredit, wealthcoin, wealth-backed, currency
License
NRL
Install
pip install ownercredit==5.0.1

Documentation

Owner Credit System


OVERVIEW

    Tools for implementing a simple, prototype wealth-backed currency system.

    For a discussion of the theory, design and implications of this credit system, visit:

        https://docs.google.com/document/d/1ohJu7kxz3JlmJZE139iFJanzb5XNS5kEzT1H543Mabk

    While this implementation might be suitable for simple applications (such as
in-game currencies, where it has been successfully deployed), it is clearly not
intended to be used for real currencies! The underlying concepts can however now
be implemented on real cryptocurrency platforms, and may lead to extremely
interesting and valuable outcomes, both for individuals and societies:

  o Using feedback control loops to issue/withdraw credit dynamically to
    eliminate inflation and deflation.

  o Defining the value of units of currency in terms of the price of a basket of
    commodities, but *not* coupling the commodity prices to eachother.

  o Issuing credit automatically on proof of ownership of any wealth that has a
    market, and can be priced, without the necessity to charge Interest.

USAGE

    The implementation requires 3 files:

        credit.py       -- implements a generic currency system
        pid.py          -- implements a PID feedback controller
        filtered.py     -- various value filtering tools
        misc.py         -- other non-specific methods and data

    Simply import the credit module, and create a currency based on a
set of commodities of your choice.  First, describe them in a
dictionary 'commodities' (this is not presently used, so its content
isn't checked):

    import credit

    commodities                 = {
        # Commodity      Units   -of-   Quality   -at-  Market
        "beer":         ( "355ml",      "Pilsner",      "7-11"      ),
        "gas":          ( "l",          "Unleaded"      "Exxon"     ),
        "bullets":      ( "30.06",      "Springfield",  "Walmart"   ),
        }

    Next, specify the basket of these commodities that back a certain
number of units of your currency:
    
    multiplier                  = 100

    basket                      = {
        # Commodity     Amount  Proportion
        'beer':        25,              # One for the road, eh!
        'gas':         50,              # Out to the hunt, and back...
        'bullets':    100,              # Should be enough to bag that Elk!
        }

    Establish your currency.  We'll say that 100 BUX (represented, of
course, by the "antler" symbol '&'), always buys 25 beer, 50l of gas,
and 100 rounds of ammunition for the 30.06.  Furthermore, we'll start
off with a K (credit factor) of 0.5, we'll feed a factor of 3x the
inflation error back into the K computation, we'll use a running
average of commodity prices over a window of 3 time periods in
computing inflation, and we'll start with time stamp 0 (instead of the
current actual time):

    now                         = 0
    buck                        = credit.currency(
                                      '&', 'BUX', commodities, basket,
                                       multiplier, K=0.5, damping=3.0,
                                       window=filtered.weighed_linear(
                                           3., value=1.0, now=now ),
                                       now=now )

    Now, in the main loop of your program, you'll need to update the
commodity prices from time to time, in order to allow BUX to compute a
new credit factor K.  Get a basket of commodity prices.  It must be
complete (have all commodities), the first time you call update().
We'll use a time unit of 1, instead of the (default) current real
time:

    now                         = 1
    prices                      = {
        # Commodity     Price   
        "gas":            1.00 /   1,   # BUX1.00/ea
        "beer":           6.00 /   6,   # BUX1.00/ea
        "bullets":       25.00 / 100,   # BUX0.25/ea
        }
    buck.update( prices, now=now )

    Since we presented a set of commodity prices that worked out to a price of
&100.00 for the full basket of BUX commodities, we have no inflation
(buck.inflation() == 1.0), and hence buck.K() will be 0.5 (the initial value).
So, how do we get credit out of this system?  We pledge a basket of commodities,
composed of 1 or more of the currency's commodities.  We could pledge the
initial basket we used to create the currency.  It should be worth &100.00 (no
inflation or deflation!), so we'll see a resultant value of &50.00 credit:

    buck.credit( basket )


    That's it!  


    Here are the details of the credit.currency interface:

currency( commodities, ... )    -- create a new currency

    commodities - A dictionary describing the commodities (unused, for now)

    basket      - A dictionary containing the number of units of each commodity
                  backing the currency

    multiplier  - How many units of currency does this basket represent

    K           - Initial (guess) at an appropriate K.  The currency's PID loop
                  will compute it.

    Lk 		- Limits on the range of K.  Unless people trade for no financial
                  reason (eg.  crazy prices like 0, K will remain sane).
                  Remember, there are NO CREDITS in existence that are not backed
                  by pledged wealth, so credits are equivalent to wealth, and
                  should (eventually) be treated as such by the market.

    damping     - A guess as to an appropriate level of in/deflation error
                  feedback into K.

    window 	- By default (for backward compatibility), how many time units we
                  should filter (average) in/deflation over, in computing K.
                  This will filter out anomolous pricing activity (momentary
                  spikes, etc.)
                  
                  Use an instance of filtered.weighted_linear instead, eg:
                     ..., =window=filtered.weighted_linear( 2., value=1.0, now=now ), ...
                  specifies an averaging window over 2 time units.

    now         - Time stamp.  Can be real time, game time, turns, etc., so long
                  as it increases.


currency.update( price, now )   -- Update prices, compute inflation and K

    price       - A dictionary of commodity prices, per standard commodity unit

    now         - An increasing time stamp of some kind

    Updates the internal state of the currency, computing Inflation, and 'K'.
    Returns nothing.  If invoked multiple times with the exact same timestamp,
    simply collects the prices for the next update.

    If you use stepwise time values (eg. "turns" or "days" vs. continuous,
    real-time values) for 'now', then you should consider how to handle times
    when you update prices.  When updating the currency system's prices,
    remember to use the "current" time for 'now', which represents the period
    during which the prices were measured. Then, advance the time to the next
    "future" value, and perform an update (probably with no new prices), to
    advance the currency.  For example:

        now = 12
        bux.update( now=now )
        #... Price changes detected sometime during "turn" 12 ...
        bux.update( {'bullets': 26.00 / 100}, now=now )
        # ...
        bux.update( {'beer': 5.25 / 6}, now=now )

        # ... Next turn; advance, and compute new currency value.
        now = 13
        bux.update( now=now )

    The currency will now reflect the Inflation (and compute K) based on the
    commodity prices having been in effect for one time period.

currency.credit( basket )       -- Compute credits available for a commodity basket

    basket      - A dictionary of commodity units pledged.

    Computes and returns the number of credits issued, given the current
    commodity prices and K.


currency.K()            -- most recent K.
currency.inflation()    -- most recent inflation factor
currency.now()          -- most recent timestamp

    Optionally supply an index (eg. 0, -1 (the default), 100...)

currency.trend          -- the whole list of trend data, if you want it


SIMULATION

   Run credit.py to see a simulation of a currency.  Adjust the
commodity prices to see Inflation go up/down, and observe the K will
decrease/increase 'til Inflation is once again restored to 1.0
(commodity prices respond to the increase/decrease in credit).  After
3 time periods (adjustable), K will settle flat again, now that it has
quenched any inflation/deflation.

    Note that K will NOT settle out, if prices do not respond; this
would be impossible in a true economy, because A) credit is withdrawn
with force when K decreases (beside the obvious large financial
incentive to sell wealth for credit at the presently inflated price),
and there is a large financial incentive to pledge wealth for credit
when K increases, and buy the (presently under-priced) commodity or
commodities cheaply, correcting the commodity price deflation.

   Run pid.py to see a PID controlled rocket, illustrating the effect
that modulating the P, I and D constant factors has on balancing a
dynamically stable system.


ALGORITHM

    The damping feedback control loop that generates K as money
inflates and deflates over time is similar to the control circuit for
a robot that balances a stick.  However, in this case, the mass of the
stick and the force of gravity would be changing over time, too!

    Therefore, the algorithm must respond only to the velocity and
acceleration of the target -- not make assumptions about its mass and
gravity.

    Some examples I looked at were a home-made "Segway" balancing algorithm:

        http://tlb.org/scooter.html

An excellent balancing robot page, with dozens of references to other
similar projects:

        http://about.share4vn.com/2008/05/nbot-balancing-robot.html


Source code in C obtained for one balancing robot:

        http://www.bkinnovation.com/bkbot/

Finally, I found a full-on Python implementation of a balancing
simulation using Bang-bang, proportional and PID controllers:

        http://www.edparadis.com/pyode/


Another PID loop implementation was found in cgkit's pidcontroller.py
file, which also illuminated some errors in the www.edparadis.com PID
loop implementation; see pidcontroller.py:

        http://gentoo.osuosl.org/distfiles/cgkit-2.0.0alpha7.tar.gz

A more complex PID controller was found in:

        http://matforge.org/fipy/browser/trunk/fipy/steppers/pidIterator.py?rev=1942&format=txt


The final PID controller was based on one Ed Paradis' work, with some
corrections deduced from other work.