[{"data":1,"prerenderedAt":2243},["ShallowReactive",2],{"navigation_docs":3,"-advanced-time-series":106,"-advanced-time-series-surround":2238},[4,26,57,83],{"title":5,"icon":6,"path":7,"stem":8,"children":9,"page":25},"Getting Started","i-lucide-rocket","/getting-started","1.getting-started",[10,15,20],{"title":11,"path":12,"stem":13,"icon":14},"Introduction","/getting-started/introduction","1.getting-started/1.introduction","i-lucide-info",{"title":16,"path":17,"stem":18,"icon":19},"Installation","/getting-started/installation","1.getting-started/2.installation","i-lucide-download",{"title":21,"path":22,"stem":23,"icon":24},"Quick Start","/getting-started/quick-start","1.getting-started/3.quick-start","i-lucide-play",false,{"title":27,"icon":28,"path":29,"stem":30,"children":31,"page":25},"Core Concepts","i-lucide-book-open","/essentials","2.essentials",[32,37,42,47,52],{"title":33,"path":34,"stem":35,"icon":36},"Models","/essentials/models","2.essentials/1.models","i-lucide-box",{"title":38,"path":39,"stem":40,"icon":41},"Collections","/essentials/collections","2.essentials/2.collections","i-lucide-folder",{"title":43,"path":44,"stem":45,"icon":46},"Views","/essentials/views","2.essentials/3.views","i-lucide-table",{"title":48,"path":49,"stem":50,"icon":51},"Schema Evolution","/essentials/schema-evolution","2.essentials/4.schema-evolution","i-lucide-git-branch",{"title":53,"path":54,"stem":55,"icon":56},"Relations","/essentials/relations","2.essentials/5.relations","i-lucide-link",{"title":58,"icon":59,"path":60,"stem":61,"children":62,"page":25},"Advanced","i-lucide-settings","/advanced","3.advanced",[63,68,73,78],{"title":64,"path":65,"stem":66,"icon":67},"Time-Series","/advanced/time-series","3.advanced/1.time-series","i-lucide-chart-line",{"title":69,"path":70,"stem":71,"icon":72},"Async Support","/advanced/async","3.advanced/2.async","i-lucide-zap",{"title":74,"path":75,"stem":76,"icon":77},"PostgreSQL","/advanced/postgresql","3.advanced/3.postgresql","i-lucide-database",{"title":79,"path":80,"stem":81,"icon":82},"Performance Guide","/advanced/performance","3.advanced/4.performance","i-lucide-gauge",{"title":84,"icon":85,"path":86,"stem":87,"children":88,"page":25},"API Reference","i-lucide-file-code","/api","4.api",[89,94,98,101],{"title":90,"path":91,"stem":92,"icon":93},"Engine","/api/engine","4.api/1.engine","i-lucide-cog",{"title":95,"path":96,"stem":97,"icon":41},"Collection","/api/collection","4.api/2.collection",{"title":33,"path":99,"stem":100,"icon":36},"/api/models","4.api/3.models",{"title":102,"path":103,"stem":104,"icon":105},"Exceptions","/api/exceptions","4.api/4.exceptions","i-lucide-alert-triangle",{"id":107,"title":64,"body":108,"description":2231,"extension":2232,"links":2233,"meta":2234,"navigation":2235,"path":65,"seo":2236,"stem":66,"__hash__":2237},"docs/3.advanced/1.time-series.md",{"type":109,"value":110,"toc":2213},"minimark",[111,115,120,141,258,272,276,282,521,528,555,558,639,659,663,666,825,831,835,838,951,956,959,1029,1036,1130,1134,1141,1237,1240,1375,1407,1411,1418,1425,1428,1540,1545,1548,1657,1662,1665,1696,1706,1709,1715,2035,2047,2051,2068,2149,2153,2163,2203,2209],[112,113,114],"p",{},"CentauroDB has first-class support for time-series data. Metadata lives in a JSON blob (like regular models), while timestamped values are stored in a separate normalized table. This guide walks you through a complete workflow — from defining a model to ingesting data, querying with Polars, and choosing the right update strategy.",[116,117,119],"h2",{"id":118},"defining-a-time-series-model","Defining a time-series model",[112,121,122,123,127,128,131,132,136,137,140],{},"Use ",[124,125,126],"code",{},"CentauroModelSeries"," instead of ",[124,129,130],{},"CentauroModel",". Each instance represents ",[133,134,135],"strong",{},"one series"," of ",[124,138,139],{},"(time, value)"," pairs alongside its metadata:",[142,143,148],"pre",{"className":144,"code":145,"language":146,"meta":147,"style":147},"language-python shiki shiki-themes material-theme-lighter material-theme material-theme-palenight","from centaurodb import CentauroModelSeries, CentauroValues\n\nclass TemperatureSensor(CentauroModelSeries):\n    __centauro_name__ = \"TemperatureSensor\"\n    location: str = \"\"\n    unit: str = \"Celsius\"\n","python","",[124,149,150,176,183,202,221,239],{"__ignoreMap":147},[151,152,155,159,163,166,169,173],"span",{"class":153,"line":154},"line",1,[151,156,158],{"class":157},"s7zQu","from",[151,160,162],{"class":161},"sTEyZ"," centaurodb ",[151,164,165],{"class":157},"import",[151,167,168],{"class":161}," CentauroModelSeries",[151,170,172],{"class":171},"sMK4o",",",[151,174,175],{"class":161}," CentauroValues\n",[151,177,179],{"class":153,"line":178},2,[151,180,182],{"emptyLinePlaceholder":181},true,"\n",[151,184,186,190,194,197,199],{"class":153,"line":185},3,[151,187,189],{"class":188},"spNyl","class",[151,191,193],{"class":192},"sBMFI"," TemperatureSensor",[151,195,196],{"class":171},"(",[151,198,126],{"class":192},[151,200,201],{"class":171},"):\n",[151,203,205,208,211,214,218],{"class":153,"line":204},4,[151,206,207],{"class":161},"    __centauro_name__ ",[151,209,210],{"class":171},"=",[151,212,213],{"class":171}," \"",[151,215,217],{"class":216},"sfazB","TemperatureSensor",[151,219,220],{"class":171},"\"\n",[151,222,224,227,230,233,236],{"class":153,"line":223},5,[151,225,226],{"class":161},"    location",[151,228,229],{"class":171},":",[151,231,232],{"class":192}," str",[151,234,235],{"class":171}," =",[151,237,238],{"class":171}," \"\"\n",[151,240,242,245,247,249,251,253,256],{"class":153,"line":241},6,[151,243,244],{"class":161},"    unit",[151,246,229],{"class":171},[151,248,232],{"class":192},[151,250,235],{"class":171},[151,252,213],{"class":171},[151,254,255],{"class":216},"Celsius",[151,257,220],{"class":171},[259,260,261,262,265,266,271],"callout",{"icon":14},"Each object tracks one measurement series. If you need temperature ",[133,263,264],{},"and"," humidity for the same location, create a separate model and object for each — see ",[267,268,270],"a",{"href":269},"#tracking-multiple-series","Tracking multiple series"," below.",[116,273,275],{"id":274},"writing-time-series-data","Writing time-series data",[112,277,278,279,229],{},"Create an object with values and write it to a ",[124,280,281],{},"TimeSeriesCollection",[142,283,285],{"className":144,"code":284,"language":146,"meta":147,"style":147},"from centaurodb import Engine, TimeSeriesCollection\n\nengine = Engine(\"monitoring.db\")\ncoll = TimeSeriesCollection(engine, \"monitoring\")\n\nreading = TemperatureSensor(\n    location=\"pelion\",\n    values=[\n        CentauroValues(time=\"2025-06-01T08:00:00\", value=22.5),\n        CentauroValues(time=\"2025-06-01T09:00:00\", value=24.1),\n        CentauroValues(time=\"2025-06-01T10:00:00\", value=26.3),\n    ],\n)\ncoll.write_object(reading)\n",[124,286,287,303,307,330,356,360,372,390,399,433,462,491,497,502],{"__ignoreMap":147},[151,288,289,291,293,295,298,300],{"class":153,"line":154},[151,290,158],{"class":157},[151,292,162],{"class":161},[151,294,165],{"class":157},[151,296,297],{"class":161}," Engine",[151,299,172],{"class":171},[151,301,302],{"class":161}," TimeSeriesCollection\n",[151,304,305],{"class":153,"line":178},[151,306,182],{"emptyLinePlaceholder":181},[151,308,309,312,314,317,319,322,325,327],{"class":153,"line":185},[151,310,311],{"class":161},"engine ",[151,313,210],{"class":171},[151,315,297],{"class":316},"s2Zo4",[151,318,196],{"class":171},[151,320,321],{"class":171},"\"",[151,323,324],{"class":216},"monitoring.db",[151,326,321],{"class":171},[151,328,329],{"class":171},")\n",[151,331,332,335,337,340,342,345,347,349,352,354],{"class":153,"line":204},[151,333,334],{"class":161},"coll ",[151,336,210],{"class":171},[151,338,339],{"class":316}," TimeSeriesCollection",[151,341,196],{"class":171},[151,343,344],{"class":316},"engine",[151,346,172],{"class":171},[151,348,213],{"class":171},[151,350,351],{"class":216},"monitoring",[151,353,321],{"class":171},[151,355,329],{"class":171},[151,357,358],{"class":153,"line":223},[151,359,182],{"emptyLinePlaceholder":181},[151,361,362,365,367,369],{"class":153,"line":241},[151,363,364],{"class":161},"reading ",[151,366,210],{"class":171},[151,368,193],{"class":316},[151,370,371],{"class":171},"(\n",[151,373,375,378,380,382,385,387],{"class":153,"line":374},7,[151,376,226],{"class":377},"sHdIc",[151,379,210],{"class":171},[151,381,321],{"class":171},[151,383,384],{"class":216},"pelion",[151,386,321],{"class":171},[151,388,389],{"class":171},",\n",[151,391,393,396],{"class":153,"line":392},8,[151,394,395],{"class":377},"    values",[151,397,398],{"class":171},"=[\n",[151,400,402,405,407,410,412,414,417,419,421,424,426,430],{"class":153,"line":401},9,[151,403,404],{"class":316},"        CentauroValues",[151,406,196],{"class":171},[151,408,409],{"class":377},"time",[151,411,210],{"class":171},[151,413,321],{"class":171},[151,415,416],{"class":216},"2025-06-01T08:00:00",[151,418,321],{"class":171},[151,420,172],{"class":171},[151,422,423],{"class":377}," value",[151,425,210],{"class":171},[151,427,429],{"class":428},"sbssI","22.5",[151,431,432],{"class":171},"),\n",[151,434,436,438,440,442,444,446,449,451,453,455,457,460],{"class":153,"line":435},10,[151,437,404],{"class":316},[151,439,196],{"class":171},[151,441,409],{"class":377},[151,443,210],{"class":171},[151,445,321],{"class":171},[151,447,448],{"class":216},"2025-06-01T09:00:00",[151,450,321],{"class":171},[151,452,172],{"class":171},[151,454,423],{"class":377},[151,456,210],{"class":171},[151,458,459],{"class":428},"24.1",[151,461,432],{"class":171},[151,463,465,467,469,471,473,475,478,480,482,484,486,489],{"class":153,"line":464},11,[151,466,404],{"class":316},[151,468,196],{"class":171},[151,470,409],{"class":377},[151,472,210],{"class":171},[151,474,321],{"class":171},[151,476,477],{"class":216},"2025-06-01T10:00:00",[151,479,321],{"class":171},[151,481,172],{"class":171},[151,483,423],{"class":377},[151,485,210],{"class":171},[151,487,488],{"class":428},"26.3",[151,490,432],{"class":171},[151,492,494],{"class":153,"line":493},12,[151,495,496],{"class":171},"    ],\n",[151,498,500],{"class":153,"line":499},13,[151,501,329],{"class":171},[151,503,505,508,511,514,516,519],{"class":153,"line":504},14,[151,506,507],{"class":161},"coll",[151,509,510],{"class":171},".",[151,512,513],{"class":316},"write_object",[151,515,196],{"class":171},[151,517,518],{"class":316},"reading",[151,520,329],{"class":171},[112,522,523,524,527],{},"Each ",[124,525,526],{},"CentauroValues"," has two fields:",[529,530,531,543],"ul",{},[532,533,534,538,539,542],"li",{},[133,535,536],{},[124,537,409],{}," — a ",[124,540,541],{},"datetime"," (ISO timestamp strings are coerced automatically)",[532,544,545,550,551,554],{},[133,546,547],{},[124,548,549],{},"value"," — a numeric value (",[124,552,553],{},"float",")",[112,556,557],{},"You can also batch-write multiple objects in a single atomic transaction:",[142,559,561],{"className":144,"code":560,"language":146,"meta":147,"style":147},"coll.write_objects([\n    TemperatureSensor(location=\"pelion\", values=[...]),\n    TemperatureSensor(location=\"thessaly\", values=[...]),\n])\n",[124,562,563,575,607,634],{"__ignoreMap":147},[151,564,565,567,569,572],{"class":153,"line":154},[151,566,507],{"class":161},[151,568,510],{"class":171},[151,570,571],{"class":316},"write_objects",[151,573,574],{"class":171},"([\n",[151,576,577,580,582,585,587,589,591,593,595,598,601,604],{"class":153,"line":178},[151,578,579],{"class":316},"    TemperatureSensor",[151,581,196],{"class":171},[151,583,584],{"class":377},"location",[151,586,210],{"class":171},[151,588,321],{"class":171},[151,590,384],{"class":216},[151,592,321],{"class":171},[151,594,172],{"class":171},[151,596,597],{"class":377}," values",[151,599,600],{"class":171},"=[",[151,602,603],{"class":316},"...",[151,605,606],{"class":171},"]),\n",[151,608,609,611,613,615,617,619,622,624,626,628,630,632],{"class":153,"line":185},[151,610,579],{"class":316},[151,612,196],{"class":171},[151,614,584],{"class":377},[151,616,210],{"class":171},[151,618,321],{"class":171},[151,620,621],{"class":216},"thessaly",[151,623,321],{"class":171},[151,625,172],{"class":171},[151,627,597],{"class":377},[151,629,600],{"class":171},[151,631,603],{"class":316},[151,633,606],{"class":171},[151,635,636],{"class":153,"line":204},[151,637,638],{"class":171},"])\n",[640,641,642,643,645,646,649,650,653,654,658],"tip",{},"Populate all values before calling ",[124,644,513],{}," — CentauroDB writes them in a single ",[124,647,648],{},"executemany"," call. This is much faster than appending one at a time via ",[124,651,652],{},"update_object",". See the ",[267,655,657],{"href":656},"/advanced/performance#batch-populate-values-before-writing","Performance guide"," for details.",[116,660,662],{"id":661},"using-polars-dataframes-as-input","Using Polars DataFrames as input",[112,664,665],{},"If your data is already in a Polars DataFrame, pass it directly — no conversion needed:",[142,667,669],{"className":144,"code":668,"language":146,"meta":147,"style":147},"import polars as pl\n\ndf = pl.DataFrame({\n    \"time\": [\"2025-06-01T08:00:00\", \"2025-06-01T09:00:00\", \"2025-06-01T10:00:00\"],\n    \"value\": [22.5, 24.1, 26.3],\n})\n\nreading = TemperatureSensor(location=\"pelion\", values=df)\ncoll.write_object(reading)\n",[124,670,671,684,688,706,745,771,776,780,811],{"__ignoreMap":147},[151,672,673,675,678,681],{"class":153,"line":154},[151,674,165],{"class":157},[151,676,677],{"class":161}," polars ",[151,679,680],{"class":157},"as",[151,682,683],{"class":161}," pl\n",[151,685,686],{"class":153,"line":178},[151,687,182],{"emptyLinePlaceholder":181},[151,689,690,693,695,698,700,703],{"class":153,"line":185},[151,691,692],{"class":161},"df ",[151,694,210],{"class":171},[151,696,697],{"class":161}," pl",[151,699,510],{"class":171},[151,701,702],{"class":316},"DataFrame",[151,704,705],{"class":171},"({\n",[151,707,708,711,713,715,717,720,722,724,726,728,730,732,734,736,738,740,742],{"class":153,"line":204},[151,709,710],{"class":171},"    \"",[151,712,409],{"class":216},[151,714,321],{"class":171},[151,716,229],{"class":171},[151,718,719],{"class":171}," [",[151,721,321],{"class":171},[151,723,416],{"class":216},[151,725,321],{"class":171},[151,727,172],{"class":171},[151,729,213],{"class":171},[151,731,448],{"class":216},[151,733,321],{"class":171},[151,735,172],{"class":171},[151,737,213],{"class":171},[151,739,477],{"class":216},[151,741,321],{"class":171},[151,743,744],{"class":171},"],\n",[151,746,747,749,751,753,755,757,759,761,764,766,769],{"class":153,"line":223},[151,748,710],{"class":171},[151,750,549],{"class":216},[151,752,321],{"class":171},[151,754,229],{"class":171},[151,756,719],{"class":171},[151,758,429],{"class":428},[151,760,172],{"class":171},[151,762,763],{"class":428}," 24.1",[151,765,172],{"class":171},[151,767,768],{"class":428}," 26.3",[151,770,744],{"class":171},[151,772,773],{"class":153,"line":241},[151,774,775],{"class":171},"})\n",[151,777,778],{"class":153,"line":374},[151,779,182],{"emptyLinePlaceholder":181},[151,781,782,784,786,788,790,792,794,796,798,800,802,804,806,809],{"class":153,"line":392},[151,783,364],{"class":161},[151,785,210],{"class":171},[151,787,193],{"class":316},[151,789,196],{"class":171},[151,791,584],{"class":377},[151,793,210],{"class":171},[151,795,321],{"class":171},[151,797,384],{"class":216},[151,799,321],{"class":171},[151,801,172],{"class":171},[151,803,597],{"class":377},[151,805,210],{"class":171},[151,807,808],{"class":316},"df",[151,810,329],{"class":171},[151,812,813,815,817,819,821,823],{"class":153,"line":401},[151,814,507],{"class":161},[151,816,510],{"class":171},[151,818,513],{"class":316},[151,820,196],{"class":171},[151,822,518],{"class":316},[151,824,329],{"class":171},[112,826,827,828,830],{},"CentauroDB validates and converts the DataFrame to a list of ",[124,829,526],{}," under the hood.",[116,832,834],{"id":833},"reading-time-series-data","Reading time-series data",[112,836,837],{},"Read objects back with their values automatically hydrated:",[142,839,841],{"className":144,"code":840,"language":146,"meta":147,"style":147},"loaded = coll.read_object_by_id(reading.row.id, TemperatureSensor)\nprint(loaded.location)        # \"pelion\"\nprint(len(loaded.values))     # 3\nprint(loaded.values[0].time)  # datetime(2025, 6, 1, 8, 0)\n",[124,842,843,879,899,923],{"__ignoreMap":147},[151,844,845,848,850,853,855,858,860,862,864,868,870,873,875,877],{"class":153,"line":154},[151,846,847],{"class":161},"loaded ",[151,849,210],{"class":171},[151,851,852],{"class":161}," coll",[151,854,510],{"class":171},[151,856,857],{"class":316},"read_object_by_id",[151,859,196],{"class":171},[151,861,518],{"class":316},[151,863,510],{"class":171},[151,865,867],{"class":866},"swJcz","row",[151,869,510],{"class":171},[151,871,872],{"class":866},"id",[151,874,172],{"class":171},[151,876,193],{"class":316},[151,878,329],{"class":171},[151,880,881,884,886,889,891,893,895],{"class":153,"line":178},[151,882,883],{"class":316},"print",[151,885,196],{"class":171},[151,887,888],{"class":316},"loaded",[151,890,510],{"class":171},[151,892,584],{"class":866},[151,894,554],{"class":171},[151,896,898],{"class":897},"sHwdD","        # \"pelion\"\n",[151,900,901,903,905,908,910,912,914,917,920],{"class":153,"line":185},[151,902,883],{"class":316},[151,904,196],{"class":171},[151,906,907],{"class":316},"len",[151,909,196],{"class":171},[151,911,888],{"class":316},[151,913,510],{"class":171},[151,915,916],{"class":866},"values",[151,918,919],{"class":171},"))",[151,921,922],{"class":897},"     # 3\n",[151,924,925,927,929,931,933,935,938,941,944,946,948],{"class":153,"line":204},[151,926,883],{"class":316},[151,928,196],{"class":171},[151,930,888],{"class":316},[151,932,510],{"class":171},[151,934,916],{"class":866},[151,936,937],{"class":171},"[",[151,939,940],{"class":428},"0",[151,942,943],{"class":171},"].",[151,945,409],{"class":866},[151,947,554],{"class":171},[151,949,950],{"class":897},"  # datetime(2025, 6, 1, 8, 0)\n",[952,953,955],"h3",{"id":954},"reading-metadata-only","Reading metadata only",[112,957,958],{},"When you need just the metadata (e.g., listing sensors on a dashboard), skip value hydration for faster reads:",[142,960,962],{"className":144,"code":961,"language":146,"meta":147,"style":147},"sensor = coll.read_object_by_id(1, TemperatureSensor, hydrate_values=False)\nprint(sensor.location)  # \"pelion\" — available immediately\nprint(sensor.values)    # [] — not loaded\n",[124,963,964,994,1012],{"__ignoreMap":147},[151,965,966,969,971,973,975,977,979,982,984,986,988,991],{"class":153,"line":154},[151,967,968],{"class":161},"sensor ",[151,970,210],{"class":171},[151,972,852],{"class":161},[151,974,510],{"class":171},[151,976,857],{"class":316},[151,978,196],{"class":171},[151,980,981],{"class":428},"1",[151,983,172],{"class":171},[151,985,193],{"class":316},[151,987,172],{"class":171},[151,989,990],{"class":377}," hydrate_values",[151,992,993],{"class":171},"=False)\n",[151,995,996,998,1000,1003,1005,1007,1009],{"class":153,"line":178},[151,997,883],{"class":316},[151,999,196],{"class":171},[151,1001,1002],{"class":316},"sensor",[151,1004,510],{"class":171},[151,1006,584],{"class":866},[151,1008,554],{"class":171},[151,1010,1011],{"class":897},"  # \"pelion\" — available immediately\n",[151,1013,1014,1016,1018,1020,1022,1024,1026],{"class":153,"line":185},[151,1015,883],{"class":316},[151,1017,196],{"class":171},[151,1019,1002],{"class":316},[151,1021,510],{"class":171},[151,1023,916],{"class":866},[151,1025,554],{"class":171},[151,1027,1028],{"class":897},"    # [] — not loaded\n",[112,1030,1031,1032,1035],{},"This avoids the extra ",[124,1033,1034],{},"SELECT"," against the values table per object. Especially useful when reading many objects:",[142,1037,1039],{"className":144,"code":1038,"language":146,"meta":147,"style":147},"# Fast overview — no values loaded\nall_sensors = coll.read_objects(TemperatureSensor, hydrate_values=False)\nfor s in all_sensors:\n    print(f\"{s.location}: {s.unit}\")\n",[124,1040,1041,1046,1070,1087],{"__ignoreMap":147},[151,1042,1043],{"class":153,"line":154},[151,1044,1045],{"class":897},"# Fast overview — no values loaded\n",[151,1047,1048,1051,1053,1055,1057,1060,1062,1064,1066,1068],{"class":153,"line":178},[151,1049,1050],{"class":161},"all_sensors ",[151,1052,210],{"class":171},[151,1054,852],{"class":161},[151,1056,510],{"class":171},[151,1058,1059],{"class":316},"read_objects",[151,1061,196],{"class":171},[151,1063,217],{"class":316},[151,1065,172],{"class":171},[151,1067,990],{"class":377},[151,1069,993],{"class":171},[151,1071,1072,1075,1078,1081,1084],{"class":153,"line":185},[151,1073,1074],{"class":157},"for",[151,1076,1077],{"class":161}," s ",[151,1079,1080],{"class":157},"in",[151,1082,1083],{"class":161}," all_sensors",[151,1085,1086],{"class":171},":\n",[151,1088,1089,1092,1094,1097,1099,1102,1105,1107,1109,1112,1115,1117,1119,1121,1124,1126,1128],{"class":153,"line":204},[151,1090,1091],{"class":316},"    print",[151,1093,196],{"class":171},[151,1095,1096],{"class":188},"f",[151,1098,321],{"class":216},[151,1100,1101],{"class":428},"{",[151,1103,1104],{"class":316},"s",[151,1106,510],{"class":171},[151,1108,584],{"class":866},[151,1110,1111],{"class":428},"}",[151,1113,1114],{"class":216},": ",[151,1116,1101],{"class":428},[151,1118,1104],{"class":316},[151,1120,510],{"class":171},[151,1122,1123],{"class":866},"unit",[151,1125,1111],{"class":428},[151,1127,321],{"class":216},[151,1129,329],{"class":171},[116,1131,1133],{"id":1132},"polars-dataframe-output","Polars DataFrame output",[112,1135,1136,1137,1140],{},"Access your time-series data as a Polars DataFrame with the ",[124,1138,1139],{},".df"," property:",[142,1142,1144],{"className":144,"code":1143,"language":146,"meta":147,"style":147},"loaded = coll.read_object_by_id(1, TemperatureSensor)\ndf = loaded.df\nprint(df)\n# ┌─────────────────────┬───────┐\n# │ time                ┆ value │\n# │ ---                 ┆ ---   │\n# │ datetime[μs]        ┆ f64   │\n# ╞═════════════════════╪═══════╡\n# │ 2025-06-01 08:00:00 ┆ 22.5  │\n# │ 2025-06-01 09:00:00 ┆ 24.1  │\n# │ 2025-06-01 10:00:00 ┆ 26.3  │\n# └─────────────────────┴───────┘\n",[124,1145,1146,1168,1182,1192,1197,1202,1207,1212,1217,1222,1227,1232],{"__ignoreMap":147},[151,1147,1148,1150,1152,1154,1156,1158,1160,1162,1164,1166],{"class":153,"line":154},[151,1149,847],{"class":161},[151,1151,210],{"class":171},[151,1153,852],{"class":161},[151,1155,510],{"class":171},[151,1157,857],{"class":316},[151,1159,196],{"class":171},[151,1161,981],{"class":428},[151,1163,172],{"class":171},[151,1165,193],{"class":316},[151,1167,329],{"class":171},[151,1169,1170,1172,1174,1177,1179],{"class":153,"line":178},[151,1171,692],{"class":161},[151,1173,210],{"class":171},[151,1175,1176],{"class":161}," loaded",[151,1178,510],{"class":171},[151,1180,1181],{"class":866},"df\n",[151,1183,1184,1186,1188,1190],{"class":153,"line":185},[151,1185,883],{"class":316},[151,1187,196],{"class":171},[151,1189,808],{"class":316},[151,1191,329],{"class":171},[151,1193,1194],{"class":153,"line":204},[151,1195,1196],{"class":897},"# ┌─────────────────────┬───────┐\n",[151,1198,1199],{"class":153,"line":223},[151,1200,1201],{"class":897},"# │ time                ┆ value │\n",[151,1203,1204],{"class":153,"line":241},[151,1205,1206],{"class":897},"# │ ---                 ┆ ---   │\n",[151,1208,1209],{"class":153,"line":374},[151,1210,1211],{"class":897},"# │ datetime[μs]        ┆ f64   │\n",[151,1213,1214],{"class":153,"line":392},[151,1215,1216],{"class":897},"# ╞═════════════════════╪═══════╡\n",[151,1218,1219],{"class":153,"line":401},[151,1220,1221],{"class":897},"# │ 2025-06-01 08:00:00 ┆ 22.5  │\n",[151,1223,1224],{"class":153,"line":435},[151,1225,1226],{"class":897},"# │ 2025-06-01 09:00:00 ┆ 24.1  │\n",[151,1228,1229],{"class":153,"line":464},[151,1230,1231],{"class":897},"# │ 2025-06-01 10:00:00 ┆ 26.3  │\n",[151,1233,1234],{"class":153,"line":493},[151,1235,1236],{"class":897},"# └─────────────────────┴───────┘\n",[112,1238,1239],{},"From here you can use the full Polars API — resample, rolling averages, joins:",[142,1241,1243],{"className":144,"code":1242,"language":146,"meta":147,"style":147},"# Compute hourly statistics\nhourly = df.group_by_dynamic(\"time\", every=\"1h\").agg(\n    pl.col(\"value\").mean().alias(\"avg_temp\"),\n    pl.col(\"value\").max().alias(\"max_temp\"),\n)\n",[124,1244,1245,1250,1295,1335,1371],{"__ignoreMap":147},[151,1246,1247],{"class":153,"line":154},[151,1248,1249],{"class":897},"# Compute hourly statistics\n",[151,1251,1252,1255,1257,1260,1262,1265,1267,1269,1271,1273,1275,1278,1280,1282,1285,1287,1290,1293],{"class":153,"line":178},[151,1253,1254],{"class":161},"hourly ",[151,1256,210],{"class":171},[151,1258,1259],{"class":161}," df",[151,1261,510],{"class":171},[151,1263,1264],{"class":316},"group_by_dynamic",[151,1266,196],{"class":171},[151,1268,321],{"class":171},[151,1270,409],{"class":216},[151,1272,321],{"class":171},[151,1274,172],{"class":171},[151,1276,1277],{"class":377}," every",[151,1279,210],{"class":171},[151,1281,321],{"class":171},[151,1283,1284],{"class":216},"1h",[151,1286,321],{"class":171},[151,1288,1289],{"class":171},").",[151,1291,1292],{"class":316},"agg",[151,1294,371],{"class":171},[151,1296,1297,1300,1302,1305,1307,1309,1311,1313,1315,1318,1321,1324,1326,1328,1331,1333],{"class":153,"line":185},[151,1298,1299],{"class":316},"    pl",[151,1301,510],{"class":171},[151,1303,1304],{"class":316},"col",[151,1306,196],{"class":171},[151,1308,321],{"class":171},[151,1310,549],{"class":216},[151,1312,321],{"class":171},[151,1314,1289],{"class":171},[151,1316,1317],{"class":316},"mean",[151,1319,1320],{"class":171},"().",[151,1322,1323],{"class":316},"alias",[151,1325,196],{"class":171},[151,1327,321],{"class":171},[151,1329,1330],{"class":216},"avg_temp",[151,1332,321],{"class":171},[151,1334,432],{"class":171},[151,1336,1337,1339,1341,1343,1345,1347,1349,1351,1353,1356,1358,1360,1362,1364,1367,1369],{"class":153,"line":204},[151,1338,1299],{"class":316},[151,1340,510],{"class":171},[151,1342,1304],{"class":316},[151,1344,196],{"class":171},[151,1346,321],{"class":171},[151,1348,549],{"class":216},[151,1350,321],{"class":171},[151,1352,1289],{"class":171},[151,1354,1355],{"class":316},"max",[151,1357,1320],{"class":171},[151,1359,1323],{"class":316},[151,1361,196],{"class":171},[151,1363,321],{"class":171},[151,1365,1366],{"class":216},"max_temp",[151,1368,321],{"class":171},[151,1370,432],{"class":171},[151,1372,1373],{"class":153,"line":223},[151,1374,329],{"class":171},[259,1376,1377,1378,1380,1381,1387,1388,1391,1392,1394,1395,1398,1399,1402,1403,1406],{"icon":14},"The ",[124,1379,1139],{}," property requires ",[267,1382,1386],{"href":1383,"rel":1384},"https://pola.rs/",[1385],"nofollow","Polars"," to be installed (",[124,1389,1390],{},"pip install \"centaurodb[polars]\"","). Accessing ",[124,1393,1139],{}," on an object read with ",[124,1396,1397],{},"hydrate_values=False"," raises ",[124,1400,1401],{},"ValuesNotHydratedError"," — call ",[124,1404,1405],{},"coll.refresh(obj)"," first to load the values.",[116,1408,1410],{"id":1409},"update-modes","Update modes",[112,1412,1413,1414,1417],{},"When updating a time-series object, the ",[124,1415,1416],{},"values_mode"," parameter controls how new values interact with existing ones:",[952,1419,1421,1424],{"id":1420},"append-default",[124,1422,1423],{},"append"," (default)",[112,1426,1427],{},"Inserts new timestamps, silently skips duplicates. Use for incremental ingestion where each batch adds new data points:",[142,1429,1431],{"className":144,"code":1430,"language":146,"meta":147,"style":147},"reading.values = [\n    CentauroValues(time=\"2025-06-01T11:00:00\", value=27.8),\n    CentauroValues(time=\"2025-06-01T12:00:00\", value=28.2),\n]\ncoll.update_object(reading, values_mode=\"append\")\n# The 3 original values are preserved, 2 new ones added\n",[124,1432,1433,1446,1475,1503,1508,1535],{"__ignoreMap":147},[151,1434,1435,1437,1439,1441,1443],{"class":153,"line":154},[151,1436,518],{"class":161},[151,1438,510],{"class":171},[151,1440,916],{"class":866},[151,1442,235],{"class":171},[151,1444,1445],{"class":171}," [\n",[151,1447,1448,1451,1453,1455,1457,1459,1462,1464,1466,1468,1470,1473],{"class":153,"line":178},[151,1449,1450],{"class":316},"    CentauroValues",[151,1452,196],{"class":171},[151,1454,409],{"class":377},[151,1456,210],{"class":171},[151,1458,321],{"class":171},[151,1460,1461],{"class":216},"2025-06-01T11:00:00",[151,1463,321],{"class":171},[151,1465,172],{"class":171},[151,1467,423],{"class":377},[151,1469,210],{"class":171},[151,1471,1472],{"class":428},"27.8",[151,1474,432],{"class":171},[151,1476,1477,1479,1481,1483,1485,1487,1490,1492,1494,1496,1498,1501],{"class":153,"line":185},[151,1478,1450],{"class":316},[151,1480,196],{"class":171},[151,1482,409],{"class":377},[151,1484,210],{"class":171},[151,1486,321],{"class":171},[151,1488,1489],{"class":216},"2025-06-01T12:00:00",[151,1491,321],{"class":171},[151,1493,172],{"class":171},[151,1495,423],{"class":377},[151,1497,210],{"class":171},[151,1499,1500],{"class":428},"28.2",[151,1502,432],{"class":171},[151,1504,1505],{"class":153,"line":204},[151,1506,1507],{"class":171},"]\n",[151,1509,1510,1512,1514,1516,1518,1520,1522,1525,1527,1529,1531,1533],{"class":153,"line":223},[151,1511,507],{"class":161},[151,1513,510],{"class":171},[151,1515,652],{"class":316},[151,1517,196],{"class":171},[151,1519,518],{"class":316},[151,1521,172],{"class":171},[151,1523,1524],{"class":377}," values_mode",[151,1526,210],{"class":171},[151,1528,321],{"class":171},[151,1530,1423],{"class":216},[151,1532,321],{"class":171},[151,1534,329],{"class":171},[151,1536,1537],{"class":153,"line":241},[151,1538,1539],{"class":897},"# The 3 original values are preserved, 2 new ones added\n",[952,1541,1543],{"id":1542},"upsert",[124,1544,1542],{},[112,1546,1547],{},"Inserts new timestamps, overwrites existing ones. Use when values can be corrected or recalculated:",[142,1549,1551],{"className":144,"code":1550,"language":146,"meta":147,"style":147},"reading.values = [\n    CentauroValues(time=\"2025-06-01T10:00:00\", value=25.9),  # corrected value\n    CentauroValues(time=\"2025-06-01T13:00:00\", value=29.0),  # new point\n]\ncoll.update_object(reading, values_mode=\"upsert\")\n",[124,1552,1553,1565,1596,1627,1631],{"__ignoreMap":147},[151,1554,1555,1557,1559,1561,1563],{"class":153,"line":154},[151,1556,518],{"class":161},[151,1558,510],{"class":171},[151,1560,916],{"class":866},[151,1562,235],{"class":171},[151,1564,1445],{"class":171},[151,1566,1567,1569,1571,1573,1575,1577,1579,1581,1583,1585,1587,1590,1593],{"class":153,"line":178},[151,1568,1450],{"class":316},[151,1570,196],{"class":171},[151,1572,409],{"class":377},[151,1574,210],{"class":171},[151,1576,321],{"class":171},[151,1578,477],{"class":216},[151,1580,321],{"class":171},[151,1582,172],{"class":171},[151,1584,423],{"class":377},[151,1586,210],{"class":171},[151,1588,1589],{"class":428},"25.9",[151,1591,1592],{"class":171},"),",[151,1594,1595],{"class":897},"  # corrected value\n",[151,1597,1598,1600,1602,1604,1606,1608,1611,1613,1615,1617,1619,1622,1624],{"class":153,"line":185},[151,1599,1450],{"class":316},[151,1601,196],{"class":171},[151,1603,409],{"class":377},[151,1605,210],{"class":171},[151,1607,321],{"class":171},[151,1609,1610],{"class":216},"2025-06-01T13:00:00",[151,1612,321],{"class":171},[151,1614,172],{"class":171},[151,1616,423],{"class":377},[151,1618,210],{"class":171},[151,1620,1621],{"class":428},"29.0",[151,1623,1592],{"class":171},[151,1625,1626],{"class":897},"  # new point\n",[151,1628,1629],{"class":153,"line":204},[151,1630,1507],{"class":171},[151,1632,1633,1635,1637,1639,1641,1643,1645,1647,1649,1651,1653,1655],{"class":153,"line":223},[151,1634,507],{"class":161},[151,1636,510],{"class":171},[151,1638,652],{"class":316},[151,1640,196],{"class":171},[151,1642,518],{"class":316},[151,1644,172],{"class":171},[151,1646,1524],{"class":377},[151,1648,210],{"class":171},[151,1650,321],{"class":171},[151,1652,1542],{"class":216},[151,1654,321],{"class":171},[151,1656,329],{"class":171},[952,1658,1660],{"id":1659},"replace",[124,1661,1659],{},[112,1663,1664],{},"Deletes all existing values and inserts fresh. Use for full series replacement:",[142,1666,1668],{"className":144,"code":1667,"language":146,"meta":147,"style":147},"coll.update_object(reading, values_mode=\"replace\")\n",[124,1669,1670],{"__ignoreMap":147},[151,1671,1672,1674,1676,1678,1680,1682,1684,1686,1688,1690,1692,1694],{"class":153,"line":154},[151,1673,507],{"class":161},[151,1675,510],{"class":171},[151,1677,652],{"class":316},[151,1679,196],{"class":171},[151,1681,518],{"class":316},[151,1683,172],{"class":171},[151,1685,1524],{"class":377},[151,1687,210],{"class":171},[151,1689,321],{"class":171},[151,1691,1659],{"class":216},[151,1693,321],{"class":171},[151,1695,329],{"class":171},[1697,1698,1699,1701,1702,1705],"warning",{},[124,1700,1659],{}," mode permanently removes ",[133,1703,1704],{},"all"," existing values for the object before inserting the new list. Historical data is lost — use with caution in production.",[116,1707,270],{"id":1708},"tracking-multiple-series",[112,1710,1711,1712,1714],{},"Since each ",[124,1713,126],{}," object represents one series, model different measurement types as separate classes:",[142,1716,1718],{"className":144,"code":1717,"language":146,"meta":147,"style":147},"class TemperatureSeries(CentauroModelSeries):\n    __centauro_name__ = \"TemperatureSeries\"\n    location: str = \"\"\n\nclass HumiditySeries(CentauroModelSeries):\n    __centauro_name__ = \"HumiditySeries\"\n    location: str = \"\"\n\ncoll = TimeSeriesCollection(engine, \"monitoring\")\n\ntemp = TemperatureSeries(location=\"pelion\", values=[\n    CentauroValues(time=\"2025-06-01T08:00:00\", value=22.5),\n])\nhumidity = HumiditySeries(location=\"pelion\", values=[\n    CentauroValues(time=\"2025-06-01T08:00:00\", value=65.0),\n])\n\ncoll.write_object(temp)\ncoll.write_object(humidity)\n\n# Query each series independently\ntemps = coll.read_objects(TemperatureSeries)\nhumids = coll.read_objects(HumiditySeries)\n",[124,1719,1720,1733,1746,1758,1762,1775,1788,1800,1804,1826,1830,1857,1883,1887,1914,1942,1947,1952,1968,1984,1989,1995,2015],{"__ignoreMap":147},[151,1721,1722,1724,1727,1729,1731],{"class":153,"line":154},[151,1723,189],{"class":188},[151,1725,1726],{"class":192}," TemperatureSeries",[151,1728,196],{"class":171},[151,1730,126],{"class":192},[151,1732,201],{"class":171},[151,1734,1735,1737,1739,1741,1744],{"class":153,"line":178},[151,1736,207],{"class":161},[151,1738,210],{"class":171},[151,1740,213],{"class":171},[151,1742,1743],{"class":216},"TemperatureSeries",[151,1745,220],{"class":171},[151,1747,1748,1750,1752,1754,1756],{"class":153,"line":185},[151,1749,226],{"class":161},[151,1751,229],{"class":171},[151,1753,232],{"class":192},[151,1755,235],{"class":171},[151,1757,238],{"class":171},[151,1759,1760],{"class":153,"line":204},[151,1761,182],{"emptyLinePlaceholder":181},[151,1763,1764,1766,1769,1771,1773],{"class":153,"line":223},[151,1765,189],{"class":188},[151,1767,1768],{"class":192}," HumiditySeries",[151,1770,196],{"class":171},[151,1772,126],{"class":192},[151,1774,201],{"class":171},[151,1776,1777,1779,1781,1783,1786],{"class":153,"line":241},[151,1778,207],{"class":161},[151,1780,210],{"class":171},[151,1782,213],{"class":171},[151,1784,1785],{"class":216},"HumiditySeries",[151,1787,220],{"class":171},[151,1789,1790,1792,1794,1796,1798],{"class":153,"line":374},[151,1791,226],{"class":161},[151,1793,229],{"class":171},[151,1795,232],{"class":192},[151,1797,235],{"class":171},[151,1799,238],{"class":171},[151,1801,1802],{"class":153,"line":392},[151,1803,182],{"emptyLinePlaceholder":181},[151,1805,1806,1808,1810,1812,1814,1816,1818,1820,1822,1824],{"class":153,"line":401},[151,1807,334],{"class":161},[151,1809,210],{"class":171},[151,1811,339],{"class":316},[151,1813,196],{"class":171},[151,1815,344],{"class":316},[151,1817,172],{"class":171},[151,1819,213],{"class":171},[151,1821,351],{"class":216},[151,1823,321],{"class":171},[151,1825,329],{"class":171},[151,1827,1828],{"class":153,"line":435},[151,1829,182],{"emptyLinePlaceholder":181},[151,1831,1832,1835,1837,1839,1841,1843,1845,1847,1849,1851,1853,1855],{"class":153,"line":464},[151,1833,1834],{"class":161},"temp ",[151,1836,210],{"class":171},[151,1838,1726],{"class":316},[151,1840,196],{"class":171},[151,1842,584],{"class":377},[151,1844,210],{"class":171},[151,1846,321],{"class":171},[151,1848,384],{"class":216},[151,1850,321],{"class":171},[151,1852,172],{"class":171},[151,1854,597],{"class":377},[151,1856,398],{"class":171},[151,1858,1859,1861,1863,1865,1867,1869,1871,1873,1875,1877,1879,1881],{"class":153,"line":493},[151,1860,1450],{"class":316},[151,1862,196],{"class":171},[151,1864,409],{"class":377},[151,1866,210],{"class":171},[151,1868,321],{"class":171},[151,1870,416],{"class":216},[151,1872,321],{"class":171},[151,1874,172],{"class":171},[151,1876,423],{"class":377},[151,1878,210],{"class":171},[151,1880,429],{"class":428},[151,1882,432],{"class":171},[151,1884,1885],{"class":153,"line":499},[151,1886,638],{"class":171},[151,1888,1889,1892,1894,1896,1898,1900,1902,1904,1906,1908,1910,1912],{"class":153,"line":504},[151,1890,1891],{"class":161},"humidity ",[151,1893,210],{"class":171},[151,1895,1768],{"class":316},[151,1897,196],{"class":171},[151,1899,584],{"class":377},[151,1901,210],{"class":171},[151,1903,321],{"class":171},[151,1905,384],{"class":216},[151,1907,321],{"class":171},[151,1909,172],{"class":171},[151,1911,597],{"class":377},[151,1913,398],{"class":171},[151,1915,1917,1919,1921,1923,1925,1927,1929,1931,1933,1935,1937,1940],{"class":153,"line":1916},15,[151,1918,1450],{"class":316},[151,1920,196],{"class":171},[151,1922,409],{"class":377},[151,1924,210],{"class":171},[151,1926,321],{"class":171},[151,1928,416],{"class":216},[151,1930,321],{"class":171},[151,1932,172],{"class":171},[151,1934,423],{"class":377},[151,1936,210],{"class":171},[151,1938,1939],{"class":428},"65.0",[151,1941,432],{"class":171},[151,1943,1945],{"class":153,"line":1944},16,[151,1946,638],{"class":171},[151,1948,1950],{"class":153,"line":1949},17,[151,1951,182],{"emptyLinePlaceholder":181},[151,1953,1955,1957,1959,1961,1963,1966],{"class":153,"line":1954},18,[151,1956,507],{"class":161},[151,1958,510],{"class":171},[151,1960,513],{"class":316},[151,1962,196],{"class":171},[151,1964,1965],{"class":316},"temp",[151,1967,329],{"class":171},[151,1969,1971,1973,1975,1977,1979,1982],{"class":153,"line":1970},19,[151,1972,507],{"class":161},[151,1974,510],{"class":171},[151,1976,513],{"class":316},[151,1978,196],{"class":171},[151,1980,1981],{"class":316},"humidity",[151,1983,329],{"class":171},[151,1985,1987],{"class":153,"line":1986},20,[151,1988,182],{"emptyLinePlaceholder":181},[151,1990,1992],{"class":153,"line":1991},21,[151,1993,1994],{"class":897},"# Query each series independently\n",[151,1996,1998,2001,2003,2005,2007,2009,2011,2013],{"class":153,"line":1997},22,[151,1999,2000],{"class":161},"temps ",[151,2002,210],{"class":171},[151,2004,852],{"class":161},[151,2006,510],{"class":171},[151,2008,1059],{"class":316},[151,2010,196],{"class":171},[151,2012,1743],{"class":316},[151,2014,329],{"class":171},[151,2016,2018,2021,2023,2025,2027,2029,2031,2033],{"class":153,"line":2017},23,[151,2019,2020],{"class":161},"humids ",[151,2022,210],{"class":171},[151,2024,852],{"class":161},[151,2026,510],{"class":171},[151,2028,1059],{"class":316},[151,2030,196],{"class":171},[151,2032,1785],{"class":316},[151,2034,329],{"class":171},[112,2036,2037,2038,2041,2042,2046],{},"Both series share the same collection (and can use the same ",[267,2039,2040],{"href":44},"views"," and ",[267,2043,2045],{"href":2044},"/essentials/views#standalone-indexes","indexes","), but are stored independently with their own values.",[116,2048,2050],{"id":2049},"querying-time-series-objects","Querying time-series objects",[112,2052,2053,2054,2056,2057,2060,2061,2060,2064,2067],{},"All the query features from ",[267,2055,38],{"href":39}," work with time-series collections — filtering, ",[124,2058,2059],{},"like",", ",[124,2062,2063],{},"is_in",[124,2065,2066],{},"OrGroup",", aggregates:",[142,2069,2071],{"className":144,"code":2070,"language":146,"meta":147,"style":147},"# All sensors in greenhouse_a\nresults = coll.read_objects(\n    TemperatureSeries.fields.location == \"pelion\"\n)\n\n# Latest reading across all locations\nlatest = coll.read_latest_object(TemperatureSeries)\n",[124,2072,2073,2078,2093,2116,2120,2124,2129],{"__ignoreMap":147},[151,2074,2075],{"class":153,"line":154},[151,2076,2077],{"class":897},"# All sensors in greenhouse_a\n",[151,2079,2080,2083,2085,2087,2089,2091],{"class":153,"line":178},[151,2081,2082],{"class":161},"results ",[151,2084,210],{"class":171},[151,2086,852],{"class":161},[151,2088,510],{"class":171},[151,2090,1059],{"class":316},[151,2092,371],{"class":171},[151,2094,2095,2098,2100,2103,2105,2107,2110,2112,2114],{"class":153,"line":185},[151,2096,2097],{"class":316},"    TemperatureSeries",[151,2099,510],{"class":171},[151,2101,2102],{"class":866},"fields",[151,2104,510],{"class":171},[151,2106,584],{"class":866},[151,2108,2109],{"class":171}," ==",[151,2111,213],{"class":171},[151,2113,384],{"class":216},[151,2115,220],{"class":171},[151,2117,2118],{"class":153,"line":204},[151,2119,329],{"class":171},[151,2121,2122],{"class":153,"line":223},[151,2123,182],{"emptyLinePlaceholder":181},[151,2125,2126],{"class":153,"line":241},[151,2127,2128],{"class":897},"# Latest reading across all locations\n",[151,2130,2131,2134,2136,2138,2140,2143,2145,2147],{"class":153,"line":374},[151,2132,2133],{"class":161},"latest ",[151,2135,210],{"class":171},[151,2137,852],{"class":161},[151,2139,510],{"class":171},[151,2141,2142],{"class":316},"read_latest_object",[151,2144,196],{"class":171},[151,2146,1743],{"class":316},[151,2148,329],{"class":171},[116,2150,2152],{"id":2151},"database-schema","Database schema",[112,2154,2155,2156,2158,2159,2162],{},"A ",[124,2157,281],{}," named ",[124,2160,2161],{},"\"monitoring\""," creates two tables:",[2164,2165,2166,2179],"table",{},[2167,2168,2169],"thead",{},[2170,2171,2172,2176],"tr",{},[2173,2174,2175],"th",{},"Table",[2173,2177,2178],{},"Purpose",[2180,2181,2182,2193],"tbody",{},[2170,2183,2184,2190],{},[2185,2186,2187],"td",{},[124,2188,2189],{},"monitoring_objects",[2185,2191,2192],{},"Metadata — id, name, write_time, edit_time, meta (JSON)",[2170,2194,2195,2200],{},[2185,2196,2197],{},[124,2198,2199],{},"monitoring_values",[2185,2201,2202],{},"Time-series — data_object_id, time, value, write_time",[112,2204,1377,2205,2208],{},[124,2206,2207],{},"(data_object_id, time)"," composite key in the values table ensures no duplicate timestamps per object.",[2210,2211,2212],"style",{},"html pre.shiki code .s7zQu, html code.shiki .s7zQu{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#89DDFF;--shiki-default-font-style:italic;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .sTEyZ, html code.shiki .sTEyZ{--shiki-light:#90A4AE;--shiki-default:#EEFFFF;--shiki-dark:#BABED8}html pre.shiki code .sMK4o, html code.shiki .sMK4o{--shiki-light:#39ADB5;--shiki-default:#89DDFF;--shiki-dark:#89DDFF}html pre.shiki code .spNyl, html code.shiki .spNyl{--shiki-light:#9C3EDA;--shiki-default:#C792EA;--shiki-dark:#C792EA}html pre.shiki code .sBMFI, html code.shiki .sBMFI{--shiki-light:#E2931D;--shiki-default:#FFCB6B;--shiki-dark:#FFCB6B}html pre.shiki code .sfazB, html code.shiki .sfazB{--shiki-light:#91B859;--shiki-default:#C3E88D;--shiki-dark:#C3E88D}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html pre.shiki code .s2Zo4, html code.shiki .s2Zo4{--shiki-light:#6182B8;--shiki-default:#82AAFF;--shiki-dark:#82AAFF}html pre.shiki code .sHdIc, html code.shiki .sHdIc{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#EEFFFF;--shiki-default-font-style:italic;--shiki-dark:#BABED8;--shiki-dark-font-style:italic}html pre.shiki code .sbssI, html code.shiki .sbssI{--shiki-light:#F76D47;--shiki-default:#F78C6C;--shiki-dark:#F78C6C}html pre.shiki code .swJcz, html code.shiki .swJcz{--shiki-light:#E53935;--shiki-default:#F07178;--shiki-dark:#F07178}html pre.shiki code .sHwdD, html code.shiki .sHwdD{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#546E7A;--shiki-default-font-style:italic;--shiki-dark:#676E95;--shiki-dark-font-style:italic}",{"title":147,"searchDepth":178,"depth":178,"links":2214},[2215,2216,2217,2218,2221,2222,2228,2229,2230],{"id":118,"depth":178,"text":119},{"id":274,"depth":178,"text":275},{"id":661,"depth":178,"text":662},{"id":833,"depth":178,"text":834,"children":2219},[2220],{"id":954,"depth":185,"text":955},{"id":1132,"depth":178,"text":1133},{"id":1409,"depth":178,"text":1410,"children":2223},[2224,2226,2227],{"id":1420,"depth":185,"text":2225},"append (default)",{"id":1542,"depth":185,"text":1542},{"id":1659,"depth":185,"text":1659},{"id":1708,"depth":178,"text":270},{"id":2049,"depth":178,"text":2050},{"id":2151,"depth":178,"text":2152},"Store and query time-series data with TimeSeriesCollection, Polars DataFrames, and flexible update modes.","md",null,{},{"icon":67},{"title":64,"description":2231},"5aI6m_No8raZwMJ-WvSd2Td2GFQwZ7khJE9AYaOCeuw",[2239,2241],{"title":53,"path":54,"stem":55,"description":2240,"icon":56,"children":-1},"Link parent and child objects with parent_ref — build one-to-many relationships without foreign key migrations.",{"title":69,"path":70,"stem":71,"description":2242,"icon":72,"children":-1},"Use AsyncCollection and AsyncTimeSeriesCollection for non-blocking database operations in async applications.",1781105060350]