onecodex

Command line interface and Python client library for the One Codex API

https://github.com/onecodex/onecodex

Science Score: 36.0%

This score indicates how likely this project is to be science-related based on various indicators:

  • CITATION.cff file
  • codemeta.json file
    Found codemeta.json file
  • .zenodo.json file
    Found .zenodo.json file
  • DOI references
  • Academic publication links
  • Committers with academic emails
    1 of 27 committers (3.7%) from academic institutions
  • Institutional organization owner
  • JOSS paper metadata
  • Scientific vocabulary similarity
    Low similarity (14.1%) to scientific vocabulary
Last synced: 10 months ago · JSON representation

Repository

Command line interface and Python client library for the One Codex API

Basic Info
Statistics
  • Stars: 24
  • Watchers: 15
  • Forks: 12
  • Open Issues: 31
  • Releases: 72
Created over 11 years ago · Last pushed 12 months ago
Metadata Files
Readme Changelog License

README.md

One Codex API - Python Client Library and CLI

test pre-commit

Command line interface (CLI) and Python client library for interacting with the One Codex v1 API (API docs).

MAINTAINERS: @clausmith, @boydgreenfield

Installation

This package provides 3 major pieces of functionality: (1) a core Python client library; (2) a simple CLI for interacting with the One Codex platform that uses that core library; and (3) optional extensions to the client library, which offers many features aimed at advanced users and provides functionality for use in interactive notebook environments (e.g., IPython notebooks).

Python 3.9 or later is required. Python 2 is no longer supported.

Basic installation

