NewYour coding agent can read the release notes before it upgrades.Set up the MCP server →
PyPI · #4584 most downloaded on PyPI
A Python package for extracting, transforming and loading tables of data.
Last release 7 days ago
29 Sep 2026
Release timing varies
gaps range from 8 days to 13 months
Most releases are documented
notes for 43 of the last 60 stable releases
Nothing withdrawn
no release was ever pulled
15 years old
103 releases · first in 2011
Add substring convenience functions by @akashmalbari in #722
Full Changelog: v1.7.27...v1.7.28
One column per quarter.
v1.7.28 Latest
Latest
Compare
Preserve missing-cell positions when displaying short rows with see(), including duplicate and numeric-looking field names. By rastagan-git, 726.
Expand the configuration reference with inspection, sorting and error handling defaults, argument precedence and executable examples. By rastagan-git, 725, closes 390.
Return row-oriented data from fromxlsx() for single-cell, whole-row and whole-column ranges, in both normal and read-only mode. Reject ranges containing row zero rather than treating zero as an unspecified bound. By rastagan-git, 724.
Add standardize() to scale numeric fields to a mean of 0 and a standard deviation of 1. Based on the contribution by CharveeSaraiya in 690. By akashmalbari, 730.
Add callable support to setheader by @akashmalbari in #721
Full Changelog: v1.7.26...v1.7.27
Preserve integer values in fromdataframe() when pandas tables contain both integer and floating-point columns, avoiding precision loss for large integers. Index inclusion and empty-table behavior are unchanged. By rastagan-git, 720.
Add callable support to setheader By akashmalbari, 721.
docs: clarify valuecounter field arguments by @codeofwxz in #714
Full Changelog: v1.7.25...v1.7.26
Support SQLAlchemy 2 database operations By umd0730, 719.
Preserve tuple values when formatting DuplicateKeyError and FieldSelectionError messages, including compound duplicate keys and invalid tuple field selectors. See 641. By umd0730, 718.
Preserve discovered columns and values with sample=1 in fromdicts() and JSON array input. Empty samples no longer raise RuntimeError. By umd0730, 717.
Read empty JSON lines files as empty tables instead of raising RuntimeError when discovering the header. By umd0730, 716.
Correct csvkit's PyPI link in related work By codeofwxz, 715.
Clarify that valuecounter() accepts multiple fields as positional arguments, with examples of mixed names/indexes and tuple unpacking. See 641. By be-student, 714.
Raise ArgumentError for invalid recast() fields, including under Python optimization, instead of relying on assertions. See 297. By umd0730, 712.
docs: demonstrate row field-name and index access in convert. By be-student, 711.
feat: add truncate argument to todb function by @ChrisJr404 in #707
Full Changelog: v1.7.24...v1.7.25
docs: demonstrate field-name and index access in row-aware conversions, including column names containing spaces. By be-student, 671.
chore: improve CI/CD workflows, update documentation By juarezr, 709.
feat: add truncate argument to todb function By ChrisJr404, 669.
Fix avro decimal precision and scale inferred from Decimal values by @gaoflow in #706
Full Changelog: v1.7.23...v1.7.24
fix: Fix avro decimal precision and scale inferred from Decimal values By gaoflow, 706.
Fix cache/complement/index/skip attributes shadowing Table methods by @gaoflow in #705
Full Changelog: v1.7.22...v1.7.23
fix: Fix cache/complement/index/skip attributes shadowing Table methods By gaoflow, 705.
Fix header instance attribute shadowing Table.header() across views by @gaoflow in #704
Full Changelog: v1.7.21...v1.7.22
fix: Fix header instance attribute shadowing Table.header across views By gaoflow, 704.
Fix filldown RuntimeError on header-only tables by @sarathfrancis90 in #698
Full Changelog: v1.7.20...v1.7.21
fix: Fix filldown RuntimeError on header-only tables By sarathfrancis90, 698.
fix: Fix DictsView.dicts instance attr shadowing Table.dicts method By gaoflow, 697.
fix: treat None cells as non-matching in capture by @santhreal in #701
Full Changelog: v1.7.19...v1.7.20
Fix filldown RuntimeError on header-only tables By sarathfrancis90, 698.
feat: modernize python dependencies in CI By juarezr, 702.
## Whats Changed
Fix filldown RuntimeError on header-only tables By sarathfrancis90, 698.
feat: modernize python dependencies in CI By juarezr, 702.
Add drop="if_exists" support to todb() by @akashmalbari in #695
Full Changelog: v1.7.18...v1.7.19
## Whats Changed
Add drop=if_exists support to todb By akashmalbari, 695.
Fix tojson() output for stdin-backed CSV input by @akashmalbari in #693
ownsb to fromdb function by @juarezr in #694Full Changelog: v1.7.17...v1.7.18
Fix tojson() output for stdin-backed CSV input By akashmalbari, 693.
feat: add argument ownsb to fromdb function By juarezr, 694.
ci: added readthedocs settings file by @juarezr in #677
Full Changelog: v1.7.16...v1.7.17
ci: added readthedocs settings file By juarezr, 677.
build and publish a wheel By dimbleby, 679.
Added ability to infer JSON column type into db_create.py By muhammadbadar1998, 682.
fix: mitigate code injection related in #672 By juarezr, 681.
Add drop='if_exists' support to petl.io.db.todb. 666.
feat(CI): add python 3.13 to CI testing on github actions by @juarezr in #675
Full Changelog: v1.7.15...v1.7.16
CI: added jobs for testing petl with python 3.13 and macos-13 on Intel platform By juarezr, 675.
CI: workaround for actions/setup-python as Github removed support for python 3.7 By juarezr, 675.
Fix: Joining tables with uneven rows gives wrong result. By MichalKarol.
Resolve DeprecationWarning: Seeding based on hashing by @bmos in #656
Add unit tests for randomtable, dummytable, and their supporting functions and classes. By bmos, 657.
Fix: DeprecationWarning: Seeding based on hashing is deprecated since Python 3.9 and will be removed in a subsequent version. By bmos, 657.
Enhancement: Fix other functions to conform with PEP 479 By augustomen, 645.
Enhancement: Fix other functions to conform with PEP 479 By augustomen, 645.
CI: fix build as SQLAlchemy 2 is not supported yet By juarezr, 635.
CI: workaround for actions/setup-python#672 as Github removed python 2.7 and 3.6 By juarezr, 649.
CI: Gh actions upgrade By juarezr, 639.
Fix in case a custom protocol was registered in fsspec By timheb, 647.
Fix in case a custom protocol was registered in fsspec By timheb, 647.
Fix: calling functions to*() should output by default to stdout By juarezr, 632.
Fix: calling functions to*() should output by default to stdout By juarezr, 632.
Add python3.11 for the build and testing By juarezr, 635.
Add support for writing to JSONL files By mzaeemz, 524.
Fix generator support in fromdicts to use file cache By arturponinski, 625.
Fix generator support in fromdicts to use file cache By arturponinski, 625.
Fix fromtsv() to pass on header argument By jfitzell, 622.
Fix fromtsv() to pass on header argument By jfitzell, 622.
Feature: Add improved support for working with Google Sheets By juarezr, 615.
Feature: Add improved support for working with Google Sheets By juarezr, 615.
Maintanance: Improve test helpers testing By juarezr, 614.
Fix iterrowslice() to conform with PEP 479 By arturponinski, 575.
Fix iterrowslice() to conform with PEP 479 By arturponinski, 575.
Cleanup and unclutter old and unused files in repository By juarezr, 606.
Add tohtml with css styles test case By juarezr, 609.
Fix sortheader() to not overwrite data for duplicate column names By arturponinski, 392.
Add NotImplementedError to IterContainer's __iter__ By arturponinski, 483.
Add casting of headers to strings in toxlsx and appendxlsx By arturponinski, 530.
Fix sorting of rows with different length By arturponinski, 385.
New pull request template. No python changes. By juarezr, 594.
New pull request template. No python changes. By juarezr, 594.
Fix convertall does not work when table header has non-string elements By dnicolodi, 579.
Fix convertall does not work when table header has non-string elements By dnicolodi, 579.
Fix todataframe() to do not iterate the table multiple times By dnicolodi, 578.
Fix broken aggregate when supplying single key By MalayGoel, 552.
Migrated to pytest By arturponinski, 584.
Testing python 3.10 on Github Actions. No python changes. By juarezr, 591.
codacity: upgrade to latest/main github action version. No python changes. By juarezr, 585.
Publish releases to PyPI with Github Actions. No python changes. By juarezr, 593.
Added Decimal to numeric types By blas, 573.
Added Decimal to numeric types By blas, 573.
Add support for ignore_workbook_corruption parameter in xls By arturponinski, 572.
Add support for generators in the petl.fromdicts By arturponinski, 570.
Add function to support fromdb, todb, appenddb via clickhouse_driver By superjcd, 566.
Fix fromdicts(...).header() raising TypeError By romainernandez, 555.
Use python 3.6 instead of 2.7 for deploy on travis-ci. No python changes. By juarezr, 550.
Use python 3.6 instead of 2.7 for deploy on travis-ci. No python changes. By juarezr, 550.
Fixed SQLAlchemy 1.4 removed the Engine.contextual_connect method By juarezr, 545.
Fixed SQLAlchemy 1.4 removed the Engine.contextual_connect method By juarezr, 545.
How to use convert with custom function and reference row By javidy, 542.
Allow aggregation over the entire table (without a key) By bmaggard, 541.
Allow aggregation over the entire table (without a key) By bmaggard, 541.
Allow specifying output field name for simple aggregation By bmaggard, 370.
Bumped version of package dependency on lxml from 4.4.0 to 4.6.2 By juarezr, 536.
Fixing conda packaging failures. By juarezr, 534.
Fixing conda packaging failures. By juarezr, 534.
Added toxml() as convenience wrapper over totext(). By juarezr, 529.
Added toxml() as convenience wrapper over totext(). By juarezr, 529.
Document behavior of multi-field convert-with-row. By chrullrich, 532.
Allow user defined sources from fsspec for remote I/O. By juarezr, 533.
Allow using a custom/restricted xml parser in fromxml(). By juarezr, 527.
Allow using a custom/restricted xml parser in fromxml(). By juarezr, 527.
Reduced memory footprint for JSONL files, huge improvement. By fahadsiddiqui, 522.
Reduced memory footprint for JSONL files, huge improvement. By fahadsiddiqui, 522.
Added python version 3.8 and 3.9 to tox.ini for using in newer distros. By juarezr, 517.
Added python version 3.8 and 3.9 to tox.ini for using in newer distros. By juarezr, 517.
Fixed compatibility with python3.8 in petl.timings.clock(). By juarezr, 484.
Added json lines support in fromjson(). By fahadsiddiqui, 521.
Fixed fromxlsx() with read_only crashes. By juarezr, 514.
Fixed fromxlsx() with read_only crashes. By juarezr, 514.
Fixed exception when writing to S3 with fsspec auto_mkdir=True. By juarezr, 512.
Fixed exception when writing to S3 with fsspec auto_mkdir=True. By juarezr, 512.
Allowed reading and writing Excel files in remote sources. By juarezr, 506.
Allowed reading and writing Excel files in remote sources. By juarezr, 506.
Allow toxlsx() to add or replace a worksheet. By churlrich, 502.
Improved avro: improve message on schema or data mismatch. By juarezr, 507.
Fixed build for failed test case. By juarezr, 508.
Fixed boolean type detection in toavro(). By juarezr, 504.
Fixed boolean type detection in toavro(). By juarezr, 504.
Fix unavoidable warning if fsspec is installed but some optional package is not installed. By juarezr, 503.
Added extras_require for the petl pip package. By juarezr, 501.
Added extras_require for the petl pip package. By juarezr, 501.
Fix unavoidable warning if fsspec is not installed. By juarezr, 500.
Added class petl.io.remotes.RemoteSource using package fsspec for reading and writing files in remote servers by using the protocol in the url for sel
Added class petl.io.remotes.RemoteSource using package fsspec for reading and writing files in remote servers by using the protocol in the url for selecting the implementation. By juarezr, 494.
Removed classes petl.io.source.s3.S3Source as it's handled by fsspec By juarezr, 494.
Removed classes petl.io.codec.xz.XZCodec, petl.io.codec.xz.LZ4Codec and petl.io.codec.zstd.ZstandardCodec as it's handled by fsspec. By juarezr, 494.
Fix bug in connection to a JDBC database using jaydebeapi. By miguelosana, 497.
Added functions petl.io.sources.register_reader and petl.io.sources.register_writer for registering custom source helpers for hanlding I/O from remote
Added functions petl.io.sources.register_reader and petl.io.sources.register_writer for registering custom source helpers for hanlding I/O from remote protocols. By juarezr, 491.
Added function petl.io.sources.register_codec for registering custom helpers for compressing and decompressing files with other algorithms. By juarezr, 491.
Added classes petl.io.codec.xz.XZCodec, petl.io.codec.xz.LZ4Codec and petl.io.codec.zstd.ZstandardCodec for compressing files with XZ and the "state of art" LZ4 and Zstandard algorithms. By juarezr, 491.
Added classes petl.io.source.s3.S3Source and petl.io.source.smb.SMBSource reading and writing files to remote servers using int url the protocols s3:// and smb://. By juarezr, 491.
Added functions petl.io.avro.fromavro, petl.io.avro.toavro, and petl.io.avro.appendavro for reading and writing to Apache Avro files. Avro generally i
Added functions petl.io.avro.fromavro, petl.io.avro.toavro, and petl.io.avro.appendavro for reading and writing to Apache Avro <https://avro.apache.org/docs/current/spec.html> files. Avro generally is faster and safer than text formats like Json, XML or CSV. By juarezr, 490.
.. note:: The parameters to the petl.io.xlsx.fromxlsx function have changed in this release. The parameters row_offset and col_offset are no longer su
Note
The parameters to the petl.io.xlsx.fromxlsx function have changed in this release. The parameters row_offset and col_offset are no longer supported. Please use min_row, min_col, max_row and max_col instead.
A new configuration option failonerror has been added to the petl.config module. This option affects various transformation functions including petl.transform.conversions.convert, petl.transform.maps.fieldmap, petl.transform.maps.rowmap and petl.transform.maps.rowmapmany. The option can have values True (raise any exceptions encountered during conversion), False (silently use a given errorvalue if any exceptions arise during conversion) or "inline" (use any exceptions as the output value). The default value is False which maintains compatibility with previous releases. By bmaggard, 460, 406, 365.
A new function petl.util.timing.log_progress has been added, which behaves in a similar way to petl.util.timing.progress but writes to a Python logger. By dusktreader, 408, 407.
Added new function petl.transform.regex.splitdown for splitting a value into multiple rows. By John-Dennert, 430, 386.
Added new function petl.transform.basics.addfields to add multiple new fields at a time. By mjumbewu, 417.
Pass through keyword arguments to xlrd.open_workbook. By gjunqueira, 470, 473.
Added new function petl.io.xlsx.appendxlsx. By victormpa and alimanfoo, 424, 475.
Fixes for upstream API changes in openpyxl and intervaltree modules. N.B., the arguments to petl.io.xlsx.fromxlsx have changed for specifying row and column offsets to match openpyxl. (472 - alimanfoo).
Exposed read_only argument in petl.io.xlsx.fromxlsx and set default to False to prevent truncation of files created by LibreOffice. By mbelmadani, 457.
Added support for reading from remote sources with gzip or bz2 compression (463 - H-Max).
The function petl.transform.dedup.distinct has been fixed for the case where None values appear in the table. By bmaggard, 414, 412.
Changed keyed sorts so that comparisons are only by keys. By DiegoEPaez, 466.
Documentation improvements by gamesbook (458).
Nothing published for this version
Fix deprecation warnings from openpyxl (447, 445 - scardine; 449 - alimanfoo).
Please note that this version drops support for Python 2.6 (443, 444 - hugovk).
Function petl.transform.basics.addrownumbers now supports a "field" argument to allow specifying the name of the new field to be added (366, 367 - thatneat).
Fix to petl.io.xlsx.fromxslx to ensure that the underlying workbook is closed after iteration is complete (387 - mattkatz).
Resolve compatibility issues with newer versions of openpyxl (393, 394 - henryrizzi).
Fix deprecation warnings from openpyxl (447, 445 - scardine; 449 - alimanfoo).
Changed exceptions to use standard exception classes instead of ArgumentError (396 - bmaggard).
Add support for non-numeric quoting in CSV files (377, 378 - vilos).
Fix bug in handling of mode in MemorySource (403 - bmaggard).
Added a get() method to the Record class (401, 402 - dusktreader).
Added ability to make constraints optional, i.e., support validation on optional fields (399, 400 - dusktreader).
Added support for CSV files without a header row (421 - LupusUmbrae).
Documentation fixes (379 - DeanWay; 381 - PabloCastellano).
Nothing published for this version
Fixed petl.transform.reshape.melt to work with non-string key argument (#209 _).
Fixed petl.transform.reshape.melt to work with non-string key argument (#209).
Added example to docstring of petl.transform.dedup.conflicts to illustrate how to analyse the source of conflicts when rows are merged from multiple tables (#256).
Added functions for working with bcolz ctables, see petl.io.bcolz (#310).
Added petl.io.base.fromcolumns (#316).
Added petl.transform.reductions.groupselectlast. (#319).
Added example in docstring for petl.io.sources.MemorySource (#323).
Added function petl.transform.basics.stack as a simpler alternative to petl.transform.basics.cat. Also behaviour of petl.transform.basics.cat has changed for tables where the header row contains duplicate fields. This was part of addressing a bug in petl.transform.basics.addfield for tables where the header contains duplicate fields (#327).
Change in behaviour of petl.io.json.fromdicts to preserve ordering of keys if ordered dicts are used. Also added petl.transform.headers.sortheader to deal with unordered cases (#332).
Added keyword strict to functions in the petl.transform.setops module to enable users to enforce strict set-like behaviour if desired (#333).
Added epilogue argument to petl.util.vis.display to enable further customisation of content of table display in Jupyter notebooks (#337).
Added petl.transform.selects.biselect as a convenience for obtaining two tables, one with rows matching a condition, the other with rows not matching the condition (#339).
Changed petl.io.json.fromdicts to avoid making two passes through the data (#341).
Changed petl.transform.basics.addfieldusingcontext to enable running calculations (#343).
Fix behaviour of join functions when tables have no non-key fields (#345).
Fix incorrect default value for 'errors' argument when using codec module (#347).
Added some documentation on how to write extension classes, see intro (#349).
Fix issue with unicode field names (#350).
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Nothing published for this version
Your coding agent can read these notes before it upgrades. Set up the MCP server →