diff --git a/pydatalab/example_data/raman/raman_example.txt b/pydatalab/example_data/raman/raman_example.txt
new file mode 100644
index 000000000..db9e3c6df
--- /dev/null
+++ b/pydatalab/example_data/raman/raman_example.txt
@@ -0,0 +1,1012 @@
+#Wave #Intensity
+1879.449219 381.030365
+1877.822266 394.858093
+1876.194336 371.721741
+1874.566406 388.523895
+1872.938477 411.459076
+1871.309570 389.870300
+1869.680664 354.481049
+1868.050781 368.202576
+1866.420898 366.579376
+1864.791016 394.092133
+1863.160156 364.868256
+1861.529297 380.106506
+1859.897461 376.949493
+1858.265625 378.389832
+1856.632813 364.513702
+1855.000000 362.893890
+1853.367188 364.336456
+1851.733398 382.613251
+1850.099609 376.399841
+1848.465820 371.719147
+1846.831055 389.980682
+1845.195313 400.588501
+1843.560547 397.433777
+1841.924805 400.393433
+1840.288086 418.630066
+1838.651367 378.813721
+1837.014648 407.736359
+1835.376953 387.789490
+1833.739258 396.853088
+1832.100586 393.704376
+1830.461914 418.018158
+1828.823242 411.815216
+1827.183594 413.239624
+1825.543945 396.369324
+1823.903320 397.796692
+1822.262695 406.842102
+1820.621094 414.359680
+1818.979492 377.706238
+1817.337891 385.227173
+1815.695313 398.833435
+1814.052734 398.735962
+1812.410156 404.724609
+1810.766602 404.625671
+1809.123047 403.005951
+1807.478516 434.835907
+1805.833984 373.928192
+1804.188477 402.710266
+1802.542969 381.341675
+1800.897461 399.475342
+1799.250977 359.895355
+1797.604492 411.425140
+1795.957031 365.790314
+1794.309570 396.049347
+1792.661133 385.332886
+1791.012695 411.022125
+1789.364258 385.144043
+1787.714844 383.533661
+1786.065430 416.782196
+1784.416016 400.012787
+1782.765625 381.736725
+1781.114258 380.128632
+1779.463867 384.577606
+1777.811523 367.832367
+1776.160156 378.335449
+1774.507813 372.190674
+1772.854492 373.611847
+1771.201172 397.715729
+1769.547852 374.940186
+1767.894531 399.031769
+1766.239258 392.889252
+1764.584961 345.959686
+1762.929688 388.164978
+1761.274414 400.149506
+1759.618164 386.464417
+1757.961914 401.461914
+1756.304688 395.327576
+1754.647461 405.789856
+1752.989258 390.608551
+1751.332031 378.450226
+1749.672852 370.820007
+1748.014648 397.855164
+1746.354492 408.303741
+1744.695313 424.772247
+1743.035156 380.996063
+1741.375000 368.857819
+1739.713867 418.437500
+1738.052734 361.151917
+1736.390625 412.213409
+1734.728516 369.998108
+1733.065430 412.010010
+1731.402344 414.914948
+1729.739258 390.765442
+1728.075195 378.648376
+1726.411133 398.083466
+1724.747070 363.443054
+1723.082031 379.869324
+1721.416016 394.786316
+1719.750000 408.195221
+1718.083984 375.086670
+1716.416992 385.493774
+1714.750000 379.400024
+1713.083008 406.292389
+1711.415039 377.713470
+1709.746094 380.617004
+1708.078125 404.492737
+1706.408203 383.424103
+1704.739258 404.292480
+1703.069336 387.725281
+1701.398438 413.072083
+1699.727539 380.051849
+1698.056641 408.379730
+1696.384766 406.782990
+1694.712891 406.682159
+1693.040039 393.128265
+1691.367188 400.502838
+1689.694336 406.379669
+1688.020508 389.848480
+1686.345703 395.724945
+1684.671875 395.626740
+1682.997070 423.887177
+1681.321289 425.274139
+1679.645508 410.250336
+1677.969727 414.622772
+1676.292969 380.224976
+1674.615234 420.379608
+1672.938477 427.726837
+1671.259766 396.331207
+1669.582031 411.128632
+1667.903320 415.494080
+1666.223633 425.812714
+1664.544922 449.522552
+1662.864258 418.160309
+1661.183594 416.568481
+1659.502930 420.926941
+1657.822266 435.692169
+1656.140625 438.556946
+1654.458008 460.741669
+1652.775391 462.112793
+1651.092773 448.627960
+1649.409180 472.278595
+1647.725586 463.252197
+1646.041992 482.434052
+1644.357422 473.409515
+1642.671875 497.030212
+1640.986328 550.305115
+1639.300781 539.787292
+1637.614258 575.234070
+1635.927734 576.572693
+1634.240234 637.183411
+1632.552734 674.060608
+1630.865234 699.070679
+1629.176758 756.643860
+1627.488281 839.353943
+1625.798828 899.823059
+1624.109375 988.374329
+1622.418945 1119.778931
+1620.728516 1224.498169
+1619.038086 1244.890869
+1617.346680 1361.351196
+1615.654297 1443.764771
+1613.962891 1436.016602
+1612.269531 1474.059448
+1610.577148 1504.699951
+1608.883789 1563.374268
+1607.189453 1602.832153
+1605.495117 1747.033081
+1603.800781 1756.921509
+1602.105469 1936.406372
+1600.410156 2087.786865
+1598.713867 2331.956787
+1597.017578 2524.425049
+1595.320313 2859.708496
+1593.623047 3184.512451
+1591.925781 3598.980713
+1590.227539 3982.323975
+1588.528320 4285.995117
+1586.830078 4688.102051
+1585.130859 5022.335938
+1583.430664 5275.511230
+1581.730469 5556.495605
+1580.029297 5549.219727
+1578.328125 5531.659668
+1576.626953 5320.166016
+1574.924805 4866.412598
+1573.222656 4677.219238
+1571.519531 4197.427734
+1569.816406 3898.413574
+1568.113281 3611.288574
+1566.409180 3204.010498
+1564.704102 3028.670654
+1562.999023 2812.362305
+1561.293945 2556.582520
+1559.587891 2377.140137
+1557.881836 2188.997070
+1556.174805 1984.835205
+1554.467773 1843.747559
+1552.760742 1661.736450
+1551.052734 1532.510620
+1549.343750 1410.666382
+1547.634766 1288.883545
+1545.925781 1162.774170
+1544.215820 1092.293335
+1542.505859 1036.466675
+1540.794922 966.053040
+1539.083984 927.819702
+1537.373047 856.008057
+1535.661133 803.217651
+1533.949219 803.014832
+1532.236328 710.853516
+1530.522461 722.348267
+1528.809570 671.103516
+1527.095703 678.226685
+1525.380859 656.182495
+1523.666016 606.450867
+1521.950195 622.329407
+1520.234375 590.116333
+1518.518555 572.486511
+1516.801758 530.107788
+1515.084961 540.165466
+1513.367188 509.461060
+1511.649414 512.242554
+1509.930664 493.199585
+1508.211914 478.529694
+1506.493164 501.674530
+1504.773438 504.454956
+1503.053711 467.992310
+1501.333008 464.967621
+1499.611328 457.586487
+1497.890625 464.731873
+1496.168945 455.902496
+1494.446289 436.916687
+1492.723633 441.159393
+1491.000000 406.227905
+1489.276367 439.485046
+1487.552734 437.923401
+1485.828125 403.019196
+1484.103516 391.322113
+1482.377930 424.549072
+1480.652344 418.646790
+1478.925781 393.920410
+1477.199219 402.507477
+1475.471680 387.930176
+1473.744141 400.855713
+1472.016602 396.413483
+1470.288086 409.330231
+1468.559570 386.089630
+1466.830078 377.317413
+1465.100586 387.338440
+1463.370117 397.354309
+1461.639648 405.920502
+1459.908203 382.710083
+1458.176758 389.831726
+1456.444336 389.732422
+1454.711914 367.986816
+1452.979492 354.908600
+1451.246094 366.356934
+1449.512695 386.451263
+1447.778320 367.611725
+1446.043945 376.165466
+1444.308594 358.778931
+1442.573242 371.652008
+1440.836914 372.997314
+1439.100586 385.860077
+1437.364258 354.094574
+1435.626953 364.077454
+1433.888672 361.107117
+1432.151367 345.193512
+1430.412109 350.857086
+1428.672852 362.267975
+1426.933594 383.733459
+1425.193359 354.898621
+1423.453125 359.117279
+1421.712891 382.003052
+1419.971680 350.319183
+1418.229492 357.406403
+1416.487305 347.269958
+1414.745117 358.658142
+1413.001953 358.566315
+1411.258789 358.474518
+1409.514648 372.718018
+1407.769531 376.922028
+1406.025391 349.602325
+1404.280273 330.891174
+1402.534180 327.942261
+1400.788086 366.513947
+1399.041016 383.595917
+1397.293945 383.497559
+1395.546875 371.954437
+1393.798828 351.835846
+1392.050781 373.193451
+1390.301758 378.815643
+1388.551758 362.998016
+1386.802734 351.474762
+1385.051758 371.381989
+1383.301758 385.566864
+1381.550781 379.757172
+1379.798828 379.659607
+1378.046875 392.404358
+1376.293945 405.142517
+1374.541016 406.464569
+1372.788086 419.192474
+1371.034180 409.106445
+1369.280273 420.401947
+1367.525391 437.390472
+1365.769531 420.185638
+1364.014648 448.557312
+1362.257813 454.136322
+1360.501953 508.103210
+1358.745117 503.703674
+1356.987305 551.939758
+1355.229492 571.707825
+1353.470703 575.825867
+1351.711914 589.891724
+1349.953125 622.424011
+1348.193359 656.360168
+1346.433594 741.410461
+1344.672852 749.739014
+1342.911133 809.168518
+1341.150391 799.025146
+1339.387695 852.735657
+1337.625977 904.999878
+1335.862305 984.181396
+1334.099609 925.799011
+1332.335938 1017.690613
+1330.571289 994.755249
+1328.806641 1034.164795
+1327.041016 1045.227905
+1325.275391 972.745239
+1323.509766 968.247009
+1321.743164 939.692627
+1319.976563 880.026611
+1318.208984 874.141052
+1316.440430 845.632874
+1314.672852 811.484375
+1312.903320 767.459839
+1311.134766 734.762085
+1309.364258 683.716858
+1307.594727 677.890686
+1305.824219 605.707825
+1304.052734 597.081665
+1302.281250 596.926941
+1300.508789 564.323608
+1298.736328 535.968445
+1296.963867 516.088379
+1295.190430 520.183655
+1293.416016 508.773987
+1291.641602 484.689301
+1289.867188 464.842926
+1288.091797 456.272797
+1286.316406 461.785858
+1284.540039 436.330627
+1282.763672 443.253082
+1280.986328 393.900421
+1279.208984 414.894409
+1277.430664 382.447296
+1275.652344 348.611328
+1273.873047 333.062103
+1272.093750 334.380493
+1270.314453 348.339478
+1268.533203 337.015045
+1266.752930 332.715759
+1264.971680 324.208191
+1263.189453 303.076813
+1261.407227 304.400696
+1259.625000 314.138275
+1257.841797 291.623871
+1256.058594 302.761292
+1254.274414 308.287628
+1252.490234 294.197906
+1250.705078 264.709106
+1248.918945 284.243073
+1247.133789 282.769135
+1245.346680 267.301086
+1243.560547 264.433136
+1241.772461 255.971634
+1239.985352 225.140335
+1238.197266 237.663788
+1236.408203 245.987686
+1234.619141 247.320770
+1232.829102 238.874619
+1231.039063 233.225983
+1229.249023 219.203079
+1227.458008 240.083313
+1225.666016 226.065887
+1223.874023 221.821487
+1222.082031 213.395065
+1220.289063 221.705505
+1218.495117 223.041534
+1216.701172 232.738708
+1214.907227 214.565170
+1213.112305 222.866531
+1211.317383 218.630539
+1209.521484 219.965500
+1207.725586 224.083359
+1205.928711 212.893021
+1204.131836 232.312561
+1202.333984 204.437119
+1200.536133 219.677567
+1198.737305 208.499985
+1196.938477 207.055695
+1195.138672 201.444321
+1193.338867 201.391495
+1191.538086 201.338669
+1189.737305 208.226746
+1187.935547 198.457413
+1186.133789 195.630432
+1184.332031 194.191986
+1182.529297 201.074615
+1180.725586 194.090027
+1178.921875 202.355011
+1177.117188 216.158142
+1175.312500 228.568726
+1173.507813 207.735138
+1171.702148 215.987762
+1169.895508 189.631683
+1168.088867 178.511353
+1166.282227 201.982971
+1164.474609 200.546753
+1162.666992 188.049530
+1160.858398 192.147095
+1159.048828 186.568573
+1157.239258 207.243835
+1155.429688 191.995377
+1153.619141 201.611099
+1151.808594 186.372116
+1149.997070 209.785904
+1148.185547 200.071976
+1146.373047 193.122025
+1144.559570 205.482834
+1142.747070 177.854340
+1140.932617 194.347656
+1139.119141 201.186325
+1137.303711 185.979370
+1135.489258 210.721008
+1133.672852 192.765717
+1131.857422 184.455612
+1130.040039 194.040115
+1128.223633 187.109833
+1126.405273 180.183182
+1124.587891 174.635254
+1122.768555 191.085709
+1120.950195 200.655685
+1119.130859 192.358704
+1117.310547 197.802353
+1115.490234 174.404541
+1113.668945 185.341629
+1111.847656 174.312286
+1110.025391 200.337479
+1108.203125 170.104599
+1106.379883 181.031158
+1104.556641 191.951904
+1102.733398 182.306015
+1100.909180 178.146652
+1099.083984 175.359467
+1097.258789 161.616669
+1095.432617 193.067047
+1093.606445 176.588989
+1091.780273 184.753433
+1089.952148 164.181717
+1088.125000 191.494537
+1086.296875 158.624802
+1084.467773 165.418182
+1082.638672 159.907364
+1080.809570 166.696747
+1078.978516 165.286484
+1077.148438 188.458496
+1075.317383 170.659821
+1073.485352 154.235489
+1071.653320 165.110931
+1069.821289 163.702866
+1067.987305 152.748718
+1066.154297 175.887024
+1064.320313 166.298523
+1062.485352 160.803329
+1060.650391 163.485306
+1058.815430 183.872040
+1056.979492 160.675018
+1055.142578 164.716110
+1053.305664 152.423904
+1051.467773 172.791794
+1049.629883 164.584564
+1047.791992 161.821030
+1045.953125 150.902084
+1044.113281 144.066299
+1042.273438 152.180420
+1040.432617 142.631104
+1038.591797 156.173370
+1036.750977 157.489380
+1034.909180 146.588928
+1033.066406 172.331726
+1031.223633 143.797546
+1029.379883 174.952179
+1027.536133 153.211777
+1025.692383 151.815369
+1023.847656 161.260742
+1022.001953 157.153351
+1020.156250 157.111374
+1018.309570 155.715332
+1016.462891 154.320023
+1014.615234 173.225281
+1012.767578 147.472717
+1010.919922 137.965088
+1009.070313 162.268433
+1007.221680 170.336273
+1005.372070 135.151337
+1003.521484 152.680145
+1001.670898 137.780579
+999.819336 162.051392
+997.967773 139.056854
+996.115234 159.265182
+994.262695 165.969223
+992.409180 151.085953
+990.555664 148.348206
+988.701172 153.701477
+986.846680 146.920776
+984.991211 138.796158
+983.135742 130.675873
+981.279297 156.230255
+979.422852 144.070267
+977.565430 156.146408
+975.708008 137.264297
+973.849609 147.990372
+971.991211 138.535583
+970.131836 138.498367
+968.271484 138.461151
+966.411133 138.423950
+964.550781 150.478790
+962.689453 147.751938
+960.828125 158.454910
+958.965820 138.275131
+957.102539 142.264282
+955.239258 150.276535
+953.375977 142.187744
+951.511719 148.854630
+949.647461 152.836563
+947.782227 164.858215
+945.916016 138.014816
+944.049805 150.033936
+942.182617 151.332748
+940.315430 145.936493
+938.448242 137.866119
+936.580078 145.857819
+934.710938 141.805145
+932.841797 155.141129
+930.971680 136.380402
+929.101563 117.629776
+927.230469 142.988510
+925.359375 140.277954
+923.488281 137.568848
+921.615234 134.861176
+919.743164 132.154968
+917.869141 146.799179
+915.996094 128.081024
+914.121094 136.049316
+912.246094 145.346741
+910.371094 149.306732
+908.495117 133.273529
+906.619141 149.225983
+904.742188 125.209358
+902.864258 146.481949
+900.987305 129.135483
+899.108398 131.762405
+897.229492 149.024170
+895.350586 134.351486
+893.470703 131.655396
+891.589844 136.937698
+889.708984 144.875381
+887.827148 142.178574
+885.945313 158.080978
+884.063477 136.789291
+882.179688 122.147598
+880.296875 122.114464
+878.413086 141.985901
+876.528320 124.701439
+874.643555 127.320099
+872.757813 133.914993
+870.871094 136.529694
+868.985352 136.492615
+867.097656 140.429977
+865.209961 169.529755
+863.322266 158.890961
+861.433594 144.286728
+859.544922 142.924133
+857.655273 150.823349
+855.764648 144.169083
+853.874023 148.096741
+851.983398 146.734512
+850.090820 140.086731
+848.199219 142.691025
+846.306641 136.047913
+844.413086 142.613342
+842.519531 145.214767
+840.625000 135.936798
+838.730469 150.413330
+836.834961 155.648560
+834.939453 127.913528
+833.042969 146.335373
+831.146484 135.751648
+829.249023 134.397018
+827.350586 130.408585
+825.452148 144.858887
+823.553711 114.538948
+821.654297 126.353310
+819.753906 135.529556
+817.853516 127.599785
+815.953125 135.455551
+814.050781 141.992264
+812.149414 135.381561
+810.246094 126.146385
+808.343750 149.757889
+806.439453 103.751221
+804.536133 144.424225
+802.630859 139.134369
+800.725586 133.847397
+798.820313 139.058243
+796.914063 135.085663
+795.007813 141.604446
+793.100586 125.836159
+791.192383 129.733002
+789.284180 138.867996
+787.375000 132.281372
+785.465820 129.626419
+783.555664 134.826889
+781.645508 130.864014
+779.734375 134.752975
+777.823242 120.328880
+775.911133 125.526131
+773.999023 129.413315
+772.085938 133.298340
+770.172852 124.116341
+768.258789 126.694527
+766.343750 141.023224
+764.428711 125.319550
+762.512695 129.200287
+760.596680 143.516434
+758.680664 122.607620
+756.762695 119.965965
+754.845703 110.807655
+752.926758 130.326096
+751.007813 114.655426
+749.088867 125.044243
+747.168945 122.405472
+745.249023 115.862648
+743.328125 126.242516
+741.406250 123.605537
+739.484375 132.676773
+737.561523 126.138260
+735.638672 143.003983
+733.714844 128.668121
+731.791016 126.034027
+729.866211 125.999283
+727.941406 124.665947
+726.015625 116.842094
+724.089844 114.214096
+722.163086 116.777649
+720.235352 128.419968
+718.307617 120.603645
+716.379883 124.459724
+714.450195 108.872192
+712.521484 119.208046
+710.590820 110.107445
+708.661133 116.552147
+706.729492 121.698601
+704.797852 111.310501
+702.866211 129.395035
+700.933594 113.836151
+699.000000 108.631729
+697.066406 125.409088
+695.132813 115.034233
+693.198242 127.924019
+691.262695 116.262375
+689.327148 125.270317
+687.390625 140.728699
+685.453125 123.910210
+683.515625 118.714394
+681.578125 121.261536
+679.639648 112.200317
+677.700195 108.301315
+675.760742 112.138123
+673.821289 121.127129
+671.879883 119.805305
+669.939453 123.635681
+667.997070 110.726234
+666.054688 127.428551
+664.112305 111.951576
+662.168945 122.212036
+660.224609 123.464180
+658.280273 113.144066
+656.335938 122.110222
+654.389648 122.076294
+652.444336 110.480453
+650.497070 124.577034
+648.550781 112.986916
+646.602539 118.089836
+644.654297 112.924072
+642.706055 102.629684
+640.756836 111.578728
+638.806641 110.265511
+636.856445 123.052811
+634.905273 130.707214
+632.954102 125.546455
+631.001953 105.019814
+629.048828 119.074646
+627.095703 99.841225
+625.142578 111.330330
+623.188477 122.813004
+621.233398 112.547195
+619.278320 117.630157
+617.322266 113.762642
+615.366211 115.008774
+613.409180 111.144119
+611.452148 126.439034
+609.494141 114.912483
+607.535156 104.668800
+605.576172 100.811279
+603.616211 112.264740
+601.656250 113.508743
+599.695313 102.001808
+597.734375 105.797295
+595.772461 115.962181
+593.809570 119.751610
+591.846680 126.086098
+589.883789 128.597290
+587.918945 137.471497
+585.955078 117.072563
+583.989258 111.951096
+582.024414 111.919746
+580.057617 122.060066
+578.090820 113.128151
+576.124023 115.637947
+574.155273 109.253578
+572.187500 109.222954
+570.217773 111.731682
+568.249023 123.124245
+566.278320 130.703491
+564.307617 110.369064
+562.336914 110.338089
+560.365234 110.307121
+558.392578 125.486649
+556.419922 116.581108
+554.446289 101.346405
+552.472656 102.584404
+550.498047 111.418404
+548.522461 110.121330
+546.546875 103.763336
+544.571289 101.204056
+542.593750 104.969681
+540.617188 96.089775
+538.638672 120.078423
+536.660156 116.253746
+534.681641 125.063927
+532.702148 99.770393
+530.721680 112.367905
+528.741211 103.500816
+526.759766 122.399399
+524.778320 104.703995
+522.795898 129.897247
+520.812500 122.295937
+518.829102 110.917603
+516.845703 103.325890
+514.861328 108.335609
+512.875977 113.342491
+510.889648 133.454590
+508.904297 110.761215
+506.916992 118.279716
+504.929688 122.020134
+502.941406 100.606735
+500.953125 115.665062
+498.963867 120.659874
+496.974609 108.060585
+494.984375 114.310852
+492.993164 109.255295
+491.001953 111.735306
+489.010742 117.979187
+487.017578 112.926834
+485.025391 110.386101
+483.031250 117.879051
+481.037109 106.562576
+479.042969 110.292366
+477.046875 120.284866
+475.051758 120.250786
+473.054688 127.730255
+471.057617 116.426933
+469.060547 123.903214
+467.062500 97.593033
+465.063477 117.578758
+463.064453 125.048302
+461.064453 116.261925
+459.064453 124.977341
+457.063477 122.443031
+455.061523 113.664818
+453.059570 126.119629
+451.057617 109.855202
+449.053711 113.567986
+447.050781 119.773941
+445.045898 125.976349
+443.041016 117.211983
+441.035156 128.397888
+439.029297 123.376465
+437.022461 134.554214
+435.015625 114.587646
+433.007813 113.309868
+431.000000 120.746468
+428.990234 114.489815
+426.981445 118.189507
+424.970703 105.718384
+422.960938 125.582527
+420.949219 119.331551
+418.937500 106.870712
+416.924805 134.171463
+414.912109 104.325829
+412.898438 122.920372
+410.884766 112.955177
+408.870117 119.127502
+406.854492 124.055733
+404.838867 110.378082
+402.822266 112.826263
+400.805664 115.273026
+398.788086 120.196663
+396.770508 118.923531
+394.750977 113.935814
+392.732422 117.617485
+390.711914 136.149719
+388.691406 131.161301
+386.670898 124.938705
+384.649414 123.666298
+382.626953 116.213051
+380.604492 129.775299
+378.581055 130.973740
+376.557617 127.230492
+374.533203 123.489372
+372.507813 123.453995
+370.482422 124.652802
+368.456055 127.084740
+366.428711 124.581352
+364.401367 135.643753
+362.374023 136.837631
+360.345703 119.544525
+358.316406 140.455307
+356.286133 135.488159
+354.255859 142.837418
+352.225586 125.562355
+350.193359 126.756943
+348.162109 140.253799
+346.128906 130.373947
+344.095703 120.499771
+342.062500 136.445206
+340.027344 126.574913
+337.993164 136.366745
+335.957031 130.186646
+333.920898 126.465729
+331.884766 133.794144
+329.847656 142.345459
+327.809570 125.129799
+325.770508 129.999405
+323.731445 126.283791
+321.692383 137.278748
+319.652344 129.887085
+317.611328 126.174660
+315.569336 137.160080
+313.527344 135.896240
+311.485352 129.737366
+309.442383 115.016930
+307.398438 133.332214
+305.353516 141.853882
+303.308594 117.362427
+301.263672 135.661133
+299.216797 133.178314
+297.170898 140.468643
+295.123047 141.649170
+293.075195 125.738350
+291.026367 124.481598
+288.977539 134.206039
+286.927734 134.167236
+284.877930 143.883224
+282.827148 143.841599
+280.775391 123.083031
+278.723633 141.321777
+276.670898 132.755295
+274.617188 131.499268
+272.563477 148.502441
+270.508789 139.941254
+268.454102 127.735428
+266.398438 125.266052
+264.341797 138.603790
+262.285156 130.055313
+260.228516 134.878067
+258.169922 146.986588
+256.111328 145.729523
+254.051758 133.546631
+251.992188 137.148987
+249.931641 152.882782
+247.871094 133.430328
+245.809570 124.903023
+243.747070 140.626602
+241.684570 156.341034
+239.621094 150.237625
+237.556641 158.672638
+235.492188 140.463150
+233.426758 136.790680
+231.361328 137.961060
+229.294922 143.970078
+227.227539 152.394531
+225.160156 168.068832
+223.091797 140.218033
+221.023438 161.928833
+218.954102 149.800934
+216.883789 140.095520
+214.813477 144.884155
+212.742188 153.291031
+210.669922 153.246323
+208.597656 139.932190
+206.524414 147.127136
+204.451172 138.644943
+202.376953 147.041260
+200.301758 136.154190
+198.226563 154.182724
+196.150391 143.299881
+194.074219 145.665726
+191.997070 145.623154
+189.918945 137.158569
+187.839844 139.524063
+185.760742 149.102798
+183.681641 143.048737
+181.601563 136.998199
+179.520508 158.583069
+177.438477 159.737701
+175.356445 147.684097
+173.273438 157.243500
+171.190430 165.597321
+169.106445 166.748428
+167.021484 171.496689
+164.936523 167.849640
+162.850586 167.800430
+160.764648 185.724579
+158.677734 162.910538
+156.589844 164.060272
+154.500977 172.392319
+152.412109 161.570358
+150.323242 174.684052
+148.233398 186.593918
+146.142578 174.581467
+144.050781 173.334778
+141.958984 181.649277
+139.866211 195.932404
+137.773438 191.097366
+135.679688 195.817200
+133.584961 192.178650
+131.490234 195.702026
+129.394531 199.223297
+127.297852 212.283295
+125.201172 221.758820
+123.103516 205.006912
+121.005859 220.436676
+118.907227 196.547775
+116.807617 178.627136
+114.708008 150.002579
+112.607422 133.296310
+110.505859 121.359062
+108.404297 118.944382
+106.301758 118.909294
+104.198242 99.854340
+102.094727 108.143600
+99.990234 96.231277
+97.885742 114.018204
+95.780273 105.673157
+93.673828 104.454948
+91.567383 96.117622
+89.459961 110.324654
+87.351563 93.688942
+85.243164 65.207191
+83.133789 50.965088
+81.023438 33.176750
+78.913086 23.690668
+76.801758 8.289280
+74.690430 11.838323
+72.578125 13.018298
+70.464844 10.648180
+68.351563 -1.182781
+66.237305 2.364860
+64.122070 2.364159
+62.006836 5.908646
+59.890625 3.544137
+57.773438 2.362057
+55.656250 4.722713
+53.538086 4.721311
+51.418945 3.539932
+49.299805 0.000000
+47.179688 0.000000
+45.059570 5.894632
+42.938477 1.178576
+40.816406 8.247582
+38.694336 7.067255
+36.571289 3.532577
+34.447266 1.177176
+32.323242 -3.530476
+30.198242 1.176475
+28.072266 1.176125
+25.946289 0.000000
+23.819336 1.175425
+21.691406 4.700300
+19.563477 3.524175
+17.434570 3.523125
+15.304688 -3.522075
+13.174805 -4.694700
+11.043945 11.733251
+8.913086 10.556776
+6.781250 34.006130
+4.648438 84.403824
+2.515625 133.599503
+0.380859 137.074356
diff --git a/pydatalab/pydatalab/apps/raman/blocks.py b/pydatalab/pydatalab/apps/raman/blocks.py
index 756bbab42..91a6526bb 100644
--- a/pydatalab/pydatalab/apps/raman/blocks.py
+++ b/pydatalab/pydatalab/apps/raman/blocks.py
@@ -4,87 +4,65 @@
import bokeh
import numpy as np
import pandas as pd
-from scipy.signal import medfilt
from pybaselines import Baseline
+from scipy.signal import medfilt
from pydatalab.blocks.blocks import DataBlock
from pydatalab.bokeh_plots import mytheme, selectable_axes_plot
from pydatalab.file_utils import get_file_info_by_id
-from pydatalab.logger import LOGGER
-from pydatalab.mongo import flask_mongo
-
-# from .utils import parse_xrdml
class RamanBlock(DataBlock):
blocktype = "raman"
description = "Raman spectroscopy"
- accepted_file_extensions = (".txt")
-
- # don't think this is needed for Raman
- # potentially the laser wavelength used but don't think it matters
- # defaults = {"wavelength": 1.54060}
+ accepted_file_extensions = (".txt",)
@property
def plot_functions(self):
return (self.generate_raman_plot,)
@classmethod
- def load_pattern(
- self, location: str
- ) -> Tuple[pd.DataFrame, List[str]]:
-
+ def load(self, location: str) -> Tuple[pd.DataFrame, List[str]]:
if not isinstance(location, str):
location = str(location)
- ext = os.path.splitext(location.split("/")[-1])[-1].lower()
-
- if ext == ".txt":
- df = pd.read_csv(location, sep=r"\s+")
-
- # elif ext == ".xy":
- # df = pd.read_csv(location, sep=r"\s+", names=["twotheta", "intensity"])
- # leaving here for other file format e.g. .spc
- else:
- df = pd.read_csv(location, sep=r"\s+", names=["twotheta", "intensity", "error"])
+ df = pd.read_csv(location, sep=r"\s+")
- df = df.rename(columns={"#Wave": "Wavenumber", "#Intensity": "intensity"})
-
- # unnecessary for Raman
- # if no wavelength (or invalid wavelength) is passed, don't convert to Q and d
- # if wavelength:
- # try:
- # df["Q (Å⁻¹)"] = 4 * np.pi / wavelength * np.sin(np.deg2rad(df["2θ (°)"]) / 2)
- # df["d (Å)"] = 2 * np.pi / df["Q (Å⁻¹)"]
- # except (ValueError, ZeroDivisionError):
- # pass
+ df = df.rename(columns={"#Wave": "wavenumber", "#Intensity": "intensity"})
df["sqrt(intensity)"] = np.sqrt(df["intensity"])
df["log(intensity)"] = np.log10(df["intensity"])
df["normalized intensity"] = df["intensity"] / np.max(df["intensity"])
polyfit_deg = 15
polyfit_baseline = np.poly1d(
- np.polyfit(df["Wavenumber"], df["normalized intensity"], deg=polyfit_deg)
- )(df["Wavenumber"])
+ np.polyfit(df["wavenumber"], df["normalized intensity"], deg=polyfit_deg)
+ )(df["wavenumber"])
df["intensity - polyfit baseline"] = df["normalized intensity"] - polyfit_baseline
- df["intensity - polyfit baseline"] /= np.max(df["intensity - polyfit baseline"])
- df[f"baseline (`numpy.polyfit`, deg={polyfit_deg})"] = polyfit_baseline / np.max(
+ df[f"baseline (`numpy.polyfit`, {polyfit_deg=})"] = polyfit_baseline / np.max(
df["intensity - polyfit baseline"]
)
+ df["intensity - polyfit baseline"] /= np.max(df["intensity - polyfit baseline"])
kernel_size = 101
median_baseline = medfilt(df["normalized intensity"], kernel_size=kernel_size)
df["intensity - median baseline"] = df["normalized intensity"] - median_baseline
+ df[f"baseline (`scipy.signal.medfilt`, {kernel_size=})"] = median_baseline / np.max(
+ df["intensity - median baseline"]
+ )
df["intensity - median baseline"] /= np.max(df["intensity - median baseline"])
- df[
- f"baseline (`scipy.signal.medfilt`, kernel_size={kernel_size})"
- ] = median_baseline / np.max(df["intensity - median baseline"])
- # baseline calculation I used in my data
+ # baseline calculation I used in my data
half_window = 30
- baseline_fitter = Baseline(x_data = df["Wavenumber"])
- morphological_baseline = baseline_fitter.mor(df["normalized intensity"], half_window=half_window)[0]
- df["intensity - morphological baseline"] = df["normalized intensity"] - morphological_baseline
+ baseline_fitter = Baseline(x_data=df["wavenumber"])
+ morphological_baseline = baseline_fitter.mor(
+ df["normalized intensity"], half_window=half_window
+ )[0]
+ df["intensity - morphological baseline"] = (
+ df["normalized intensity"] - morphological_baseline
+ )
+ df[
+ f"baseline (`pybaselines.Baseline.mor`, {half_window=})"
+ ] = morphological_baseline / np.max(df["intensity - morphological baseline"])
df["intensity - morphological baseline"] /= np.max(df["intensity - morphological baseline"])
df.index.name = location.split("/")[-1]
@@ -94,18 +72,17 @@ def load_pattern(
"sqrt(intensity)",
"log(intensity)",
"intensity - median baseline",
- f"baseline (`scipy.signal.medfilt`, kernel_size={kernel_size})",
+ f"baseline (`scipy.signal.medfilt`, {kernel_size=})",
"intensity - polyfit baseline",
- f"baseline (`numpy.polyfit`, deg={polyfit_deg})",
+ f"baseline (`numpy.polyfit`, {polyfit_deg=})",
"intensity - morphological baseline",
- f"baseline (`pybaselines.Baseline.mor`, half_window={half_window})"
+ f"baseline (`pybaselines.Baseline.mor`, {half_window=})",
]
return df, y_options
def generate_raman_plot(self):
file_info = None
- all_files = None
pattern_dfs = None
if "file_id" not in self.data:
@@ -121,16 +98,15 @@ def generate_raman_plot(self):
ext,
)
- pattern_dfs, y_options = self.load_pattern(
+ pattern_dfs, y_options = self.load_raman_spectrum(
file_info["location"],
- # wavelength=float(self.data.get("wavelength", self.defaults["wavelength"])),
)
pattern_dfs = [pattern_dfs]
if pattern_dfs:
p = selectable_axes_plot(
pattern_dfs,
- x_options=["Wavenumber"],
+ x_options=["wavenumber"],
y_options=y_options,
plot_line=True,
plot_points=True,
diff --git a/pydatalab/pydatalab/apps/raman/models.py b/pydatalab/pydatalab/apps/raman/models.py
deleted file mode 100644
index afebbeaeb..000000000
--- a/pydatalab/pydatalab/apps/raman/models.py
+++ /dev/null
@@ -1,49 +0,0 @@
-from typing import List, Optional
-
-from pydantic import BaseModel
-
-__all__ = ("RamanPattern", "RamanMeasurement")
-
-
-class RamanPattern(BaseModel):
- """This model defines the structure of the data that is expected
- for a solid-state XRD pattern.
-
- """
-
- # wavelength: float
-
- # two_theta: List[float]
-
- wavenumber : List[float]
-
- # d_spacings: List[float]
-
- # q_values: List[float]
-
- intensities: List[float]
-
-
-class RamanProcessing(BaseModel):
-
- peak_positions: List[float]
-
- peak_intensities: List[float]
-
- peak_widths: List[float]
-
- baselines: List[List[float]]
-
- class Config:
- extra = "allow"
-
-
-class RamanMetadata(BaseModel):
- ...
-
-
-class RamanMeasurement(BaseModel):
-
- data: Optional[RamanPattern]
- processing: Optional[RamanProcessing]
- metadata: Optional[RamanMetadata]
diff --git a/pydatalab/pydatalab/apps/raman/utils.py b/pydatalab/pydatalab/apps/raman/utils.py
deleted file mode 100644
index 67d1dbe52..000000000
--- a/pydatalab/pydatalab/apps/raman/utils.py
+++ /dev/null
@@ -1,148 +0,0 @@
-import os
-import re
-import warnings
-from typing import List, Tuple
-
-import numpy as np
-import pandas as pd
-
-STARTEND_REGEX = (
- r"(\d+\.\d+)\s+(\d+\.\d+)"
-)
-DATA_REGEX = r'((-?\d+ )+-?\d+)'
-
-
-class XrdmlParseError(Exception):
- pass
-
-
-def parse_xrdml(filename: str) -> pd.DataFrame:
- """Parses an XRDML file and returns a pandas DataFrame with columns
- twotheta and intensity.
-
- Parameters:
- filename: The file to parse.
-
- """
- with open(filename, "r") as f:
- s = f.read()
-
- start, end = getStartEnd(s) # extract first and last angle
- intensities = getIntensities(s) # extract intensities
-
- angles = np.linspace(start, end, num=len(intensities))
-
- return pd.DataFrame(
- {
- "twotheta": angles,
- "intensity": intensities,
- }
- )
-
-
-def convertSinglePattern(
- filename: str,
- directory: str = ".",
- adjust_baseline: bool = False,
- overwrite: bool = False,
-) -> str:
- """Converts an XRDML file to a simple xy and writes it to the passed directory, without
- overwriting any existing files.
-
- Parameters:
- filename: The file to convert.
- directory: The output directory.
- adjust_baseline: If True, the baseline will be adjusted so that no points are negative.
- overwrite: If True, existing files with the same filenames will be overwritten.
-
- Returns:
- The output filename.
-
- """
- filename = os.path.join(directory, filename)
- outfn = filename + ".xy"
- if os.path.exists(outfn):
- if overwrite:
- print(f"{outfn} already exists in the directory {directory}. Overwriting.")
- else:
- warnings.warn(
- f"{outfn} already exists in the directory {directory}, will not overwrite"
- )
- return outfn
-
- with open(filename, "r") as f:
- s = f.read()
-
- print(f"Processing file {filename}")
- start, end = getStartEnd(s)
- print(f"\tstart angle: {start}\tend angle: {end}")
- intensities = getIntensities(s)
-
- if adjust_baseline:
- intensities = np.array(intensities) # type: ignore
- minI = np.min(intensities)
- if minI < 0:
- print(
- f"\tadjusting baseline so that no points are negative (adding {-1 * minI} counts)"
- )
- intensities -= minI
- else:
- print("\tno intensitites are less than zero, so no baseline adjustment performed")
-
- intensities = intensities.tolist() # type: ignore
-
- print(f"\tnumber of datapoints: {len(intensities)}")
- xystring = toXY(intensities, start, end)
- with open(outfn, "w") as of:
- of.write(xystring)
- print("\tSuccess!")
- return outfn
-
-
-def getStartEnd(s: str) -> Tuple[float, float]:
- """Parse a given string representation of an xrdml file to find the start and end 2Theta points of the scan.
- Note: this could match either Omega or 2Theta depending on their order in the XRDML file.
-
- Raises:
- XrdmlParseError: if the start and end positions could not be found.
-
- Returns:
- (start, end) positions in the XRDML file.
-
- """
- match = re.search(STARTEND_REGEX, s)
- if not match:
- raise XrdmlParseError("the start and end 2theta positions were not found in the XRDML file")
-
- start = float(match.group(1))
- end = float(match.group(2))
-
- return start, end
-
-
-def getIntensities(s: str) -> List[float]:
- """Parse a given string representation of an xrdml file to find the peak intensities.
-
- Raises:
- XrdmlParseError: if intensities could not be found in the file
-
- Returns:
- The array of intensitites.
-
- """
- match = re.search(DATA_REGEX, s)
- if not match:
- raise XrdmlParseError("the intensitites were not found in the XML file")
-
- out = [float(x) for x in match.group(1).split()] # the intensitites as a list of integers
- return out
-
-
-def toXY(intensities: List[float], start: float, end: float) -> str:
- """Converts a given list of intensities, along with a start and end angle,
- to a string in XY format.
-
- """
- angles = np.linspace(start, end, num=len(intensities))
- xylines = ["{:.5f} {:.3f}\r\n".format(a, i) for a, i in zip(angles, intensities)]
- return "".join(xylines)
diff --git a/pydatalab/tests/blocks/test_raman.py b/pydatalab/tests/blocks/test_raman.py
new file mode 100644
index 000000000..8a19ddf07
--- /dev/null
+++ b/pydatalab/tests/blocks/test_raman.py
@@ -0,0 +1,16 @@
+from pathlib import Path
+
+import pytest
+
+from pydatalab.apps.raman.blocks import RamanBlock
+
+
+@pytest.fixture
+def data_files():
+ return (Path(__file__).parent.parent.parent / "example_data" / "raman").glob("*")
+
+
+def test_load(data_files):
+ for f in data_files:
+ df, y_options = RamanBlock.load(f)
+ assert all(y in df.columns for y in y_options)
diff --git a/webapp/src/resources.js b/webapp/src/resources.js
index c29f9b59e..ef5813a2c 100644
--- a/webapp/src/resources.js
+++ b/webapp/src/resources.js
@@ -32,7 +32,7 @@ export const blockTypes = {
comment: { description: "Comment", component: DataBlockBase },
media: { description: "Media", component: MediaBlock },
xrd: { description: "Powder XRD", component: XRDBlock },
- raman: { description: "Raman", component: RamanBlock},
+ raman: { description: "Raman", component: RamanBlock },
cycle: { description: "Electrochemistry", component: CycleBlock },
eis: { description: "EIS", component: EISBlock },
nmr: { description: "NMR", component: NMRBlock },