The CLI (and core Python library) may be simply installed using pip. To download a minimal installation (#1 and #2), simply run: shell pip install onecodex

Installation with optional extensions

To also download the optional extensions to the client library, and all of their dependencies, run:

shell pip install 'onecodex[all]'

Using the CLI

Logging in

The CLI supports authentication using either your One Codex API key or your One Codex username and password. To log in using your username and password:

shell onecodex login

This command will save a credentials file at ~/.onecodex, which will then automatically be used for authentication the next time the CLI or Python client library are used (OS X/Linux only). You can clear this file and remove your API key from your machine with onecodex logout.

In a shared environment, we recommend directly using your One Codex API key, rather than logging in and storing it in a credentials file. To use API key authentication, simply pass your key as an argument to the onecodex command: shell onecodex --api-key=YOUR_API_KEY samples

Your API key can be found on the One Codex settings page and should be 32 character string. You may also generate a new API key on the settings page in the web application. Note: Because your API key provides access to all of the samples and metadata in your account, you should immediately reset your key on the website if it is ever accidentally revealed or saved (e.g., checked into a GitHub repository).

Uploading files

The CLI supports uploading FASTA or FASTQ files (optionally gzip compressed) via the upload command. shell onecodex upload bacterial_reads_file.fq.gz

Multiple files can be uploaded in a single command as well: shell onecodex upload file1.fq.gz file2.fq.gz ...

You can also upload files using the Python client library:

```python uploaded_sample1 = ocx.Samples.upload("/path/to/file.fastq")

Or upload a tuple of paired end files

uploaded_sample2 = ocx.Samples.upload(("/path/to/R1.fastq", "/path/to/R2.fastq")) ```

Which returns a Samples resource (as of 0.5.0). Samples can be associated with tags, metadata, and projects at upload timing using those respective keyword arguments:

```python

Note format must match the schema defined for our API, with arbitrary

metadata allowed as a single-level dictionary in the custom field.

See https://developer.onecodex.com/api-reference/metadata-resource for details.

metadata = { "platform": "Illumina NovaSeq 6000", "datecollected": "2019-04-14T00:51:54.832048+00:00", "externalsample_id": "my-lims-ID-or-similar", "custom": { "my-string-field": "A most interesting sample...", "my-boolean-field": True, "my-number-field-1": 1, "my-number-field-2": 2.0, } } ```

Uploads can be made in parallel using Python threads (or multiple processes), e.g.:

```python import concurrent.futures uploaded_samples = []

with concurrent.futures.ThreadPoolExecutor(maxworkers=4) as executor: futures = {executor.submit(ocx.Samples.upload, file) for file in LISTOFFILES} for future in concurrent.futures.ascompleted(futures): try: uploaded_samples.append(future.result()) except Exception as e: print("An execption occurred during your upload: {}".format(e)) ```

Resources

The CLI supports retrieving your One Codex samples and analyses. The following resources may be queried:

  • Your samples (Samples)

  • Sample metadata (Metadata)

  • Analyses, which include several subtypes with additional functionality and fields:

    • Classifications, which are basic metagenomic classification results for your samples
    • Panels, which are in silico panels for particular genes or other functional markers (example on One Codex)
  • Jobs, which provide information on the name, version, and type of analysis which was performed for a given Analyses

Simply invoke the onecodex command, using one of the above resource names as a subcommand (all lowercase). For example: ```shell

fetch all your samples

onecodex samples

fetch a list of panels based on their ids

onecodex panels 0123456789abcdef 0987654321fdecba ```

Using the Python client library

Initialization

To load the API, use the following import: python from onecodex.api import Api

Instantiate an API client either by passing your API key or automatically fetching your credentials from ~/.onecodex if you've previously called onecodex login.

```python from onecodex.api import Api

Instantiate a One Codex API object, will attempt to get credentials from ~/.onecodex

ocx = Api()

Instantiate an API object, manually specifying an API key

ocx = Api(apikey="YOURAPIKEYHERE") ```

Resources

Resources are exposed as attributes on the API object. You can fetch a resource directly by its ID or you can fetch it using the query interface. Currently you can access resources using either get() or where(). If you need help finding the ID for a sample, its identifier is part of its url on our webpage: e.g. for an analysis at https://app.onecodex.com/analysis/public/1d9491c5c31345b6, the ID is 1d9491c5c31345b6. IDs are all short unique identifiers, consisting of 16 hexadecimal characters (0-9a-f).

python sample_analysis = ocx.Classifications.get("1d9491c5c31345b6") # Fetch an individual classification sample_analysis.results() # Returns classification results as JSON object sample_analysis.table() # Returns a pandas dataframe

In addition to methods on individual instances of a given resource (e.g., a Sample or an Analysis), the library also provides methods for aggregating sets of samples or analyses:

python all_completed_analyses = ocx.Classifications.where(complete=True) all_completed_analyses.to_otu() # Returns classification results as JSON object all_completed_analyses.to_df() # Returns a pandas dataframe

Development

Environment Setup

Before developing, git and python version >=3.9 are needed. We recommend using uv for Python version management and dependency installation.

To download the client library from GitHub:

shell git clone https://github.com/onecodex/onecodex.git cd onecodex/

To set up the project, install dependencies using uv:

```shell

If you are on a M1 Macbook, run the line below, adjusting the version as needed

export HDF5DIR=/opt/homebrew/Cellar/hdf5/1.12.11/

uv sync --all-extras --dev --locked ```

To activate the virtual environment:

shell source .venv/bin/activate

Tests are run via pytest while code formatting and linting is done using ruff:

shell make lint make test

We use pre-commit for automated linting using ruff and various whitespace and newline formatters during development.

Writing Unit Tests

We use pytest as our unit testing framework. Tests should be able to run without an internet connection, and One Codex API calls must be mocked. We use responses to mock API responses.

Tip: Any API calls that do not have a matching mock will raise an error. You can figure out which API calls need to be mocked by writing a test, running it, and inspecting the error message to see which route(s) are missing.

Warning: Mocked URLs without a query string will ignore query strings in any matching requests. If the mocked URL includes a query string, it will be used when matching requests.

Fixtures

These pytest fixtures may be helpful when writing unit tests:

  • ocx: this is a mocked Api object that uses the api/v1 One Codex API schema.
  • ocx_experimental: this is a mocked Api object that uses the api/v1_experimental One Codex API schema. Use this to test experimental features.
  • api_data: this mocks some API data for v1 and v1_experimental APIs.

Mocking API Data

API data, including schemas, are stored in tests/data/api/:

tests/data/api ├── v1 # the API version │   ├── ... │   ├── analyses │   │   └── index.json # payload for accessing GET::api/v1/analyses. Will also be used to mock each resource instance, e.g. GET::api/v1/analyses/<uuid> │   ├── classifications │   │   ├── 0f4ee4ecb3a3412f │   │   │   └── results │   │   │   └── index.json # payload for accessing GET::api/v1/classifications/0f4ee4ecb3a3412f/results │   │   └── index.json # payload for accessing GET::api/v1/classifications. Instance routes are also auto-mocked │   ├── ... │   ├── schema │   │   ├── index.json # payload for accessing GET::api/v1/schema │   │   └── index_all.json # payload for accessing GET::api/v1/schema?expand=all │   └── ... └── v1_experimental └── ...

The directory structure mirrors the One Codex API. For example:

  • The payload for API route api/v1/classifications is stored at tests/data/api/v1/classifications/index.json.
  • API route api/v1/classifications/0f4ee4ecb3a3412f/results has its payload stored at tests/data/api/v1/classifications/0f4ee4ecb3a3412f/results/index.json.
  • For the v1_experimental API, store things under api/v1_experimental/.

This idea can be extended to arbitrary nesting/depths within the API.

Note: If the payload is large, you can gzip it and name it index.json.gz.

A resource's instance list payload (e.g. api/v1/analyses gives you a list of analyses) is used to auto-mock each resource instance (e.g. api/v1/analyses/<uuid>). You don't need to create an index.json for each instance.

Mocking API Schemas

API schemas work similarly to regular API data, but with a couple of special rules:

  • Each API schema directory must have index.json and index_all.json. index.json contains the payload for e.g. api/v1/schema, and index_all.json contains the payload for e.g. api/v1/schema?expand=all.
  • If the schema requires it, you can optionally define resource-specific schemas by including <resource-name>.json in the schema directory (e.g. assemblies.json for api/v1_experimental/assemblies/schema).

conftest.py

API data is loaded in tests/conftest.py. If you need to mock API calls in a way that's not supported by this framework, you can add custom mocked calls in conftest.py.

Things that are not supported by mocking in tests/data/api/:

  • Non-GET requests (e.g. DELETE)
  • Query parameters (with the exception of schema?expand=all)

Jupyter Notebook Custom Exporters

We also package custom Jupyter notebook nbconvert exporters. These can be tested with the following snippets and the provided example.ipynb report.

Our OneCodexHTMLExporter:

sh ONE_CODEX_REPORT_FILENAME=example.html jupyter nbconvert --execute --to onecodex_html --ExecutePreprocessor.timeout=-1 --output="$ONE_CODEX_REPORT_FILENAME" --output-dir="." notebook_examples/example.ipynb && open example.html

And using the OneCodexPDFExporter:

sh ONE_CODEX_REPORT_FILENAME=example.pdf jupyter nbconvert --execute --to onecodex_pdf --ExecutePreprocessor.timeout=-1 --output="$ONE_CODEX_REPORT_FILENAME" --output-dir="." notebook_examples/example.ipynb && open example.pdf

Note that OneCodexPDFExporter requires the vl-convert-python package to be installed.

Owner

  • Name: One Codex
  • Login: onecodex
  • Kind: organization
  • Email: hello@onecodex.com

GitHub Events

Total
  • Release event: 2
  • Watch event: 1
  • Delete event: 19
  • Issue comment event: 4
  • Push event: 106
  • Pull request review comment event: 63
  • Pull request review event: 78
  • Pull request event: 51
  • Create event: 29
Last Year
  • Release event: 2
  • Watch event: 1
  • Delete event: 19
  • Issue comment event: 4
  • Push event: 106
  • Pull request review comment event: 63
  • Pull request review event: 78
  • Pull request event: 51
  • Create event: 29

Committers

Last synced: over 2 years ago

All Time
  • Total Commits: 510
  • Total Committers: 27
  • Avg Commits per committer: 18.889
  • Development Distribution Score (DDS): 0.696
Past Year
  • Commits: 28
  • Committers: 6
  • Avg Commits per committer: 4.667
  • Development Distribution Score (DDS): 0.536
Top Committers
Name Email Commits
polyatail a****z@g****m 155
Nick Greenfield b****d@g****m 124
Nick Greenfield n****k@o****m 74
Jai Ram Rideout j****i@o****m 35
Alena a****k 25
Christopher Smith c****r@o****m 18
Austin Davis-Richardson h****a@g****m 11
Vincent Prouillet b****k@g****m 8
Jai Ram Rideout j****t@i****m 8
Roderick Bovee r****k@o****m 8
Brett Camarda b****a@g****m 8
Kyle m****e@g****m 7
Paweł Konieczny p****l@o****m 4
Nick Greenfield n****d@g****m 4
Austin Richardson a****n@o****m 3
Gerrit Gerritsen g****n@g****m 3
Cindy c****g@b****u 3
Andrew Sczesnak p****l 2
Denise Lynch l****e@g****m 2
Christopher Smith c****r@s****a 1
Scott Fay s****y@g****m 1
Jai Ram Rideout j****t@g****m 1
Petras Zdanavičius p****d@g****m 1
TR 1****r 1
Cindy Wang c****y@o****m 1
Jeremy Mason-Herr j****r@g****m 1
brainfish 4****h 1
Committer Domains (Top 20 + Academic)

Issues and Pull Requests

Last synced: 10 months ago

All Time
  • Total issues: 12
  • Total pull requests: 169
  • Average time to close issues: 10 months
  • Average time to close pull requests: 11 days
  • Total issue authors: 6
  • Total pull request authors: 15
  • Average comments per issue: 1.92
  • Average comments per pull request: 0.85
  • Merged pull requests: 148
  • Bot issues: 0
  • Bot pull requests: 0
Past Year
  • Issues: 0
  • Pull requests: 18
  • Average time to close issues: N/A
  • Average time to close pull requests: 11 days
  • Issue authors: 0
  • Pull request authors: 4
  • Average comments per issue: 0
  • Average comments per pull request: 0.11
  • Merged pull requests: 12
  • Bot issues: 0
  • Bot pull requests: 0
Top Authors
Issue Authors
  • clausmith (4)
  • boydgreenfield (3)
  • MarianneRay (2)
  • polyatail (1)
  • jdimmerman (1)
  • jwin4740 (1)
Pull Request Authors
  • jairideout (82)
  • alenajk (31)
  • audy (29)
  • pkonieczny (15)
  • petraszd (13)
  • boydgreenfield (8)
  • clausmith (6)
  • Keats (3)
  • GSGerritsen (3)
  • lynchde (2)
  • bcamarda (2)
  • safay (1)
  • brainfish (1)
  • fossabot (1)
  • treynr (1)
Top Labels
Issue Labels
low-priority (1)
Pull Request Labels
feature (1)

Packages

  • Total packages: 1
  • Total downloads:
    • pypi 502 last-month
  • Total dependent packages: 0
  • Total dependent repositories: 5
  • Total versions: 76
  • Total maintainers: 1
pypi.org: onecodex

One Codex API client and Python library

  • Versions: 76
  • Dependent Packages: 0
  • Dependent Repositories: 5
  • Downloads: 502 Last month
Rankings
Dependent repos count: 6.8%
Dependent packages count: 7.4%
Downloads: 8.5%
Average: 9.3%
Forks count: 10.6%
Stargazers count: 13.1%
Maintainers (1)
Last synced: 11 months ago

Dependencies

setup.py pypi
  • boto3 >=1.17.98
  • click >=8.0
  • filelock >=3.0.12,<4
  • jsonschema >=2.4
  • python-dateutil >=2.5.3
  • pytz >=2014.1
  • requests >=2.27.1
  • requests_toolbelt >=0.7.0
  • sentry-sdk >=0.10.2
  • six >=1.10.0
  • unidecode >=1.0.23
.github/workflows/pre-commit.yml actions
  • actions/checkout v2 composite
  • actions/setup-python v2 composite
.github/workflows/test.yml actions
  • actions/checkout v2 composite
  • actions/setup-node v1 composite
  • actions/setup-python v2 composite
  • actions/upload-artifact v1 composite