Skip to content

Commit fa901a6

Browse files
authored
Remove 1ms fixed rate from lazer fixed rate channels (#2953)
1 parent de1b47e commit fa901a6

File tree

9 files changed

+87
-36
lines changed

9 files changed

+87
-36
lines changed

Cargo.lock

Lines changed: 5 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

lazer/contracts/solana/programs/pyth-lazer-solana-contract/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ no-log-ix-name = []
1919
idl-build = ["anchor-lang/idl-build"]
2020

2121
[dependencies]
22-
pyth-lazer-protocol = { path = "../../../../sdk/rust/protocol", version = "0.10.1" }
22+
pyth-lazer-protocol = { path = "../../../../sdk/rust/protocol", version = "0.12.0" }
2323

2424
anchor-lang = "0.31.1"
2525
bytemuck = { version = "1.20.0", features = ["derive"] }

lazer/publisher_sdk/proto/governance_instruction.proto

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -235,7 +235,7 @@ message AddFeed {
235235
// [required]
236236
optional uint32 min_publishers = 103;
237237
// [required]
238-
optional google.protobuf.Duration min_rate = 104;
238+
optional Channel min_channel = 104;
239239
// [required]
240240
optional google.protobuf.Duration expiry_time = 105;
241241
// [required]
@@ -282,7 +282,7 @@ message UpdateFeedProperties {
282282
// [optional]
283283
optional uint32 min_publishers = 103;
284284
// [optional]
285-
optional google.protobuf.Duration min_rate = 104;
285+
optional Channel min_channel = 104;
286286
// [optional]
287287
optional google.protobuf.Duration expiry_time = 105;
288288
// [optional]

lazer/publisher_sdk/proto/state.proto

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,20 @@ package pyth_lazer;
33

44
import "google/protobuf/duration.proto";
55
import "google/protobuf/timestamp.proto";
6+
import "google/protobuf/empty.proto";
67

78
import "dynamic_value.proto";
89

10+
911
// All optional fields should always be set unless documented otherwise.
1012

13+
message Channel {
14+
oneof kind {
15+
google.protobuf.Duration rate = 1;
16+
google.protobuf.Empty real_time = 2;
17+
}
18+
}
19+
1120
// State of a Pyth Lazer shard.
1221
//
1322
// The state is shared across all Pyth Lazer aggregators that process this shard.
@@ -92,9 +101,9 @@ message Feed {
92101
optional sint32 exponent = 102;
93102
// [required] Minimal number of publisher prices required to produce an aggregate.
94103
optional uint32 min_publishers = 103;
95-
// [required] Minimal rate of aggregation performed by the aggregator for this feed.
104+
// [required] Minimal channel of aggregation performed by the aggregator for this feed.
96105
// Cannot be lower than the shard's top level `State.min_rate`.
97-
optional google.protobuf.Duration min_rate = 104;
106+
optional Channel min_channel = 104;
98107
// [required] Time after which the publisher update is discarded.
99108
optional google.protobuf.Duration expiry_time = 105;
100109
// [required] Market schedule in Pythnet format.

lazer/publisher_sdk/rust/Cargo.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
[package]
22
name = "pyth-lazer-publisher-sdk"
3-
version = "0.5.0"
3+
version = "0.6.0"
44
edition = "2021"
55
description = "Pyth Lazer Publisher SDK types."
66
license = "Apache-2.0"
77
repository = "https://github.com/pyth-network/pyth-crosschain"
88

99
[dependencies]
10-
pyth-lazer-protocol = { version = "0.10.2", path = "../../sdk/rust/protocol" }
10+
pyth-lazer-protocol = { version = "0.12.0", path = "../../sdk/rust/protocol" }
1111
anyhow = "1.0.98"
1212
protobuf = "3.7.2"
1313
serde_json = "1.0.140"

lazer/publisher_sdk/rust/src/lib.rs

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,3 +114,36 @@ impl From<state::FeedKind> for FeedKind {
114114
}
115115
}
116116
}
117+
118+
impl TryFrom<state::Channel> for pyth_lazer_protocol::router::Channel {
119+
type Error = anyhow::Error;
120+
121+
fn try_from(value: state::Channel) -> Result<Self, Self::Error> {
122+
Ok(match value.kind {
123+
Some(kind) => match kind {
124+
state::channel::Kind::Rate(rate) => {
125+
pyth_lazer_protocol::router::Channel::FixedRate(rate.try_into()?)
126+
}
127+
state::channel::Kind::RealTime(_) => pyth_lazer_protocol::router::Channel::RealTime,
128+
},
129+
None => pyth_lazer_protocol::router::Channel::FixedRate(
130+
pyth_lazer_protocol::router::FixedRate::MIN,
131+
),
132+
})
133+
}
134+
}
135+
136+
impl From<pyth_lazer_protocol::router::Channel> for state::Channel {
137+
fn from(value: pyth_lazer_protocol::router::Channel) -> Self {
138+
let mut result = state::Channel::new();
139+
match value {
140+
pyth_lazer_protocol::router::Channel::FixedRate(rate) => {
141+
result.set_rate(rate.into());
142+
}
143+
pyth_lazer_protocol::router::Channel::RealTime => {
144+
result.set_real_time(::protobuf::well_known_types::empty::Empty::new());
145+
}
146+
};
147+
result
148+
}
149+
}

lazer/sdk/rust/client/Cargo.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
11
[package]
22
name = "pyth-lazer-client"
3-
version = "2.0.1"
3+
version = "2.1.0"
44
edition = "2021"
55
description = "A Rust client for Pyth Lazer"
66
license = "Apache-2.0"
77

88
[dependencies]
9-
pyth-lazer-protocol = { path = "../protocol", version = "0.10.2" }
9+
pyth-lazer-protocol = { path = "../protocol", version = "0.12.0" }
1010
tokio = { version = "1", features = ["full"] }
1111
tokio-tungstenite = { version = "0.20", features = ["native-tls"] }
1212
futures-util = "0.3"

lazer/sdk/rust/protocol/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "pyth-lazer-protocol"
3-
version = "0.10.2"
3+
version = "0.12.0"
44
edition = "2021"
55
description = "Pyth Lazer SDK - protocol types."
66
license = "Apache-2.0"

lazer/sdk/rust/protocol/src/router.rs

Lines changed: 30 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ use {
1212
rust_decimal::{prelude::FromPrimitive, Decimal},
1313
serde::{de::Error, Deserialize, Serialize},
1414
std::{
15+
cmp::Ordering,
1516
fmt::Display,
1617
num::NonZeroI64,
1718
ops::{Add, Deref, DerefMut, Div, Sub},
@@ -206,9 +207,24 @@ pub enum JsonBinaryEncoding {
206207
Hex,
207208
}
208209

209-
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, PartialOrd, Ord, From)]
210+
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, From)]
210211
pub enum Channel {
211212
FixedRate(FixedRate),
213+
RealTime,
214+
}
215+
216+
impl PartialOrd for Channel {
217+
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
218+
let rate_left = match self {
219+
Channel::FixedRate(rate) => rate.duration().as_micros(),
220+
Channel::RealTime => FixedRate::MIN.duration().as_micros(),
221+
};
222+
let rate_right = match other {
223+
Channel::FixedRate(rate) => rate.duration().as_micros(),
224+
Channel::RealTime => FixedRate::MIN.duration().as_micros(),
225+
};
226+
Some(rate_left.cmp(&rate_right))
227+
}
212228
}
213229

214230
impl Serialize for Channel {
@@ -217,34 +233,30 @@ impl Serialize for Channel {
217233
S: serde::Serializer,
218234
{
219235
match self {
220-
Channel::FixedRate(fixed_rate) => {
221-
if *fixed_rate == FixedRate::MIN {
222-
return serializer.serialize_str("real_time");
223-
}
224-
serializer.serialize_str(&format!(
225-
"fixed_rate@{}ms",
226-
fixed_rate.duration().as_millis()
227-
))
228-
}
236+
Channel::FixedRate(fixed_rate) => serializer.serialize_str(&format!(
237+
"fixed_rate@{}ms",
238+
fixed_rate.duration().as_millis()
239+
)),
240+
Channel::RealTime => serializer.serialize_str("real_time"),
229241
}
230242
}
231243
}
232244

233245
pub mod channel_ids {
234246
use super::ChannelId;
235247

236-
pub const FIXED_RATE_1: ChannelId = ChannelId(1);
248+
pub const REAL_TIME: ChannelId = ChannelId(1);
237249
pub const FIXED_RATE_50: ChannelId = ChannelId(2);
238250
pub const FIXED_RATE_200: ChannelId = ChannelId(3);
239251
}
240252

241253
impl Display for Channel {
242254
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
243255
match self {
244-
Channel::FixedRate(fixed_rate) => match *fixed_rate {
245-
FixedRate::MIN => write!(f, "real_time"),
246-
rate => write!(f, "fixed_rate@{}ms", rate.duration().as_millis()),
247-
},
256+
Channel::FixedRate(fixed_rate) => {
257+
write!(f, "fixed_rate@{}ms", fixed_rate.duration().as_millis())
258+
}
259+
Channel::RealTime => write!(f, "real_time"),
248260
}
249261
}
250262
}
@@ -253,11 +265,11 @@ impl Channel {
253265
pub fn id(&self) -> ChannelId {
254266
match self {
255267
Channel::FixedRate(fixed_rate) => match fixed_rate.duration().as_millis() {
256-
1 => channel_ids::FIXED_RATE_1,
257268
50 => channel_ids::FIXED_RATE_50,
258269
200 => channel_ids::FIXED_RATE_200,
259270
_ => panic!("unknown channel: {self:?}"),
260271
},
272+
Channel::RealTime => channel_ids::REAL_TIME,
261273
}
262274
}
263275
}
@@ -271,7 +283,7 @@ fn id_supports_all_fixed_rates() {
271283

272284
fn parse_channel(value: &str) -> Option<Channel> {
273285
if value == "real_time" {
274-
Some(Channel::FixedRate(FixedRate::MIN))
286+
Some(Channel::RealTime)
275287
} else if let Some(rest) = value.strip_prefix("fixed_rate@") {
276288
let ms_value = rest.strip_suffix("ms")?;
277289
Some(Channel::FixedRate(FixedRate::from_millis(
@@ -298,9 +310,6 @@ pub struct FixedRate {
298310
}
299311

300312
impl FixedRate {
301-
pub const RATE_1_MS: Self = Self {
302-
rate: DurationUs::from_millis_u32(1),
303-
};
304313
pub const RATE_50_MS: Self = Self {
305314
rate: DurationUs::from_millis_u32(50),
306315
};
@@ -312,7 +321,7 @@ impl FixedRate {
312321
// - Values are sorted.
313322
// - 1 second contains a whole number of each interval.
314323
// - all intervals are divisable by the smallest interval.
315-
pub const ALL: [Self; 3] = [Self::RATE_1_MS, Self::RATE_50_MS, Self::RATE_200_MS];
324+
pub const ALL: [Self; 2] = [Self::RATE_50_MS, Self::RATE_200_MS];
316325
pub const MIN: Self = Self::ALL[0];
317326

318327
pub fn from_millis(millis: u32) -> Option<Self> {

0 commit comments

Comments
 (0)