pmxt 1.5.6__tar.gz → 1.6.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (80) hide show
  1. {pmxt-1.5.6 → pmxt-1.6.0}/PKG-INFO +1 -1
  2. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/__init__.py +1 -1
  3. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/api_client.py +1 -1
  4. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/configuration.py +1 -1
  5. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/create_order_params.py +4 -2
  6. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/market_outcome.py +4 -2
  7. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/unified_market.py +4 -2
  8. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/__init__.py +19 -1
  9. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/_server/server/bundled.js +289 -24
  10. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/client.py +224 -2
  11. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/models.py +71 -0
  12. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/server_manager.py +18 -1
  13. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt.egg-info/PKG-INFO +1 -1
  14. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt.egg-info/SOURCES.txt +1 -0
  15. {pmxt-1.5.6 → pmxt-1.6.0}/pyproject.toml +1 -1
  16. pmxt-1.6.0/tests/test_filtering.py +361 -0
  17. {pmxt-1.5.6 → pmxt-1.6.0}/README.md +0 -0
  18. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/api/__init__.py +0 -0
  19. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/api/default_api.py +0 -0
  20. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/api_response.py +0 -0
  21. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/exceptions.py +0 -0
  22. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/__init__.py +0 -0
  23. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/balance.py +0 -0
  24. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/base_request.py +0 -0
  25. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/base_response.py +0 -0
  26. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/cancel_order_request.py +0 -0
  27. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/create_order200_response.py +0 -0
  28. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/create_order_request.py +0 -0
  29. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/error_detail.py +0 -0
  30. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/error_response.py +0 -0
  31. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/exchange_credentials.py +0 -0
  32. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/exchange_credentials_signature_type.py +0 -0
  33. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/execution_price_result.py +0 -0
  34. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_balance200_response.py +0 -0
  35. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_markets200_response.py +0 -0
  36. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_markets_request.py +0 -0
  37. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_ohlcv200_response.py +0 -0
  38. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_ohlcv_request.py +0 -0
  39. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_ohlcv_request_args_inner.py +0 -0
  40. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_open_orders200_response.py +0 -0
  41. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_open_orders_request.py +0 -0
  42. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_order_book200_response.py +0 -0
  43. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_order_book_request.py +0 -0
  44. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_positions200_response.py +0 -0
  45. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_positions_request.py +0 -0
  46. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_trades200_response.py +0 -0
  47. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/fetch_trades_request.py +0 -0
  48. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/get_execution_price200_response.py +0 -0
  49. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/get_execution_price_detailed200_response.py +0 -0
  50. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/get_execution_price_request.py +0 -0
  51. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/get_execution_price_request_args_inner.py +0 -0
  52. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/get_markets_by_slug_request.py +0 -0
  53. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/health_check200_response.py +0 -0
  54. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/history_filter_params.py +0 -0
  55. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/market_filter_params.py +0 -0
  56. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/order.py +0 -0
  57. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/order_book.py +0 -0
  58. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/order_level.py +0 -0
  59. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/position.py +0 -0
  60. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/price_candle.py +0 -0
  61. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/search_events200_response.py +0 -0
  62. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/search_events_request.py +0 -0
  63. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/search_markets_request.py +0 -0
  64. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/search_markets_request_args_inner.py +0 -0
  65. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/trade.py +0 -0
  66. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/unified_event.py +0 -0
  67. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/watch_order_book_request.py +0 -0
  68. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/watch_order_book_request_args_inner.py +0 -0
  69. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/models/watch_trades_request.py +0 -0
  70. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/py.typed +0 -0
  71. {pmxt-1.5.6 → pmxt-1.6.0}/generated/pmxt_internal/rest.py +0 -0
  72. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/_server/__init__.py +0 -0
  73. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/_server/bin/pmxt-ensure-server +0 -0
  74. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt/_server/bin/pmxt-ensure-server.js +0 -0
  75. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt.egg-info/dependency_links.txt +0 -0
  76. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt.egg-info/requires.txt +0 -0
  77. {pmxt-1.5.6 → pmxt-1.6.0}/pmxt.egg-info/top_level.txt +0 -0
  78. {pmxt-1.5.6 → pmxt-1.6.0}/setup.cfg +0 -0
  79. {pmxt-1.5.6 → pmxt-1.6.0}/tests/test_integration.py +0 -0
  80. {pmxt-1.5.6 → pmxt-1.6.0}/tests/test_server_manager.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: pmxt
3
- Version: 1.5.6
3
+ Version: 1.6.0
4
4
  Summary: Unified prediction market data API - The ccxt for prediction markets
5
5
  Author: PMXT Contributors
6
6
  License: MIT
