1   
  2   
  3   
  4   
  5   
  6   
  7   
  8   
  9   
 10   
 11   
 12   
 13   
 14   
 15   
 16   
 17   
 18   
 19   
 20   
 21   
 22   
 23  """PCS-based system tests.""" 
 24   
 25   
 26   
 27  from os import sep 
 28  from re import search 
 29  from tempfile import mkdtemp, mktemp 
 30   
 31   
 32  from data_store import Relax_data_store; ds = Relax_data_store() 
 33  from pipe_control.mol_res_spin import count_spins, spin_loop 
 34  from status import Status; status = Status() 
 35  from test_suite.system_tests.base_classes import SystemTestCase 
 36   
 37   
 38 -class Pcs(SystemTestCase): 
  39      """Class for testing PCS operations.""" 
 40   
 42          """Test the operation of the pcs.corr_plot user function.""" 
 43   
 44           
 45          self.interpreter.pipe.create('orig', 'N-state') 
 46   
 47           
 48          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
 49   
 50           
 51          self.interpreter.sequence.read(file='pcs.txt', dir=dir, spin_name_col=1) 
 52          self.interpreter.sequence.display() 
 53   
 54           
 55          self.interpreter.pcs.read(align_id='tb', file='pcs.txt', dir=dir, spin_name_col=1, data_col=2) 
 56          self.interpreter.sequence.display() 
 57   
 58           
 59          for spin in spin_loop(): 
 60              if hasattr(spin, 'pcs'): 
 61                  if not hasattr(spin, 'pcs_bc'): 
 62                      spin.pcs_bc = {} 
 63                  spin.pcs_bc['tb'] = spin.pcs['tb'] 
 64                  if spin.pcs_bc['tb'] != None: 
 65                      spin.pcs_bc['tb'] += 1.0 
 66   
 67           
 68          ds.tmpfile = mktemp() 
 69          self.interpreter.pcs.corr_plot(format='grace', title='Test', subtitle='Test2', file=ds.tmpfile, dir=None, force=True) 
 70   
 71           
 72          real_contents = [ 
 73              "@version 50121", 
 74              "@page size 842, 595", 
 75              "@with g0", 
 76              "@    world 0.0, 0.0, 2.0, 2.0", 
 77              "@    view 0.15, 0.15, 1.28, 0.85", 
 78              "@    title \"Test\"", 
 79              "@    subtitle \"Test2\"", 
 80              "@    xaxis  label \"Back-calculated PCS (ppm)\"", 
 81              "@    xaxis  label char size 1.00", 
 82              "@    xaxis  tick major 1", 
 83              "@    xaxis  tick major size 0.50", 
 84              "@    xaxis  tick major linewidth 0.5", 
 85              "@    xaxis  tick minor ticks 9", 
 86              "@    xaxis  tick minor linewidth 0.5", 
 87              "@    xaxis  tick minor size 0.25", 
 88              "@    xaxis  ticklabel char size 0.70", 
 89              "@    yaxis  label \"Measured PCS (ppm)\"", 
 90              "@    yaxis  label char size 1.00", 
 91              "@    yaxis  tick major 1", 
 92              "@    yaxis  tick major size 0.50", 
 93              "@    yaxis  tick major linewidth 0.5", 
 94              "@    yaxis  tick minor ticks 9", 
 95              "@    yaxis  tick minor linewidth 0.5", 
 96              "@    yaxis  tick minor size 0.25", 
 97              "@    yaxis  ticklabel char size 0.70", 
 98              "@    legend on", 
 99              "@    legend 1, 0.5", 
100              "@    legend box fill pattern 1", 
101              "@    legend char size 1.0", 
102              "@    frame linewidth 0.5", 
103              "@    s0 symbol 1", 
104              "@    s0 symbol size 0.45", 
105              "@    s0 symbol linewidth 0.5", 
106              "@    s0 errorbar size 0.5", 
107              "@    s0 errorbar linewidth 0.5", 
108              "@    s0 errorbar riser linewidth 0.5", 
109              "@    s0 line linestyle 2", 
110              "@    s1 symbol 2", 
111              "@    s1 symbol size 0.45", 
112              "@    s1 symbol linewidth 0.5", 
113              "@    s1 errorbar size 0.5", 
114              "@    s1 errorbar linewidth 0.5", 
115              "@    s1 errorbar riser linewidth 0.5", 
116              "@    s1 line linestyle 0", 
117              "@    s1 legend \"tb (None)\"", 
118              "@target G0.S0", 
119              "@type xy", 
120              "          -100.000000000000000           -100.000000000000000    \"0\"", 
121              "           100.000000000000000            100.000000000000000    \"0\"", 
122              "&", 
123              "@target G0.S1", 
124              "@type xy", 
125              "             1.004000000000000              0.004000000000000    \"@C1\"", 
126              "             1.008000000000000              0.008000000000000    \"@C2\"", 
127              "             1.021000000000000              0.021000000000000    \"@C3\"", 
128              "             1.029000000000000              0.029000000000000    \"@C4\"", 
129              "             1.016000000000000              0.016000000000000    \"@C5\"", 
130              "             1.010000000000000              0.010000000000000    \"@C6\"", 
131              "             1.008000000000000              0.008000000000000    \"@H1\"", 
132              "             1.003000000000000              0.003000000000000    \"@H2\"", 
133              "             1.006000000000000              0.006000000000000    \"@H3\"", 
134              "             1.003000000000000              0.003000000000000    \"@H4\"", 
135              "             1.007000000000000              0.007000000000000    \"@H5\"", 
136              "             1.005000000000000              0.005000000000000    \"@H6\"", 
137              "             1.001000000000000              0.001000000000000    \"@H7\"", 
138              "             1.070000000000000              0.070000000000000    \"@C7\"", 
139              "             1.025000000000000              0.025000000000000    \"@C9\"", 
140              "             1.098000000000000              0.098000000000000    \"@C10\"", 
141              "             1.054000000000000              0.054000000000000    \"@C11\"", 
142              "             1.075000000000000              0.075000000000000    \"@C12\"", 
143              "             1.065000000000000              0.065000000000000    \"@H12\"", 
144              "             1.070000000000000              0.070000000000000    \"@H14\"", 
145              "             1.015000000000000              0.015000000000000    \"@H15\"", 
146              "             1.098000000000000              0.098000000000000    \"@H16\"", 
147              "             1.060000000000000              0.060000000000000    \"@H17\"", 
148              "             1.120000000000000              0.120000000000000    \"@H18\"", 
149              "&" 
150          ] 
151   
152           
153          print("\nChecking the Grace file contents.") 
154          file = open(ds.tmpfile) 
155          lines = file.readlines() 
156          file.close() 
157          self.assertEqual(len(real_contents), len(lines)) 
158          for i in range(len(lines)): 
159              print(lines[i][:-1]) 
160              self.assertEqual(real_contents[i], lines[i][:-1]) 
 161   
