pidibble 1.3.2__tar.gz → 1.4.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {pidibble-1.3.2 → pidibble-1.4.0}/PKG-INFO +5 -1
- {pidibble-1.3.2 → pidibble-1.4.0}/README.md +4 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/mmcif_parse.py +8 -7
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/pdbparse.py +10 -8
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/pdbrecord.py +74 -1
- {pidibble-1.3.2 → pidibble-1.4.0}/pyproject.toml +1 -1
- {pidibble-1.3.2 → pidibble-1.4.0}/.github/workflows/release.yaml +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/.gitignore +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/.readthedocs.yaml +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/LICENSE +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/MANIFEST.in +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/Makefile +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/make.bat +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/requirements.txt +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/_static/css/custom.css +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/API.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.baseparsers.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.baserecord.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.hex.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.mmcif_parse.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.pdbparse.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.pdbrecord.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.resources.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/api/pidibble.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/conf.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/index.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/installation.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/notes.md +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/docs/source/usage.rst +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/__init__.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/baseparsers.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/baserecord.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/hex.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/resources/__init__.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/resources/mmcif_format.yaml +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/pidibble/resources/pdb_format.yaml +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/__init__.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/conftest.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_hex/my_system.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_hex.py +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/4tvp.cif +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/4tvp.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/4zmj-newresnames.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/4zmj.cif +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/4zmj.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/6m0j.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/8fae.cif +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/G.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/GG.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/test.pdb +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb/test_pdb_format.yaml +0 -0
- {pidibble-1.3.2 → pidibble-1.4.0}/tests/unit/test_rcsb.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: pidibble
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.4.0
|
|
4
4
|
Summary: A complete Protein Data Bank (PDB) file parser
|
|
5
5
|
Project-URL: Source, https://github.com/cameronabrams/pidibble
|
|
6
6
|
Project-URL: Documentation, https://pidibble.readthedocs.io/en/latest/
|
|
@@ -91,6 +91,10 @@ ATOM
|
|
|
91
91
|
```
|
|
92
92
|
|
|
93
93
|
## Release History
|
|
94
|
+
* 1.4.0
|
|
95
|
+
* Introduced `PDBRecordList` and `PDBRecordDict` classes
|
|
96
|
+
* 1.3.3
|
|
97
|
+
* fixed bugs regarding assuming missing records actually present in mmcif parsing
|
|
94
98
|
* 1.3.2
|
|
95
99
|
* implemented `filepath` parameter in `PDBParser()` to make
|
|
96
100
|
reading local files more transparent
|
|
@@ -73,6 +73,10 @@ ATOM
|
|
|
73
73
|
```
|
|
74
74
|
|
|
75
75
|
## Release History
|
|
76
|
+
* 1.4.0
|
|
77
|
+
* Introduced `PDBRecordList` and `PDBRecordDict` classes
|
|
78
|
+
* 1.3.3
|
|
79
|
+
* fixed bugs regarding assuming missing records actually present in mmcif parsing
|
|
76
80
|
* 1.3.2
|
|
77
81
|
* implemented `filepath` parameter in `PDBParser()` to make
|
|
78
82
|
reading local files more transparent
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
"""
|
|
10
10
|
|
|
11
11
|
from collections import UserDict
|
|
12
|
-
from .pdbrecord import PDBRecord
|
|
12
|
+
from .pdbrecord import PDBRecord, PDBRecordDict, PDBRecordList
|
|
13
13
|
from .baserecord import BaseRecord
|
|
14
14
|
import logging
|
|
15
15
|
logger=logging.getLogger(__name__)
|
|
@@ -214,8 +214,9 @@ class MMCIF_Parser:
|
|
|
214
214
|
spawns_on=mapspec.get('spawns_on',None)
|
|
215
215
|
allcaps=mapspec.get('allcaps',[])
|
|
216
216
|
if_dot_replace_with=mapspec.get('if_dot_replace_with',{})
|
|
217
|
+
logger.debug(f'getting cifrec for {mapspec["data_obj"]}')
|
|
217
218
|
cifrec=self.cif_data.getObj(mapspec['data_obj'])
|
|
218
|
-
if not tables:
|
|
219
|
+
if not tables and cifrec is not None:
|
|
219
220
|
for idx in range(len(cifrec)):
|
|
220
221
|
if not use_signal or (cifrec.getValue(sigattr,idx)==sigval):
|
|
221
222
|
if global_maps:
|
|
@@ -334,18 +335,18 @@ class MMCIF_Parser:
|
|
|
334
335
|
|
|
335
336
|
Returns
|
|
336
337
|
-------
|
|
337
|
-
|
|
338
|
-
A dictionary where keys are record types and values are lists of :class:`pdbrecord.
|
|
338
|
+
PDBRecordDict
|
|
339
|
+
A dictionary where keys are record types and values are lists of :class:`pdbrecord.PDBRecord` instances.
|
|
339
340
|
"""
|
|
340
|
-
recdict=
|
|
341
|
+
recdict=PDBRecordDict()
|
|
341
342
|
for rectype,mapspec in self.formats.items():
|
|
342
343
|
idicts=self.gen_dict(mapspec)
|
|
343
344
|
for idict in idicts:
|
|
344
345
|
this_key=idict.get('tmp_label','')
|
|
345
346
|
reckey=rectype if not this_key else f'{rectype}.{this_key}'
|
|
346
347
|
if reckey in recdict:
|
|
347
|
-
if not type(recdict[reckey])==
|
|
348
|
-
recdict[reckey]=[recdict[reckey]]
|
|
348
|
+
if not type(recdict[reckey])==PDBRecordList:
|
|
349
|
+
recdict[reckey]=PDBRecordList([recdict[reckey]])
|
|
349
350
|
idict['key']=reckey
|
|
350
351
|
recdict[reckey].append(PDBRecord(idict))
|
|
351
352
|
else:
|
|
@@ -14,10 +14,11 @@ import yaml
|
|
|
14
14
|
import numpy as np
|
|
15
15
|
from pathlib import Path
|
|
16
16
|
from mmcif.io.IoAdapterCore import IoAdapterCore
|
|
17
|
+
from typing import List, Dict
|
|
17
18
|
from . import resources
|
|
18
19
|
from .baseparsers import ListParsers, ListParser, str2int_sig, safe_float
|
|
19
20
|
from .baserecord import BaseRecordParser
|
|
20
|
-
from .pdbrecord import PDBRecord
|
|
21
|
+
from .pdbrecord import PDBRecord, PDBRecordDict, PDBRecordList
|
|
21
22
|
from .mmcif_parse import MMCIF_Parser
|
|
22
23
|
from pidibble import resources
|
|
23
24
|
logger=logging.getLogger(__name__)
|
|
@@ -35,9 +36,10 @@ class PDBParser:
|
|
|
35
36
|
|
|
36
37
|
Attributes
|
|
37
38
|
----------
|
|
38
|
-
|
|
39
|
-
parsed :
|
|
40
|
-
A dictionary
|
|
39
|
+
|
|
40
|
+
parsed : PDBRecordDict
|
|
41
|
+
A dictionary containing parsed records, where keys are record types and values are :class:`.pdbrecord.PDBRecord` instances or lists of instances.
|
|
42
|
+
This dictionary is populated after parsing the PDB or mmCIF file.
|
|
41
43
|
|
|
42
44
|
mappers : dict
|
|
43
45
|
A dictionary of mappers for parsing different data types, including custom formats and delimiters.
|
|
@@ -75,7 +77,7 @@ class PDBParser:
|
|
|
75
77
|
self.pdb_lines=[]
|
|
76
78
|
self.cif_data={}
|
|
77
79
|
|
|
78
|
-
self.parsed=
|
|
80
|
+
self.parsed=PDBRecordDict()
|
|
79
81
|
self.pdb_format_file=pdb_format_file
|
|
80
82
|
if not os.path.isfile(self.pdb_format_file):
|
|
81
83
|
# if pdb_format_file is not a file in the CWD, assume it is a relative path to the resources directory
|
|
@@ -262,7 +264,7 @@ class PDBParser:
|
|
|
262
264
|
if tok[0]==group_open_record.key:
|
|
263
265
|
groupid=getattr(group_open_record,tok[1])
|
|
264
266
|
setattr(new_record,group_open_record.key.lower(),groupid)
|
|
265
|
-
self.parsed[key]=[new_record]
|
|
267
|
+
self.parsed[key]=PDBRecordList([new_record])
|
|
266
268
|
else:
|
|
267
269
|
# this is either
|
|
268
270
|
# (a) a continuation record of a given key.(determinants)
|
|
@@ -328,7 +330,7 @@ class PDBParser:
|
|
|
328
330
|
rf=p.format
|
|
329
331
|
if 'embedded_records' in rf:
|
|
330
332
|
new_parsed_records.update(p.parse_embedded(self.pdb_format_dict['record_formats'],self.mappers))
|
|
331
|
-
elif type(p)==
|
|
333
|
+
elif type(p)==PDBRecordList:
|
|
332
334
|
for q in p:
|
|
333
335
|
rf=q.format
|
|
334
336
|
if 'embedded_records' in rf:
|
|
@@ -361,7 +363,7 @@ class PDBParser:
|
|
|
361
363
|
It updates the :attr:`PDBParser.parsed` dictionary with the new parsed records.
|
|
362
364
|
"""
|
|
363
365
|
for key,p in self.parsed.items():
|
|
364
|
-
if type(p)==
|
|
366
|
+
if type(p)==PDBRecordList:
|
|
365
367
|
continue # don't expect to read a table from a multiple-record entry
|
|
366
368
|
rf=p.format
|
|
367
369
|
if 'tables' in rf:
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
.. moduleauthor: Cameron F. Abrams, <cfa22@drexel.edu>
|
|
8
8
|
|
|
9
9
|
"""
|
|
10
|
-
|
|
10
|
+
from collections import UserList, UserDict
|
|
11
11
|
from .baserecord import BaseRecord, BaseRecordParser
|
|
12
12
|
from .baseparsers import StringParser
|
|
13
13
|
import logging
|
|
@@ -442,6 +442,79 @@ class PDBRecord(BaseRecord):
|
|
|
442
442
|
if not all([x=='' for x in parsedrow.__dict__.values()]):
|
|
443
443
|
self.tables[tname].append(parsedrow)
|
|
444
444
|
|
|
445
|
+
class PDBRecordList(UserList):
|
|
446
|
+
"""
|
|
447
|
+
A class representing a list of PDBRecord instances, inheriting from UserList.
|
|
448
|
+
It provides methods for parsing and handling multiple PDB records.
|
|
449
|
+
"""
|
|
450
|
+
def __init__(self, initlist=None):
|
|
451
|
+
if initlist is not None:
|
|
452
|
+
self._validate_all(initlist)
|
|
453
|
+
super().__init__(initlist or [])
|
|
454
|
+
|
|
455
|
+
def _validate(self, item):
|
|
456
|
+
if not isinstance(item, PDBRecord):
|
|
457
|
+
raise TypeError(f"All items must be instances of PDBRecord, got {type(item)}")
|
|
458
|
+
|
|
459
|
+
def _validate_all(self, iterable):
|
|
460
|
+
for item in iterable:
|
|
461
|
+
self._validate(item)
|
|
462
|
+
|
|
463
|
+
def __setitem__(self, index, item):
|
|
464
|
+
# Support slice assignment
|
|
465
|
+
if isinstance(index, slice):
|
|
466
|
+
self._validate_all(item)
|
|
467
|
+
else:
|
|
468
|
+
self._validate(item)
|
|
469
|
+
super().__setitem__(index, item)
|
|
470
|
+
|
|
471
|
+
def append(self, item):
|
|
472
|
+
self._validate(item)
|
|
473
|
+
super().append(item)
|
|
474
|
+
|
|
475
|
+
def insert(self, index, item):
|
|
476
|
+
self._validate(item)
|
|
477
|
+
super().insert(index, item)
|
|
478
|
+
|
|
479
|
+
def extend(self, other):
|
|
480
|
+
self._validate_all(other)
|
|
481
|
+
super().extend(other)
|
|
482
|
+
|
|
483
|
+
def __add__(self, other):
|
|
484
|
+
self._validate_all(other)
|
|
485
|
+
return AList(super().__add__(other))
|
|
486
|
+
|
|
487
|
+
def __iadd__(self, other):
|
|
488
|
+
self._validate_all(other)
|
|
489
|
+
return super().__iadd__(other)
|
|
490
|
+
|
|
491
|
+
class PDBRecordDict(UserDict):
|
|
492
|
+
"""
|
|
493
|
+
A class representing a dictionary of PDBRecord or PDBRecordList instances, inheriting from UserDict.
|
|
494
|
+
It provides methods for parsing and handling multiple PDB records stored in a dictionary.
|
|
495
|
+
"""
|
|
496
|
+
def __init__(self, *args, **kwargs):
|
|
497
|
+
super().__init__()
|
|
498
|
+
self.update(*args, **kwargs)
|
|
499
|
+
|
|
500
|
+
def _validate(self, value):
|
|
501
|
+
if not isinstance(value, (PDBRecord, PDBRecordList)):
|
|
502
|
+
raise TypeError(f"Values must be PDBRecord or PDBRecordList, got {type(value)}")
|
|
503
|
+
|
|
504
|
+
def __setitem__(self, key, value):
|
|
505
|
+
self._validate(value)
|
|
506
|
+
super().__setitem__(key, value)
|
|
507
|
+
|
|
508
|
+
def update(self, *args, **kwargs):
|
|
509
|
+
other = dict(*args, **kwargs)
|
|
510
|
+
for key, value in other.items():
|
|
511
|
+
self[key] = value # Triggers __setitem__
|
|
512
|
+
|
|
513
|
+
def setdefault(self, key, default=None):
|
|
514
|
+
if key not in self:
|
|
515
|
+
self[key] = default # Triggers __setitem__
|
|
516
|
+
return self[key]
|
|
517
|
+
|
|
445
518
|
def header_check(record,headers,parse,hold=[]):
|
|
446
519
|
"""
|
|
447
520
|
Check if a record is a header line and parse it accordingly.
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|