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

Asset prices #1658

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

Conversation

vitorpamplona
Copy link
Collaborator

@vitorpamplona vitorpamplona commented Dec 24, 2024

Simple NIP to make $BTCUSD-like prices available on Nostr.

Read here

@v0l
Copy link
Member

v0l commented Dec 24, 2024

For reference I've been publishing BitcoinAverage prices for about a year under kind 1009

It has tags like this:
["d", "BTCUSD", <ask>, <bid>, <low>, <high>]

nak req -k 1009 -l 1 --stream wss://relay.snort.social

@vitorpamplona
Copy link
Collaborator Author

@v0l what time range do you use for the low and high?

Are those from book orders or from final sales?

@frbitten
Copy link
Contributor

@v0l what time range do you use for the low and high?

Are those from book orders or from final sales?

It depends on the candle's configured time. I think the simplest thing to do is to use a 1-minute period, which is the smallest and can be calculated later on. The Exchange saves all transactions for 1 minute and generates the candle with the values mentioned above.
You also need to know the Exchange where the candle was generated, as it can vary from Exchange to Exchange.

Semisol
Semisol previously requested changes Jan 1, 2025
Copy link
Collaborator

@Semisol Semisol left a comment

Choose a reason for hiding this comment

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

While we are at it, could we expand this somewhat more to general data sources? Would be good for things like weather data, etc too.

@KotlinGeekDev
Copy link

While we are at it, could we expand this somewhat more to general data sources? Would be good for things like weather data, etc too.

I agree. Maybe the 'd' tag then could be change to the category of the data source, and a different tag(which could be category-specific(?)) can be used as a label.

@frbitten
Copy link
Contributor

frbitten commented Jan 1, 2025

While we are at it, could we expand this somewhat more to general data sources? Would be good for things like weather data, etc too.

I think it's better to separate data types by different types. It is easier to deal with on the relay side, especially for blocking.

Obviously you have to reach a balance point of when to separate into types and when to identify in tags. Because we don't have infinite kinds. Maybe define a range of types for public data, and each kind for a group of data.
Example
One kind for currency data, another for meteorological data, etc.

@v0l
Copy link
Member

v0l commented Jan 1, 2025

While we are at it, could we expand this somewhat more to general data sources? Would be good for things like weather data, etc too.

no

@v0l
Copy link
Member

v0l commented Jan 1, 2025

While we are at it, could we expand this somewhat more to general data sources? Would be good for things like weather data, etc too.

I agree. Maybe the 'd' tag then could be change to the category of the data source, and a different tag(which could be category-specific(?)) can be used as a label.

Why are you wanting to add kind into d tag when we have basically unlimited kinds?

@vitorpamplona
Copy link
Collaborator Author

I am not opposed to generalizing it but I don't like open-ended specs. If we generalize it, we need to know exactly what can go here.

@conduition
Copy link

I think NIP88 proposal #919 is more appropriate than this PR, as that would allow nostr users to create financial transactions (DLCs) predicated on the data in a future event, before that event is published. Whereas in this NIP, you're basically just uploading the price string inside a signed event without any precise structure or prior announcement. This rules out conditional payments, or other cool smart contracts we can do, such as ticketed DLCs or ecash DLCs

@vitorpamplona
Copy link
Collaborator Author

vitorpamplona commented Jan 12, 2025

Is anyone using #919? I am not opposed to using DLCs, but they seem to be way too complicated for anyone to actually use it.

Do you see any asset price over there that I could easily query? Say.. the latest BTCUSD sale? How would I do that? And how would I find which pubkeys have it?

@conduition
Copy link

they seem to be way too complicated for anyone to actually use it.

https://lava.xyz (currently my contract client) is using DLCs right now to enable bitcoin-backed loans with stablecoins. But they have a centralized oracle, so they could theoretically cheat by just signing arbitrary prices. Having access to a distributed network of oracles on Nostr would make their service much safer for the end-user, because they could negotiate and pick a multiset of oracles they trust to arbitrate the loan.

Do you see any asset price over there that I could easily query? Say.. the latest BTCUSD sale? How would I do that? And how would I find which pubkeys have it?