162   
164          """Test the creation of Grace plots of PCS data.""" 
165   
166           
167          self.interpreter.pipe.create('CaM N-dom', 'N-state') 
168   
169           
170          self.interpreter.spin.create(spin_name='N', spin_num=1, res_name='Gly', res_num=3) 
171          self.interpreter.spin.create(spin_name='H', spin_num=2, res_name='Gly', res_num=3) 
172          self.interpreter.spin.create(spin_name='N', spin_num=3, res_name='Gly', res_num=4) 
173          self.interpreter.spin.create(spin_name='H', spin_num=4, res_name='Gly', res_num=4) 
174          self.interpreter.sequence.display() 
175   
176           
177          self.interpreter.spin.element(element='N', spin_id='@N') 
178          self.interpreter.spin.element(element='H', spin_id='@H') 
179   
180           
181          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
182   
183           
184          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=2, error_col=4, spin_id='@N') 
185          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=3, error_col=4, spin_id='@H') 
186   
187           
188          for spin in spin_loop(): 
189              spin.pcs_bc = {} 
190              spin.pcs_bc['dy'] = spin.pcs['dy'] + 0.1 
191   
192           
193          self.tmpdir = mkdtemp() 
194          self.interpreter.pcs.corr_plot(format='grace', file='pcs_corr.agr', dir=self.tmpdir, force=True) 
195   
196           
197          file = open(self.tmpdir+sep+'pcs_corr.agr') 
198          lines = file.readlines() 
199          file.close() 
200   
201           
202          for i in range(len(lines)): 
203              if search('G0.S0', lines[i]): 
204                  point1 = lines[i+2].split() 
205                  point2 = lines[i+3].split() 
206                  self.assertAlmostEqual(float(point1[0]), -100.0) 
207                  self.assertAlmostEqual(float(point1[1]), -100.0) 
208                  self.assertAlmostEqual(float(point2[0]), 100.0) 
209                  self.assertAlmostEqual(float(point2[1]), 100.0) 
210   
211           
212          for i in range(len(lines)): 
213              if search('G0.S1', lines[i]): 
214                  point1 = lines[i+2].split() 
215                  point2 = lines[i+3].split() 
216                  self.assertAlmostEqual(float(point1[0]), 0.917+0.1) 
217                  self.assertAlmostEqual(float(point1[1]), 0.917) 
218                  self.assertAlmostEqual(float(point1[2]), 0.1) 
219                  self.assertAlmostEqual(float(point2[0]), 1.131+0.1) 
220                  self.assertAlmostEqual(float(point2[1]), 1.131) 
221                  self.assertAlmostEqual(float(point2[2]), 0.1) 
222   
223           
224          for i in range(len(lines)): 
225              if search('G0.S2', lines[i]): 
226                  point1 = lines[i+2].split() 
227                  point2 = lines[i+3].split() 
228                  self.assertAlmostEqual(float(point1[0]), 0.843+0.1) 
229                  self.assertAlmostEqual(float(point1[1]), 0.843) 
230                  self.assertAlmostEqual(float(point1[2]), 0.1) 
231                  self.assertAlmostEqual(float(point2[0]), 1.279+0.1) 
232                  self.assertAlmostEqual(float(point2[1]), 1.279) 
233                  self.assertAlmostEqual(float(point2[2]), 0.1) 
 234   