@@ -14,7 +14,7 @@
14
14
  """ # noqa: E501
15
15
 
16
16
 
17
- __version__ = "1.5.6"
17
+ __version__ = "1.6.0"
18
18
 
19
19
  # Define package exports
20
20
  __all__ = [
@@ -91,7 +91,7 @@ class ApiClient:
91
91
  self.default_headers[header_name] = header_value
92
92
  self.cookie = cookie
93
93
  # Set default User-Agent.
94
- self.user_agent = 'OpenAPI-Generator/1.5.6/python'
94
+ self.user_agent = 'OpenAPI-Generator/1.6.0/python'
95
95
  self.client_side_validation = configuration.client_side_validation
96
96
 
97
97
  def __enter__(self):
@@ -506,7 +506,7 @@ class Configuration:
506
506
  "OS: {env}\n"\
507
507
  "Python Version: {pyversion}\n"\
508
508
  "Version of the API: 0.4.4\n"\
509
- "SDK Package Version: 1.5.6".\
509
+ "SDK Package Version: 1.6.0".\
510
510
  format(env=sys.platform, pyversion=sys.version)
511
511
 
512
512
  def get_host_settings(self) -> List[HostSetting]:
@@ -32,7 +32,8 @@ class CreateOrderParams(BaseModel):
32
32
  type: StrictStr
33
33
  amount: Union[StrictFloat, StrictInt]
34
34
  price: Optional[Union[StrictFloat, StrictInt]] = None
35
- __properties: ClassVar[List[str]] = ["marketId", "outcomeId", "side", "type", "amount", "price"]
35
+ fee: Optional[Union[StrictFloat, StrictInt]] = None
36
+ __properties: ClassVar[List[str]] = ["marketId", "outcomeId", "side", "type", "amount", "price", "fee"]
36
37
 
37
38
  @field_validator('side')
38
39
  def side_validate_enum(cls, value):
@@ -104,7 +105,8 @@ class CreateOrderParams(BaseModel):
104
105
  "side": obj.get("side"),
105
106
  "type": obj.get("type"),
106
107
  "amount": obj.get("amount"),
107
- "price": obj.get("price")
108
+ "price": obj.get("price"),
109
+ "fee": obj.get("fee")
108
110
  })
109
111
  return _obj
110
112
 
@@ -26,12 +26,13 @@ class MarketOutcome(BaseModel):
26
26
  """
27
27
  MarketOutcome
28
28
  """ # noqa: E501
29
- id: Optional[StrictStr] = None
29
+ id: Optional[StrictStr] = Field(default=None, description="DEPRECATED: Use outcomeId instead. Will be removed in v2.0")
30
+ outcome_id: Optional[StrictStr] = Field(default=None, description="Outcome ID for trading operations (CLOB Token ID for Polymarket, Market Ticker for Kalshi)", alias="outcomeId")
30
31
  label: Optional[StrictStr] = None
31
32
  price: Optional[Union[StrictFloat, StrictInt]] = None
32
33
  price_change24h: Optional[Union[StrictFloat, StrictInt]] = Field(default=None, alias="priceChange24h")
33
34
  metadata: Optional[Dict[str, Any]] = Field(default=None, description="Exchange-specific metadata (e.g., clobTokenId for Polymarket)")
34
- __properties: ClassVar[List[str]] = ["id", "label", "price", "priceChange24h", "metadata"]
35
+ __properties: ClassVar[List[str]] = ["id", "outcomeId", "label", "price", "priceChange24h", "metadata"]
35
36
 
36
37
  model_config = ConfigDict(
37
38
  populate_by_name=True,
@@ -85,6 +86,7 @@ class MarketOutcome(BaseModel):
85
86
 
86
87
  _obj = cls.model_validate({
87
88
  "id": obj.get("id"),
89
+ "outcomeId": obj.get("outcomeId"),
88
90
  "label": obj.get("label"),
89
91
  "price": obj.get("price"),
90
92
  "priceChange24h": obj.get("priceChange24h"),
@@ -28,7 +28,8 @@ class UnifiedMarket(BaseModel):
28
28
  """
29
29
  UnifiedMarket
