Skip to content

Commit bd54520

Browse files
committed
* Make sort_order private in SamBuilder to avoid changes/inconsistency
with header * Update poetry environment for newer python * Insist sort_order is a SamOrder, elminate None option * Allow writing with unknown sort order
1 parent dc4785b commit bd54520

File tree

4 files changed

+59
-22
lines changed

4 files changed

+59
-22
lines changed

fgpyo/sam/builder.py

Lines changed: 12 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ def __init__(
106106
rg: Optional[Dict[str, str]] = None,
107107
extra_header: Optional[Dict[str, Any]] = None,
108108
seed: int = 42,
109-
sort_order: Optional[SamOrder] = SamOrder.Coordinate,
109+
sort_order: SamOrder = SamOrder.Coordinate,
110110
) -> None:
111111
"""Initializes a new SamBuilder for generating alignment records and SAM/BAM files.
112112
@@ -119,21 +119,17 @@ def __init__(
119119
extra_header: a dictionary of extra values to add to the header, None otherwise. See
120120
`::class::~pysam.AlignmentHeader` for more details.
121121
seed: a seed value for random number/string generation
122-
sort_order: optional sort order, if `None` reads will be output in the same order as
123-
they were appended.
122+
sort_order: Order to sort records when writing to file, or output of to_sorted_list()
124123
"""
125124

126125
self.r1_len: int = r1_len if r1_len is not None else self.DEFAULT_R1_LENGTH
127126
self.r2_len: int = r2_len if r2_len is not None else self.DEFAULT_R2_LENGTH
128127
self.base_quality: int = base_quality
129128
self.mapping_quality: int = mapping_quality
130129

131-
sort_order = SamOrder.Unsorted if sort_order is None else sort_order
132-
assert sort_order in [SamOrder.Coordinate, SamOrder.QueryName, SamOrder.Unsorted], (
133-
"`sort_order` for `SamBuilder` must be one of `Coordinate` `QueryName` or `Unsorted`."
134-
+ f" Found {sort_order}"
135-
)
136-
self.sort_order: SamOrder = sort_order
130+
if not isinstance(sort_order, SamOrder):
131+
raise ValueError(f"sort_order must be a SamOrder, got {type(sort_order)}")
132+
self._sort_order = sort_order
137133

138134
self._header: Dict[str, Any] = {
139135
"HD": {"VN": "1.5", "SO": sort_order.value},
@@ -580,7 +576,7 @@ def to_path(
580576

581577
with NamedTemporaryFile(suffix=".bam", delete=True) as fp:
582578
file_handle: IO
583-
if self.sort_order is SamOrder.Unsorted:
579+
if self._sort_order in {SamOrder.Unsorted, SamOrder.Unknown}:
584580
file_handle = path.open("w")
585581
else:
586582
file_handle = fp.file
@@ -592,18 +588,17 @@ def to_path(
592588
if pred(rec):
593589
writer.write(rec)
594590

595-
default_samtools_opt_list = ["-o", str(path), fp.name]
591+
samtools_sort_args = ["-o", str(path), fp.name]
596592

597593
file_handle.close()
598-
if self.sort_order == SamOrder.QueryName:
594+
if self._sort_order == SamOrder.QueryName:
599595
# Ignore type hints for now until we have wrappers to use here.
600-
pysam.sort(*(["-n"] + default_samtools_opt_list)) # type: ignore
601-
elif self.sort_order == SamOrder.Coordinate:
596+
pysam.sort("-n", *samtools_sort_args) # type: ignore
597+
elif self._sort_order == SamOrder.Coordinate:
602598
# Ignore type hints for now until we have wrappers to use here.
603-
pysam.sort(*default_samtools_opt_list) # type: ignore
604599
if index:
605-
# Ignore type hints for now until we have wrappers to use here.
606-
pysam.index(str(path)) # type: ignore
600+
samtools_sort_args.insert(0, "--write-index")
601+
pysam.sort(*samtools_sort_args) # type: ignore
607602

608603
return path
609604

fgpyo/sam/tests/test_builder.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -272,9 +272,9 @@ def make_sort_order_builder(tmp_path: Path, sort_order: SamOrder) -> Path:
272272
(SamOrder.Coordinate, ["test2", "test3", "test4", "test1"]),
273273
(SamOrder.QueryName, ["test1", "test2", "test3", "test4"]),
274274
(SamOrder.Unsorted, ["test3", "test2", "test1", "test4"]),
275-
(None, ["test3", "test2", "test1", "test4"]),
275+
(SamOrder.Unknown, ["test3", "test2", "test1", "test4"]),
276276
],
277-
ids=["Coordinate sorting", "Query name sorting", "Unsorted output", "Unsorted output - None"],
277+
ids=["Coordinate sorting", "Query name sorting", "Unsorted output", "Unknown sorting"],
278278
)
279279
def test_sort_types(
280280
tmp_path: Path, sort_order: Optional[SamOrder], expected_name_order: List[str]

poetry.lock

Lines changed: 40 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pyproject.toml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,9 +37,13 @@ pysam = ">=0.22.0"
3737
docs = ["sphinx", "sphinx_rtd_theme"]
3838

3939
[tool.poetry.dev-dependencies]
40+
setuptools = ">=68.0.0"
4041
pytest = ">=5.4.2"
4142
mypy = ">=0.770"
42-
flake8 = ">=3.8.1"
43+
flake8 = [
44+
{ version = ">=3.8.1", python = "<3.12.0" },
45+
{ version = ">=6.1.0", python = ">=3.12.0" },
46+
]
4347
black = ">=19.10b0"
4448
pytest-cov = ">=2.8.1"
4549
isort = ">=5.10.1"

0 commit comments

Comments
 (0)