--- /dev/null
+OpenDispense^2
+Client/Server Dispense Protocol
+
+The protocol is ASCII based, similar to the FTP protocol
+All server responses are on one line and are prefixed by a three digit response code.
+
+== Response Codes ==
+100 Information
+200 Command succeeded, no extra information
+201 Command succeeded, multiple lines follow (<length>)
+202 Command succeeded, per-command format
+400 Unknown Command
+401 Not Authenticated (or Authentication failure)
+402 Balance insufficient
+403 User not allowed to perform this action
+404 Bad other username
+406 Bad Item ID
+407 Invalid arguments
+500 Unknown Dispense Failure
+501 Action Rejected
+
+== Item IDs ==
+<item_id> represents the item ID
+Item IDs are allowed to contain any non-whitespace character, but in
+general they will be limited to the standard alpha-numeric set
+
+=== User Auth ===
+c USER <username>\n
+s 100 SALT <string>\n or 100 User Set\n (If no salt used)
+c PASS <hash>\n (Hex-Encoded SHA-1 Hash of <username><salt><password>)
+s 200 Auth OK\n or 401 Auth Failure\n
+User is now authenticated
+--- Alternate Method (Implicit Trust Authentication) ---
+If the client is connecting from a trusted machine on a root port then
+automatic authentication is allowed
+c AUTOAUTH <username>\n
+s 200 Auth OK\n or 404 Bad Username\n or 401 Untrusted\n
+--- Set effective user (User in `dispense -u`) ---
+c SETEUSER <username>\n
+s 200 User set\n or 403 Not in coke\n or 404 User not found\n
+
+=== Commands ===
+--- Dispense an item ---
+c DISPENSE <item_id>\n
+s 200 Dispense OK\n or 402 Poor You\n or 500 Dispense Error\n or 406 Bad Item\n
+--- Give to another user ---
+c GIVE <user> <ammount> <reason>\n
+s 200 Give OK\n or 402 Poor You\n or 404 Bad User\n
+--- Alter balance ---
+c ADD <user> <ammount> <reason>\n
+s 200 Add OK\n or 402 No balance\n or 403 Not Coke\n or 404 Bad User\n
+
+--- Get Item list ---
+c ENUM_ITEMS\n
+s 201 Items <count>\n
+s 202 Item <item_id> <price> <description>\n
+ ...
+s 200 List End\n
+--- Get Item Information ---
+c ITEM_INFO <item_id>\n
+s 202 Item <item_id> <price> <description>\n
+
+--- Get Users' Balances ---
+ <max balance> and <min balance> can be '-' to indicate "none"
+c ENUM_USERS[ <min balance> [<max balance>]]\n
+s 201 Users <count>\n
+s 202 User <username> <balance> <flags>\n
+ ...
+s 200 List End\n
+--- Get a User's Balance ---
+c USER_INFO\n
+s 202 User <username> <balance> <flags>\n
+
+--- Add a new user ---
+c USER_ADD <username>\n
+s 200 User Added\n or 403 Not Wheel\n or 404 User Exists\n
+--- Set user flags ---
+ <flags> is a comma-separated list of flag values (optionally preceded by
+ - to remove the flag) Valid values are: user,coke,wheel,meta,disabled,door
+c USER_FLAGS <username> <flags>\n
+s 200 User Updated\n or 403 Not Wheel\n or 404 Bad User\n or 407 Unknown Flags\n