30
30
  """ # noqa: E501
31
- id: Optional[StrictStr] = None
31
+ id: Optional[StrictStr] = Field(default=None, description="DEPRECATED: Use marketId instead. Will be removed in v2.0")
32
+ market_id: Optional[StrictStr] = Field(default=None, description="The unique identifier for this market", alias="marketId")
32
33
  title: Optional[StrictStr] = None
33
34
  description: Optional[StrictStr] = None
34
35
  outcomes: Optional[List[MarketOutcome]] = None
@@ -45,7 +46,7 @@ class UnifiedMarket(BaseModel):
45
46
  no: Optional[MarketOutcome] = None
46
47
  up: Optional[MarketOutcome] = None
47
48
  down: Optional[MarketOutcome] = None
48
- __properties: ClassVar[List[str]] = ["id", "title", "description", "outcomes", "resolutionDate", "volume24h", "volume", "liquidity", "openInterest", "url", "image", "category", "tags", "yes", "no", "up", "down"]
49
+ __properties: ClassVar[List[str]] = ["id", "marketId", "title", "description", "outcomes", "resolutionDate", "volume24h", "volume", "liquidity", "openInterest", "url", "image", "category", "tags", "yes", "no", "up", "down"]
49
50
 
50
51
  model_config = ConfigDict(
51
52
  populate_by_name=True,
@@ -118,6 +119,7 @@ class UnifiedMarket(BaseModel):
118
119
 
119
120
  _obj = cls.model_validate({
120
121
  "id": obj.get("id"),
122
+ "marketId": obj.get("marketId"),
121
123
  "title": obj.get("title"),
122
124
  "description": obj.get("description"),
123
125
  "outcomes": [MarketOutcome.from_dict(_item) for _item in obj["outcomes"]] if obj.get("outcomes") is not None else None,
@@ -33,7 +33,23 @@ from .models import (
33
33
  CreateOrderParams,
34
34
  )
35
35
 
36
- __version__ = "1.5.6"
36
+
37
+ # Global server management functions
38
+ _default_manager = ServerManager()
39
+
40
+ def stop_server():
41
+ """
42
+ Stop the background PMXT sidecar server.
43
+ """
44
+ _default_manager.stop()
45
+
46
+ def restart_server():
47
+ """
48
+ Restart the background PMXT sidecar server.
49
+ """
50
+ _default_manager.restart()
51
+
52
+ __version__ = "1.6.0"
37
53
  __all__ = [
38
54
  # Exchanges
39
55
  "Polymarket",
@@ -42,6 +58,8 @@ __all__ = [
42
58
  "Exchange",
43
59
  # Server Management
44
60
  "ServerManager",
61
+ "stop_server",
62
+ "restart_server",
45
63
  # Data Models
46
64
  "UnifiedMarket",
47
65
  "MarketOutcome",
@@ -24494,6 +24494,227 @@ var require_BaseExchange = __commonJS({
24494
24494
  return (0, math_1.getExecutionPriceDetailed)(orderBook, side, amount);
24495
24495
  }
24496
24496
  // ----------------------------------------------------------------------------
24497
+ // Filtering Methods
24498
+ // ----------------------------------------------------------------------------
24499
+ /**
24500
+ * Filter markets based on criteria or custom function.
24501
+ *
24502
+ * @param markets - Array of markets to filter
24503
+ * @param criteria - Filter criteria object, string (simple text search), or predicate function
24504
+ * @returns Filtered array of markets
24505
+ *
24506
+ * @example Simple text search
24507
+ * api.filterMarkets(markets, 'Trump')
24508
+ *
24509
+ * @example Advanced filtering
24510
+ * api.filterMarkets(markets, {
24511
+ * text: 'Trump',
24512
+ * searchIn: ['title', 'tags'],
24513
+ * volume24h: { min: 10000 },
24514
+ * category: 'Politics',
24515
+ * price: { outcome: 'yes', max: 0.5 }
24516
+ * })
24517
+ *
24518
+ * @example Custom predicate
24519
+ * api.filterMarkets(markets, m => m.liquidity > 5000 && m.yes?.price < 0.3)
24520
+ */
24521
+ filterMarkets(markets, criteria) {
24522
+ if (typeof criteria === "function") {
24523
+ return markets.filter(criteria);
24524
+ }
24525
+ if (typeof criteria === "string") {
24526
+ const lowerQuery = criteria.toLowerCase();
24527
+ return markets.filter((m) => m.title.toLowerCase().includes(lowerQuery));
24528
+ }
24529
+ return markets.filter((market) => {
24530
+ if (criteria.text) {
24531
+ const lowerQuery = criteria.text.toLowerCase();
24532
+ const searchIn = criteria.searchIn || ["title"];
24533
+ let textMatch = false;
24534
+ for (const field of searchIn) {
24535
+ if (field === "title" && market.title?.toLowerCase().includes(lowerQuery)) {
24536
+ textMatch = true;
24537
+ break;
24538
+ }
24539
+ if (field === "description" && market.description?.toLowerCase().includes(lowerQuery)) {
24540
+ textMatch = true;
24541
+ break;
24542
+ }
24543
+ if (field === "category" && market.category?.toLowerCase().includes(lowerQuery)) {
24544
+ textMatch = true;
24545
+ break;
24546
+ }
24547
+ if (field === "tags" && market.tags?.some((tag) => tag.toLowerCase().includes(lowerQuery))) {
24548
+ textMatch = true;
24549
+ break;
24550
+ }
24551
+ if (field === "outcomes" && market.outcomes?.some((o) => o.label.toLowerCase().includes(lowerQuery))) {
24552
+ textMatch = true;
24553
+ break;
24554
+ }
24555
+ }
24556
+ if (!textMatch)
24557
+ return false;
24558
+ }
24559
+ if (criteria.category && market.category !== criteria.category) {
24560
+ return false;
24561
+ }
24562
+ if (criteria.tags && criteria.tags.length > 0) {
24563
+ const hasMatchingTag = criteria.tags.some((tag) => market.tags?.some((marketTag) => marketTag.toLowerCase() === tag.toLowerCase()));
24564
+ if (!hasMatchingTag)
24565
+ return false;
24566
+ }
24567
+ if (criteria.volume24h) {
24568
+ if (criteria.volume24h.min !== void 0 && market.volume24h < criteria.volume24h.min) {
24569
+ return false;
24570
+ }
24571
+ if (criteria.volume24h.max !== void 0 && market.volume24h > criteria.volume24h.max) {
24572
+ return false;
24573
+ }
24574
+ }
24575
+ if (criteria.volume) {
24576
+ if (criteria.volume.min !== void 0 && (market.volume || 0) < criteria.volume.min) {
24577
+ return false;
24578
+ }
24579
+ if (criteria.volume.max !== void 0 && (market.volume || 0) > criteria.volume.max) {
24580
+ return false;
24581
+ }
24582
+ }
24583
+ if (criteria.liquidity) {
24584
+ if (criteria.liquidity.min !== void 0 && market.liquidity < criteria.liquidity.min) {
24585
+ return false;
24586
+ }
24587
+ if (criteria.liquidity.max !== void 0 && market.liquidity > criteria.liquidity.max) {
24588
+ return false;
24589
+ }
24590
+ }
24591
+ if (criteria.openInterest) {
24592
+ if (criteria.openInterest.min !== void 0 && (market.openInterest || 0) < criteria.openInterest.min) {
24593
+ return false;
24594
+ }
24595
+ if (criteria.openInterest.max !== void 0 && (market.openInterest || 0) > criteria.openInterest.max) {
24596
+ return false;
24597
+ }
24598
+ }
24599
+ if (criteria.resolutionDate) {
24600
+ const resDate = market.resolutionDate;
24601
+ if (criteria.resolutionDate.before && resDate >= criteria.resolutionDate.before) {
24602
+ return false;
24603
+ }
24604
+ if (criteria.resolutionDate.after && resDate <= criteria.resolutionDate.after) {
24605
+ return false;
24606
+ }
24607
+ }
24608
+ if (criteria.price) {
24609
+ const outcome = market[criteria.price.outcome];
24610
+ if (!outcome)
24611
+ return false;
24612
+ if (criteria.price.min !== void 0 && outcome.price < criteria.price.min) {
24613
+ return false;
24614
+ }
24615
+ if (criteria.price.max !== void 0 && outcome.price > criteria.price.max) {
24616
+ return false;
24617
+ }
24618
+ }
24619
+ if (criteria.priceChange24h) {
24620
+ const outcome = market[criteria.priceChange24h.outcome];
24621
+ if (!outcome || outcome.priceChange24h === void 0)
24622
+ return false;
24623
+ if (criteria.priceChange24h.min !== void 0 && outcome.priceChange24h < criteria.priceChange24h.min) {
24624
+ return false;
24625
+ }
24626
+ if (criteria.priceChange24h.max !== void 0 && outcome.priceChange24h > criteria.priceChange24h.max) {
24627
+ return false;
24628
+ }
24629
+ }
24630
+ return true;
24631
+ });
24632
+ }
24633
+ /**
24634
+ * Filter events based on criteria or custom function.
24635
+ *
24636
+ * @param events - Array of events to filter
24637
+ * @param criteria - Filter criteria object, string (simple text search), or predicate function
24638
+ * @returns Filtered array of events
24639
+ *
24640
+ * @example Simple text search
24641
+ * api.filterEvents(events, 'Trump')
24642
+ *
24643
+ * @example Advanced filtering
24644
+ * api.filterEvents(events, {
24645
+ * text: 'Election',
24646
+ * searchIn: ['title', 'tags'],
24647
+ * category: 'Politics',
24648
+ * marketCount: { min: 5 }
24649
+ * })
24650
+ *
24651
+ * @example Custom predicate
24652
+ * api.filterEvents(events, e => e.markets.length > 10)
24653
+ */
24654
+ filterEvents(events, criteria) {
24655
+ if (typeof criteria === "function") {
24656
+ return events.filter(criteria);
24657
+ }
24658
+ if (typeof criteria === "string") {
24659
+ const lowerQuery = criteria.toLowerCase();
24660
+ return events.filter((e) => e.title.toLowerCase().includes(lowerQuery));
24661
+ }
24662
+ return events.filter((event) => {
24663
+ if (criteria.text) {
24664
+ const lowerQuery = criteria.text.toLowerCase();
24665
+ const searchIn = criteria.searchIn || ["title"];
24666
+ let textMatch = false;
24667
+ for (const field of searchIn) {
24668
+ if (field === "title" && event.title?.toLowerCase().includes(lowerQuery)) {
24669
+ textMatch = true;
24670
+ break;
24671
+ }
24672
+ if (field === "description" && event.description?.toLowerCase().includes(lowerQuery)) {
24673
+ textMatch = true;
24674
+ break;
24675
+ }
24676
+ if (field === "category" && event.category?.toLowerCase().includes(lowerQuery)) {
24677
+ textMatch = true;
24678
+ break;
24679
+ }
24680
+ if (field === "tags" && event.tags?.some((tag) => tag.toLowerCase().includes(lowerQuery))) {
24681
+ textMatch = true;
24682
+ break;
24683
+ }
24684
+ }
24685
+ if (!textMatch)
24686
+ return false;
24687
+ }
24688
+ if (criteria.category && event.category !== criteria.category) {
24689
+ return false;
24690
+ }
24691
+ if (criteria.tags && criteria.tags.length > 0) {
24692
+ const hasMatchingTag = criteria.tags.some((tag) => event.tags?.some((eventTag) => eventTag.toLowerCase() === tag.toLowerCase()));
24693
+ if (!hasMatchingTag)
24694
+ return false;
24695
+ }
24696
+ if (criteria.marketCount) {
24697
+ const count = event.markets.length;
24698
+ if (criteria.marketCount.min !== void 0 && count < criteria.marketCount.min) {
24699
+ return false;
24700
+ }
24701
+ if (criteria.marketCount.max !== void 0 && count > criteria.marketCount.max) {
24702
+ return false;
24703
+ }
24704
+ }
24705
+ if (criteria.totalVolume) {
24706
+ const totalVolume = event.markets.reduce((sum, m) => sum + m.volume24h, 0);
24707
+ if (criteria.totalVolume.min !== void 0 && totalVolume < criteria.totalVolume.min) {
24708
+ return false;
24709
+ }
24710
+ if (criteria.totalVolume.max !== void 0 && totalVolume > criteria.totalVolume.max) {
24711
+ return false;
24712
+ }
24713
+ }
24714
+ return true;
24715
+ });
24716
+ }
24717
+ // ----------------------------------------------------------------------------
24497
24718
  // WebSocket Streaming Methods
24498
24719
  // ----------------------------------------------------------------------------
24499
24720
  /**
@@ -38170,9 +38391,11 @@ var require_utils4 = __commonJS({
38170
38391
  if (index === 0 || label.toLowerCase() === "yes" || candidateName && label === candidateName) {
38171
38392
  priceChange = Number(market.oneDayPriceChange || 0);
38172
38393
  }
38394
+ const outcomeIdValue = clobTokenIds[index] || String(index);
38173
38395
  outcomes.push({
38174
- id: clobTokenIds[index] || String(index),
38396
+ id: outcomeIdValue,
38175
38397
  // Use CLOB Token ID as the primary ID
38398
+ outcomeId: outcomeIdValue,
38176
38399
  label: outcomeLabel,
38177
38400
  price: parseFloat(rawPrice) || 0,
38178
38401
  priceChange24h: priceChange,
@@ -38185,6 +38408,7 @@ var require_utils4 = __commonJS({
38185
38408
  }
38186
38409
  const um = {
38187
38410
  id: market.id,
38411
+ marketId: market.id,
38188
38412
  title: market.question ? `${event.title} - ${market.question}` : event.title,
38189
38413
  description: market.description || event.description,
38190
38414
  outcomes,
@@ -38421,6 +38645,26 @@ var require_getMarketsBySlug = __commonJS({
38421
38645
  }
38422
38646
  });
38423
38647
 
38648
+ // dist/utils/validation.js
38649
+ var require_validation = __commonJS({
38650
+ "dist/utils/validation.js"(exports2) {
38651
+ "use strict";
38652
+ Object.defineProperty(exports2, "__esModule", { value: true });
38653
+ exports2.validateOutcomeId = validateOutcomeId;
38654
+ exports2.validateIdFormat = validateIdFormat;
38655
+ function validateOutcomeId(id, context) {
38656
+ if (id.length < 10 && /^\d+$/.test(id)) {
38657
+ throw new Error(`Invalid ID for ${context}: "${id}". This appears to be a market ID (deprecated: market.id, use: market.marketId). Please use outcome ID (preferred: outcome.outcomeId, deprecated: outcome.id).`);
38658
+ }
38659
+ }
38660
+ function validateIdFormat(id, context) {
38661
+ if (!id || id.trim().length === 0) {
38662
+ throw new Error(`Invalid ID for ${context}: ID cannot be empty`);
38663
+ }
38664
+ }
38665
+ }
38666
+ });
38667
+
38424
38668
  // dist/exchanges/polymarket/fetchOHLCV.js
38425
38669
  var require_fetchOHLCV = __commonJS({
38426
38670
  "dist/exchanges/polymarket/fetchOHLCV.js"(exports2) {
@@ -38432,10 +38676,10 @@ var require_fetchOHLCV = __commonJS({
38432
38676
  exports2.fetchOHLCV = fetchOHLCV;
38433
38677
  var axios_1 = __importDefault(require_axios());
38434
38678
  var utils_1 = require_utils4();
38679
+ var validation_1 = require_validation();
38435
38680
  async function fetchOHLCV(id, params) {
38436
- if (id.length < 10 && /^\d+$/.test(id)) {
38437
- throw new Error(`Invalid ID for Polymarket history: "${id}". You provided a Market ID, but Polymarket's CLOB API requires a Token ID. Ensure you are using 'outcome.id'.`);
38438
- }
38681
+ (0, validation_1.validateIdFormat)(id, "OHLCV");
38682
+ (0, validation_1.validateOutcomeId)(id, "OHLCV");
38439
38683
  try {
38440
38684
  const fidelity = (0, utils_1.mapIntervalToFidelity)(params.resolution);
38441
38685
  const nowTs = Math.floor(Date.now() / 1e3);
@@ -38519,7 +38763,10 @@ var require_fetchOrderBook = __commonJS({
38519
38763
  exports2.fetchOrderBook = fetchOrderBook;
38520
38764
  var axios_1 = __importDefault(require_axios());
38521
38765
  var utils_1 = require_utils4();
38766
+ var validation_1 = require_validation();
38522
38767
  async function fetchOrderBook(id) {
38768
+ (0, validation_1.validateIdFormat)(id, "OrderBook");
38769
+ (0, validation_1.validateOutcomeId)(id, "OrderBook");
38523
38770
  try {
38524
38771
  const response = await axios_1.default.get(`${utils_1.CLOB_API_URL}/book`, {
38525
38772
  params: { token_id: id }
@@ -38557,10 +38804,10 @@ var require_fetchTrades = __commonJS({
38557
38804
  exports2.fetchTrades = fetchTrades;
38558
38805
  var axios_1 = __importDefault(require_axios());
38559
38806
  var utils_1 = require_utils4();
38807
+ var validation_1 = require_validation();
38560
38808
  async function fetchTrades(id, params) {
38561
- if (id.length < 10 && /^\d+$/.test(id)) {
38562
- throw new Error(`Invalid ID for Polymarket trades: "${id}". You provided a Market ID, but Polymarket's CLOB API requires a Token ID.`);
38563
- }
38809
+ (0, validation_1.validateIdFormat)(id, "Trades");
38810
+ (0, validation_1.validateOutcomeId)(id, "Trades");
38564
38811
  try {
38565
38812
  const queryParams = {
38566
38813
  asset_id: id
@@ -76055,7 +76302,7 @@ var require_permessage_deflate = __commonJS({
76055
76302
  });
76056
76303
 
76057
76304
  // ../node_modules/ws/lib/validation.js
76058
- var require_validation = __commonJS({
76305
+ var require_validation2 = __commonJS({
76059
76306
  "../node_modules/ws/lib/validation.js"(exports2, module2) {
76060
76307
  "use strict";
76061
76308
  var { isUtf8 } = require("buffer");
@@ -76268,7 +76515,7 @@ var require_receiver = __commonJS({
76268
76515
  kWebSocket
76269
76516
  } = require_constants();
76270
76517
  var { concat: concat2, toArrayBuffer, unmask } = require_buffer_util();
76271
- var { isValidStatusCode, isValidUTF8 } = require_validation();
76518
+ var { isValidStatusCode, isValidUTF8 } = require_validation2();
76272
76519
  var FastBuffer = Buffer[Symbol.species];
76273
76520
  var GET_INFO = 0;
76274
76521
  var GET_PAYLOAD_LENGTH_16 = 1;
@@ -76855,7 +77102,7 @@ var require_sender = __commonJS({
76855
77102
  var { randomFillSync } = require("crypto");
76856
77103
  var PerMessageDeflate = require_permessage_deflate();
76857
77104
  var { EMPTY_BUFFER, kWebSocket, NOOP } = require_constants();
76858
- var { isBlob: isBlob2, isValidStatusCode } = require_validation();
77105
+ var { isBlob: isBlob2, isValidStatusCode } = require_validation2();
76859
77106
  var { mask: applyMask, toBuffer } = require_buffer_util();
76860
77107
  var kByteLength = Symbol("kByteLength");
76861
77108
  var maskBuffer = Buffer.alloc(4);
@@ -77568,7 +77815,7 @@ var require_event_target = __commonJS({
77568
77815
  var require_extension = __commonJS({
77569
77816
  "../node_modules/ws/lib/extension.js"(exports2, module2) {
77570
77817
  "use strict";
77571
- var { tokenChars } = require_validation();
77818
+ var { tokenChars } = require_validation2();
77572
77819
  function push(dest, name, elem) {
77573
77820
  if (dest[name] === void 0) dest[name] = [elem];
77574
77821
  else dest[name].push(elem);
@@ -77732,7 +77979,7 @@ var require_websocket = __commonJS({
77732
77979
  var PerMessageDeflate = require_permessage_deflate();
77733
77980
  var Receiver = require_receiver();
77734
77981
  var Sender = require_sender();
77735
- var { isBlob: isBlob2 } = require_validation();
77982
+ var { isBlob: isBlob2 } = require_validation2();
77736
77983
  var {
77737
77984
  BINARY_TYPES,
77738
77985
  EMPTY_BUFFER,
@@ -78701,7 +78948,7 @@ var require_stream = __commonJS({
78701
78948
  var require_subprotocol = __commonJS({
78702
78949
  "../node_modules/ws/lib/subprotocol.js"(exports2, module2) {
78703
78950
  "use strict";
78704
- var { tokenChars } = require_validation();
78951
+ var { tokenChars } = require_validation2();
78705
78952
  function parse(header) {
78706
78953
  const protocols = /* @__PURE__ */ new Set();
78707
78954
  let start = -1;
@@ -83892,7 +84139,7 @@ var require_permessage_deflate2 = __commonJS({
83892
84139
  });
83893
84140
 
83894
84141
  // ../node_modules/@nevuamarkets/poly-websockets/node_modules/ws/lib/validation.js
83895
- var require_validation2 = __commonJS({
84142
+ var require_validation3 = __commonJS({
83896
84143
  "../node_modules/@nevuamarkets/poly-websockets/node_modules/ws/lib/validation.js"(exports2, module2) {
83897
84144
  "use strict";
83898
84145
  var { isUtf8 } = require("buffer");
@@ -84105,7 +84352,7 @@ var require_receiver2 = __commonJS({
84105
84352
  kWebSocket
84106
84353
  } = require_constants2();
84107
84354
  var { concat: concat2, toArrayBuffer, unmask } = require_buffer_util2();
84108
- var { isValidStatusCode, isValidUTF8 } = require_validation2();
84355
+ var { isValidStatusCode, isValidUTF8 } = require_validation3();
84109
84356
  var FastBuffer = Buffer[Symbol.species];
84110
84357
  var GET_INFO = 0;
84111
84358
  var GET_PAYLOAD_LENGTH_16 = 1;
@@ -84692,7 +84939,7 @@ var require_sender2 = __commonJS({
84692
84939
  var { randomFillSync } = require("crypto");
84693
84940
  var PerMessageDeflate = require_permessage_deflate2();
84694
84941
  var { EMPTY_BUFFER, kWebSocket, NOOP } = require_constants2();
84695
- var { isBlob: isBlob2, isValidStatusCode } = require_validation2();
84942
+ var { isBlob: isBlob2, isValidStatusCode } = require_validation3();
84696
84943
  var { mask: applyMask, toBuffer } = require_buffer_util2();
84697
84944
  var kByteLength = Symbol("kByteLength");
84698
84945
  var maskBuffer = Buffer.alloc(4);
@@ -85405,7 +85652,7 @@ var require_event_target2 = __commonJS({
85405
85652
  var require_extension2 = __commonJS({
85406
85653
  "../node_modules/@nevuamarkets/poly-websockets/node_modules/ws/lib/extension.js"(exports2, module2) {
85407
85654
  "use strict";
85408
- var { tokenChars } = require_validation2();
85655
+ var { tokenChars } = require_validation3();
85409
85656
  function push(dest, name, elem) {
85410
85657
  if (dest[name] === void 0) dest[name] = [elem];
85411
85658
  else dest[name].push(elem);
@@ -85569,7 +85816,7 @@ var require_websocket2 = __commonJS({
85569
85816
  var PerMessageDeflate = require_permessage_deflate2();
85570
85817
  var Receiver = require_receiver2();
85571
85818
  var Sender = require_sender2();
85572
- var { isBlob: isBlob2 } = require_validation2();
85819
+ var { isBlob: isBlob2 } = require_validation3();
85573
85820
  var {
85574
85821
  BINARY_TYPES,
85575
85822
  CLOSE_TIMEOUT,
@@ -86542,7 +86789,7 @@ var require_stream2 = __commonJS({
86542
86789
  var require_subprotocol2 = __commonJS({
86543
86790
  "../node_modules/@nevuamarkets/poly-websockets/node_modules/ws/lib/subprotocol.js"(exports2, module2) {
86544
86791
  "use strict";
86545
- var { tokenChars } = require_validation2();
86792
+ var { tokenChars } = require_validation3();
86546
86793
  function parse(header) {
86547
86794
  const protocols = /* @__PURE__ */ new Set();
86548
86795
  let start = -1;
@@ -104956,13 +105203,16 @@ var require_polymarket = __commonJS({
104956
105203
  }
104957
105204
  }
104958
105205
  try {
104959
- const response = await client.createAndPostOrder({
105206
+ const orderArgs = {
104960
105207
  tokenID: params.outcomeId,
104961
105208
  price,
104962
105209
  side,
104963
- size: params.amount,
104964
- feeRateBps: 0
104965
- }, {
105210
+ size: params.amount
105211
+ };
105212
+ if (params.fee !== void 0 && params.fee !== null) {
105213
+ orderArgs.feeRateBps = params.fee;
105214
+ }
105215
+ const response = await client.createAndPostOrder(orderArgs, {
104966
105216
  tickSize
104967
105217
  });
104968
105218
  if (!response || !response.success) {
@@ -104979,6 +105229,7 @@ var require_polymarket = __commonJS({
104979
105229
  status: "open",
104980
105230
  filled: 0,
104981
105231
  remaining: params.amount,
105232
+ fee: params.fee,
104982
105233
  timestamp: Date.now()
104983
105234
  };
104984
105235
  } catch (error) {
@@ -105188,8 +105439,10 @@ var require_utils10 = __commonJS({
105188
105439
  const tokenEntries = Object.entries(market.tokens);
105189
105440
  tokenEntries.forEach(([label, tokenId], index) => {
105190
105441
  const outcomePrice = market.prices[index] || 0;
105442
+ const outcomeIdValue = tokenId;
105191
105443
  outcomes.push({
105192
- id: tokenId,
105444
+ id: outcomeIdValue,
105445
+ outcomeId: outcomeIdValue,
105193
105446
  label: label.charAt(0).toUpperCase() + label.slice(1),
105194
105447
  // Capitalize 'yes'/'no'
105195
105448
  price: outcomePrice,
@@ -105203,6 +105456,7 @@ var require_utils10 = __commonJS({
105203
105456
  }
105204
105457
  const um = {
105205
105458
  id: market.slug,
105459
+ marketId: market.slug,
105206
105460
  title: market.title || market.question,
105207
105461
  description: market.description,
105208
105462
  outcomes,
@@ -105411,7 +105665,9 @@ var require_fetchOHLCV2 = __commonJS({
105411
105665
  exports2.fetchOHLCV = fetchOHLCV;
105412
105666
  var axios_1 = __importDefault(require_axios());
105413
105667
  var utils_1 = require_utils10();
105668
+ var validation_1 = require_validation();
105414
105669
  async function fetchOHLCV(id, params) {
105670
+ (0, validation_1.validateIdFormat)(id, "OHLCV");
105415
105671
  try {
105416
105672
  const fidelity = (0, utils_1.mapIntervalToFidelity)(params.resolution);
105417
105673
  const url2 = `${utils_1.LIMITLESS_API_URL}/markets/${id}/historical-price`;
@@ -105462,7 +105718,9 @@ var require_fetchOrderBook2 = __commonJS({
105462
105718
  exports2.fetchOrderBook = fetchOrderBook;
105463
105719
  var axios_1 = __importDefault(require_axios());
105464
105720
  var utils_1 = require_utils10();
105721
+ var validation_1 = require_validation();
105465
105722
  async function fetchOrderBook(id) {
105723
+ (0, validation_1.validateIdFormat)(id, "OrderBook");
105466
105724
  try {
105467
105725
  const url2 = `${utils_1.LIMITLESS_API_URL}/markets/${id}/orderbook`;
105468
105726
  const response = await axios_1.default.get(url2);
@@ -106088,6 +106346,7 @@ var require_utils11 = __commonJS({
106088
106346
  {
106089
106347
  id: market.ticker,
106090
106348
  // The actual market ticker (primary tradeable)
106349
+ outcomeId: market.ticker,
106091
106350
  label: candidateName || "Yes",
106092
106351
  price,
106093
106352
  priceChange24h: priceChange
@@ -106095,6 +106354,7 @@ var require_utils11 = __commonJS({
106095
106354
  {
106096
106355
  id: `${market.ticker}-NO`,
106097
106356
  // Virtual ID for the No outcome
106357
+ outcomeId: `${market.ticker}-NO`,
106098
106358
  label: candidateName ? `Not ${candidateName}` : "No",
106099
106359
  price: 1 - price,
106100
106360
  priceChange24h: -priceChange
@@ -106114,6 +106374,7 @@ var require_utils11 = __commonJS({
106114
106374
  }
106115
106375
  const um = {
106116
106376
  id: market.ticker,
106377
+ marketId: market.ticker,
106117
106378
  title: event.title,
106118
106379
  description: market.rules_primary || market.rules_secondary || "",
106119
106380
  outcomes,
@@ -106442,7 +106703,9 @@ var require_fetchOHLCV3 = __commonJS({
106442
106703
  exports2.fetchOHLCV = fetchOHLCV;
106443
106704
  var axios_1 = __importDefault(require_axios());
106444
106705
  var utils_1 = require_utils11();
106706
+ var validation_1 = require_validation();
106445
106707
  async function fetchOHLCV(id, params) {
106708
+ (0, validation_1.validateIdFormat)(id, "OHLCV");
106446
106709
  try {
106447
106710
  const cleanedId = id.replace(/-NO$/, "");
106448
106711
  const normalizedId = cleanedId.toUpperCase();
@@ -106528,7 +106791,9 @@ var require_fetchOrderBook3 = __commonJS({
106528
106791
  Object.defineProperty(exports2, "__esModule", { value: true });
106529
106792
  exports2.fetchOrderBook = fetchOrderBook;
106530
106793
  var axios_1 = __importDefault(require_axios());
106794
+ var validation_1 = require_validation();
106531
106795
  async function fetchOrderBook(id) {
106796
+ (0, validation_1.validateIdFormat)(id, "OrderBook");
106532
106797
  try {
106533
106798
  const isNoOutcome = id.endsWith("-NO");
106534
106799
  const ticker = id.replace(/-NO$/, "");