235   
237          """Test the loading of PCS data from a file with different columns for each spin type.""" 
238   
239           
240          self.interpreter.pipe.create('CaM N-dom', 'N-state') 
241   
242           
243          self.interpreter.spin.create(spin_name='N', spin_num=1, res_name='Gly', res_num=3) 
244          self.interpreter.spin.create(spin_name='H', spin_num=2, res_name='Gly', res_num=3) 
245          self.interpreter.spin.create(spin_name='N', spin_num=3, res_name='Gly', res_num=4) 
246          self.interpreter.spin.create(spin_name='H', spin_num=4, res_name='Gly', res_num=4) 
247          self.interpreter.sequence.display() 
248   
249           
250          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
251   
252           
253          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=2, error_col=4, spin_id='@N') 
254          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=3, error_col=4, spin_id='@H') 
255   
256           
257          pcs_data = { 
258              ':3@N': 0.917, 
259              ':3@H': 0.843, 
260              ':4@N': 1.131, 
261              ':4@H': 1.279, 
262          } 
263   
264           
265          print("\n") 
266          for spin, spin_id in spin_loop(return_id=True): 
267              print("Checking the PCS data of spin '%s'." % spin_id) 
268              self.assert_(hasattr(spin, 'pcs')) 
269              self.assertEqual(spin.pcs['dy'], pcs_data[spin_id]) 
270              self.assertEqual(spin.pcs_err['dy'], 0.1) 
 271   
272   
274          """Test the loading of PCS data from a file with different columns for each spin type.""" 
275   
276           
277          self.interpreter.pipe.create('CaM N-dom', 'N-state') 
278   
279           
280          self.interpreter.spin.create(spin_name='N', spin_num=1, res_name='Gly', res_num=3, mol_name='CaM') 
281          self.interpreter.spin.create(spin_name='H', spin_num=2, res_name='Gly', res_num=3, mol_name='CaM') 
282          self.interpreter.spin.create(spin_name='N', spin_num=3, res_name='Gly', res_num=4, mol_name='CaM') 
283          self.interpreter.spin.create(spin_name='H', spin_num=4, res_name='Gly', res_num=4, mol_name='CaM') 
284          self.interpreter.sequence.display() 
285   
286           
287          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
288   
289           
290          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=2, error_col=4, spin_id='@N') 
291          self.interpreter.pcs.read(align_id='dy', file='pcs_dy_200911.txt', dir=dir, res_num_col=1, data_col=3, error_col=4, spin_id='@H') 
292   
293           
294          pcs_data = { 
295              '#CaM:3@N': 0.917, 
296              '#CaM:3@H': 0.843, 
297              '#CaM:4@N': 1.131, 
298              '#CaM:4@H': 1.279, 
299          } 
300   
301           
302          print("\n") 
303          for spin, spin_id in spin_loop(return_id=True): 
304              print("Checking the PCS data of spin '%s'." % spin_id) 
305              self.assert_(hasattr(spin, 'pcs')) 
306              self.assertEqual(spin.pcs['dy'], pcs_data[spin_id]) 
307              self.assertEqual(spin.pcs_err['dy'], 0.1) 
 308   
