Skip to main content

Memory-mapped columnar binary format for fast random-access I/O on structured arrays.

Project description

ColStore

A memory-mapped columnar binary format for fast, memory-efficient I/O on structured arrays. colstore lets you write a tabular dataset to a single .cstore file (in one shot or streamed across many records) and then load arbitrary row/column subsets without materializing the rest. Internally, columns are stored back-to-back as raw NumPy bytes, reads use np.memmap, and fancy-index gathers run through a parallel C++ kernel (OpenMP + software prefetching) bound via Cython. Process memory stays bounded by the size of the output you ask for; the source file is never fully read into RAM.

Install

pip install colstore

Building from source needs a C++17 compiler and CMake ≥ 3.18. On macOS install libomp (brew install libomp) to get the parallel kernel; without it the build still succeeds but the kernel runs single-threaded.

Quick start

import colstore

# One-shot write + open. `.cstore` is the canonical extension.
ds = colstore.store(df, "data.cstore")

# Or open an existing file for read.
ds = colstore.open("data.cstore")

# Indexing returns lazy views; no data is read yet.
ds['price']                          # ColumnView
ds[100:200]                          # TableView
ds[100:200, 'price']                 # ColumnView
ds[100:200, ['price', 'qty']]        # TableView
ds[[1, 5, 9], ['price', 'qty']]      # TableView (fancy rows + cols)

# Materialize through one of the materialization methods.
ds['price'].array()                          # 1D ndarray
ds[indices, ['price', 'qty']].dict()         # dict of 1D arrays
ds[indices, ['price', 'qty']].recarray()     # structured ndarray
ds[indices, ['price', 'qty']].frame()        # pandas DataFrame

Writing

colstore.store(data, path) is the one-shot path; it dispatches on the input type:

import colstore
import numpy as np

# From a dict of 1D arrays.
colstore.store(
    {"x": np.arange(100, dtype=np.float32), "y": np.arange(100, dtype=np.int64)},
    "data.cstore",
)

# From a structured (record) array.
records = np.empty(100, dtype=[("price", np.float32), ("qty", np.int32)])
colstore.store(records, "data.cstore", mode="recreate")

# From a pandas DataFrame.
colstore.store(df, "data.cstore", mode="recreate")

mode="create" (default) refuses to overwrite; mode="recreate" truncates an existing file.

For multi-record streaming writes (data arriving in batches, or appending to an existing file), use colstore.create / colstore.recreate / colstore.update:

# Append-only stream into a new file.
with colstore.create("data.cstore") as f:
    for batch in source:
        f.write({"x": batch.x, "y": batch.y})

# Resume appending to an existing file. Schema is loaded from the manifest
# and every write must match it. Bytes from a crashed prior writer are
# truncated on open.
with colstore.update("data.cstore") as f:
    f.write({"x": more_x, "y": more_y})

The writer commits records atomically on close() by rewriting a 32-byte counters block. A reader opening the file mid-write sees only what the last successful close committed.

Compaction

A streaming write produces one record per write() call. Reads of slice and sorted-fancy index patterns scale near-flat with record count, but unsorted-fancy reads degrade as records accumulate. colstore.compact collapses all records into one, so every read pattern takes the single-record fast path:

colstore.compact("data.cstore")                 # in-place
colstore.compact("data.cstore", out="new.cstore")  # leave source untouched

In-place compaction writes to a sibling temp file and atomically renames into place; the source is untouched on failure. The byte copy uses os.sendfile on Linux (kernel-space copy, no Python-side surfacing) and shutil.copyfileobj on macOS/Windows; on both paths memory footprint is bounded by the kernel/I/O buffer (tens of KB) regardless of file size — files much larger than RAM compact fine.

Introspection

i = colstore.info("data.cstore")
# ColStoreInfo(path='data.cstore', n_rows=1_000_000, n_records=42,
#              columns=[a:<f4, b:<i8], file_size=8_001_232B,
#              needs_compaction=True)

colstore.schema("data.cstore")
# [{'name': 'a', 'dtype': '<f4', 'encoding': 'raw', 'nullable': False}, ...]

Both info and schema read only the file header (no record bodies are scanned), so they're cheap on multi-GB files.

Configuration

from colstore import set_max_workers, set_default_madvise, set_default_backend

set_max_workers(8)                # parallel gathers across columns
set_default_madvise("sequential") # OS read-ahead hint for sorted-index reads
set_default_backend("cpp")        # gather kernel: cpp | numpy | numba

On-disk format

[magic 8B = b"CSTORE\x00\x01"]
[counters 32B: n_records(8) + committed_rows(8) + crc32(4) + reserved(12)]
[manifest_len 8B (u64 little-endian)]
[manifest_json: format_version + columns + manifest_crc32]
[zero-padding to 64-byte alignment]
[record_0 header 32B][record_0 body, padded to 8B]
[record_1 header 32B][record_1 body, padded to 8B]
...

The JSON manifest is immutable and carries only the schema; the mutable record/row counters live in their own fixed-position 32-byte block (with its own CRC) right after the magic. Each record body holds the columns back-to-back as raw bytes. A one-shot write produces a single-record file that reads via a per-column memmap fast path; a streamed write produces a multi-record file with per-pattern dispatch (contiguous range, sorted fancy, unsorted fancy).

Supported dtypes

