Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Suggestion] Sign accounts, not questions. #5

Open
livinginformation opened this issue Sep 15, 2015 · 17 comments
Open

[Suggestion] Sign accounts, not questions. #5

livinginformation opened this issue Sep 15, 2015 · 17 comments

Comments

@livinginformation
Copy link

Hey Arsenische, neat project you've got here. I like the direction you're going in, and I think expanding it to include (but not require) user accounts would be interesting. If you have an account, you can sign it with your address, which gives it credits to use on questions (your account credit is the maximum amount you can vote with on any given question, you don't "spend" it per se). Note that I use the word "credit" in place of a better term that I can't think of at the moment.

The ability to assign credits to accounts instead of questions would let some other interesting avenues for development emerge:

  1. Questions you can vote on only if your credit count is above a certain number.
  2. Questions where any user above a certain amount of credit can vote a single time (sybil resistant voting on things that aren't necessarily binary)
  3. Allocation (and reallocation) of credits within a single question with multiple options, allowing the voter to adjust his/her preferences over time.

If you're interested at all in going in this direction, I would be very interested in becoming involved in the project myself.

@arsenische
Copy link
Owner

Hi Livinginformation. Thanks for your interest, lets discuss it!

I was thinking about user accounts too. The main advantages are usability and security. It would be much safer and easier to vote without copy-pasting strings of text and typing in your password every time. But it comes at a cost: voting results won't be that convincing and will require trust to our database.

The current solution doesn't require trust: arguments' validity can be calculated from text statements, bitcoin signatures and the Blockchain. All this data is public (and if we try to censor it - anyone can just use other channels to distribute it).

I think the mentioned avenues for development are possible without user accounts (people can use different bitcoin addresses, swap the coins between them, etc).

In fact, 1) and 2) can be implemented by trivial filtering of the signatures.

Allowing multiple options (3) is less trivial, it can be implemented in various ways. The simplest approach would be to allow more options to a signature (instead of binary believe/doubt), but I was thinking more about combining binary arguments into a graph to enable users to:

  • compare arguments to each other (argument1 vs argument2 vs argument3...),
  • try to prove something (if argument1 then argument2),
  • identify the contradictions (if argument1 then not argument2),
    etc.

It could be a platform for massive pseudonomous discussions, a graph of logical arguments, that are evaluated against each other based on bitcoin signatures and laws of logic.

As for user accounts, they can be thought as arguments too. Example:

  1. Bob creates his account by signing the argument (A: "Bob is credible") with his bitcoin addresses thus voting for this argument and giving it a credit/validity of 1 btc
  2. Alice signs the argument (B: "Bitcoin is ready for mass adoption") with 2 btc
  3. Bob votes against B thus implicitly creating a compound argument "If Bob is credible then it is doubtful that Bitcoin is ready for mass adoption" with validity 21000000 btc.
  4. Now we can evaluate the argument B: "Bitcoin is ready for mass adoption" as (sum of pros)-(sum of cons) = 2 - min(1, 21000000) = 1 btc.

Interesting side effect of this approach: other users might vote on Bob's credibility too (thus increasing/decreasing his influence and indirectly affecting the validity of the argument B).

User accounts would be very convenient for Bob, he wouldn't need to sign each argument individually (as Alice does). But probably we should require him to sign the list of his votes before using them in our calculations (or to calculate confirmed/unconfirmed votes separately).

Sorry for the long message, not sure if all this makes sense to you. Please let me know what you think.

Update: renamed "rationality" to "credibility", the terms need to be thought over.

@livinginformation
Copy link
Author

Okay, so a few thoughts:

The DB has "arguments" as the primary data structure at the moment, where a single argument is a statement, and two fields, "pros" and "cons", which each have a substatement, and a list of address/signature/timestamp blocks. It appears as though, at the moment, a signature is all-or-nothing. If you sign, all coins in that address are immediately associated with your choice.

If we go with a user-centric approach, we can instead change the schema to have the main data structure be singular users.

User structure:

{ user_id: ..., 
  statements: [
      { 
         argument_id: ...,
         argument: ...,
         opinion: ...,
         weight: ...
      },
      {
         ...
      }
  ]
}

