diff --git a/modelling/doc/index.rst b/modelling/doc/index.rst index 5d6a8aee8e982c14aa10365072775f09bc7926c8..ffdaebf9bbede2597c9ccf717eb7c4834c36b2df 100644 --- a/modelling/doc/index.rst +++ b/modelling/doc/index.rst @@ -70,6 +70,11 @@ Modelling Pipeline - Side chains which contain all atoms of the parent amino acid, e.g. phosphoserine are copied as a whole with the modifications stripped off. + Residues with missing backbone atoms and D-peptides are generally skipped and + treated as gaps. Missing Cbeta atoms in backbone are ok and reconstructed. + If all residues are skipped (e.g. Calpha traces), we report an error and + return an empty model. + Residue numbers are set such that missing residue in gaps are honoured and subsequent loop modelling can insert new residues without having to renumber. **The numbering of residues starts for every chain with the value 1**. diff --git a/modelling/pymod/_pipeline.py b/modelling/pymod/_pipeline.py index 3cc3ed289cb410075f2f152da0ade3c55fff3fda..9fe9f49bbda5c4083226401b894c2fddf3bb2f00 100644 --- a/modelling/pymod/_pipeline.py +++ b/modelling/pymod/_pipeline.py @@ -188,9 +188,16 @@ def CheckFinalModel(mhandle): :type mhandle: :class:`ModellingHandle` ''' # report incomplete models + for chain in mhandle.model.chains: + if chain.residue_count < 3: + ost.LogWarning("Chain %s of returned model contains only %d "\ + "residues! This typically indicates that the "\ + "template is mostly a Calpha trace or contains "\ + "too many D-peptides."\ + % (chain.name, chain.residue_count)) if len(mhandle.gaps) > 0: - ost.LogWarning("Failed to close %d gap(s). Returning incomplete model!" % \ - len(mhandle.gaps)) + ost.LogWarning("Failed to close %d gap(s). Returning incomplete model!"\ + % len(mhandle.gaps)) else: # check sequences for chain, seq in zip(mhandle.model.chains, mhandle.seqres): @@ -263,7 +270,12 @@ def BuildFromRawModel(mhandle): :return: Delivers the model as an |ost_s| entity. :rtype: :class:`Entity <ost.mol.EntityHandle>` ''' - ost.LogInfo("Starting modelling based on a raw model.") + # ignore empty models + if mhandle.model.residue_count == 0: + ost.LogError("Cannot perform modelling with an empty raw model.") + return mhandle.model + else: + ost.LogInfo("Starting modelling based on a raw model.") # a bit of setup fragment_db = loop.LoadFragDB() diff --git a/modelling/src/model.cc b/modelling/src/model.cc index a90685cc3823b5a88a3751abe5e11932a86c783d..3b8a13d4753ca0e7c34fb600cbafd58a0c7140e2 100644 --- a/modelling/src/model.cc +++ b/modelling/src/model.cc @@ -600,8 +600,13 @@ void BuildRawChain(const ost::seq::AlignmentHandle& aln, before=dst_res; } - // add trailing gap, if needed. - if (last_num!=res_num) { + // check if we have added anything at all + if (last_num == 0) { + LOG_ERROR("No residues added for chain " << chain_name << "! " + "This typically indicates that the template is a Calpha trace " + "or only contains D-peptides.") + } else if (last_num != res_num) { + // add trailing gap (only if there are residues at all) gap_list.push_back(StructuralGap(before, ResidueHandle(), gap_seq)); } } diff --git a/modelling/tests/CMakeLists.txt b/modelling/tests/CMakeLists.txt index 9118480db8b353105b66b6b03cc8b2e517ae2d1d..6d66dd6a93c64b2e2cd8923abc3ea01f1409bdcb 100644 --- a/modelling/tests/CMakeLists.txt +++ b/modelling/tests/CMakeLists.txt @@ -26,6 +26,8 @@ set(MODELLING_TEST_DATA data/5d52-1_cut.pdb data/5d52-1_cut_A.fasta data/5d52-1_cut_B.fasta + data/CA-3cm91E.fasta + data/CA-3cm91E.pdb data/cbeta.fasta data/cbeta.pdb data/compounds.chemlib @@ -33,6 +35,7 @@ set(MODELLING_TEST_DATA data/gly.pdb data/hetero-punched.pdb data/ins.fasta + data/modelCApartial-5tgl1A.pdb data/neighbor-punched.pdb data/sep.fasta data/sep.pdb diff --git a/modelling/tests/data/CA-3cm91E.fasta b/modelling/tests/data/CA-3cm91E.fasta new file mode 100644 index 0000000000000000000000000000000000000000..94b2817007305f9e40224a9d0ffab253cf0ed7d3 --- /dev/null +++ b/modelling/tests/data/CA-3cm91E.fasta @@ -0,0 +1,6 @@ +>Seqres Secretory component +PRSPTVVKGVAGSSVAVLCPYNRKESKSIKYWCLWEGAQNGRCPLLVDSEGWVKAQYEGRLSLLEEPGNGTF +TVILNQLTSRDAGFYWCLTNGDTLWRTTVEIKII +>3cm9.1.E +PRSPTVVKGVAGSSVAVLCPYNRKESKSIKYWCLWEGAQNGRCPLLVDSEGWVKAQYEGRLSLLEEPGNGTF +TVILNQLTSRDAGFYWCLTNGDTLWRTTVEIKII diff --git a/modelling/tests/data/CA-3cm91E.pdb b/modelling/tests/data/CA-3cm91E.pdb new file mode 100644 index 0000000000000000000000000000000000000000..c1ccd02b0a4975e754b60fbd4f79897368250493 --- /dev/null +++ b/modelling/tests/data/CA-3cm91E.pdb @@ -0,0 +1,108 @@ +ATOM 1853 CA PRO E 1 100.196 75.627 -39.098 1.00 63.23 C +ATOM 1854 CA ARG E 2 98.384 77.035 -42.067 1.00120.44 C +ATOM 1855 CA SER E 3 97.087 80.479 -42.746 1.00 83.71 C +ATOM 1856 CA PRO E 4 96.803 82.986 -45.476 1.00134.50 C +ATOM 1857 CA THR E 5 100.216 83.858 -46.805 1.00 95.95 C +ATOM 1858 CA VAL E 6 99.057 87.278 -47.829 1.00 81.98 C +ATOM 1859 CA VAL E 7 96.004 89.255 -46.930 1.00 38.63 C +ATOM 1860 CA LYS E 8 95.002 92.456 -48.607 1.00 71.47 C +ATOM 1861 CA GLY E 9 92.471 94.934 -47.400 1.00 27.04 C +ATOM 1862 CA VAL E 10 91.770 98.550 -47.831 1.00119.84 C +ATOM 1863 CA ALA E 11 91.574 101.495 -45.463 1.00165.73 C +ATOM 1864 CA GLY E 12 88.862 101.454 -42.803 1.00126.59 C +ATOM 1865 CA SER E 13 87.643 97.941 -43.628 1.00 64.68 C +ATOM 1866 CA SER E 14 87.880 95.059 -41.159 1.00 41.47 C +ATOM 1867 CA VAL E 15 89.769 91.865 -41.756 1.00 92.19 C +ATOM 1868 CA ALA E 16 89.817 88.416 -40.278 1.00 26.82 C +ATOM 1869 CA VAL E 17 92.670 85.967 -40.373 1.00 95.17 C +ATOM 1870 CA LEU E 18 92.213 82.282 -39.701 1.00 47.99 C +ATOM 1871 CA CYS E 19 95.026 79.892 -38.799 1.00 64.99 C +ATOM 1872 CA PRO E 20 94.770 76.122 -38.375 1.00157.50 C +ATOM 1873 CA TYR E 21 96.559 73.884 -35.776 1.00104.19 C +ATOM 1874 CA ASN E 22 96.945 70.339 -34.130 1.00114.35 C +ATOM 1875 CA ARG E 23 96.004 68.495 -30.890 1.00118.92 C +ATOM 1876 CA LYS E 24 98.603 69.600 -28.381 1.00 75.16 C +ATOM 1877 CA GLU E 25 98.017 72.885 -29.992 1.00103.64 C +ATOM 1878 CA SER E 26 94.359 72.926 -29.006 1.00 88.80 C +ATOM 1879 CA LYS E 27 95.386 73.630 -25.426 1.00150.54 C +ATOM 1880 CA SER E 28 98.382 75.877 -26.043 1.00103.15 C +ATOM 1881 CA ILE E 29 98.353 79.655 -26.148 1.00165.80 C +ATOM 1882 CA LYS E 30 97.530 81.262 -29.469 1.00147.77 C +ATOM 1883 CA TYR E 31 99.038 84.518 -30.474 1.00108.16 C +ATOM 1884 CA TRP E 32 99.251 87.156 -33.180 1.00109.30 C +ATOM 1885 CA CYS E 33 102.466 89.156 -33.552 1.00128.35 C +ATOM 1886 CA LEU E 34 104.068 91.737 -35.773 1.00139.81 C +ATOM 1887 CA TRP E 35 107.531 90.962 -37.046 1.00155.42 C +ATOM 1888 CA GLU E 36 110.293 93.311 -35.997 1.00215.03 C +ATOM 1889 CA GLY E 37 113.320 94.008 -38.127 1.00116.30 C +ATOM 1890 CA ALA E 38 116.708 93.530 -36.544 1.00273.64 C +ATOM 1891 CA GLN E 39 119.462 90.998 -36.401 1.00129.56 C +ATOM 1892 CA ASN E 40 117.650 89.799 -33.353 1.00192.43 C +ATOM 1893 CA GLY E 41 114.108 90.969 -33.364 1.00140.96 C +ATOM 1894 CA ARG E 42 111.039 89.707 -31.669 1.00294.56 C +ATOM 1895 CA CYS E 43 107.540 89.770 -32.963 1.00130.73 C +ATOM 1896 CA PRO E 44 105.641 91.853 -30.556 1.00134.93 C +ATOM 1897 CA LEU E 45 102.683 90.074 -29.034 1.00 82.87 C +ATOM 1898 CA LEU E 46 99.772 91.988 -30.478 1.00201.41 C +ATOM 1899 CA VAL E 47 96.987 89.818 -29.016 1.00115.60 C +ATOM 1900 CA ASP E 48 96.966 86.460 -27.250 1.00142.99 C +ATOM 1901 CA SER E 49 94.538 83.728 -26.214 1.00103.39 C +ATOM 1902 CA GLU E 50 95.775 84.336 -22.702 1.00121.01 C +ATOM 1903 CA GLY E 51 93.758 87.464 -22.262 1.00 42.73 C +ATOM 1904 CA TRP E 52 96.458 89.890 -23.248 1.00 56.12 C +ATOM 1905 CA VAL E 53 95.712 92.591 -25.769 1.00 44.48 C +ATOM 1906 CA LYS E 54 98.107 95.299 -26.879 1.00110.61 C +ATOM 1907 CA ALA E 55 97.166 98.912 -26.444 1.00 24.42 C +ATOM 1908 CA GLN E 56 97.081 99.560 -30.140 1.00 95.40 C +ATOM 1909 CA TYR E 57 94.757 96.622 -30.653 1.00193.01 C +ATOM 1910 CA GLU E 58 92.631 96.963 -27.520 1.00100.03 C +ATOM 1911 CA GLY E 59 89.029 97.255 -28.610 1.00 34.61 C +ATOM 1912 CA ARG E 60 90.081 97.240 -32.254 1.00197.00 C +ATOM 1913 CA LEU E 61 90.788 93.534 -32.565 1.00117.70 C +ATOM 1914 CA SER E 62 89.782 90.148 -31.235 1.00 42.96 C +ATOM 1915 CA LEU E 63 91.279 86.664 -31.146 1.00 78.60 C +ATOM 1916 CA LEU E 64 88.988 83.673 -30.899 1.00149.43 C +ATOM 1917 CA GLU E 65 89.948 80.041 -30.690 1.00107.90 C +ATOM 1918 CA GLU E 66 87.730 77.171 -31.659 1.00109.02 C +ATOM 1919 CA PRO E 67 89.443 73.953 -30.848 1.00 76.41 C +ATOM 1920 CA GLY E 68 87.058 71.592 -32.567 1.00 26.76 C +ATOM 1921 CA ASN E 69 87.712 73.263 -35.874 1.00 60.67 C +ATOM 1922 CA GLY E 70 91.363 73.587 -35.093 1.00 58.48 C +ATOM 1923 CA THR E 71 91.349 77.242 -35.882 1.00 73.02 C +ATOM 1924 CA PHE E 72 91.582 80.588 -34.205 1.00 83.08 C +ATOM 1925 CA THR E 73 90.580 83.821 -35.814 1.00110.84 C +ATOM 1926 CA VAL E 74 92.005 87.258 -35.393 1.00 45.60 C +ATOM 1927 CA ILE E 75 89.610 89.985 -36.319 1.00 39.80 C +ATOM 1928 CA LEU E 76 90.954 93.457 -36.785 1.00140.02 C +ATOM 1929 CA ASN E 77 88.917 96.556 -37.480 1.00 99.87 C +ATOM 1930 CA GLN E 78 89.761 100.094 -38.500 1.00 70.76 C +ATOM 1931 CA LEU E 79 92.672 98.999 -40.611 1.00 66.25 C +ATOM 1932 CA THR E 80 95.035 101.897 -41.059 1.00105.54 C +ATOM 1933 CA SER E 81 98.213 102.569 -42.970 1.00 33.75 C +ATOM 1934 CA ARG E 82 100.129 101.465 -39.905 1.00158.44 C +ATOM 1935 CA ASP E 83 98.684 97.978 -40.211 1.00 78.32 C +ATOM 1936 CA ALA E 84 100.479 96.973 -43.382 1.00 34.42 C +ATOM 1937 CA GLY E 85 103.357 94.731 -42.450 1.00 24.83 C +ATOM 1938 CA PHE E 86 104.420 91.223 -41.536 1.00 96.18 C +ATOM 1939 CA TYR E 87 102.685 89.282 -38.827 1.00 82.67 C +ATOM 1940 CA TRP E 88 102.733 85.789 -37.414 1.00 90.00 C +ATOM 1941 CA CYS E 89 100.043 83.588 -35.927 1.00 68.91 C +ATOM 1942 CA LEU E 90 101.439 80.864 -33.778 1.00159.07 C +ATOM 1943 CA THR E 91 100.997 78.563 -30.805 1.00 70.17 C +ATOM 1944 CA ASN E 92 102.920 78.615 -27.507 1.00157.71 C +ATOM 1945 CA GLY E 93 105.907 80.911 -27.177 1.00 34.16 C +ATOM 1946 CA ASP E 94 106.773 83.360 -29.936 1.00 67.01 C +ATOM 1947 CA THR E 95 110.384 82.225 -30.115 1.00112.14 C +ATOM 1948 CA LEU E 96 109.488 78.620 -30.821 1.00 70.63 C +ATOM 1949 CA TRP E 97 108.569 79.626 -34.349 1.00141.75 C +ATOM 1950 CA ARG E 98 105.744 77.153 -34.600 1.00185.54 C +ATOM 1951 CA THR E 99 103.875 79.866 -36.455 1.00126.66 C +ATOM 1952 CA THR E 100 102.906 80.890 -39.930 1.00112.49 C +ATOM 1953 CA VAL E 101 103.937 84.168 -41.457 1.00 36.22 C +ATOM 1954 CA GLU E 102 101.260 86.387 -42.862 1.00 78.91 C +ATOM 1955 CA ILE E 103 101.782 89.519 -44.879 1.00 80.88 C +ATOM 1956 CA LYS E 104 99.102 92.108 -44.566 1.00 82.43 C +ATOM 1957 CA ILE E 105 98.844 94.946 -47.016 1.00 33.94 C +ATOM 1958 CA ILE E 106 96.373 97.661 -46.228 1.00130.48 C +TER 1959 ILE E 106 +END diff --git a/modelling/tests/data/modelCApartial-5tgl1A.pdb b/modelling/tests/data/modelCApartial-5tgl1A.pdb new file mode 100644 index 0000000000000000000000000000000000000000..6f8524d601598633ea4dc452656646e46cf59d6b --- /dev/null +++ b/modelling/tests/data/modelCApartial-5tgl1A.pdb @@ -0,0 +1,20 @@ +ATOM 1 N SER A 144 -19.381 16.755 81.609 1.00 9.56 N +ATOM 2 CA SER A 144 -18.509 17.263 82.707 1.00 11.28 C +ATOM 3 C SER A 144 -17.236 17.865 82.069 1.00 13.66 C +ATOM 4 O SER A 144 -17.099 17.757 80.817 1.00 10.69 O +ATOM 5 CB SER A 144 -18.231 16.093 83.688 1.00 7.43 C +ATOM 6 OG SER A 144 -17.652 16.566 84.900 1.00 10.40 O +ATOM 7 OXT SER A 144 -16.427 18.467 82.808 1.00 0.00 O +ATOM 8 N HIS A 257 -26.481 14.980 87.899 1.00 11.49 N +ATOM 9 CA HIS A 257 -25.321 15.085 86.964 1.00 10.96 C +ATOM 10 C HIS A 257 -25.021 13.659 86.434 1.00 12.37 C +ATOM 11 O HIS A 257 -25.706 12.704 86.894 1.00 13.62 O +ATOM 12 CB HIS A 257 -24.126 15.688 87.741 1.00 11.73 C +ATOM 13 CG HIS A 257 -22.930 15.853 86.892 1.00 21.65 C +ATOM 14 ND1 HIS A 257 -23.011 16.693 85.795 1.00 13.23 N +ATOM 15 CD2 HIS A 257 -21.787 15.147 86.872 1.00 15.49 C +ATOM 16 CE1 HIS A 257 -21.913 16.458 85.129 1.00 15.72 C +ATOM 17 NE2 HIS A 257 -21.115 15.529 85.731 1.00 17.92 N +ATOM 18 OXT HIS A 257 -24.128 13.517 85.570 1.00 0.00 O +TER 19 HIS A 257 +END diff --git a/modelling/tests/test_pipeline.py b/modelling/tests/test_pipeline.py index 13d9053835f33fbeb8c727796463d485090edf2b..8c3f6a8e605e26c1ad7e960c95d25ed2970af114 100644 --- a/modelling/tests/test_pipeline.py +++ b/modelling/tests/test_pipeline.py @@ -314,6 +314,50 @@ class PipelineTests(unittest.TestCase): mhandle = self.getRawModelOligo("data/5d52-1_cut") self.checkFinalModel(mhandle, exp_gaps=2, num_chains=2) + def testBuildModelCalpha(self): + '''Check treatment of CA traces.''' + # setup log + log = _FetchLog() + ost.PushLogSink(log) + ost.PushVerbosityLevel(1) + log.messages['ERROR'] = list() + # setup tpl and aln + tpl = io.LoadPDB('data/CA-3cm91E.pdb') + aln = io.LoadAlignment('data/CA-3cm91E.fasta') + aln.AttachView(1, tpl.CreateFullView()) + # check that we get error and empty model + mhandle = modelling.BuildRawModel(aln) + self.assertEqual(len(log.messages['ERROR']), 1) + self.assertEqual(log.messages['ERROR'][-1], + "No residues added for chain A! This typically "\ + "indicates that the template is a Calpha trace "\ + "or only contains D-peptides.") + self.assertEqual(mhandle.model.residue_count, 0) + # check that we produce an error when trying to build model + final_model = modelling.BuildFromRawModel(mhandle) + self.assertEqual(len(log.messages['ERROR']), 2) + self.assertEqual(log.messages['ERROR'][-1], + "Cannot perform modelling with an empty raw model.") + self.assertEqual(final_model.residue_count, 0) + + def testCheckFinalModelShort(self): + '''Check that we report chains with only 2 residues.''' + # setup log + log = _FetchLog() + ost.PushLogSink(log) + ost.PushVerbosityLevel(1) + # setup raw model + mhandle = self.getMockModel(io.LoadPDB('data/modelCApartial-5tgl1A.pdb')) + # check + log.messages['WARNING'] = list() + modelling.CheckFinalModel(mhandle) + self.assertEqual(len(log.messages['WARNING']), 1) + self.assertEqual(log.messages['WARNING'][-1], + "Chain A of returned model contains only 2 "\ + "residues! This typically indicates that the "\ + "template is mostly a Calpha trace or contains "\ + "too many D-peptides.") + if __name__ == "__main__": from ost import testutils testutils.RunTests()