document for luke for beta release

pull/121/head
Weiwu Zhang 7 years ago
parent e6bbfeb306
commit a11847be80
  1. 134
      desktop/README.md
  2. 121
      dmz/README.md

@ -0,0 +1,134 @@
### Authorisation server use cases
In the March release, there will be 3 cases when the authorisation server is needed.
1. When a user purchases an asset from the issuer's website, using his credit card, the website generates a Universal Link. The authorisation server generates the link because it has the issuer's key. The link is sent to the user by email through the issuer's own email service.
2. When the user received the Universal Link, he can "import" the asset to his wallet. If he has Ethers, the import is done by sending a transaction. If he hasn't Ether, the import is done by sending an HTTP POST request to the authorisation server, which generates such a transaction.
3. When the user wants to transfer the ticket to someone, if he knows the other person' Ethereum address, the transfer is done through a normal `transfer()` call. If he doesn't know it, he can generate a Universal Link himself, signed by himself, and send to that someone by email or SMS. If the beneficiary has Ether, he can move the asset himself; otherwise, he will send an HTTP POST request, where the authorisation server, finding it not spam, transfer the asset for him.
### Do we separate the role of authorisation server to 2 further roles: pay-master and key-master?
It is easy to see that in the 3 cases when authorisation server is used, only the first case requires the use of authorisation key. The second and third case can all be done by a service that has some pocket money, but not the issuer's key. In fact, it is intended, so that there can be no issuer's key behind the web APIs. In the future, we can divide the roles. The first case can be done by a keymaster and the second and third case by a paymaster.
The advantages of this separation are:
1. The issuer's key is not behind the web API; the attacker who went through web API only gets some pocket money;
2. Paymaster can be outsourced to make the asset issuer's side simple;
3. the keymaster is a target of hacking and the paymaster is a target of spamming. Separating them helps define attack models and optimise security.
Do we do the separation now? It's attempting but there is a reason not to do so:
To fight spams, paymaster needs to access business logic to determine spam attacks. For a small asset issuer, it may be easier to integrate it into their system if all "blockchain" stuff is just one component.
### The security issue with Universal Link
The apparent security issue is that Universal link is an attestation upon an unknown public key. Whoever receives the attestation can "import" the asset easily. The correct cryptographic solution, by asking for a public key first, isn't applicable here, for, among the 3 cases listed, in the first case it leads to shopping cart abandonment and in the last case leads to extra user communication (suggesting user install a wallet and asking the user to submit a public key).
Two methods, both by James Brown, are these:
1. The "import" requires the beneficiary to validate phone number by SMS verification code.
2. The "import" requires the beneficiary to decrypt a part of the universal link (say, `r` or `s`). The password defaults to beneficiary's phone number.
With the first method, I expect the phone number to be in the Universal Link, signed together with other data, and the paymaster is responsible for validating the number. With the second method, the change to the scheme is little.
## The smart-contract itself ##
2 keys are used in the smart-contract:
- executioner (suicide key), which is the constructor's sender, held by either issuer, or αWallet team (if the issuer has too weak blockchain capacity).
- issuer key. always held by issuer.
## The Asset Definition file ##
It came a long way for me to create asset definition in an XML format due to the complex metadata needed for a client to access a smart contract in a programmable way. The next question is: what key should be used to sign this asset definition XML?
There are 2 candidates:
1. The owner's key of the smart-contract.
2. The private key of a web certificate of the company or organisation starting the smart-contract.
There are a few advantages of using the contract owner's key:
- It doesn't force any dependencies - many smart contracts authors are reasonably anonymous; to force them to leave a trace of their identity by applying a web certificate is not our design goal.
- The admin key of a smart-contract is intended to last longer - for most contracts, being valid as long as the contract is at work. The web certificate, although can be renewed without changing the private key, is regenerated yearly, in many organisations.
- The web certificates have a designated purpose (to secure the website). It may come as a surprise to some administrator users that its use is needed to control the way the world interacts with a smart contract.
- When it comes down to trust, we trust the contract owner about their smart contract almost as much as about their definition of how apps should interact with that smart-contract. A webmaster is an external guest invited to the party from the point of view of the smart-contract owner.
- Only one signature is needed. Many organisations own more than one websites, and it is not clear which site's key should be used.
However, there are also advantages from the second option, of using the website SSL key.
True
- Most people get to know a smart-contract from a website. There should be a way to certify that "this smart contract is recommended by this website". The trust is passed from website to smart-contracts.
- Most SSL certificates are kept in a format that can be easily used for signing stuff. The smart-contract owner's key could be kept in Trezor, which has difficulty displaying a long XML file (it may be an advantage if the user took some strenuous effort to scroll down Trezor 1000 times to verify the XML file being signed is correct).
- SSL certificates can be used to sign XML file while Ethereum key might be kept by a security device which can only sign strings starting with "Ethereum Signed Message..." which breaks XML Signature standards.
I am more inclined to use a combined way: signing the XML file from the website's key and acknowledge it from the smart-contract.
First, let's define a new interface:
`contract.getDefinition()`
It either returns a full XML file or returns a hash that must match that of the XML file. In either case, no matter if the XML file is signed or not, it's considered acceptable. As long as the XML file hashes to the hash value returned by the smart-contract, we call the ADF "true".
Then, this very XML file may optionally be signed by a website SSL key. If the signature is correct, the website's certificate is verifiable and has not updated, and we call the ADF "trusted".
Then, there are cases when an XML definition is outdated, contains errors or for some reason; people are still using it after the smart-contract owner refuses to provide an update to that XML file - typically because the key is already lost. In such a case, a webmaster can provide an XML patch, which updates the True ADF, and that update has to be signed by the webmaster. If the True ADF was a signed one, and the update is signed by a key certified by a certificate of the same website, it's called "amended".
Finally, if the True ADF was not a signed one, or that a contract does not provide getDefinition(), an ADF could be signed by αWallet, in which case it is called "rectified".
The priority of selecting ADF in the event that there are conflicting versions is the following.
- Category 1. Amended (imply trusted)
- Category 2. True and Trusted.
- Category 3. True.
- Category 4. Rectified.
Let's examine this ordering method by scenarios.
### Scenario 1. The thorne builder who, if revealed, may be buried alive ###
Let's say that there is a King of Ether smart-contract: anyone can deposit money and get rewarded by the next deposit, with the condition that the next deposit has to be higher in amount.
For example, Alice deposits 100 Ethers in it. She will get rewarded when another day Bob deposits 101 Ethers in it. Alice gets exactly 101Ether in reward; Bob will be rewarded when, or if, another person comes and deposits more than 101 Ethers.
The smart contract is created by someone called James Brown. However, James didn't believe that his contract can stand the test of time. He lives in a communism dictatorship country where he is punishable in the event that his contract is hacked.
Therefore, he produced an ADF file to allow wallets to interact with his smart-contract, yet he did not sign the ADF file. The smart-contract spits out the hash of the ADF file as a way to validate the ADF file. Since there is no signature on the ADF file, the ADF file can't be "Trusted", but it still can be "True". By our ladder of priority, the only ADF file that can be accepted by the wallet is the True one, category 3.
The user who accesses this smart-contract from the wallet is given the security status message "No trust assumed".
### Scenario 2. The smart-contract admin key is lost. ###
Alice started a smart-contract and a website www.alice.com about it. She wrote an ADF file and signed it with her SSL key, together with the SSL certificate. The smart-contract is configured to spit out the hash of that very ADF file on `getDefinition()` call.
The user who accesses this smart-contract from the wallet is given the security status message "as trustworthy as www.alice.com".
For a year it worked fine - the ADF file is category 2 on the priority list. Then, like the most smart-contract authors, she lost her owner's key. She still owns the website though, and the contract is still operational.
She obtained a new SSL certificate and a new SSL key. She signed another ADF file. Although she couldn't update the smart-contract with its hash, the wallet recognises that it comes from the same website, and prioritises the ADF file over the previous one because it is a category 1 ADF file.
As time goes buy she has to move to a new smart-contract because she couldn't update the old one, and business changed since. There is no way to destroy the old contract, but she created a new one and updated a new XML file, preventing the users to interact with the old contract. The new XML file is also a category 1 ADF file, with a newer timestamp signed by the same SSL key. Therefore it replaces the old category 1 ADF file. The user was introduced to use the new contract from a prompt message defined in the new ADF file.
### Scenario 3: The smart-contract owner and the website owner isn't the same person. ###
TTM coin (short for To The Moon!) is a new ICO in town started by CEO John and his brother, CTO Joey. John hired a webmaster to build the ICO website, and Joey wrote the smart-contract. Joey also did some prototype for a new technology he called Sigmund, of which the ICO is about. Both John and Joey are led by their ICO coin buyers to believe that Sigmund is a technology with great potential, giving users the potential to be whatever they want to be.
ADF file was released as True and Trusted category 2. Having raised 10 million USD in ICO, John and Joey fought over a Youtube video on who owns the project. John believes that he got the crowd and Joey thinks he owns the contract and therefore the money. Joey decided not to give the money to John, and John, in turn, released a new ADF file blocking user's access to the smart-contract. Most simply, John can publish a really messed-up XML file to confuse the users unless Joey coughs up the money.
In this case, John's ADF file is in category 1 - Amended. Unlike Alice's case, Joey did not lose the smart-contract key. He simply updated the smart-contract to invalidate the previous True and Trusted ADF, therefore invalidating the Amended as well, moving it out of the list.
Consider that the action of buying ICO token is done to the contract, despite its reputation is assumed from the website, the fact that the contract holds users tokens and funds makes it the trusted party. Coherence between the contract and user's means to access it (ADF) is prioritized.
Furthermore, it's more sensible that the wallet should behave as intended by the contract, assuming trust from a website, not that wallet should behave as intended by a website to access a contract. Therefore, a design allowing Joey to have an upper hand wins in the lines of common sense, without judging who is the rightful actor.
### Scenario 5: The smart-contract doesn't support `getDefinition()` ###
In this case, a Rectified ADF is used which is signed by αWallet team.