Then, the user signs the entire JSON string as a whole, and once the system processes it, the votes are applied. You can sign that string with multiple addresses too, so you don't need to consolidate your coins in one account.

In this schema, "Opinion" can currently just be believe/doubt, but could later be modified to carry a logical operation, such as implies, and, or, etc for compound statements. Additionally, "Weight" refers to either a percentage from 0-100 of the signed coins, or a cap of how much vote you give it (say I sign with 50 coins, but I only really think this question is worth 20, for some reason). There needs to be some way of adding granularity to votes as opposed to lump sums.

@NxtChg
Copy link

NxtChg commented Sep 16, 2015

But it comes at a cost: voting results won't be that convincing and will require trust to our database.

Just show a list of all voters, so people could see their votes and could also calculate the results themselves. Each voter can verify that his vote is correct and everybody can get the total vote.

@arsenische
Copy link
Owner

@NxtChg, thanks for your proposal, but I don't think it is solves the problem: if somebody complains that we faked a vote, we won't be able to disprove it. And if we (or malicious hackers) create fake votes, nobody will be able to prove they are fake.

@livinginformation, I think your proposal could work, but I am not sure it is a good idea to make users sign the JSON data. Wouldn't it be better to present it in human-readable form?

E. g. the list of statements:

I believe that <text of argument>
I doubt that <text of argument>
<...>

is quite natural to sign for a human being.

@NxtChg
Copy link

NxtChg commented Sep 22, 2015

Ask users to sign secondary key you generate on registration, then use that key to sign their votes.

@arsenische
Copy link
Owner

Yes, that could work unless we leak the secondary key (or a table with all our secondary keys).

Though hacker would need not only to know the keys, but to somehow submit the signatures to our database on behalf of users as well.

In case of such (detected) event we could restore the database from backup, change the keys and ask users to sign them again.

@NxtChg
Copy link

NxtChg commented Sep 22, 2015

Why would you leak them? That would be suicidal and just mean "voting canceled".

@arsenische
Copy link
Owner

Unintentionally, of course. Or forced by authorities. Yes, I think your approach could work. It is convenient for users (since they need to provide just 1 signature). But it requires trust to us.

@NxtChg
Copy link

NxtChg commented Sep 22, 2015

There's not much trust, since you still need to publish everything openly. If there are claims that you manipulate votes, but they are too rare to make a difference, voting can still be considered successful.

There's no reason for you to manipulate votes unless it makes a significant difference, but in that case people will most certainly notice it.

This also means that you need some margin, like 5%, where you can't declare a clear winner and have to declare a tie instead, i.e. 49/51 won't mean the 51 side won.

@NxtChg
Copy link

NxtChg commented Sep 22, 2015

Also, when somebody complains that you manipulate votes, just tell them to re-sign whatever they really want with their real key. Make secondary keys optional, this will clear you completely.

@livinginformation
Copy link
Author

@arsenische Signing a list of statements works, but here's a complicating example:

I have 21 BTC and see the statement "This statement is True". I fully believe that, and am willing to sign it with all 21 BTC in my posession.

I see a second statement, "Troll 2 is literally the best movie ever made". Now, in the context of the question, lets assume that I thought Troll 2 was pretty damn good (it absolutely was not), but not the best ever. I only half believe that statement. So, I want to only allocate 50% of my BTC to that statement. If I sign both messages at once, there is no metadata in that text block indicating how much to allocate to each, so both statements get a vote of 21 BTC.

I think a more elegant solution would be to have an interface in which the user can see a list of all questions they've agreed/disagreed with, and how much they've allocated to each question. Once the user presses "Sign" on that list of statements, we generate a JSON object, which the user signs. I'm not suggesting that the user actively generates the JSON themselves, just that we use it as an intermediate representation so we can attach relevant metadata to questions in the future without breaking backwards compatibility.

@arsenische
Copy link
Owner

@livinginformation we could enhance the human readable syntax, make it:

I am 35% sure <text of argument>

