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

Reinstate NIP-88: Polls on Nostr #1507

Open
wants to merge 6 commits into
base: master
Choose a base branch
from

Conversation

abhay-raizada
Copy link
Contributor

@abhay-raizada abhay-raizada commented Sep 20, 2024

Since the drama that caused NIP 88 to be removed: #1501

There have been two major updates:

I have made very slight changes according to some of the concerns raised in the comment thread.

@fiatjaf @vitorpamplona @staab @smolgrrr @alexgleason

88.md Outdated Show resolved Hide resolved
Co-authored-by: Asai Toshiya <to.asai.60@gmail.com>
@mikedilger
Copy link
Contributor

This looks about right. I didn't study it in detail, but I like the non-replaceable response event, the use of an 'e' tag instead of a 'd' tag, the option for multiple choice, and explaining how to count.

@smolgrrr
Copy link

bump

@alexgleason
Copy link
Member

This should still use a replaceable event for votes. That was never addressed. Say something that actually makes sense about it please, that's all I ask.

@abhay-raizada
Copy link
Contributor Author

@alexgleason explain how you can achieve expiration polls, with PREs, where the tally of the results doesn't change post expiration, when a user updates their PRE vote.

@alexgleason
Copy link
Member

@abhay-raizada You would simply query votes with the "until" filter, and you would HAVE to be querying from a trusted relay that enforces the created_at timestamp to be within a reasonable range of the current time when it accepts events. This is true for both the regular and replaceable event scenario.

The edge case where a user responds after the poll has ended because their malfunctioning client allowed them to, and the relay deletes the old version of their event, is not a sensible argument. So I will ask you again to please say something that makes sense.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Sep 27, 2024

@alexgleason This edge case argument makes perfect sense to me, since I want to be able to trust the polls I create. An editable vote with no paper trail is just manipulation.

You being non chalant about it is what doesn't make sense.

@alexgleason
Copy link
Member

alexgleason commented Sep 27, 2024

What you're describing is a buggy client behavior that does not benefit the person who voted in the poll. It would potentially allow a user to rescind their vote. People can already do that after a poll ends with kind 5 deletions. Why are you so worried about people rescinding their vote?

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Sep 27, 2024

@alexgleason They can manipulate the tally, they could pump fake votes and then rescind their votes even after the poll has expired. This could be a huge deal when poll results have actual outcomes, like decisions being taken or awards being given on the basis of these polls.

Manipulating the tally IS the incentive in this case and DOES benefit the manipulator(s).

With this spec I could run my own relay with slight adjustments (honor current time, no delete for votes), which already exists on a lot of existing relays, to make sure the poll remains authentic, with PREs there's no guarantee without heavy modifications.

@alexgleason
Copy link
Member

Okay so explain why people can't do that with kind 5 events.

@alexgleason
Copy link
Member

If you have to build a custom relay for your implementation to work, then your argument against replaceable events is moot. Because no matter what you have to build a custom relays for polls to work perfectly.

There may be an argument in favor of regular events. But until you can form a coherent argument for it, I am totally against this MR.

I want us to only merge NIPs where thoughtful choices have been made. Not ones with senseless reasons. Because then developers will suffer from those choices forever.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Sep 27, 2024

Ouch. I'm of the opinion that devs and users will suffer if we go the PRE route.

The point isn't to win an argument it's to have a good spec. Both options need custom relays,
but this method works using relay features that are out even NOW. It doesn't make the point moot, which you would want to win your stupid argument.

I can also begin talking about uneditable votes and other things which are easier to do with the current spec, but arguing with you at 2:00 am in the night is not worth it.

If you don't want to merge it, don't. My job was to write a decent spec, and a decent implementation for polls and I believe I've done that. I'll just continue making it better, if anybody else wants to use It, It's right here.

88.md Outdated

- **option**: The option tags contain an OptionId(any alphanumeric) field, followed by an option label field.
- **relay**: One or multiple tags that the poll is expecting respondents to respond on.
- **polltype**: can be "singlechoice", "multiplechoice", or "rankedchoice". Polls that do not have a polltype should be considered a "singlechoice" poll.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would like to have different kind numbers for each poll type instead of this polltype tag, so clients can specifically query the ones they support.

Copy link
Contributor Author

@abhay-raizada abhay-raizada Sep 28, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The usecase make sense, should we use an indexable tag like ["T", poll-type] instead? that way we wouldn't be polluting kinds

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm ok either way but I think having different kinds is cleaner.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, multiple types make more sense because you can always expand to new poll types without breaking current clients with new types as tags.

@vitorpamplona
Copy link
Collaborator

vitorpamplona commented Sep 28, 2024

The only benefit of regular events is simplicity: clients don't need to code the PRE system (deal witha indexes, PRE deletions, etc). PREs are better for those of us that already implemented the PRE system (which is a requirement), but it is terrible for new clients.

The only benefit of doing PRE is to offer fast-changing votes. Yes, this could be done by kind:5 deleting and re-submiting a regular event, but that will fill up the relay's database quickly. In non-fast-changing votes, PRE doesn't really save much data.