All fixed-size NumPy dtypes are supported: float32/float64, int8/16/32/64, uint8/16/32/64, bool, datetime64, timedelta64, and fixed-width strings (S bytes and U unicode, with the width baked into the dtype, e.g. S16 or U8). Object dtype (variable-length strings, Python objects) is rejected at write time — the design point is zero-copy random access, which requires a fixed stride per row.

License

MIT License - see LICENSE file for details.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

colstore-0.2.0.tar.gz (93.6 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

colstore-0.2.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (163.4 kB view details)

Uploaded CPython 3.13manylinux: glibc 2.17+ x86-64

colstore-0.2.0-cp313-cp313-macosx_11_0_arm64.whl (74.2 kB view details)

Uploaded CPython 3.13macOS 11.0+ ARM64

colstore-0.2.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (163.8 kB view details)

Uploaded CPython 3.12manylinux: glibc 2.17+ x86-64

colstore-0.2.0-cp312-cp312-macosx_11_0_arm64.whl (74.4 kB view details)

Uploaded CPython 3.12macOS 11.0+ ARM64

colstore-0.2.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (162.0 kB view details)

Uploaded CPython 3.11manylinux: glibc 2.17+ x86-64

colstore-0.2.0-cp311-cp311-macosx_11_0_arm64.whl (74.4 kB view details)

Uploaded CPython 3.11macOS 11.0+ ARM64

colstore-0.2.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (162.0 kB view details)

Uploaded CPython 3.10manylinux: glibc 2.17+ x86-64

colstore-0.2.0-cp310-cp310-macosx_11_0_arm64.whl (74.7 kB view details)

Uploaded CPython 3.10macOS 11.0+ ARM64

File details

Details for the file colstore-0.2.0.tar.gz.

File metadata

  • Download URL: colstore-0.2.0.tar.gz
  • Upload date:
  • Size: 93.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for colstore-0.2.0.tar.gz
Algorithm Hash digest
SHA256 264ef1bd2b5910ba493344e3de8c9f12b63b68b849fcd274159c99fa12e71795
MD5 e97b878d34a26ab592303152f2419d87
BLAKE2b-256 27884a2641b202e58fc88d44b045fbe12b4a06abe30a7f9697d4d2ef2e4ad40a

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0.tar.gz:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 5d5b6035c4d2fde40dac8e1a93ecbcdeeb9e31f6b17c163e40684df2b1a4b44a
MD5 a1b780f28f7639cc7c968db1b3cf99f0
BLAKE2b-256 5e84fbcbee88d9c0c439a87d44e5a939d5b19b3317ca83f8840456b300b55c3f

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp313-cp313-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp313-cp313-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 f5cc5ff5817a4851cfe945b60242e856c6d76c061d339439699cf63ba4ac7bf7
MD5 25bcbb4e0a42036113e72ce5458ab00f
BLAKE2b-256 db5d6b75dca97b73fbc18e70e2a5b30ee78b096787cbf3bbbed3ea3be4228db7

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp313-cp313-macosx_11_0_arm64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 fc4f826cde8ba67cd63d9a1816bd1fa2c6cab94578ea54920c0028eaf2e816af
MD5 4b2b6acf71933afc87d557cc2335352b
BLAKE2b-256 e92abe0318ad84d6a9179ba18b2d73bf1dcf71ca7930e64bde165179c323d878

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp312-cp312-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp312-cp312-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 72146cb4435b06867e508144de74c9adaeb7d56afe8592d44c001894fcf32ddd
MD5 3e8f22656446b3f22f78c7d569220b17
BLAKE2b-256 2abe05457be54e10b003fb379a871a9ad2ae063bc47984258252015147d9e8bc

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp312-cp312-macosx_11_0_arm64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 dcaaeefdc2799f7fa70d68ff025f4898b17da568371cd54b96ab45e2cb6228c4
MD5 ee618cc194dc64581a224e9b3be24de7
BLAKE2b-256 e35ca8a9cc7c2d95b95fc144d9e1267e33ff4955bb0e186e17946a14e73b6e3a

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp311-cp311-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp311-cp311-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 acc9e1a76ead358ca17948aff7110e8c5676f21367dbe726a11fcb7ae9552537
MD5 3ca421b8c4c299b0581004c1066b866b
BLAKE2b-256 3ec7680ac57955a96e20a53fdab1e9fc34266a5e0d5720e30e73220d0ebe1cd9

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp311-cp311-macosx_11_0_arm64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 8aa28b20b917b840618982d903e1ccc0c8f4e8eb0c5b249c0c942c91dd2b2ece
MD5 63ef9c711b8efebb722698bb02a7ce40
BLAKE2b-256 ad5cb3ac70a1b333558333b675ae4cfa88f98bea3cb6b1f7d96d34bc7cfc8306

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file colstore-0.2.0-cp310-cp310-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for colstore-0.2.0-cp310-cp310-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 c64fc9052976e3f0fb21af8dfb9607791d5beec7bd16d269331ff44741d72a54
MD5 3f553aa83847d95343b6c1833953c09e
BLAKE2b-256 d049f3d9e987f10113ab0acbceb16757101c026d815784c1d4cd8bc63f59f67b

See more details on using hashes here.

Provenance

The following attestation bundles were made for colstore-0.2.0-cp310-cp310-macosx_11_0_arm64.whl:

Publisher: release.yml on AlkaidCheng/colstore

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page