309   
311          """Test the operation of the pcs.copy user function.""" 
312   
313           
314          self.interpreter.pipe.create('orig', 'N-state') 
315   
316           
317          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
318   
319           
320          self.interpreter.sequence.read(file='pcs.txt', dir=dir, spin_name_col=1) 
321          self.interpreter.sequence.display() 
322   
323           
324          self.interpreter.pcs.read(align_id='tb', file='pcs.txt', dir=dir, spin_name_col=1, data_col=2) 
325          self.interpreter.sequence.display() 
326   
327           
328          pcs = [0.004, 0.008, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.060, 0.120] 
329   
330           
331          self.interpreter.pipe.copy(pipe_from='orig', pipe_to='new') 
332          self.interpreter.pipe.switch(pipe_name='new') 
333   
334           
335          self.interpreter.pcs.delete() 
336   
337           
338          self.interpreter.pcs.copy(pipe_from='orig', align_id='tb') 
339   
340           
341          self.assert_(hasattr(cdp, 'align_ids')) 
342          self.assert_('tb' in cdp.align_ids) 
343          self.assert_(hasattr(cdp, 'pcs_ids')) 
344          self.assert_('tb' in cdp.pcs_ids) 
345          self.assertEqual(count_spins(), 26) 
346          self.assertEqual(len(cdp.interatomic), 0) 
347          i = 0 
348          for spin in spin_loop(): 
349              self.assertEqual(pcs[i], spin.pcs['tb']) 
350              i += 1 
 351   
352   
354          """Test the operation of the pcs.copy user function for two data pipes with different spin system.""" 
355   
356           
357          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
358   
359           
360          pipes = ['orig', 'new'] 
361          delete = ['@C2', '@H17'] 
362          for i in range(2): 
363               
364              self.interpreter.pipe.create(pipes[i], 'N-state') 
365   
366               
367              self.interpreter.sequence.read(file='pcs.txt', dir=dir, spin_name_col=1) 
368   
369               
370              self.interpreter.spin.delete(delete[i]) 
371              self.interpreter.sequence.display() 
372   
373           
374          self.interpreter.pipe.switch('orig') 
375          self.interpreter.pcs.read(align_id='tb', file='pcs.txt', dir=dir, spin_name_col=1, data_col=2) 
376   
377           
378          self.interpreter.pcs.copy(pipe_from='orig', pipe_to='new', align_id='tb') 
379   
380           
381          pcs = [ 
382              [0.004, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.060, 0.120], 
383              [0.004, 0.008, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.120] 
384          ] 
385          for i in range(2): 
386              print("\nChecking data pipe '%s'." % pipes[i]) 
387              self.assert_(hasattr(ds[pipes[i]], 'align_ids')) 
388              self.assert_('tb' in ds[pipes[i]].align_ids) 
389              self.assert_(hasattr(ds[pipes[i]], 'pcs_ids')) 
390              self.assert_('tb' in ds[pipes[i]].pcs_ids) 
391              self.assertEqual(count_spins(), 25) 
392              self.assertEqual(len(cdp.interatomic), 0) 
393              j = 0 
394              for spin in spin_loop(pipe=pipes[i]): 
395                   
396                  if i == 1 and j == 1: 
397                      self.assert_(not hasattr(spin, 'pcs')) 
398                  else: 
399                      if pcs[i][j] == None: 
400                          self.assertEqual(pcs[i][j], spin.pcs['tb']) 
401                      else: 
402                          self.assertAlmostEqual(pcs[i][j], spin.pcs['tb']) 
403                  j += 1 
 404   