Expiration polls can be offered with both systems, but with regular events votes after the date are downloaded and discarded while with PRE public keys that voted a second time after the date get removed from the tally for cheating.

Neither option protects against tally manipulation. Frankly, I would never take the results of these pools seriously, since spammers, real users, and relays can all manipulate the tally, both while people are voting AND after the vote has finished.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Sep 28, 2024

but with regular events votes after the date are downloaded and discarded

@vitorpamplona How? I only query regular votes until poll expiration time?

Neither option protects against tally manipulation.

@vitorpamplona do you mean they don't protect against tally manipulation by default? because I can see both of the methods offer protection against tally manipulation given relays with custom rules.

@vitorpamplona
Copy link
Collaborator

but with regular events votes after the date are downloaded and discarded

@vitorpamplona How? I only query regular votes until poll expiration time?

Yes, isnt it what you want?

Neither option protects against tally manipulation.

@vitorpamplona do you mean they don't protect against tally manipulation by default? because I can see both of the methods offer protection against tally manipulation given relays with custom rules.

Sure, custom relays can make both cases work. And regular relays don't offer any protection.

But I wouldn't build custom relays for this. It's too niche. No one will know how to use it. Instead, you can simply make a DVM that confirms each vote with a new event by whatever rule the DVM is tallying.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Sep 28, 2024

Instead, you can simply make a DVM that confirms each vote with a new event by whatever rule the DVM is tallying.

that still doesn't solve manipulation? just makes applying rules easier, Also with regular events the custom-poll relays are not complicated, only needs to handle back dating and deletes , I'll see if i can add an implementation for it soon.

Yes, isnt it what you want?

Yes what i'm pointing out is that, votes after the date are not downloaded even for regular events.

@vitorpamplona
Copy link
Collaborator

vitorpamplona commented Sep 28, 2024

If you do DVM tallying, the author could select the DVM that is counting the votes and then clients can just download what the DVM is signing instead of the user's votes. The DVM can just output the results with a bloom filter of the events included in the tally, for each option.

But that feels like it could be its own event kind.

Basic bloomfilter spec if you want to try: #1497

@abhay-raizada
Copy link
Contributor Author

Understood, a very round about way to go at it, but it could work. How does a DVM know if an event is back dated though?

@vitorpamplona
Copy link
Collaborator

vitorpamplona commented Sep 28, 2024

Understood, a very roundabout way to go at it, but it could work

It depends on how serious you want these polls. If it is really serious, you want to separate the responsibility of tallying from storing. You also don't want clients to tally at all. People can choose 3-4 relays to store, but only one service to tally. And that service is the final result. There is no client, relay shenanigans where vote can keep changing over time if the client allows it.

How does a DVM know if an event is back dated though?

The DVM either runs while the poll is active and allows users to confirm their vote was counted OR it runs only at the end. Either way, the DVM stops when the poll closes and counts from everything it can download from relays.

Separating them from relays also allow anyone out there to code custom tallying methods, like checking for membership in lists or groups, etc.

Comment on lines +65 to +66
["response", "gga6cdnqj"],
["response", "m3agjsdq1"]
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we make the response tag indexable, response -> r ?

A client might omit some poll options, e.g. in cases where the option list is ridiculously long or a label is deemed to be inappropriate. When this is the case it would be nice to be able to only fetch responses to options that are displayed.

Copy link
Member

@fiatjaf fiatjaf Oct 13, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ridiculously long option lists are an attack, just like ridiculously long notes, ridiculously long hellthreads and all that. Both clients and relays should eventually guard against these things. Forcing relays to index more stuff unnecessarily doesn't sound like a fair tradeoff.

@abhay-raizada abhay-raizada changed the title Reinstate NIP-88 Reinstate NIP-88: Polls on Nostr Oct 15, 2024
@dluvian
Copy link
Contributor

dluvian commented Oct 23, 2024

I have implemented this nip in Voyage with the caveats that only nip22 replies are supported for commenting/replying on polls and kind:1068 is always interpreted as a singlevotepoll. Other poll types should have different kind numbers.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Oct 23, 2024

After giving this some thought, I am of the opinion that single and multiple choice voting should still be the same kind interpreted through tags, one is just the superset of the other and existence of one doesn't break the other as well, multiple choice can easily be interpreted as single choice in other clients and even vice versa without breaking other clients.

I do however think ranked choice will break this, and I should move it to a different kind, I will update this.

@abhay-raizada
Copy link
Contributor Author

abhay-raizada commented Oct 23, 2024

@dluvian removed ranked choice from the NIP, may add it as a different kind once I implement it on pollerama.fun

@dluvian
Copy link
Contributor

dluvian commented Oct 23, 2024

@abhay-raizada I'm ok with this but I still think having different kinds is the cleaner way. No need for a polltype tag and clients could decide which poll types they want to fetch.

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

Successfully merging this pull request may close these issues.

8 participants