KuroCloudDicom
KuroCloudDicom computes volumes over DICOM image collections stored in S3-compatible object storage, running the work in parallel with Lithops.
It works in two steps:
- Preprocess and upload. Each DICOM image is decoded, split into chunks and uploaded as a
compressed "CloudDicom" object, together with a
metadata.jsondescribing the collection. - Compute the volume. The chunk keys are distributed across Lithops workers, each worker sums the physical area of its chunks, and the results are reduced and multiplied by the slice thickness.
The computed volume is the full image extent of every slice
(Σ rows · cols · pixel_spacing[0] · pixel_spacing[1] · slice_thickness), in the units of the DICOM
spacing attributes (normally mm³). No segmentation is performed.
Installation
pip install KuroCloudDicom
Python 3.9 or newer is required. The dependencies include lithops, boto3, pydicom (2.x),
python-gdcm, numpy and scipy.
Lithops configuration
Lithops reads its configuration from a .lithops_config file (see the
Lithops configuration docs for where
it is looked up). The project was tested with the Kubernetes backend and MinIO storage, for example:
lithops:
backend: k8s
storage: minio
k8s:
docker_server: docker.io
docker_user: <your-docker-user>
docker_password: <your-docker-password-or-token>
runtime_timeout: 3600
max_workers: 12
runtime_memory: 256
minio:
storage_bucket: <existing-lithops-bucket>
endpoint: <http://your-minio-host:9000>
access_key_id: <your-access-key-id>
secret_access_key: <your-secret-access-key>
Never commit real credentials to version control.
The default Lithops runtime image used by the volume functions is aarons28/kuro-dicom-v310:1.0. You
can pass your own image with the runtime= argument. Lithops generally expects the Python version of
your local environment to match the one in the runtime image.
Usage
S3 configuration
Both steps take an s3_config mapping with these keys:
s3_config = {
"aws_access_key_id": "<your-access-key-id>",
"aws_secret_access_key": "<your-secret-access-key>",
"endpoint_url": "<http://your-minio-host:9000>", # None for AWS S3
"region_name": "<your-region>",
}
1. Upload a collection
from KuroCloudDicom.CloudDicomHandlers.CloudDicomDataManager import CloudDicomDataManager
bucket_name = "dicom" # chunks are stored in the bucket "dicom.meta"
prefix_key = "patient-01" # folder for this collection
data_manager = CloudDicomDataManager(
s3_config=s3_config,
bucket_name=bucket_name,
prefix_key=prefix_key,
)
# Each item needs a `.name` (str) and a binary, readable `.file`,
# e.g. Starlette/FastAPI UploadFile objects.
files = [...]
data_manager.UploadDicomCollection(files)
The chunks are written to <bucket_name>.meta/<prefix_key>/<file name>.000, .001, and so on.
metadata.json is written next to them. The <bucket_name>.meta bucket must already exist.
2. Compute the volume
from KuroCloudDicom.CloudDicomHandlers.CloudDicomOperations import ComputeVolumenFullParallel
volume = ComputeVolumenFullParallel(
metadata=data_manager.ObtainMetadata(),
s3_config=s3_config,
s3_path=data_manager.S3Path(),
bucket_name=bucket_name,
workers=8,
)
print(volume)
workers is the maximum number of Lithops tasks the chunks are split across.
Tested environment
The library was tested by the author with:
- Lithops with the Kubernetes backend on k3s
- MinIO as the S3-compatible storage
Other Lithops backends and storage providers have not been tested.
Limitations
- Bucket names: chunks are stored in a second bucket named
<bucket_name>.meta. It must exist beforehand. Bucket names containing dots can cause TLS errors on AWS S3 with virtual-hosted addressing. MinIO is not affected. - Pixel data is read as 16-bit unsigned integers. The default upload format rescales values assuming 12-bit data and stores them as 8-bit. This does not affect the volume, which only depends on image shape and spacing.
metadata.json(pixel spacing and slice thickness) is taken from the last file of the upload, so all files of a collection are assumed to share the same spacing.s3_configis sent to the Lithops workers as part of the task arguments.- The unit tests mock S3 and Lithops. End-to-end behaviour is only verified in the tested environment above.
License
MIT. See LICENSE.
Metadata
Release files for KuroCloudDicom 0.0.3
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| kuroclouddicom-0.0.3.tar.gz | 14.6 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| kuroclouddicom-0.0.3-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 32.5 kB
Release files / kuroclouddicom-0.0.3.tar.gz
| Download URL | kuroclouddicom-0.0.3.tar.gz |
|---|---|
| Size | 14.6 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
64cdfd2735bf7432f568afdff9a6bc2c25a3808d921f81c29662664c9c7ec94a
|
|
BLAKE2b-256 checksum How to use checksums |
eccfa921cb364af5fbc6f61de3a47d76ef3cb3f9c4989fedcdcf95769d54d3d4
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.11.9
|
Release files / kuroclouddicom-0.0.3-py3-none-any.whl
| Download URL | kuroclouddicom-0.0.3-py3-none-any.whl |
|---|---|
| Size | 17.9 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
c234a2d6112a939b0ed5ec72c28adec098d3b5bea1d5f4488b246b36eb459b3c
|
|
BLAKE2b-256 checksum How to use checksums |
3be93a46d732cd20409ca8a83dcefd6612a29da7a0636fb6ac3d3620c8e9a973
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.11.9
|