"I doubt" would be an alias to "I am 0% sure", and "I believe" would be equivalent to "I am 100% sure".

It is not that difficult to generate or parse and is easy to understand. I think any non-technical person should be able to understand what s/he signs. Do you agree?

Btw, what do you think about @NxtChg 's suggestion? S/he suggests users to sign the keys that would be used by our system to sign the statements on behalf of them when they vote.

@livinginformation
Copy link
Author

@arsenische I agree that human readability would be a nice goal to have, but it makes it very difficult to change the schema to be more permissive in the future (logical operators, for example). If we use JSON as our intermediate representation over plain text, it gives us the ability to add fields on-the-fly without significant modification of the codebase (and possibly breaking backwards compatibility). If we assume that the users have implicit trust in the site from the beginning, and the things that they sign are auditable, I don't think benefit of (non-coder) human readability is greater than the benefit gained by using an easily modifiable data structure.

@NxtChg 's suggestion is interesting, but it removes the possibility of the system becoming decentralized in the future. That is, it removes the potential for auditability by a third party proving that the users themselves signed the statements, as opposed to us signing them against their will. Now, that isn't necessarily a dealbreaker, but it presents us with a choice in direction (centralized / potentially decentralized in the future). Thoughts?

@arsenische
Copy link
Owner

@livinginformation I mostly agree with your arguments. Though I think it is not a big problem to write additional adapters that would parse new formats if plain text format becomes insufficient.

I think the format should be generic and shouldn't depend on IDs from our database. The general idea is that something is signed with bitcoin address and thus is backed by its value. If we want to make a reference to something, we can use hash of it instead of ID.

Users should probably sign only new votes (that haven't been signed by them), so we could represent this piece of data either as list of lines:

I am <confidence>% sure that <statement>
<...>

or as a JSON array:

[
  {
    statement: <statement>,
    confidence: <confidence>
  },
  <...>
]

When user signs it and submits the signature, we save the signed document with the signature to our database as a proof of votes and then parse it, creating the statements linked to it (and link these statements to the % of the bitcoin address value as well).

PS: just couple examples to demonstrate the meaning of the : if the confidence is 50% then the validity of the signed statement won't change; if the confidence is 25% then the signed argument is backed by 25% and objected by 75% of the value of the signer's bitcoin address and the validity should decrease.

@livinginformation
Copy link
Author

I 100% agree about not depending on IDs, that was more of an oversight (I'm used to JSON always having an ID for the things I've used it for).

Signing only new documents makes sense, because we can assume if at time T, M statements are signed, then at time T+1 if there are N new statements, there is no need to re-sign the statements valid at time T.

Some thoughts:

  1. Should users be allowed to revoke a signature, or do we consider revocation to mean a transfer of coins from address X to another address Y?
  2. How should we handle the case where a user signs the same statement with two different confidence levels? Do we default to the (highest/lowest) confidence, or only consider the first signature we see? If we only consider the first signature, auditability becomes a problem. Off the top of my head, the only fixes I can think of for that would be to timelock the hash (a la Proof of Existence), or to make the user submit a numerical revision (monotonically increasing number in the JSON) where only the highest known revision is valid. Timestamps might work in this case.

*Edit: Unix Epoch timestamps will work perfectly, that second thought is a non-problem.

@arsenische
Copy link
Owner

Good thinking. It would be nice to allow users to change their opinion, though it adds some complexity. I like the idea of timestamping and using the latest vote as valid.

In the text file that could be just the first line for the timestamp. In the JSON it could look like that:

{
    timestamp: <timestamp>,
    statements: [
        {
            statement: <statement>,
            confidence: <confidence>
        },
        <...>
    ]
}

@ChristopherKing42
Copy link

You could have users sign a key, but instead of uploading the private key, they only give you the public key. That way you can't leak the keys at all. If their private key gets compromised, they either issue a retraction, or drain all the btc from account associated with it. (These both require getting out their bitcoin private key, unfortunately.)

This is good for users because then they need to bring out their private key less often (especially if they are using cold storage). They only need it at the beginning, and if they compromise their voting key. (The voting key is less likely to be attacked, since it has less value).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants