1use serde::{Deserialize, Serialize};
4use tsify::Tsify;
5use wowlab_parsers::parcel::{
6 DEFAULT_MAX_DECODED_BODY, DEFAULT_MAX_ENCODED_LEN, DEFAULT_MAX_PAYLOAD_BYTES, DecodeMeta,
7 ExportKind, ResultExport, ResultItem,
8};
9
10#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
11#[tsify(into_wasm_abi, from_wasm_abi)]
12#[serde(rename_all = "camelCase")]
13pub struct ParcelConfigDto {
14 pub prefix: String,
15 #[serde(default)]
16 pub content_types: Vec<String>,
17 #[serde(default)]
18 pub default_content_type: Option<String>,
19 #[serde(default)]
20 pub max_encoded_len: Option<u32>,
21 #[serde(default)]
22 pub max_decoded_body: Option<u32>,
23 #[serde(default)]
24 pub max_payload_bytes: Option<u32>,
25}
26
27impl ParcelConfigDto {
28 pub(crate) fn into_codec_config(self) -> wowlab_parsers::parcel::CodecConfig {
29 wowlab_parsers::parcel::CodecConfig {
30 prefix: self.prefix,
31 content_types: self.content_types,
32 default_content_type: self.default_content_type,
33 max_encoded_len: self.max_encoded_len.map(|v| v as usize),
34 max_decoded_body: self.max_decoded_body.map(|v| v as usize),
35 max_payload_bytes: self.max_payload_bytes.map(|v| v as usize),
36 }
37 }
38}
39
40#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
41#[tsify(into_wasm_abi, from_wasm_abi)]
42#[serde(rename_all = "camelCase")]
43pub struct ParcelDecodeMetaDto {
44 pub prefix: String,
45 pub content_type: String,
46 pub checksum: String,
47 pub encoded_bytes: u32,
48 pub decoded_body_bytes: u32,
49 pub payload_bytes: u32,
50}
51
52impl From<DecodeMeta> for ParcelDecodeMetaDto {
53 fn from(value: DecodeMeta) -> Self {
54 Self {
55 prefix: value.prefix,
56 content_type: value.content_type,
57 checksum: value.checksum,
58 encoded_bytes: wowlab_types::numeric::usize_to_u32_saturating(value.encoded_bytes),
59 decoded_body_bytes: wowlab_types::numeric::usize_to_u32_saturating(
60 value.decoded_body_bytes,
61 ),
62 payload_bytes: wowlab_types::numeric::usize_to_u32_saturating(value.payload_bytes),
63 }
64 }
65}
66
67#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
68#[tsify(into_wasm_abi, from_wasm_abi)]
69#[serde(rename_all = "camelCase")]
70pub struct ParcelDecodedDto {
71 pub payload: Vec<u8>,
72 pub meta: ParcelDecodeMetaDto,
73}
74
75#[derive(Clone, Copy, Debug, Deserialize, Eq, PartialEq, Serialize, Tsify)]
76#[tsify(into_wasm_abi, from_wasm_abi)]
77#[serde(rename_all = "snake_case")]
78#[non_exhaustive]
79pub enum ExportKindDto {
80 Bib,
81 Drops,
82}
83
84impl From<ExportKind> for ExportKindDto {
85 fn from(value: ExportKind) -> Self {
86 match value {
87 ExportKind::Drops => Self::Drops,
88 _ => Self::Bib,
89 }
90 }
91}
92
93impl From<ExportKindDto> for ExportKind {
94 fn from(value: ExportKindDto) -> Self {
95 match value {
96 ExportKindDto::Bib => Self::Bib,
97 ExportKindDto::Drops => Self::Drops,
98 }
99 }
100}
101
102#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
103#[tsify(into_wasm_abi, from_wasm_abi)]
104#[serde(rename_all = "camelCase")]
105pub struct ResultItemDto {
107 pub slot: String,
108 pub item_id: u32,
109 #[serde(default)]
110 pub bonus_ids: Vec<u32>,
111 #[serde(default)]
112 pub gem_ids: Vec<u32>,
113 #[serde(default)]
114 pub gem_bonus_ids: Vec<u32>,
115 #[serde(default)]
116 pub enchant_id: Option<u32>,
117 #[serde(default)]
118 pub crafted_stats: Vec<u32>,
119 #[serde(default)]
120 pub crafting_quality: Option<u8>,
121 #[serde(default)]
122 pub drop_level: Option<u32>,
123 #[serde(default)]
124 pub suffix: Option<i32>,
125 #[serde(default)]
126 pub item_level: Option<u32>,
127 pub mean_dps: f64,
128 pub dps_delta_vs_baseline: f64,
129 #[serde(default)]
130 pub ci95_half: Option<f64>,
131 pub rank: u32,
132 #[serde(default)]
133 pub win_rate: Option<f64>,
134 #[serde(default)]
135 pub source_label: Option<String>,
136}
137
138impl From<ResultItem> for ResultItemDto {
139 fn from(v: ResultItem) -> Self {
140 Self {
141 slot: v.slot,
142 item_id: v.item_id,
143 bonus_ids: v.bonus_ids,
144 gem_ids: v.gem_ids,
145 gem_bonus_ids: v.gem_bonus_ids,
146 enchant_id: v.enchant_id,
147 crafted_stats: v.crafted_stats,
148 crafting_quality: v.crafting_quality,
149 drop_level: v.drop_level,
150 suffix: v.suffix,
151 item_level: v.item_level,
152 mean_dps: v.mean_dps,
153 dps_delta_vs_baseline: v.dps_delta_vs_baseline,
154 ci95_half: v.ci95_half,
155 rank: v.rank,
156 win_rate: v.win_rate,
157 source_label: v.source_label,
158 }
159 }
160}
161
162impl From<ResultItemDto> for ResultItem {
163 fn from(v: ResultItemDto) -> Self {
164 Self {
165 slot: v.slot,
166 item_id: v.item_id,
167 bonus_ids: v.bonus_ids,
168 gem_ids: v.gem_ids,
169 gem_bonus_ids: v.gem_bonus_ids,
170 enchant_id: v.enchant_id,
171 crafted_stats: v.crafted_stats,
172 crafting_quality: v.crafting_quality,
173 drop_level: v.drop_level,
174 suffix: v.suffix,
175 item_level: v.item_level,
176 mean_dps: v.mean_dps,
177 dps_delta_vs_baseline: v.dps_delta_vs_baseline,
178 ci95_half: v.ci95_half,
179 rank: v.rank,
180 win_rate: v.win_rate,
181 source_label: v.source_label,
182 }
183 }
184}
185
186#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
187#[tsify(into_wasm_abi, from_wasm_abi)]
188#[serde(rename_all = "camelCase")]
189pub struct ResultExportDto {
190 pub v: u32,
191 pub kind: ExportKindDto,
192 pub spec: String,
193 #[serde(default)]
194 pub job_id: Option<String>,
195 pub generated_at_ms: f64,
196 pub baseline_dps: f64,
197 pub winner_dps: f64,
198 pub items: Vec<ResultItemDto>,
199 #[serde(default)]
200 pub note: Option<String>,
201}
202
203impl From<ResultExport> for ResultExportDto {
204 fn from(v: ResultExport) -> Self {
205 Self {
206 v: v.v,
207 kind: v.kind.into(),
208 spec: v.spec,
209 job_id: v.job_id,
210 generated_at_ms: crate::numeric::u64_to_js_number(v.generated_at_ms),
211 baseline_dps: v.baseline_dps,
212 winner_dps: v.winner_dps,
213 items: v.items.into_iter().map(ResultItemDto::from).collect(),
214 note: v.note,
215 }
216 }
217}
218
219impl From<ResultExportDto> for ResultExport {
220 fn from(v: ResultExportDto) -> Self {
221 Self {
222 v: v.v,
223 kind: v.kind.into(),
224 spec: v.spec,
225 job_id: v.job_id,
226 generated_at_ms: crate::numeric::js_number_to_u64(v.generated_at_ms),
227 baseline_dps: v.baseline_dps,
228 winner_dps: v.winner_dps,
229 items: v.items.into_iter().map(ResultItem::from).collect(),
230 note: v.note,
231 }
232 }
233}
234
235#[derive(Clone, Debug, Deserialize, Serialize, Tsify)]
236#[tsify(into_wasm_abi, from_wasm_abi)]
237#[serde(rename_all = "camelCase")]
238pub struct ParcelLimitsDto {
239 pub max_encoded_len: u32,
240 pub max_decoded_body: u32,
241 pub max_payload_bytes: u32,
242}
243
244impl ParcelLimitsDto {
245 pub(crate) fn defaults() -> Self {
246 Self {
247 max_encoded_len: wowlab_types::numeric::usize_to_u32_saturating(
248 DEFAULT_MAX_ENCODED_LEN,
249 ),
250 max_decoded_body: wowlab_types::numeric::usize_to_u32_saturating(
251 DEFAULT_MAX_DECODED_BODY,
252 ),
253 max_payload_bytes: wowlab_types::numeric::usize_to_u32_saturating(
254 DEFAULT_MAX_PAYLOAD_BYTES,
255 ),
256 }
257 }
258}