Why these two datasets
Laboratory ageing data for single cells is easy to find; ageing data for whole packs is not. Work that estimates pack state of health from cell knowledge therefore starts from well-documented public cell campaigns and adapts what they show to the pack. The two datasets on this page are commonly used for that: the XJTU set, with many identical cells under six controlled duty types including partial and random use, and the CALCE CS2 set, with long campaigns on one small prismatic cell under full, partial-window and variable-rate cycling.
Both have been imported with the tools of the open battery-data repository. The repository holds those tools and, for every file, its link, hash and retrieval date; it does not hold the data. The imported cycle values are kept by Lemonergy and are not yet served on this site or through the Data API. This page records what each dataset contains, how its tests ran, its licence and citation, how its files are laid out, what was wrong in those files, and how the import was carried out and checked.
| Dataset | Cells | Cell | Cycles imported | Licence |
|---|---|---|---|---|
| XJTU (Xi’an Jiaotong University), 2024 | 55 in 6 batches | LISHEN 18650, NCM523, 2.0 Ah | 27,642 | CC BY 4.0 |
| CALCE CS2 (University of Maryland), 2010–2013 campaigns | 15 | Prismatic LiCoO2, 1.1 Ah, maker not named | 35,424 | None stated; cite the articles |
XJTU battery dataset
Source, licence and citation
The data was published by Fujin Wang of Xi’an Jiaotong University as Zenodo record 10963339 (doi:10.5281/zenodo.10963339), released on 12 April 2024 under CC BY 4.0. It accompanies Wang, Zhai, Zhao et al., “Physics-informed neural network for lithium-ion battery degradation stable modeling and prognosis”, Nature Communications 15, 4332 (2024), doi:10.1038/s41467-024-48779-z. Cite the article and the record. The batch protocols are described on the authors’ dataset page.
The record is one archive, Battery Dataset.zip, 2.4 GB. The copy imported here matched the published MD5 a635cef9678e0de21f9d5c1f78a4342c.
Cells and test conditions
All 55 cells are LISHEN cylindrical 18650 cells with a LiNi0.5Co0.2Mn0.3O2 positive electrode, 2000 mAh nominal capacity and 3.6 V nominal voltage. They were cycled at room temperature between a 4.2 V charge limit and a 2.5 V discharge limit, with every quantity sampled at 1 Hz. A cell’s test ended when its capacity fell below 80 % of its initial value, about 1.6 Ah. The dataset names the maker but no model number, so the database records the product as cell/lishen/unstated.
The six batches
Each batch applies one charge and discharge strategy. Batches 1–3 discharge fully every cycle, so every cycle measures capacity. Batches 4–6 stop the discharge early or follow a mission profile, so only the cycles the files label test capacity measure it. The last two columns are the median over each batch’s cells.
| Batch (file prefix) | Cells | Strategy | Discharge ends at | Cycles per cell | First capacity check | Last recorded capacity |
|---|---|---|---|---|---|---|
1 (2C_battery) | 8 | Charge at 2C (4 A), discharge at 1C (2 A) | 2.5 V, full | 390–420 | 2.000 Ah | 1.598 Ah |
2 (3C_battery) | 15 | Charge at 3C (6 A), discharge at 1C | 2.5 V, full | 131–322 | 1.984 Ah | 1.598 Ah |
3 (R2.5_battery) | 8 | Charge at 2C; discharge rate stepped through 0.5, 1, 2, 3 and 5C | 2.5 V, full | 527–667 | 1.987 Ah | 1.590 Ah |
4 (R3_battery) | 8 | As batch 3, with capacity checked by a separate full cycle | 3.0 V, partial | 601–799 | 1.988 Ah | 1.594 Ah |
5 (RW_battery) | 8 | Random discharge pulses of 2–8 A lasting 2–6 minutes; periodic capacity checks from cycle 21 | 3.0 V, partial | 186–340 | 1.874 Ah | 1.553 Ah |
6 (Sim_satellite_battery) | 8 | Simulated geostationary-satellite duty: charge at 2C, discharge at 0.667C for profile-set durations; capacity checked about every 5 cycles | Profile, partial | 908–1301 | 1.985 Ah | 1.596 Ah |
The first capacity check is a slow cycle (0.5C charge, 0.2C discharge). For batches 1–3 the last recorded capacity is the final 1C discharge; for batches 4–6 it is the last labelled check. Every file also labels each cycle with its rates, so mixed-rate batches can be separated cycle by cycle.
How the files are laid out
The archive holds six folders, Batch-1 to Batch-6, with one MATLAB file per cell. A separate Temperature_Compensation_Data.mat in the archive root is not a cell file and was not imported. Each cell file carries two variables:
data, one record per cycle, withsystem_time,relative_time_min,voltage_V,current_A,capacity_Ah,power_Wh,temperature_Cand a textdescriptionof that cycle.summary, per cell, with per-cycle charge and discharge capacity and energy, median and mean voltages, the cycle life, and a description of the test.
The field layout follows the authors’ own reader in their preprocessing code library.
What was found in the files
- Timestamps carry a comma.
system_timeis written as date, comma, time. Generic date parsers fail on it, so the known layouts are parsed explicitly. - Relative time restarts at every step.
relative_time_minstarts again at zero for the charge, each rest and the discharge, not once per cycle. Integrated as it stands, each restart is a negative time step, and every 1C discharge in batch 1 came out about 0.17 Ah short. Each restart is bridged with the wall-clock gap between the two samples. - Some cycles miss their first timestamp. In R3_battery-1, R3_battery-7 and Sim_satellite_battery-8, some cycles have no first timestamp while the rest are valid. Their start is taken from the next valid timestamp, back-dated by its offset within the cycle.
- Repeated timestamps sit in rests. Some samples repeat a timestamp at zero current (422 in 2C_battery-1). They carry no charge and are kept as published.
- The capacity column is not used. Its accumulation rule is not documented, so capacity is integrated from current instead. The current is positive on charge (+4 A in batch 1) and negative on discharge.
Import results
All 55 cells imported, 27,642 cycles in total, and every cell gives the same cycle count as its file’s own records. The charge and discharge capacity integrated from current agrees with each file’s reported per-cycle values to a median difference under 1 mAh; the worst cell, in the random-pulse batch 5, differs by at most 13 mAh, under 1 %.
CALCE CS2 cells
Source, licence and citation
The Center for Advanced Life Cycle Engineering at the University of Maryland publishes the CS2 data on its battery data page. The page calls the data open access but states no licence, and asks publications to cite the articles that describe the experiments. For CS2 these are He, Williard, Osterman and Pecht, “Prognostics of lithium-ion batteries based on Dempster–Shafer theory and the Bayesian Monte Carlo method”, Journal of Power Sources 196(23), 10314–10321 (2011) (abstract); Xing, Ma, Tsui and Pecht, Microelectronics Reliability 53(6), 811–820 (2013); and Williard, He, Osterman and Pecht, International Journal of Prognostics and Health Management 4, 1–7 (2013). Because no licence is stated, the raw files are not redistributed; the database keeps their links, hashes and the results derived from them.
The cell and its charge protocol
CS2 is a prismatic LiCoO2 cell rated at 1100 mAh, 5.4 × 33.6 × 50.6 mm and 21.1 g without its protection circuit. CALCE does not name its maker, so the database records it as cell/maker-not-stated/cs2, under the library’s placeholder for a maker the source does not name. CALCE’s other cell types (CX2, PL, INR18650-20R and A123) are separate products; the import reads the type from the file names and refuses a run that mixes two types. Every CS2 cell was charged at 0.5C constant current to 4.2 V, then held at 4.2 V until the current fell below 0.05 A. Discharges end at 2.7 V unless the test type sets another limit.
The six test types and the imported cells
CALCE ran six kinds of test. Initial capacity is the largest discharge in each cell’s first 5 % of cycles. The recorded span is the test time in the merged record; for the two CADEX cells it leaves out the unknown gaps between sessions, so it understates calendar time.
| Cell | Test type | Sessions kept | Cycles (tester’s count) | Recorded span | Initial capacity |
|---|---|---|---|---|---|
| CS2_8 | 1: 0.5C cycling (CADEX) | 19 of 35 | 725 (not recorded) | 143 days | 1.127 Ah |
| CS2_21 | 1: 0.5C cycling (CADEX) | 12 of 22 | 499 (not recorded) | 99 days | 1.100 Ah |
| CS2_33 | 1: 0.5C cycling | 23 of 23 | 866 (868) | 169 days | 1.162 Ah |
| CS2_34 | 1: 0.5C cycling | 23 of 23 | 777 (781) | 199 days | 1.154 Ah |
| CS2_35 | 2: 1C cycling | 24 of 25 | 882 (886) | 171 days | 1.138 Ah |
| CS2_36 | 2: 1C cycling | 26 of 26 | 973 (976) | 170 days | 1.145 Ah |
| CS2_37 | 2: 1C cycling | 27 of 27 | 1,038 (1,043) | 170 days | 1.135 Ah |
| CS2_38 | 2: 1C cycling | 27 of 28 | 1,028 (1,032) | 171 days | 1.140 Ah |
| CS2_3 | 3: discharge current stepped from 0.11 to 2.2 A, cycle to cycle | 38 of 39 | 1,361 (863) | 412 days | 1.109 Ah |
| CS2_9 | 3: discharge current stepped from 0.11 to 2.2 A, cycle to cycle | 41 of 41 | 1,181 (204) | 322 days | 1.141 Ah |
| CS2_7 | 4: 0.55 A discharge, cut-off voltage changed at random | 48 of 49 | 1,118 (1,109) | 213 days | 1.137 Ah |
| CS2_5 | 5: partial cycling between 3.77 V and 2.7 V | 75 of 77 | 7,020 (6,901) | 699 days | 1.155 Ah |
| CS2_6 | 5: partial cycling between 3.77 V and 2.7 V | 66 of 66 | 6,307 (6,246) | 580 days | 1.156 Ah |
| CS2_24 | 6: partial cycling between 4.2 V and 3.77 V | 53 of 53 | 5,039 (4,990) | 494 days | 1.111 Ah |
| CS2_25 | 6: partial cycling between 4.2 V and 3.77 V | 72 of 72 | 6,610 (6,545) | 689 days | 1.105 Ah |
The partial-cycling cells (types 5 and 6) stay inside a voltage window, so most of their cycles are not capacity measurements. The cycle count follows one rule for every cell (see the import section); the tester’s own count is stored beside it. The two disagree most for type 3, where the tester numbers cycles by its own schedule rather than by charge and discharge pairs.
How the files are laid out
Each cell is one zip holding a folder of session files, one per stretch of testing, named after the cell and the export date (CS2_35_10_15_10 is CS2_35, exported 15 October 2010). Thirteen cells were tested on an Arbin cycler: each session is an Excel workbook whose Channel sheets hold test time, a timestamp, step and cycle index, current, voltage and charge and discharge capacity counters. CS2_8 and CS2_21 came off a CADEX tester as tab-separated text: time in minutes, voltage in millivolts, current in milliamperes, and a capacity column in percent, which was not used.
What was wrong in the files, and what was done
A session file is not a continuation of the last one: test time and cycle index restart in every file, and sessions are days apart. Merging them showed the following.
| Problem | Where | What was done |
|---|---|---|
| The same session exported twice under two names | CS2_35 and CS2_38 (2_4_11 and 2_10_11), CS2_7 (12_13_10 and 12_10_10) | The repeat was dropped. |
| An earlier export repeated at the start of a later one | CS2_5 (8_9_13 inside 8_19_13); rows repeating the previous session in CS2_25 (22,767) and CS2_7 (974) | The repeated rows were dropped by timestamp. |
| Every CADEX export repeats the earlier exports of the same running test from its start | CS2_8 (16 of 35 files), CS2_21 (10 of 22) | Each chain was reduced to its longest file. Joined as published, most cycles would count two or three times. |
| Two recordings of the same period whose values disagree at every shared timestamp | CS2_3 (10_19_12 and 10_25_12, 12–18 October 2012); CS2_25 (03_11_13 and 03_04_13, 4–5 March 2013) | The session that started first was kept and the other’s overlapping rows were dropped. The files cannot say which recording is right. |
| Recording gaps of 19.6 and 49.5 hours with current flowing after them | CS2_8, CS2_21 | No charge is counted across a gap. Before, one CS2_8 cycle gained 27 Ah. |
| Currents of about ±1 mA held during rests | Arbin cells | Treated as rest. Before, every cycle split into a charge half and a discharge half. |
| Sessions CALCE itself named as problems | CS2_5: brokenchannel (four days at rest), logicerror (normal 0.5C cycling), tricklecharge (32 rows) | The first two were kept, as neither adds false charge; the trickle-charge file falls inside another session and was dropped. |
| CADEX files carry no clock | CS2_8, CS2_21 | Sessions were joined end to end; the real gaps between them are unknown. |
Every session file and what was done with it is listed in each cell’s session log.
Import results
All 15 CS2 cells imported, 35,424 cycles in total. For the 13 Arbin cells, the capacity integrated from current in every cycle equals the cycler’s own capacity counter, at the median and at the 99th percentile. The 0.5C and 1C cells match the tester’s cycle count to within 2–5 cycles. No cycle discharges more than 1.5 Ah from a 1.1 Ah cell.
How the import works
The battery-data repository does not copy published datasets. It records where each file came from, with a link, a SHA-256 hash and a retrieval date, and stores what is derived from it: one product, one unit per cell, one test run per cell, the run’s segments and one row of values per cycle. Each run cites its own file, by file name and SHA-256, not just the dataset. Nothing presentational is stored: charts are drawn from these values. The two datasets are registered as xjtu-2024 and calce in tools/ingest_open_dataset.py, and described in the data-source notes.
- Convert.
tools/convert_xjtu_mat.pyturns each XJTU cell file into a Battery Data Format table.tools/convert_calce_cs2.pymerges a CALCE cell’s sessions into one, as described above. - Normalise.
tools/cyclers.pyreads the table and settles its conventions from the data itself: the current sign, how capacity counters accumulate, and where cycles begin. - Summarise. A new cycle begins at the first charging sample after a discharge. Rests in between do not hide the boundary, and currents within a noise floor (5 mA, or 0.5 % of the test’s peak current for small cells) count as rest. Each cycle’s charge and discharge capacity is integrated from current. An interval longer than twenty typical sample intervals, and never under an hour, is a recording gap and carries no charge.
- Emit. The result is a single SQL file per dataset, which is reviewed and then loaded with
psql.
Importing these files exposed four faults in the shared pipeline, all fixed before the import with tests that fail on the old behaviour. Cycle boundaries were missed when a rest separated discharge from charge, so one 390-cycle cell came out as a single cycle. Milliamp noise in rests split cycles in two. Current was integrated across recording gaps. And every imported test run cited the first provenance row in the database instead of its own dataset. A review on 30 October found two more: runs still cited the dataset’s first file rather than their own, and a CALCE import could file other cell types under CS2. Both are fixed; each file now has its own source location and provenance row, and the cell type comes from the file names.
To reproduce the import, download the data from the sources above and run:
python tools/convert_xjtu_mat.py ~/data/xjtu/ --out ~/data/xjtu-csv/
python tools/ingest_open_dataset.py ingest xjtu-2024 ~/data/xjtu-csv/ --emit-sql xjtu.sql
python tools/convert_calce_cs2.py ~/data/calce/CS2_* --out ~/data/calce-csv/
python tools/ingest_open_dataset.py ingest calce ~/data/calce-csv/ --emit-sql calce.sql
psql -v ON_ERROR_STOP=1 -d batterydb -f xjtu.sql
psql -v ON_ERROR_STOP=1 -d batterydb -f calce.sql
Both files were loaded into a freshly built database holding the repository’s seed data on 29 October. They predate the 30 October fixes, so they must be emitted again with the current tools before the values are published; the per-file citation is checked on every change to the repository.
Using the data
- Licences differ. XJTU is CC BY 4.0: reuse it with attribution. CALCE states no licence: cite its articles and fetch the files from CALCE rather than from a copy.
- These are single cells in a laboratory. XJTU ran at room temperature, and both sets are free of the cell-to-cell spread, thermal gradients and balancing of a pack. They inform pack work; they are not pack measurements.
- Not every cycle is a capacity measurement. In XJTU batches 4–6 and CALCE types 5 and 6, use the labelled or full cycles when tracking capacity fade.
- Cycle numbers are defined, not inherited. The database’s cycle count follows one stated rule for every dataset, and it differs from a tester’s own numbering where that numbering follows the test schedule. Both are stored.
- Two CALCE periods are uncertain. For the overlapping recordings in CS2_3 and CS2_25, check with CALCE before relying on those days.
Other open datasets and pack data
The same registry already knows four more open cycling datasets, not yet imported: the Severson et al. 2019 fast-charging set (124 A123 LFP cells, 1.1 Ah), the Oxford Battery Degradation Dataset 1 (8 Kokam pouch cells, 0.74 Ah, drive-cycle ageing), the NASA Prognostics Center of Excellence battery sets (18650 cells with impedance sweeps), and the Battery Archive, an aggregator of several laboratories.
Pack-level public data is rarer. Two candidates are under review: a year of real-world electric-vehicle driving and charging data at pack level, published by Stanford University on Mendeley Data in 2023 under CC BY-NC 3.0, and a transporter-drone battery module cycled to end of life by the Singapore Institute of Technology (Journal of Energy Storage 66, 2023). Neither is imported yet, and the pack capacities still have to be confirmed against the original sources.