@ -0,0 +1,121 @@
## Universal link for Ethers
A universal link is like this:
https://app.awallet.io/AAGGoFq1tAC8mhAmpLxvC6i75IbR0J2lcys55AECAwQFBgcICfENh9BG3IRgrrkXGuLWKddxeI/PpXzaZ/RdyUxbrKi4MSEHa8NMnKTyjVw7uODNrpcboqSWZfIrHCFoug/YGegb
The part portion of the link is entirely made of a single base64 string. At the moment '/' (slash) is a part of the base64 string; in the future, we will use a 64-character set that is web-safe. The format of the data encoded in base-64 is explained in UniversalLinkTest.java. Put it simply, it closely resembles an order to the MarketQueue, with some limitations.
Every link contains a purchasable token. The link serves to let the user redeem the token.
It behaves differently depending on if the user has the app or not.
If the user did not install the app, the universal link shows a simple webpage, which displays the information about the token. In simple cases like ERC20, it merely presents three fields:
- token's name, e.g. "EOS"
- token's amount, e.g. "1"
- how much Ether is needed to redeem the token, e.g. "0.1"
In more complicated cases, like event tickets, it displays information like the location of the event, the venue, the entrance instruction, the time, as well as how many tickets, their seat number and how much Ether is needed to redeem them a whole.
In even more complicated cases, like CryptoKittens, a kitten is drawn on that webpage with a price tag.
Below these token information is a link to our app in App Store or Play Store, so that they can install the app to buy the token.
If the user has the app, the app will open the link from the app, presenting the same set of information as the user would get from the website. The app would download the asset definition XML file if necessary. The app would ask the user if she wants to purchase the token (or that the user doesn't have enough Ether to acquire these token).
In the long run, it should be possible to build Universal Links which asks for other tokens than Ether.
## Pickup-Links
Pickup-Links are just Universal Links except that it requires zero Ethers to redeem. There are 2 cases where this could happen.
1. The asset issuer issues the link to users who pay with non-crypto currency (e.g. Credit Card). Since the token is already paid, it has a price of 0 Ether.
2. When Alice transfers her tickets to her friend Bob for free. Maybe because she bought it for him.
In the case of pick-up links, the token issuer may want to send the transaction on behalf of the users, to spare the users of having to have Ether in the wallet at the outset.
## How do the apps handle universal link
If the mobile device has the app installed, Universal Link triggers
the app to open the link. The app would launch and does the following:
1. Recover the public key from the signature and base64 encoded
message _order_. Check that it is not 0.
2. Take the recovered public key, generate an Ethereum address from it and look up the contract (which is in _order_) to check it still owns the tickets under the specified indices (which is also in _order_). There is a good chance that the link was previously used, so be clear on that.
3. Present the user with information of the token. E.g. draw a cat. Present the user with the price to redeem the link. If the price is zero, just show the transaction fee needed (if the user does not have Ether, provide the option to attempt to get issuer to send the transaction).
4. The wallet then calls `trade()` function on the smart contract, attaching required Ethers. The call should result in the token be allocated to user's address. Or, the wallet calls the issuer's server for it to send the transaction on behalf of the user.
### The servers
Two types of servers are involved in the Universal Link: DMZ server and FeeMasters. The two are named so to make it crystal clear what are the security implications, that DMZ server is exposed, doesn't have any Ether in it; the FeeMaster servers each have a wallet to replenish and needs to be protected.
+------------------+
+------------------+ | |
| | | Shengkai's |
| CryptoKitties | | business servers |
| business servers | | |
| | +--------+---------+
+--------+---------+ |
| |
| |
+--------+-------+ +--------+-------+
| | +-------------+ | |
| FeeMaster of <-------+ Wallet App +-----> FeeMaster of |
| CryptoKitties | +------+------+ | Shankai Co Ltd |
| | ^ | |
+--------+-------+ | +--------+-------+
| +--------+--------+ |
| | | |
| | DMZ Server | |
| | by Stormbird | |
| | | |
| +--------+--------+ |
| | |
| | |
+--------+----------------------+---------------------+---------+
The Ethereum Node Network
- DMZ server handles the link if the user doesn't have the app, introducing the user to install the app.
- The app handles the link without any of the servers in the graph, if the user can cover the transaction fee.
- If the user can't cover the transaction fee, the wallet app forwards the link to FeeMaster of corrisponding asset-issuers, who may or may not send the transaction on behalf of its user.
- All of these servers are connected to Ethereum. DMZ server needs it to work out if the link has been used.
### The logic in a fee master, example
First, the wallet reads the feemaster server defined in the Asset Definition File. Say, Shanhai's feemaster is 'feemaster.shankaisports.com'.
Then, the wallet replaces the Universal Link's hostname with the paymaster's hostname, and sends a POST request to that URL. The content of the POST request is the wallet's address, say,`0xde0B295669a9FD93d5F28D9Ec85E40f4cb697BAe`. This is an example HTTP POST:
POST /AAGGoFq1tAC8mhAmpLxvC6i75IbR0J2lcys55AECAwQFBgcICfENh9BG3IRgrrkXGuLWKddxeI/PpXzaZ/RdyUxbrKi4MSEHa8NMnKTyjVw7uODNrpcboqSWZfIrHCFoug/YGegb HTTP/1.1
Host: feemaster.shankaisports.com
Content-Type: application/x-www-form-urlencoded
Content-Length: 42
address=0xde0B295669a9FD93d5F28D9Ec85E40f4cb697BAe
There, the server first does some spam detection - e.g. check if the date of the event is too much into the future. Finding it not a spam, the server then constructs a call to the smart-contract to allocate the token to 0xde0B295669a9FD93d5F28D9Ec85E40f4cb697BAe
tradeTo("0xde0B295669a9FD93d5F28D9Ec85E40f4cb697BAe", 0, [3, 4], 28,
"0x95B06BF20CD3F45497CC193028ADBADB140984E3E803E53D52356969BB408AD8",
"0x680EA2AB7CDC3E4D91B653BBC16886B143BDE426EF6978DFFC8C4CFBDCF883AF")
The server broadcasts the transaction and returns the transaction hash in response to the HTTP POST.
The possible statuses returned from an authorisation server can be one of these. In either case, the wallet prompts the user that they can add some Ether to their wallet and try again.
Spam: the asset is transferred more than 5 times
: The authorisation server refused to do the transaction.
Authorisation Server is poor
: The authorisation server has no Ether to finalise the transaction.
Authorisation Server is not available
: This can be caused by server maintenance.
Loading…
Cancel
Save