world.treeline.activity.record
Schema Diff
+14 -0
Compatibility Analysis
Backward Compatible
Backward compatible. 7 non-breaking changes.
Non-Breaking Changes (7)
- AddedVertex AddedVertex { vertex_id: "world.treeline.activity.record:body.clonedFrom" }
- AddedVertex AddedVertex { vertex_id: "world.treeline.activity.record:body.coAthletes" }
- AddedVertex AddedVertex { vertex_id: "world.treeline.activity.record:body.coAthletes:items" }
- AddedEdge AddedEdge { src: "world.treeline.activity.record:body", tgt: "world.treeline.activity.record:body.clonedFrom", kind: "prop", name: Some("clonedFrom") }
- AddedEdge AddedEdge { src: "world.treeline.activity.record:body", tgt: "world.treeline.activity.record:body.coAthletes", kind: "prop", name: Some("coAthletes") }
- AddedEdge AddedEdge { src: "world.treeline.activity.record:body.clonedFrom", tgt: "com.atproto.repo.strongRef", kind: "ref", name: None }
- AddedEdge AddedEdge { src: "world.treeline.activity.record:body.coAthletes", tgt: "world.treeline.activity.record:body.coAthletes:items", kind: "items", name: None }
Migration Guidance
Added Elements
AddedVertex { vertex_id: "world.treeline.activity.record:body.clonedFrom" }AddedVertex { vertex_id: "world.treeline.activity.record:body.coAthletes" }AddedVertex { vertex_id: "world.treeline.activity.record:body.coAthletes:items" }
Additional Notes
- Non-breaking: AddedEdge { src: "world.treeline.activity.record:body", tgt: "world.treeline.activity.record:body.clonedFrom", kind: "prop", name: Some("clonedFrom") }
- Non-breaking: AddedEdge { src: "world.treeline.activity.record:body", tgt: "world.treeline.activity.record:body.coAthletes", kind: "prop", name: Some("coAthletes") }
- Non-breaking: AddedEdge { src: "world.treeline.activity.record:body.clonedFrom", tgt: "com.atproto.repo.strongRef", kind: "ref", name: None }
- Non-breaking: AddedEdge { src: "world.treeline.activity.record:body.coAthletes", tgt: "world.treeline.activity.record:body.coAthletes:items", kind: "items", name: None }
1
1
{
2
2
"$type": "com.atproto.lexicon.schema",
3
3
"defs": {
4
4
"deviceMetadata": {
5
5
"description": "Metadata about the recording hardware or sensor device.",
6
6
"properties": {
7
7
"manufacturer": {
8
8
"description": "Manufacturer name (e.g. Garmin, Wahoo, COROS, Apple).",
9
9
"maxLength": 100,
10
10
"type": "string"
11
11
},
12
12
"model": {
13
13
"description": "Device model name (e.g. Forerunner 965, ELEMNT BOLT, Apple Watch Ultra).",
14
14
"maxLength": 100,
15
15
"type": "string"
16
16
}
17
17
},
18
18
"type": "object"
19
19
},
20
20
"geometry": {
21
21
"description": "Simplified GeoJSON LineString geometry representing the activity path.",
22
22
"properties": {
23
23
"coordinates": {
24
24
"description": "RDP-simplified array of coordinate tuples [lon, lat, ele?].",
25
25
"items": {
26
26
"type": "unknown"
27
27
},
28
28
"maxLength": 500,
29
29
"type": "array"
30
30
},
31
31
"type": {
32
32
"const": "LineString",
33
33
"description": "GeoJSON geometry type specifier.",
34
34
"type": "string"
35
35
}
36
36
},
37
37
"required": [
38
38
"type",
39
39
"coordinates"
40
40
],
41
41
"type": "object"
42
42
},
43
43
"main": {
44
44
"description": "A sports activity or outdoor adventure record logged on Treeline.",
45
45
"key": "tid",
46
46
"record": {
47
47
"properties": {
48
+
"clonedFrom": {
49
+
"description": "Optional reference to the activity this record was saved from (Save as My Activity). The AppView checks the source's reuse rules at index time and hides this record's geometry and co-athlete link when they are not met.",
50
+
"ref": "com.atproto.repo.strongRef",
51
+
"type": "ref"
52
+
},
53
+
"coAthletes": {
54
+
"description": "DIDs of athletes who participated in this activity together.",
55
+
"items": {
56
+
"format": "did",
57
+
"type": "string"
58
+
},
59
+
"maxLength": 50,
60
+
"type": "array"
61
+
},
48
62
"createdAt": {
49
63
"description": "Record creation timestamp on client/PDS (ISO 8601 UTC format).",
50
64
"format": "datetime",
51
65
"type": "string"
52
66
},
53
67
"description": {
54
68
"description": "Detailed notes, trip report, weather observations, or gear notes.",
55
69
"maxGraphemes": 3000,
56
70
"maxLength": 30000,
57
71
"type": "string"
58
72
},
59
73
"deviceInfo": {
60
74
"description": "Recording hardware or sensor device metadata.",
61
75
"ref": "#deviceMetadata",
62
76
"type": "ref"
63
77
},
64
78
"endedAt": {
65
79
"description": "Timestamp when the activity finished (ISO 8601 UTC format).",
66
80
"format": "datetime",
67
81
"type": "string"
68
82
},
69
83
"gearRef": {
70
84
"description": "Optional reference to a world.treeline.gear.item used in this activity.",
71
85
"ref": "com.atproto.repo.strongRef",
72
86
"type": "ref"
73
87
},
74
88
"geometry": {
75
89
"description": "Simplified GeoJSON LineString path (recommended <= 250 points) for lightweight relay and feed distribution.",
76
90
"ref": "#geometry",
77
91
"type": "ref"
78
92
},
79
93
"hideStartEndMeters": {
80
94
"description": "Distance trimmed from each end of the public preview only. The original telemetry blob remains untrimmed and publicly retrievable.",
81
95
"maximum": 100000,
82
96
"minimum": 0,
83
97
"type": "integer"
84
98
},
85
99
"privacy": {
86
100
"default": "public",
87
101
"description": "AppView visibility, not confidentiality of the public repository or original blob. New clients publish public or unlisted; unsupported restricted values must fail closed.",
88
102
"knownValues": [
89
103
"public",
90
104
"unlisted",
91
105
"followers",
92
106
"private",
93
107
"permissioned"
94
108
],
95
109
"type": "string"
96
110
},
97
111
"rawBlob": {
98
112
"accept": [
99
113
"application/gpx+xml",
100
114
"application/vnd.ant.fit",
101
115
"application/vnd.garmin.tcx+xml",
102
116
"application/octet-stream",
103
117
"application/xml",
104
118
"text/xml"
105
119
],
106
120
"description": "Full-resolution original raw telemetry file (.fit, .gpx, .tcx) stored directly as an ATProto blob on the athlete's PDS.",
107
121
"maxSize": 52428800,
108
122
"type": "blob"
109
123
},
110
124
"route": {
111
125
"description": "Optional reference to a world.treeline.route.record course or trail guide followed.",
112
126
"ref": "com.atproto.repo.strongRef",
113
127
"type": "ref"
114
128
},
115
129
"routeRef": {
116
130
"description": "Optional reference to a world.treeline.route.record followed.",
117
131
"ref": "com.atproto.repo.strongRef",
118
132
"type": "ref"
119
133
},
120
134
"sport": {
121
135
"description": "Sport or activity type category.",
122
136
"knownValues": [
123
137
"run",
124
138
"trail_run",
125
139
"walk",
126
140
"hike",
127
141
"ride",
128
142
"mountain_bike",
129
143
"gravel_ride",
130
144
"e_bike",
131
145
"road_bike",
132
146
"handcycle",
133
147
"ski",
134
148
"snowboard",
135
149
"backcountry_ski",
136
150
"nordic_ski",
137
151
"roller_ski",
138
152
"swim",
139
153
"open_water_swim",
140
154
"kayak",
141
155
"canoe",
142
156
"rowing",
143
157
"paddleboard",
144
158
"surf",
145
159
"kitesurf",
146
160
"windsurf",
147
161
"sail",
148
162
"climb",
149
163
"boulder",
150
164
"mountaineering",
151
165
"wheelchair",
152
166
"workout",
153
167
"yoga",
154
168
"crossfit",
155
169
"weight_training",
156
170
"pilates",
157
171
"hiit",
158
172
"other"
159
173
],
160
174
"type": "string"
161
175
},
162
176
"startedAt": {
163
177
"description": "Timestamp when the activity started (ISO 8601 UTC format).",
164
178
"format": "datetime",
165
179
"type": "string"
166
180
},
167
181
"stats": {
168
182
"description": "Summary metrics and telemetry statistics for the activity.",
169
183
"ref": "#stats",
170
184
"type": "ref"
171
185
},
172
186
"tags": {
173
187
"description": "Categorization tags (e.g. race, commute, intervals, summits).",
174
188
"items": {
175
189
"maxLength": 64,
176
190
"type": "string"
177
191
},
178
192
"maxLength": 20,
179
193
"type": "array"
180
194
},
181
195
"title": {
182
196
"description": "Display title of the activity (e.g., Morning Trail Run, Grand Canyon R2R2R).",
183
197
"maxGraphemes": 300,
184
198
"maxLength": 3000,
185
199
"type": "string"
186
200
}
187
201
},
188
202
"required": [
189
203
"title",
190
204
"sport",
191
205
"startedAt",
192
206
"createdAt"
193
207
],
194
208
"type": "object"
195
209
},
196
210
"type": "record"
197
211
},
198
212
"stats": {
199
213
"description": "Summary telemetry metrics calculated from the raw activity dataset.",
200
214
"properties": {
201
215
"averageCadenceRpm": {
202
216
"description": "[Deprecated: use avgCadence] Average cadence in rpm or spm.",
203
217
"minimum": 0,
204
218
"type": "integer"
205
219
},
206
220
"averageHeartRateBpm": {
207
221
"description": "[Deprecated: use avgHeartRateBpm] Average heart rate in beats per minute.",
208
222
"maximum": 300,
209
223
"minimum": 0,
210
224
"type": "integer"
211
225
},
212
226
"averagePowerWatts": {
213
227
"description": "[Deprecated: use avgPowerWatts] Average power output in watts.",
214
228
"minimum": 0,
215
229
"type": "integer"
216
230
},
217
231
"averageSpeedMps": {
218
232
"description": "[Deprecated: use avgSpeedMps] Average moving speed in meters per second.",
219
233
"type": "unknown"
220
234
},
221
235
"avgCadence": {
222
236
"description": "Mean cadence (rpm or spm).",
223
237
"minimum": 0,
224
238
"type": "integer"
225
239
},
226
240
"avgCadenceRpm": {
227
241
"description": "Mean cadence in revolutions or steps per minute.",
228
242
"minimum": 0,
229
243
"type": "integer"
230
244
},
231
245
"avgHeartRateBpm": {
232
246
"description": "Mean heart rate in beats per minute.",
233
247
"maximum": 300,
234
248
"minimum": 0,
235
249
"type": "integer"
236
250
},
237
251
"avgPowerWatts": {
238
252
"description": "Mean power output in watts from a recorded sensor.",
239
253
"minimum": 0,
240
254
"type": "integer"
241
255
},
242
256
"avgSpeedMps": {
243
257
"description": "Calculated mean moving speed in meters per second.",
244
258
"type": "unknown"
245
259
},
246
260
"calories": {
247
261
"description": "Estimated energy expenditure in kilocalories.",
248
262
"minimum": 0,
249
263
"type": "integer"
250
264
},
251
265
"distanceMeters": {
252
266
"description": "Total distance traveled in meters.",
253
267
"minimum": 0,
254
268
"type": "integer"
255
269
},
256
270
"durationSeconds": {
257
271
"description": "[Deprecated: use elapsedDurationSeconds] Total elapsed time in seconds.",
258
272
"minimum": 0,
259
273
"type": "integer"
260
274
},
261
275
"elapsedDurationSeconds": {
262
276
"description": "Total elapsed time including pauses in seconds.",
263
277
"minimum": 0,
264
278
"type": "integer"
265
279
},
266
280
"elevationGainMeters": {
267
281
"description": "Cumulative elevation gain in meters.",
268
282
"minimum": 0,
269
283
"type": "integer"
270
284
},
271
285
"elevationLossMeters": {
272
286
"description": "Cumulative elevation loss in meters.",
273
287
"minimum": 0,
274
288
"type": "integer"
275
289
},
276
290
"energyKilojoules": {
277
291
"description": "Total mechanical work in kilojoules (session.total_work or avgPowerWatts * movingDurationSeconds / 1000).",
278
292
"minimum": 0,
279
293
"type": "integer"
280
294
},
281
295
"maxHeartRateBpm": {
282
296
"description": "Maximum recorded heart rate in beats per minute.",
283
297
"maximum": 300,
284
298
"minimum": 0,
285
299
"type": "integer"
286
300
},
287
301
"maxPowerWatts": {
288
302
"description": "Maximum power output in watts.",
289
303
"minimum": 0,
290
304
"type": "integer"
291
305
},
292
306
"maxSpeedMps": {
293
307
"description": "Maximum recorded speed in meters per second.",
294
308
"type": "unknown"
295
309
},
296
310
"movingDurationSeconds": {
297
311
"description": "Active moving duration excluding pauses in seconds.",
298
312
"minimum": 0,
299
313
"type": "integer"
300
314
},
301
315
"movingTimeSeconds": {
302
316
"description": "[Deprecated: use movingDurationSeconds] Total moving time excluding pauses in seconds.",
303
317
"minimum": 0,
304
318
"type": "integer"
305
319
},
306
320
"temperatureCelsius": {
307
321
"description": "Average ambient temperature in degrees Celsius.",
308
322
"type": "integer"
309
323
}
310
324
},
311
325
"type": "object"
312
326
}
313
327
},
314
328
"id": "world.treeline.activity.record",
315
329
"lexicon": 1
316
330
}