Skip to content

Commit dffd470

Browse files
committed
MOD: Reimplement metadata endpoints to RFC spec
1 parent 99038af commit dffd470

File tree

5 files changed

+43
-61
lines changed

5 files changed

+43
-61
lines changed

CHANGELOG.md

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,18 @@
11
# Changelog
22

3+
## TBD
4+
5+
This release includes improvements to the ergonomics of the clients metadata API, you can read more about the changes [here](https://databento.com/blog/api-improvements-august-2023).
6+
7+
#### Breaking changes
8+
- Changed `metadata.list_publishers()` to return a list of publisher details objects
9+
- Changed `metadata.list_fields(...)` to return a list of field detail objects for a particular schema and encoding
10+
- Changed `metadata.list_fields(...)` to require the `schema` and `encoding` parameters
11+
- Changed `metadata.list_unit_prices(...)` to return a list of unit prices for each feed mode and data schema
12+
- Changed `metadata.list_unit_prices(...)` to require the `dataset` parameter
13+
- Removed `metadata.list_unit_prices(...)` `mode` and `schema` parameters
14+
- Removed `metadata.list_fields(...)` `dataset` parameter
15+
316
## 0.16.1 - 2023-08-03
417

518
#### Bug fixes

databento/historical/api/metadata.py

Lines changed: 24 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616
from databento.common.parsing import optional_datetime_to_string
1717
from databento.common.parsing import optional_symbols_list_to_list
1818
from databento.common.validation import validate_enum
19-
from databento.common.validation import validate_maybe_enum
2019
from databento.common.validation import validate_semantic_string
2120
from databento.historical.api import API_VERSION
2221
from databento.historical.http import BentoHttpAPI
@@ -31,17 +30,17 @@ def __init__(self, key: str, gateway: str) -> None:
3130
super().__init__(key=key, gateway=gateway)
3231
self._base_url = gateway + f"/v{API_VERSION}/metadata"
3332

34-
def list_publishers(self) -> dict[str, int]:
33+
def list_publishers(self) -> list[dict[str, Any]]:
3534
"""
3635
Request all publishers from Databento.
3736
3837
Makes a `GET /metadata.list_publishers` HTTP request.
3938
40-
Use this method to list the mappings of publisher names to publisher IDs.
39+
Use this method to list the details of publishers, including their dataset and venue mappings.
4140
4241
Returns
4342
-------
44-
dict[str, int]
43+
list[dict[str, Any]]
4544
4645
"""
4746
response: Response = self._get(
@@ -56,11 +55,11 @@ def list_datasets(
5655
end_date: date | str | None = None,
5756
) -> list[str]:
5857
"""
59-
Request all available datasets from Databento.
58+
Request all valid dataset codes from Databento.
6059
6160
Makes a `GET /metadata.list_datasets` HTTP request.
6261
63-
Use this method to list the _names_ of all available datasets, so you
62+
Use this method to list the valid dataset _codes (string identifiers), so you
6463
can use other methods which take the `dataset` parameter.
6564
6665
Parameters
@@ -118,82 +117,67 @@ def list_schemas(self, dataset: Dataset | str) -> list[str]:
118117

119118
def list_fields(
120119
self,
121-
dataset: Dataset | str,
122-
schema: Schema | str | None = None,
123-
encoding: Encoding | str | None = None,
124-
) -> dict[str, dict[str, str]]:
120+
schema: Schema | str,
121+
encoding: Encoding | str,
122+
) -> list[dict[str, Any]]:
125123
"""
126-
Request all fields for a dataset, schema and encoding from Databento.
124+
List all fields for a particular schema and encoding from Databento.
127125
128126
Makes a `GET /metadata.list_fields` HTTP request.
129127
130-
The `schema` and `encoding` parameters act as optional filters. All
131-
metadata for that parameter is returned if they are not specified.
132-
133128
Parameters
134129
----------
135-
dataset : Dataset or str
136-
The dataset code (string identifier) for the request.
137-
schema : Schema or str {'mbo', 'mbp-1', 'mbp-10', 'trades', 'tbbo', 'ohlcv-1s', 'ohlcv-1m', 'ohlcv-1h', 'ohlcv-1d', 'definition', 'statistics', 'status'}, optional # noqa
130+
schema : Schema or str {'mbo', 'mbp-1', 'mbp-10', 'trades', 'tbbo', 'ohlcv-1s', 'ohlcv-1m', 'ohlcv-1h', 'ohlcv-1d', 'definition', 'statistics', 'status'},
138131
The data record schema for the request.
139-
encoding : Encoding or str {'dbn', 'csv', 'json'}, optional
132+
encoding : Encoding or str {'dbn', 'csv', 'json'}
140133
The data encoding.
141134
142135
Returns
143136
-------
144-
dict[str, dict[str, str]]
145-
A mapping of dataset to encoding to schema to field to data type.
137+
list[dict[str, Any]]
138+
A list of field details.
146139
147140
"""
148-
params: list[tuple[str, Dataset | Schema | Encoding | str | None]] = [
149-
("dataset", validate_semantic_string(dataset, "dataset")),
150-
("schema", validate_maybe_enum(schema, Schema, "schema")),
151-
("encoding", validate_maybe_enum(encoding, Encoding, "encoding")),
141+
params: list[tuple[str, str | Any]] = [
142+
("schema", validate_enum(schema, Schema, "schema")),
143+
("encoding", validate_enum(encoding, Encoding, "encoding")),
152144
]
153145

154146
response: Response = self._get(
155147
url=self._base_url + ".list_fields",
156-
params=params, # type: ignore [arg-type]
148+
params=params,
157149
basic_auth=True,
158150
)
159151
return response.json()
160152

161153
def list_unit_prices(
162154
self,
163155
dataset: Dataset | str,
164-
mode: FeedMode | str | None = None,
165-
schema: Schema | str | None = None,
166-
) -> float | dict[str, Any]:
156+
) -> list[dict[str, Any]]:
167157
"""
168-
List unit prices for each data schema in US dollars per gigabyte.
158+
List unit prices for each feed mode and data schema in US dollars per
159+
gigabyte.
169160
170161
Makes a `GET /metadata.list_unit_prices` HTTP request.
171162
172163
Parameters
173164
----------
174165
dataset : Dataset or str
175166
The dataset code for the request.
176-
mode : FeedMode or str {'live', 'historical-streaming', 'historical'}, optional
177-
The data feed mode for the request.
178-
schema : Schema or str {'mbo', 'mbp-1', 'mbp-10', 'trades', 'tbbo', 'ohlcv-1s', 'ohlcv-1m', 'ohlcv-1h', 'ohlcv-1d', 'definition', 'statistics', 'status'}, optional # noqa
179-
The data record schema for the request.
180167
181168
Returns
182169
-------
183-
float or dict[str, Any]
184-
If both `mode` and `schema` are specified, the unit price is returned as a single number.
185-
Otherwise, return a map of feed mode to schema to unit price.
170+
list[dict[str, Any]]
171+
A list of maps of feed mode to schema to unit price.
186172
187173
"""
188-
params: list[tuple[str, Dataset | FeedMode | Schema | str | None]] = [
174+
params: list[tuple[str, Dataset | str]] = [
189175
("dataset", validate_semantic_string(dataset, "dataset")),
190-
("mode", validate_maybe_enum(mode, FeedMode, "mode")),
191-
("schema", validate_maybe_enum(schema, Schema, "schema")),
192176
]
193177

194178
response: Response = self._get(
195179
url=self._base_url + ".list_unit_prices",
196-
params=params, # type: ignore [arg-type]
180+
params=params,
197181
basic_auth=True,
198182
)
199183
return response.json()

examples/historical_metadata.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,4 +8,4 @@
88
print(client.metadata.list_publishers())
99
print(client.metadata.list_datasets())
1010
print(client.metadata.list_schemas(dataset="GLBX.MDP3"))
11-
print(client.metadata.list_fields(dataset="GLBX.MDP3"))
11+
print(client.metadata.list_fields(schema="trades", encoding="dbn"))

examples/historical_metadata_list_unit_price.py

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,6 @@
77
key = "YOUR_API_KEY"
88
client = Historical(key=key)
99

10-
unit_prices = client.metadata.list_unit_prices(
11-
dataset="GLBX.MDP3",
12-
mode="historical-streaming",
13-
)
10+
unit_prices = client.metadata.list_unit_prices(dataset="GLBX.MDP3")
1411

1512
pprint(unit_prices)

tests/test_historical_metadata.py

Lines changed: 4 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,7 @@
66
import pytest
77
import requests
88
from databento.common.enums import Dataset
9-
from databento.common.enums import FeedMode
109
from databento.historical.client import Historical
11-
from databento_dbn import Schema
1210

1311

1412
def test_list_publishers_sends_expected_request(
@@ -95,7 +93,6 @@ def test_list_fields_sends_expected_request(
9593

9694
# Act
9795
historical_client.metadata.list_fields(
98-
dataset="GLBX.MDP3",
9996
schema="mbo",
10097
encoding="dbn",
10198
)
@@ -106,7 +103,6 @@ def test_list_fields_sends_expected_request(
106103
call["url"]
107104
== f"{historical_client.gateway}/v{db.API_VERSION}/metadata.list_fields"
108105
)
109-
assert ("dataset", "GLBX.MDP3") in call["params"]
110106
assert ("schema", "mbo") in call["params"]
111107
assert ("encoding", "dbn") in call["params"]
112108
assert sorted(call["headers"].keys()) == ["accept", "user-agent"]
@@ -117,28 +113,22 @@ def test_list_fields_sends_expected_request(
117113

118114

119115
@pytest.mark.parametrize(
120-
"dataset, schema, mode",
116+
"dataset",
121117
[
122-
["GLBX.MDP3", "mbo", "live"],
123-
[Dataset.GLBX_MDP3, Schema.MBO, FeedMode.LIVE],
118+
"GLBX.MDP3",
119+
Dataset.GLBX_MDP3,
124120
],
125121
)
126122
def test_list_unit_price_sends_expected_request(
127123
monkeypatch: pytest.MonkeyPatch,
128124
historical_client: Historical,
129125
dataset: Dataset | str,
130-
schema: Schema | str,
131-
mode: FeedMode | str,
132126
) -> None:
133127
# Arrange
134128
monkeypatch.setattr(requests, "get", mocked_get := MagicMock())
135129

136130
# Act
137-
historical_client.metadata.list_unit_prices(
138-
dataset=dataset,
139-
schema=schema,
140-
mode=mode,
141-
)
131+
historical_client.metadata.list_unit_prices(dataset=dataset)
142132

143133
# Assert
144134
call = mocked_get.call_args.kwargs
@@ -151,8 +141,6 @@ def test_list_unit_price_sends_expected_request(
151141
assert all(v in call["headers"]["user-agent"] for v in ("Databento/", "Python/"))
152142
assert call["params"] == [
153143
("dataset", "GLBX.MDP3"),
154-
("mode", "live"),
155-
("schema", "mbo"),
156144
]
157145
assert call["timeout"] == (100, 100)
158146
assert isinstance(call["auth"], requests.auth.HTTPBasicAuth)

0 commit comments

Comments
 (0)