Good question, it might be a nice touch to add a tag similar to your n tag in this PR, for numeric-outcome oracles which sign the prices of asset pairs. To enable easier searchability of oracles, as you say

@vitorpamplona
Copy link
Collaborator Author

vitorpamplona commented Jan 12, 2025

Having access to a distributed network of oracles on Nostr would make their service much safer for the end-user, because they could negotiate and pick a multiset of oracles they trust to arbitrate the loan.

That's what this PR does. It allows oracles to post their prices into Nostr. Lava can then use this PR, and the multiple price providers they trust on it, to get an average price.

@conduition
Copy link

But you can't use the data from this NIP for trustless financial transactions. And if you publish two valid but conflicting price events, there is no fallout, unlike with DLC oracles.

Sure it gets the prices "into Nostr", but what use is that if the pricing data can't be leveraged for trustless financial transactions? How do I create a trustless derivatives contract using the data from this NIP? I don't think you can, at least not without OP_CAT expressiveness or turing complete smart contracts.

I guess if all you want is a signed proxy to the cryptocompare API you could argue in favor of this NIP. But personally i'd prefer if we can actually use the data to do something novel

@conduition
Copy link

By the way, if a signed cryptocompare proxy is indeed what you want, I run one here which you can play with to test drive how oracles work.

