-
Notifications
You must be signed in to change notification settings - Fork 95
/
PerfMeasuredInverseK0.cs
240 lines (218 loc) · 11.3 KB
/
PerfMeasuredInverseK0.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
/*
* Original author: Brian Pratt <bspratt .at. u.washington.edu>,
* MacCoss Lab, Department of Genome Sciences, UW
*
* Copyright 2017 University of Washington - Seattle, WA
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
using System;
using System.IO;
using System.Linq;
using System.Text;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using pwiz.ProteowizardWrapper;
using pwiz.Skyline;
using pwiz.Skyline.Controls;
using pwiz.Skyline.FileUI;
using pwiz.Skyline.Model;
using pwiz.Skyline.Model.DocSettings;
using pwiz.Skyline.Model.IonMobility;
using pwiz.Skyline.Model.Results;
using pwiz.Skyline.Properties;
using pwiz.Skyline.SettingsUI;
using pwiz.Skyline.SettingsUI.IonMobility;
using pwiz.Skyline.Util;
using pwiz.Skyline.Util.Extensions;
using pwiz.SkylineTestUtil;
namespace TestPerf // Note: tests in the "TestPerf" namespace only run when the global RunPerfTests flag is set
{
/// <summary>
/// Verify measured ion mobility derivation and filtering with Bruker TIMS data
/// </summary>
[TestClass]
public class MeasuredInverseK0PerfTest : AbstractFunctionalTestEx
{
private const string bsaFmolTimsInfusionesiPrecMz5Mz5 = "_BSA_50fmol_TIMS_InfusionESI_10prec_mz5.mz5";
private const string BSA_50fmol_TIMS_InfusionESI_10precd = "BSA_50fmol_TIMS_InfusionESI_10prec.d";
[TestMethod]
public void MeasuredInverseK0ValuesPerfTest()
{
TestFilesZip = GetPerfTestDataURL(@"PerfMeasuredInverseK0_v3.zip");
TestFilesPersistent = new[] { BSA_50fmol_TIMS_InfusionESI_10precd, bsaFmolTimsInfusionesiPrecMz5Mz5 }; // list of files that we'd like to unzip alongside parent zipFile, and (re)use in place
RunFunctionalTest();
}
protected override void DoTest()
{
string skyFile = TestFilesDir.GetTestPath("tims_test.sky");
Program.ExtraRawFileSearchFolder = TestFilesDir.PersistentFilesDir;
var testPath = TestFilesDir.GetTestPath("local.sky");
// Make sure that commandline loading employs 3-array IMS (should be quick if it does)
TestCommandlineImport(skyFile, testPath);
RunUI(() => Settings.Default.ImportResultsSimultaneousFiles = (int)MultiFileLoader.ImportResultsSimultaneousFileOptions.many); // use maximum threads for multiple file import
RunUI(() => SkylineWindow.OpenFile(skyFile));
ImportResults(BSA_50fmol_TIMS_InfusionESI_10precd);
var document = WaitForDocumentLoaded(240000); // mz5 part of this this can take awhile
AssertEx.IsDocumentState(document, null, 1, 34, 89, 1007);
RunUI(() =>
{
// Show that we can reopen a document with 3-array data in it
SkylineWindow.SaveDocument(testPath);
SkylineWindow.NewDocument();
VerifySerialization(testPath, false);
SkylineWindow.LoadFile(testPath);
});
document = WaitForDocumentLoaded(240000);
var transitions = document.MoleculeTransitions.ToArray();
// Verify ability to extract ion mobility peaks from raw data
var transitionSettingsDlg = ShowDialog<TransitionSettingsUI>(
() => SkylineWindow.ShowTransitionSettingsUI(TransitionSettingsUI.TABS.IonMobility));
RunUI(()=>
{
transitionSettingsDlg.IonMobilityControl.WindowWidthType =
IonMobilityWindowWidthCalculator.IonMobilityWindowWidthType.resolving_power;
transitionSettingsDlg.IonMobilityControl.IonMobilityFilterResolvingPower = 40;
});
// Simulate user picking Add from the ion mobility Predictor combo control
var editIonMobilityLibraryDlg = ShowDialog<EditIonMobilityLibraryDlg>(transitionSettingsDlg.IonMobilityControl.AddIonMobilityLibrary);
var testlibName = "test_tims";
var databasePath = TestFilesDir.GetTestPath(testlibName + IonMobilityDb.EXT);
RunUI(() =>
{
editIonMobilityLibraryDlg.SetOffsetHighEnergySpectraCheckbox(true);
editIonMobilityLibraryDlg.LibraryName = testlibName;
editIonMobilityLibraryDlg.CreateDatabaseFile(databasePath); // Simulate user click on Create button
editIonMobilityLibraryDlg.GetIonMobilitiesFromResults();
});
// PauseTest(); // Uncomment this to inspect ion mobility finder results
RunUI(() =>
{
editIonMobilityLibraryDlg.OkDialog();
});
WaitForClosedForm(editIonMobilityLibraryDlg);
RunUI(() =>
{
transitionSettingsDlg.OkDialog();
});
WaitForClosedForm(transitionSettingsDlg);
var docChangedDriftTimePredictor = WaitForDocumentChange(document);
// Reimport data - should shift precursors
RunDlg<ManageResultsDlg>(SkylineWindow.ManageResults, dlg =>
{
var chromatograms = docChangedDriftTimePredictor.Settings.MeasuredResults.Chromatograms;
dlg.SelectedChromatograms = new[] { chromatograms[0] };
dlg.ReimportResults();
dlg.OkDialog();
});
document = WaitForDocumentChangeLoaded(docChangedDriftTimePredictor);
var transitionsNew = document.MoleculeTransitions.ToArray();
var nChanges = 0;
var nNonEmpty = 0;
for (var i = 0; i < transitions.Length; i++)
{
Assert.AreEqual(transitions[i].Mz, transitionsNew[i].Mz);
if (transitions[i].AveragePeakArea.HasValue)
{
nNonEmpty++;
if (transitions[i].AveragePeakArea != transitionsNew[i].AveragePeakArea) // Using filter should alter peak area
{
nChanges++;
}
}
else
{
Assert.AreEqual(transitions[i].AveragePeakArea, transitionsNew[i].AveragePeakArea);
}
}
Assert.IsTrue(nChanges >= nNonEmpty*.9); // We expect nearly all peaks to change in area with IMS filter in use
// And read some mz5 converted from Bruker in 2-array IMS format, then compare replicates - should be identical
var mz5 = TestFilesDir.GetTestPath(bsaFmolTimsInfusionesiPrecMz5Mz5);
ImportResultsFile(mz5);
document = WaitForDocumentChange(document);
var sb = new StringBuilder();
int trials = 0;
int diffs = 0;
foreach (var nodeGroup in document.MoleculeTransitionGroups)
{
Assert.AreEqual(2, nodeGroup.Results.Count);
foreach (TransitionDocNode nodeTran in nodeGroup.Children)
{
Assume.AreEqual(2, nodeTran.Results.Count);
if (nodeTran.Results[0].Any() || nodeTran.Results[1].Any())
trials++;
if (Equals(nodeTran.Results[0], nodeTran.Results[1]))
continue;
if (nodeTran.Results[0].First().Area != nodeTran.Results[1].First().Area)
{
diffs++;
var diff =
Math.Abs(nodeTran.Results[0].First().Area - nodeTran.Results[1].First().Area) /
Math.Min(nodeTran.Results[0].First().Area, nodeTran.Results[1].First().Area);
sb.AppendLine(string.Format("{0}% difference {3} vs {4}(mz5) in precursor {1} transition {2}",
diff, nodeGroup, nodeTran.Transition, nodeTran.Results[0].First().Area, nodeTran.Results[1].First().Area));
}
else
{
sb.AppendLine(string.Format("No area difference in precursor {0} transition {1}",
nodeGroup, nodeTran.Transition));
}
}
}
if (diffs != 0)
Assert.Fail(TextUtil.LineSeparate(string.Format("{0} differences found in peak areas between 2- and 3- array spectra", diffs), sb.ToString()));
// Verify that the data was loaded in 3-array IMS format for .d and 2-array for .mz5 (which was converted that way on purpose) by looking at serialization
RunUI(() =>
{
SkylineWindow.SaveDocument(testPath);
});
VerifySerialization(testPath, true);
}
private void TestCommandlineImport(string skyFile, string testPath)
{
if (File.Exists(testPath))
File.Delete(testPath);
var imsdbPath = TestFilesDir.GetTestPath("testlib.imsdb");
// Show anyone watching that work is being performed
// Create an ion mobility library after import just to exercise that code
RunUI(() => {
using (var longWait = new LongWaitDlg(SkylineWindow) { Message = "Running command-line import" })
{
longWait.PerformWork(SkylineWindow, 500, () =>
{
RunCommand("--in=" + skyFile,
"--import-file=" + TestFilesDir.GetTestPath(BSA_50fmol_TIMS_InfusionESI_10precd),
"--ionmobility-create-library=" + imsdbPath,
"--ionmobility-create-library-name=testlib",
"--out=" + testPath);
});
}
});
AssertEx.FileExists(imsdbPath);
VerifySerialization(testPath, false);
}
private void VerifySerialization(string testPath, bool expect_mz5)
{
var lines = File.ReadAllLines(testPath);
VerifyFileInfoSerialization(lines, TestFilesDir.GetTestPath(BSA_50fmol_TIMS_InfusionESI_10precd), !MsDataFileImpl.ForceUncombinedIonMobility);
if (expect_mz5)
VerifyFileInfoSerialization(lines, TestFilesDir.GetTestPath(bsaFmolTimsInfusionesiPrecMz5Mz5), false);
}
private void VerifyFileInfoSerialization(string[] lines, string filePath, bool combinedIms)
{
var encodePath = SampleHelp.EncodePath(filePath, null, -1, null);
var lineFilePath = lines.FirstOrDefault(l => l.Contains(encodePath + '"'));
Assert.IsNotNull(lineFilePath);
// Nothing gets serialized to the XML about whether the MsData had combined spectra - can only be found in the SKYD file
}
}
}