405   
407          """Test the operation of the pcs.copy user function for back-calculated values.""" 
408   
409           
410          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
411   
412           
413          pipes = ['orig', 'new'] 
414          delete = ['@C2', '@H17'] 
415          for i in range(2): 
416               
417              self.interpreter.pipe.create(pipes[i], 'N-state') 
418   
419               
420              self.interpreter.sequence.read(file='pcs.txt', dir=dir, spin_name_col=1) 
421   
422               
423              self.interpreter.spin.delete(delete[i]) 
424              self.interpreter.sequence.display() 
425   
426           
427          self.interpreter.pipe.switch('orig') 
428          self.interpreter.pcs.read(align_id='tb', file='pcs.txt', dir=dir, spin_name_col=1, data_col=2) 
429   
430           
431          for spin in spin_loop(): 
432              if hasattr(spin, 'pcs'): 
433                  if not hasattr(spin, 'pcs_bc'): 
434                      spin.pcs_bc = {} 
435                  spin.pcs_bc['tb'] = spin.pcs['tb'] 
436                  if spin.pcs_bc['tb'] != None: 
437                      spin.pcs_bc['tb'] += 1.0 
438   
439           
440          self.interpreter.pcs.copy(pipe_from='orig', pipe_to='new', align_id='tb', back_calc=True) 
441   
442           
443          pcs = [ 
444              [0.004, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.060, 0.120], 
445              [0.004, 0.008, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.120] 
446          ] 
447          for i in range(2): 
448              print("\nChecking data pipe '%s'." % pipes[i]) 
449              self.assert_(hasattr(ds[pipes[i]], 'align_ids')) 
450              self.assert_('tb' in ds[pipes[i]].align_ids) 
451              self.assert_(hasattr(ds[pipes[i]], 'pcs_ids')) 
452              self.assert_('tb' in ds[pipes[i]].pcs_ids) 
453              self.assertEqual(count_spins(), 25) 
454              self.assertEqual(len(cdp.interatomic), 0) 
455              j = 0 
456              for spin in spin_loop(pipe=pipes[i]): 
457                   
458                  if i == 1 and j == 1: 
459                      self.assert_(not hasattr(spin, 'pcs')) 
460                  else: 
461                      if pcs[i][j] == None: 
462                          self.assertEqual(None, spin.pcs['tb']) 
463                          self.assertEqual(None, spin.pcs_bc['tb']) 
464                      else: 
465                          self.assertAlmostEqual(pcs[i][j], spin.pcs['tb']) 
466                          self.assertAlmostEqual(pcs[i][j]+1.0, spin.pcs_bc['tb']) 
467                  j += 1 
 468   
469   
471          """Test for the loading of some PCS data with the spin ID format.""" 
472   
473           
474          self.interpreter.pipe.create('test', 'N-state') 
475   
476           
477          dir = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'align_data'+sep 
478   
479           
480          self.interpreter.sequence.read(file='pcs.txt', dir=dir, spin_name_col=1) 
481          self.interpreter.sequence.display() 
482   
483           
484          self.interpreter.pcs.read(align_id='tb', file='pcs.txt', dir=dir, spin_name_col=1, data_col=2) 
485          self.interpreter.sequence.display() 
486   
487           
488          pcs = [0.004, 0.008, 0.021, 0.029, 0.016, 0.010, 0.008, 0.003, 0.006, 0.003, 0.007, 0.005, 0.001, 0.070, None, 0.025, 0.098, 0.054, 0.075, 0.065, None, 0.070, 0.015, 0.098, 0.060, 0.120] 
489   
490           
491          self.assertEqual(count_spins(), 26) 
492          self.assertEqual(len(cdp.interatomic), 0) 
493          i = 0 
494          for spin in spin_loop(): 
495              self.assertEqual(pcs[i], spin.pcs['tb']) 
496              i += 1 
 497   
498   
500          """Test the operation of the pcs.structural_noise user function.""" 
501   
502           
503          state = status.install_path + sep+'test_suite'+sep+'shared_data'+sep+'saved_states'+sep+'pcs_structural_noise_test.bz2' 
504   
505           
506          self.interpreter.state.load(state) 
507   
508           
509          self.interpreter.pcs.structural_noise(rmsd=200.0, sim_num=100, file='devnull', dir=None, force=True) 
510          self.interpreter.pcs.structural_noise(rmsd=0.2, sim_num=20000, file='devnull', dir=None, force=True) 
511   
512           
513          pcs_struct_err = { 
514              'Dy N-dom': 0.014643633242475744, 
515              'Er N-dom': 0.0047594540182391868, 
516              'Tm N-dom': 0.010454580925459261, 
517              'Tb N-dom': 0.01613972832580988 
518          } 
519          pcs_err = { 
520              'Dy N-dom': 0.1010664929367797, 
521              'Er N-dom': 0.10011319794388618, 
522              'Tm N-dom': 0.1005450061531003, 
523              'Tb N-dom': 0.10129408092495312 
524          } 
525   
526           
527          spin = cdp.mol[0].res[0].spin[0] 
528   
529           
530          for id in ['Dy N-dom', 'Tb N-dom', 'Tm N-dom', 'Er N-dom']: 
531              self.assertAlmostEqual(spin.pcs_struct_err[id], pcs_struct_err[id], 2) 
532              self.assertAlmostEqual(spin.pcs_err[id], pcs_err[id], 2) 
  533