$ curl https://conduition.io/oracle/announcements/cryptocompare/BTC/USD/2024-05-30T22:00:00Z/open
{
  "announcement": {
    "announcementSignature": "040fdc3610a9743db98ff3300da6b8178d9022af0db0e1a6696d4cc72b306678a91968abc28c4f84bd529a81dca7526e0a361716f60faaaee240c77cef937184",
 ...

@vitorpamplona
Copy link
Collaborator Author

What if Lava posted the price Oracle you use as a pubkey. If you use it, I assume it is safe enough for everyone else to use as well.

The goal for this PR is to have an easy way to tag an asset and dynamically render the price, like many sites do:
Screenshot_20250111-222233.png

If we can do that quickly for rendering via DLC that would be great.

@conduition
Copy link

The goal for this PR is to have an easy way to tag an asset and dynamically render the price, like many sites do:

In theory, #919 should meet your criteria as-is. If you wanted to render an asset price/trend dynamically using only data from Nostr oracles, you'd reference the nostr pubkey of an oracle, possibly also a filter for asset pair, and fetch the latest price attestation events (kind 89) posted by the oracle which match that query. Then you can parse the prices embedded in those events, and render whatever you need (e.g. the current price, the % change, whatever).

If the data is all you need and you don't care about the integrity of the data for financial purposes, you could skip validation of the attestation and just parse out the outcomes field, which for a numeric outcome is the digits of the price it signed.

If you wanna get fancy, you could fetch from multiple oracles and average them out, take the median, etc.

@conduition
Copy link

conduition commented Jan 12, 2025

I posted this in #919 as well, but I think we should try to reduce the scope of NIP88 to only oracle messages, and leave DLC client messages for later. There is upstream work still going on and I don't think we should standardize some of those messages. This would be good for you too, because it would probably mean a faster track to standardization.

I'll see about adding an optional asset-pair metadata tag to the NIP88 spec sometime soon 👍 Possibly it might come in the form of a new PR so I can take over as Ben is apparently not driving #919 much anymore.

@vitorpamplona
Copy link
Collaborator Author

Cool, if you do a new PR, I still need kind 10041 from here so that the user himself can declare which oracles he/she trusts.

@frbitten
Copy link
Contributor

@conduition The proposal for this PR, as far as I understand, is the public disclosure of prices. Any currency/asset. While the PR you mentioned is asset purchase and sale transactions.
They are different objectives and, in my understanding, complementary.

@conduition
Copy link

I've submitted a new version of NIP-88 with reduced scope, which includes only kinds 88 and 89 (announcements & attestations): #1681

@conduition
Copy link

@frbitten I think you may have misunderstood; #919 #1681 and specifically the oracle events of kind 88 and 89 are more general and encompass everything this PR can do and much more. If "public disclosure of prices" from trusted sources is what you're after, DLC oracle announcements are the perfect way to standardize that.

Think of it this way: A DLC oracle doesn't just publish asset prices. A DLC oracle publishes announcements and attestations for arbitrary events, potentially including asset prices.

  • An announcement is effectively a promise which says "I will sign the outcome of this future event x at time t".
    • Other people can make a wager (AKA: a DLC) based on an announcement.
  • An attestation is the oracle's signature which fulfills that promise, once the event outcome is decided.
    • Once the oracle's attestation is revealed, the wager (DLC) can be resolved correctly on-chain.

I'm using generic words like "event" and "outcome" here because DLCs are extremely general. As an oracle, I could announce and attest to literally anything: the weather tomorrow, the price of fish in USD next week; the relative value of BTC to ETH at market close today; how many hot dogs Timmy can eat on his birthday; Whatever the oracle wants, basically.

More info about DLCs in general here.

@frbitten
Copy link
Contributor

@conduition You are thinking from the point of view of a user who wants to sell coins and is advertising on the network. That's not price. It's an offer. To be a price, the deal needs to be completed.

There are several asset exchanges in the world. Not just cryptos. The idea of ​​this PR, as far as I understand, is just to publish quotes. So that customers can use this information for calculations or simply visualization. Something like google did in their search. The transaction was actually made on another platform.

I don't see the Oracle DLC ads disclosing Microsoft stock prices traded on the New York Stock Exchange.

I imagine that the functionality you are proposing can disclose the values ​​when a transaction is actually completed using this PR's proposal.

One approach I have suggested is that these events are not from a single transaction but rather the summary of a 1 minute trade. To avoid overloading with little-used events. Where in the event there will be the maximum, minimum, opening and closing.

@conduition
Copy link

Cool, if you do a new PR, I still need kind 10041 from here so that the user himself can declare which oracles he/she trusts.

@vitorpamplona Done ✔️ I will say the event kind 10041 is very permissive; it allows a user to say "I trust this oracle and he publishes at these relays", but not to specify which exact types of announcements the user is open to using. For an oracle which attests to many things, e.g. the price of fish and sporting events, there is no way to say "i trust this oracle to attest to the price of fish but not to anything else". But in a realistic scenario, i don't see that kind of thing coming up a lot, and the user always has the final say about which DLCs they participate in.

@vitorpamplona
Copy link
Collaborator Author

vitorpamplona commented Jan 13, 2025

Ok, so to get the BTCUSD from #1681, what do I need to do? I guess I can ignore kind 88. Then I need to figure out how to download kind 89s, but only the latest one that attests to BTCUSD from the pubkeys listed on 10088. Then I need to figure out a way to parse the attestation to find where the value is. Is there a specific attestation format for asset prices that all providers are required to use?

@conduition
Copy link

If the oracle you're using only publishes a specific type of attestation, e.g. the BTC/USD price, then basically all you'd need to do is query for the latest kind:89 events issued by the oracle's nostr pubkey, and then parse the attestation using a library such as the dlc_messages crate. The binary format is quite clearly specified, so you can also write your own simpler self-contained decoder if you want. It uses LN-style type-length-value (TLV) encoding.

If the oracle publishes different types of attestations, such as BTC/EUR, ETH/AUD, etc, or enum events for real-world stuff, then you'd need some way to filter the announcements/attestations to find the specific data you want. I like your idea of using an indexed tag (n tag) for asset pairs to do that. That should help for searchability.

There are some options here:

  1. ["n", "BTC", "USD"]
  2. ["n", "BTCUSD"]
  3. ["n", "BTC"] + ["n", "USD"] (the approach you're using in your PR here)

I think because of this statement in NIP-01:

Only the first value in any given tag is indexed.

it would make more sense to go with either option 2 or option 3, and only option 3 allows us to query for individual assets. (e.g. "show me all numeric announcements involving Bitcoin". So I think that's a reasonable approach to stick with. To make searching attestations easier and more performant it'd make sense to add this tag to both kind:88 and kind:89 events. I'll update my PR

@conduition
Copy link

Updated #1681 with these changes

@conduition
Copy link

conduition commented Jan 14, 2025

I don't see the Oracle DLC ads disclosing Microsoft stock prices traded on the New York Stock Exchange.

@frbitten That's precisely the kind of thing a DLC oracle would publish 😉 If you'd like to see this in action, i could even add MSFT to my DLC oracle as a demo.

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.

6 participants