Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1from __future__ import with_statement 

2from builtins import zip 

3from builtins import object 

4import os 

5import numpy as np 

6import unittest 

7import tempfile 

8import shutil 

9import lsst.utils.tests 

10from lsst.utils import getPackageDir 

11from lsst.sims.utils.CodeUtilities import sims_clean_up 

12from lsst.sims.utils import defaultSpecMap, altAzPaFromRaDec, ObservationMetaData 

13from lsst.sims.catalogs.definitions import CompoundInstanceCatalog 

14from lsst.sims.catalogs.db import fileDBObject 

15from lsst.sims.catUtils.baseCatalogModels import SNDBObj 

16from lsst.sims.catUtils.utils import (testStarsDBObj, testGalaxyDiskDBObj, 

17 testGalaxyBulgeDBObj, testGalaxyAgnDBObj) 

18from lsst.sims.catUtils.exampleCatalogDefinitions import (PhoSimCatalogSersic2D, PhoSimCatalogPoint, 

19 PhoSimCatalogZPoint, PhoSimCatalogSSM, 

20 PhoSimCatalogSN) 

21from lsst.sims.catUtils.utils import makePhoSimTestDB 

22 

23# 2016 November 22 

24# For some reason, the Jenkins nodes used for continuous integration 

25# cannot properly load the astropy config directories used by sncosmo. 

26# To prevent this from crashing every build, we will test whether 

27# the directories can be accessed and, if they cannot, use unittest.skipIf() 

28# to skip all of the unit tests in this file. 

29from astropy.config import get_config_dir 

30 

31_skip_sn_tests = False 

32try: 

33 get_config_dir() 

34except: 

35 _skip_sn_tests = True 

36 

37ROOT = os.path.abspath(os.path.dirname(__file__)) 

38 

39 

40def createTestSNDB(): 

41 """ 

42 Create a CatalogDBObject-like database that contains everything needed to create 

43 a supernova catalog. Return the CatalogDBObject and an ObservationMetaData pointing 

44 to its center. 

45 

46 Note: the OpsimMetaData for the returned ObservationMetaData will be inconsistent. 

47 It is just there so that PhoSim InstanceCatalog classes can write out a header. 

48 """ 

49 

50 raCenter = 23.0 

51 decCenter = -19.0 

52 radius = 0.1 

53 obs = ObservationMetaData(pointingRA=raCenter, pointingDec=decCenter, boundType='circle', 

54 boundLength=radius, rotSkyPos=33.0, mjd=59580.0, 

55 bandpassName='r') 

56 

57 # these will be totally inconsistent; just need something to put in the header 

58 obs.OpsimMetaData = {'dist2Moon': 0.1, 'moonalt': -0.2, 

59 'moonra': 1.1, 'moondec': 0.5, 

60 'rottelpos': 0.4, 'sunalt': -1.1} 

61 

62 rng = np.random.RandomState(88) 

63 n_obj = 10 

64 rr = rng.random_sample(n_obj)*radius 

65 theta = rng.random_sample(n_obj)*2.0*np.pi 

66 ra_list = raCenter + rr*np.cos(theta) 

67 dec_list = decCenter + rr*np.sin(theta) 

68 t0_list = 0.5*rng.random_sample(n_obj) 

69 x0_list = rng.random_sample(n_obj)*1.0e-4 

70 x1_list = rng.random_sample(n_obj) 

71 c_list = rng.random_sample(n_obj)*2.0 

72 z_list = rng.random_sample(n_obj)*1.1 + 0.1 

73 

74 txt_file_name = tempfile.mktemp(dir=ROOT, prefix='test_phosim_sn_source', suffix='.txt') 

75 

76 dtype = np.dtype([('id', int), ('snra', float), ('sndec', float), 

77 ('t0', float), ('x0', float), ('x1', float), 

78 ('c', float), ('redshift', float), ('galtileid', int)]) 

79 

80 with open(txt_file_name, 'w') as output_file: 

81 for ix, (ra, dec, t0, x0, x1, c, z) in enumerate(zip(ra_list, dec_list, t0_list, x0_list, 

82 x1_list, c_list, z_list)): 

83 output_file.write('%d %e %e %e %e %e %e %e %d\n' % 

84 (ix, ra, dec, t0, x0, x1, c, z, ix)) 

85 

86 class testSNDBObj(SNDBObj, fileDBObject): 

87 tableid = 'test' 

88 

89 def query_columns(self, *args, **kwargs): 

90 return fileDBObject.query_columns(self, *args, **kwargs) 

91 

92 dbobj = testSNDBObj(txt_file_name, runtable='test', dtype=dtype) 

93 

94 if os.path.exists(txt_file_name): 

95 os.unlink(txt_file_name) 

96 

97 return dbobj, obs 

98 

99 

100test_header_map = {'dist2moon': ('dist2moon', np.degrees), 

101 'moonalt': ('moonalt', np.degrees), 

102 'moondec': ('moondec', np.degrees), 

103 'moonra': ('moonra', np.degrees), 

104 'rottelpos': ('rottelpos', np.degrees), 

105 'sunalt': ('sunalt', np.degrees)} 

106 

107 

108def setup_module(module): 

109 lsst.utils.tests.init() 

110 

111 

112class PhoSimCatalogTest(unittest.TestCase): 

113 

114 longMessage = True 

115 

116 @classmethod 

117 def setUpClass(cls): 

118 cls.scratch_dir = tempfile.mkdtemp(dir=ROOT, prefix='PhoSimCatalogTest-') 

119 

120 @classmethod 

121 def tearDownClass(cls): 

122 sims_clean_up() 

123 if os.path.exists(cls.scratch_dir): 

124 shutil.rmtree(cls.scratch_dir, ignore_errors=True) 

125 

126 def setUp(self): 

127 self.tempDB = os.path.join(self.scratch_dir, 'PhoSimTestDatabase.db') 

128 self.obs_metadata = makePhoSimTestDB(size=10, filename=self.tempDB) 

129 self.bulgeDB = testGalaxyBulgeDBObj(driver='sqlite', database=self.tempDB) 

130 self.diskDB = testGalaxyDiskDBObj(driver='sqlite', database=self.tempDB) 

131 self.agnDB = testGalaxyAgnDBObj(driver='sqlite', database=self.tempDB) 

132 self.starDB = testStarsDBObj(driver='sqlite', database=self.tempDB) 

133 filter_translation = {'u': 0, 'g': 1, 'r': 2, 'i': 3, 'z': 4, 'y': 5} 

134 alt, az, pa = altAzPaFromRaDec(self.obs_metadata.pointingRA, 

135 self.obs_metadata.pointingDec, 

136 self.obs_metadata, includeRefraction=False) 

137 self.control_header = ['moondec %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['moondec']), 

138 'rottelpos %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['rottelpos']), 

139 'declination %.17f\n' % self.obs_metadata.pointingDec, 

140 'moonalt %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['moonalt']), 

141 'rotskypos %.17f\n' % self.obs_metadata.rotSkyPos, 

142 'moonra %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['moonra']), 

143 'sunalt %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['sunalt']), 

144 'mjd %.17f\n' % (self.obs_metadata.mjd.TAI+16.5/86400.0), 

145 'azimuth %.17f\n' % az, 

146 'rightascension %.17f\n' % self.obs_metadata.pointingRA, 

147 'dist2moon %.7f\n' % np.degrees(self.obs_metadata.OpsimMetaData['dist2moon']), 

148 'filter %d\n' % filter_translation[self.obs_metadata.bandpass], 

149 'altitude %.17f\n' % alt] 

150 

151 def tearDown(self): 

152 del self.starDB 

153 del self.bulgeDB 

154 del self.diskDB 

155 del self.agnDB 

156 if os.path.exists(self.tempDB): 

157 os.unlink(self.tempDB) 

158 

159 def verify_catalog(self, file_name): 

160 """ 

161 Verify that the catalog specified by file_name has the expected header and is not empty 

162 """ 

163 with open(file_name, 'r') as input_file: 

164 lines = input_file.readlines() 

165 for control_line in self.control_header: 

166 self.assertIn(control_line, lines) 

167 

168 self.assertGreater(len(lines), len(self.control_header)+3) 

169 

170 def testSpecFileMap(self): 

171 """ 

172 Test that the PhoSim InstanceCatalog SpecFileMaps map MLT dwarf spectra 

173 to the starSED/phoSimMLT/ directory (that is where the MLT spectra which 

174 have been clipped to honor PhoSim's 'no more than 24,999 lines per SED 

175 file' requirement reside) 

176 """ 

177 

178 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=self.obs_metadata) 

179 self.assertEqual(cat.specFileMap['lte_123.txt'], 'starSED/phoSimMLT/lte_123.txt.gz') 

180 self.assertEqual(cat.specFileMap['lte_123.txt.gz'], 'starSED/phoSimMLT/lte_123.txt.gz') 

181 self.assertNotEqual(cat.specFileMap['lte_123.txt'], defaultSpecMap['lte_123.txt']) 

182 

183 # verify that the usual stellar mappings still apply 

184 for test_name in ('kp_123.txt', 'km_123.txt', 'Const_123.txt', 'Exp_123.txt', 'Burst_123.txt', 

185 'bergeron_123.txt', 'burrows_123.txt', 'm1_123.txt', 'L1_123.txt', 'l1_123.txt', 

186 'Inst_123.txt'): 

187 

188 self.assertEqual(cat.specFileMap[test_name], defaultSpecMap[test_name]) 

189 

190 def test_incomplete_obs(self): 

191 """ 

192 Test that an exception gets raised if you try to make a PhoSim InstanceCatalog 

193 with an ObservationMetaData that lacks RA, Dec, mjd, bandpass, or rotSkyPos 

194 """ 

195 obs = ObservationMetaData(pointingDec=19.0, mjd=43000.0, rotSkyPos=19.0, bandpassName='u') 

196 with self.assertRaises(TypeError): 

197 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

198 cat.phoSimHeaderMap = {} 

199 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

200 cat.write_catalog(catName) 

201 

202 obs = ObservationMetaData(pointingRA=19.0, mjd=43000.0, rotSkyPos=19.0, bandpassName='u') 

203 with self.assertRaises(TypeError): 

204 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

205 cat.phoSimHeaderMap = {} 

206 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

207 cat.write_catalog(catName) 

208 

209 obs = ObservationMetaData(pointingRA=88.0, pointingDec=19.0, rotSkyPos=19.0, bandpassName='u') 

210 with self.assertRaises(RuntimeError): 

211 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

212 cat.phoSimHeaderMap = {} 

213 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

214 cat.write_catalog(catName) 

215 

216 obs = ObservationMetaData(pointingRA=88.0, pointingDec=19.0, mjd=43000.0, bandpassName='u') 

217 with self.assertRaises(TypeError): 

218 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

219 cat.phoSimHeaderMap = {} 

220 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

221 cat.write_catalog(catName) 

222 

223 obs = ObservationMetaData(pointingRA=88.0, pointingDec=19.0, mjd=43000.0, rotSkyPos=19.0) 

224 with self.assertRaises(KeyError): 

225 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

226 cat.phoSimHeaderMap = {} 

227 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

228 cat.write_catalog(catName) 

229 

230 obs = ObservationMetaData(pointingRA=88.0, pointingDec=19.0, mjd=43000.0, rotSkyPos=19.0, 

231 bandpassName='u') 

232 

233 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=obs) 

234 cat.phoSimHeaderMap = {} 

235 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

236 cat.write_catalog(catName) 

237 

238 def testCatalog(self): 

239 """ 

240 This test writes a PhoSim input catalog and compares it, one line at a time 

241 to a previously written catalog that should be identical. 

242 """ 

243 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata = self.obs_metadata) 

244 testDisk = PhoSimCatalogSersic2D(self.diskDB, obs_metadata = self.obs_metadata) 

245 testAgn = PhoSimCatalogZPoint(self.agnDB, obs_metadata = self.obs_metadata) 

246 testStar = PhoSimCatalogPoint(self.starDB, obs_metadata = self.obs_metadata) 

247 

248 testBulge.phoSimHeaderMap = test_header_map 

249 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

250 testBulge.write_catalog(catName) 

251 testDisk.write_catalog(catName, write_header=False, write_mode='a') 

252 testAgn.write_catalog(catName, write_header=False, write_mode='a') 

253 testStar.write_catalog(catName, write_header=False, write_mode='a') 

254 

255 self.verify_catalog(catName) 

256 

257 def testHeaderMap(self): 

258 """ 

259 Test the behavior of the phoSimHeaderMap 

260 """ 

261 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

262 testBulge.phoSimHeaderMap = {'lunar_distance': ('dist2moon', None), 

263 'rotation_of_the_telescope': ('rottelpos', np.degrees), 

264 'other_rotation': ('rottelpos', lambda x: x*x)} 

265 

266 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

267 testBulge.write_catalog(catName) 

268 

269 with open(catName, 'r') as input_file: 

270 input_header = {} 

271 for line in input_file: 

272 vv = line.split() 

273 if vv[0] != 'object': 

274 input_header[vv[0]] = vv[1] 

275 else: 

276 break 

277 

278 self.assertIn('rightascension', input_header) 

279 self.assertIn('declination', input_header) 

280 self.assertIn('altitude', input_header) 

281 self.assertIn('azimuth', input_header) 

282 self.assertIn('filter', input_header) 

283 self.assertIn('rotskypos', input_header) 

284 self.assertIn('mjd', input_header) 

285 self.assertIn('lunar_distance', input_header) 

286 self.assertAlmostEqual(float(input_header['lunar_distance']), 

287 self.obs_metadata.OpsimMetaData['dist2moon'], 6) 

288 self.assertIn('rotation_of_the_telescope', input_header) 

289 self.assertAlmostEqual(float(input_header['rotation_of_the_telescope']), 

290 np.degrees(self.obs_metadata.OpsimMetaData['rottelpos']), 

291 delta=1.0e-6*np.degrees(self.obs_metadata.OpsimMetaData['rottelpos'])) 

292 self.assertIn('other_rotation', input_header) 

293 self.assertAlmostEqual(float(input_header['other_rotation']), 

294 self.obs_metadata.OpsimMetaData['rottelpos']**2, 

295 delta=1.0e-6*self.obs_metadata.OpsimMetaData['rottelpos']**2) 

296 self.assertEqual(len(input_header), 10) 

297 

298 def testBlankHeaderMap(self): 

299 """ 

300 Test behavior of a blank header map 

301 """ 

302 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

303 testBulge.phoSimHeaderMap = {} 

304 

305 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

306 testBulge.write_catalog(catName) 

307 

308 with open(catName, 'r') as input_file: 

309 input_header = {} 

310 for line in input_file: 

311 vv = line.split() 

312 if vv[0] != 'object': 

313 input_header[vv[0]] = vv[1] 

314 else: 

315 break 

316 

317 # verify that only the default header parameters are included in the 

318 # PhoSimInstanceCatalog, even though obs_metadata has a non-None 

319 # OpsimMetaData 

320 self.assertIn('rightascension', input_header) 

321 self.assertIn('declination', input_header) 

322 self.assertIn('altitude', input_header) 

323 self.assertIn('azimuth', input_header) 

324 self.assertIn('filter', input_header) 

325 self.assertIn('rotskypos', input_header) 

326 self.assertIn('mjd', input_header) 

327 self.assertEqual(len(input_header), 7) 

328 self.assertGreater(len(self.obs_metadata.OpsimMetaData), 0) 

329 

330 def testNoHeaderMap(self): 

331 """ 

332 Test that the correct error is raised if no header map is specified 

333 """ 

334 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

335 

336 with self.assertRaises(RuntimeError) as context: 

337 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

338 testBulge.write_catalog(catName) 

339 

340 self.assertIn("without specifying a phoSimHeaderMap", 

341 context.exception.args[0]) 

342 

343 if os.path.exists(catName): 

344 os.unlink(catName) 

345 

346 # now make sure that the exception is raised, even if ObservationMetaData 

347 # does not have an OpsimMetaData 

348 obs = ObservationMetaData(pointingRA=35.0, pointingDec=-23.0, 

349 mjd=43900.0, rotSkyPos=22.0, 

350 boundType='circle', boundLength=1.75) 

351 

352 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=obs) 

353 with self.assertRaises(RuntimeError) as context: 

354 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

355 testBulge.write_catalog(catName) 

356 

357 if os.path.exists(catName): 

358 os.unlink(catName) 

359 

360 self.assertIn("without specifying a phoSimHeaderMap", 

361 context.exception.args[0]) 

362 self.assertIn("you may wish to consider adding default PhoSim parameters", 

363 context.exception.args[0]) 

364 

365 def test_default_values_in_header_map(self): 

366 """ 

367 Test that default PhoSim header values in the header map get appropriately applied 

368 """ 

369 test_header_map = {'lunar_distance': ('dist2moon', None), 

370 'nsnap': 3} 

371 

372 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

373 testBulge.phoSimHeaderMap = test_header_map 

374 

375 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

376 testBulge.write_catalog(catName) 

377 

378 with open(catName, 'r') as input_file: 

379 input_header = {} 

380 for line in input_file: 

381 vv = line.split() 

382 if vv[0] != 'object': 

383 input_header[vv[0]] = vv[1] 

384 else: 

385 break 

386 

387 self.assertIn('rightascension', input_header) 

388 self.assertIn('declination', input_header) 

389 self.assertIn('altitude', input_header) 

390 self.assertIn('azimuth', input_header) 

391 self.assertIn('filter', input_header) 

392 self.assertIn('rotskypos', input_header) 

393 self.assertIn('mjd', input_header) 

394 self.assertIn('lunar_distance', input_header) 

395 self.assertAlmostEqual(float(input_header['lunar_distance']), 

396 self.obs_metadata.OpsimMetaData['dist2moon'], 6) 

397 self.assertIn('nsnap', input_header) 

398 self.assertEqual(int(input_header['nsnap']), 3) 

399 self.assertEqual(len(input_header), 9) 

400 

401 def test_non_existent_values_in_header_map(self): 

402 """ 

403 Test that header params that are defined in the header map but not 

404 in OpsimMetaData are ommitted from the header 

405 """ 

406 test_header_map = {'lunar_distance': ('dist2moon', None), 

407 'nsnap': 3, 

408 'nonesense': ('gobbledygook', lambda x: 2.0*x)} 

409 

410 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

411 testBulge.phoSimHeaderMap = test_header_map 

412 

413 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

414 testBulge.write_catalog(catName) 

415 

416 with open(catName, 'r') as input_file: 

417 input_header = {} 

418 for line in input_file: 

419 vv = line.split() 

420 if vv[0] != 'object': 

421 input_header[vv[0]] = vv[1] 

422 else: 

423 break 

424 

425 self.assertIn('rightascension', input_header) 

426 self.assertIn('declination', input_header) 

427 self.assertIn('altitude', input_header) 

428 self.assertIn('azimuth', input_header) 

429 self.assertIn('filter', input_header) 

430 self.assertIn('rotskypos', input_header) 

431 self.assertIn('mjd', input_header) 

432 self.assertIn('lunar_distance', input_header) 

433 self.assertAlmostEqual(float(input_header['lunar_distance']), 

434 self.obs_metadata.OpsimMetaData['dist2moon'], 6) 

435 self.assertIn('nsnap', input_header) 

436 self.assertEqual(int(input_header['nsnap']), 3) 

437 self.assertEqual(len(input_header), 9) 

438 

439 # now try it with no OpsimMetaData at all 

440 obs = ObservationMetaData(pointingRA=23.0, pointingDec=-11.0, 

441 mjd=43000.0, rotSkyPos=44.0, 

442 bandpassName='g', 

443 boundType='circle', boundLength=1.0) 

444 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=obs) 

445 testBulge.phoSimHeaderMap = test_header_map 

446 with lsst.utils.tests.getTempFilePath('.txt') as catName: 

447 testBulge.write_catalog(catName) 

448 

449 with open(catName, 'r') as input_file: 

450 input_header = {} 

451 for line in input_file: 

452 vv = line.split() 

453 if vv[0] != 'object': 

454 input_header[vv[0]] = vv[1] 

455 else: 

456 break 

457 

458 self.assertIn('rightascension', input_header) 

459 self.assertIn('declination', input_header) 

460 self.assertIn('altitude', input_header) 

461 self.assertIn('azimuth', input_header) 

462 self.assertIn('filter', input_header) 

463 self.assertIn('rotskypos', input_header) 

464 self.assertIn('mjd', input_header) 

465 self.assertIn('nsnap', input_header) 

466 self.assertEqual(int(input_header['nsnap']), 3) 

467 self.assertEqual(len(input_header), 8) 

468 

469 def testCompoundCatalog(self): 

470 """ 

471 This test writes a PhoSim input catalog and compares it, one line at a time 

472 to a previously written catalog that should be identical. 

473 

474 This test uses CompoundInstanceCatalog 

475 """ 

476 

477 # first, generate the catalog without a CompoundInstanceCatalog 

478 single_catName = tempfile.mktemp(dir=ROOT, prefix='phoSimTestCatalog_single', 

479 suffix='.txt') 

480 

481 testBulge = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata = self.obs_metadata) 

482 testDisk = PhoSimCatalogSersic2D(self.diskDB, obs_metadata = self.obs_metadata) 

483 testAgn = PhoSimCatalogZPoint(self.agnDB, obs_metadata = self.obs_metadata) 

484 testStar = PhoSimCatalogPoint(self.starDB, obs_metadata = self.obs_metadata) 

485 

486 testBulge.phoSimHeaderMap = test_header_map 

487 testBulge.write_catalog(single_catName) 

488 testDisk.write_catalog(single_catName, write_header=False, write_mode='a') 

489 testAgn.write_catalog(single_catName, write_header=False, write_mode='a') 

490 testStar.write_catalog(single_catName, write_header=False, write_mode='a') 

491 

492 # now, generate the catalog using CompoundInstanceCatalog 

493 # 

494 # because the CompoundCatalogDBObject requires that database 

495 # connection parameters be set in the input CatalogDBObject 

496 # daughter class definitions, we have to declare dummy 

497 # CatalogDBObject daughter classes below 

498 

499 class dummyDBbase(object): 

500 driver = 'sqlite' 

501 database = 'PhoSimTestDatabase.db' 

502 

503 dummyDBbase.database = self.tempDB 

504 

505 class dummyBulgeDB(dummyDBbase, testGalaxyBulgeDBObj): 

506 objid = 'dummy_bulge' 

507 

508 class dummyDiskDB(dummyDBbase, testGalaxyDiskDBObj): 

509 objid = 'dummy_disk' 

510 

511 class dummyAgnDB(dummyDBbase, testGalaxyAgnDBObj): 

512 objid = 'dummy_agn' 

513 

514 class dummyStarDB(dummyDBbase, testStarsDBObj): 

515 objid = 'dummy_stars' 

516 

517 compoundCatalog = CompoundInstanceCatalog([PhoSimCatalogSersic2D, PhoSimCatalogSersic2D, 

518 PhoSimCatalogZPoint, PhoSimCatalogPoint], 

519 [dummyBulgeDB, dummyDiskDB, dummyAgnDB, dummyStarDB], 

520 obs_metadata=self.obs_metadata) 

521 

522 self.assertEqual(len(compoundCatalog._dbObjectGroupList[0]), 3) 

523 

524 compound_catName = tempfile.mktemp(dir=ROOT, prefix='phoSimTestCatalog_compound', 

525 suffix='.txt') 

526 

527 compoundCatalog.phoSimHeaderMap = test_header_map 

528 compoundCatalog.write_catalog(compound_catName) 

529 

530 # verify that the compound catalog is what we expect 

531 self.verify_catalog(compound_catName) 

532 

533 # verify that the two catalogs are equivalent 

534 with open(single_catName, 'r') as single_file: 

535 with open(compound_catName, 'r') as compound_file: 

536 single_lines = single_file.readlines() 

537 compound_lines = compound_file.readlines() 

538 

539 for line in single_lines: 

540 self.assertIn(line, compound_lines) 

541 

542 for line in compound_lines: 

543 self.assertIn(line, single_lines) 

544 

545 if os.path.exists(compound_catName): 

546 os.unlink(compound_catName) 

547 

548 if os.path.exists(single_catName): 

549 os.unlink(single_catName) 

550 

551 def testPointSourceSchema(self): 

552 """ 

553 Create a PhoSim InstanceCatalog of point sources (stars). Verify 

554 that the schema of the actual objects conforms to what PhoSim expects, 

555 as defined here 

556 

557 https://bitbucket.org/phosim/phosim_release/wiki/Instance%20Catalog 

558 """ 

559 cat = PhoSimCatalogPoint(self.starDB, obs_metadata=self.obs_metadata) 

560 cat.phoSimHeaderMap = test_header_map 

561 

562 with lsst.utils.tests.getTempFilePath('.txt') as cat_name: 

563 cat.write_catalog(cat_name) 

564 

565 with open(cat_name, 'r') as input_file: 

566 cat_lines = input_file.readlines() 

567 

568 n_obj = 0 

569 for line in cat_lines: 

570 params = line.split() 

571 if len(params) > 2: 

572 n_obj += 1 

573 self.assertEqual(len(params), 17) 

574 self.assertEqual(params[0], 'object') 

575 self.assertEqual(round(float(params[1])), float(params[1]), 10) # id 

576 float(params[2]) # ra 

577 float(params[3]) # dec 

578 float(params[4]) # mag norm 

579 self.assertIn('starSED', params[5]) # sed name 

580 self.assertAlmostEqual(float(params[6]), 0.0, 10) # redshift 

581 self.assertAlmostEqual(float(params[7]), 0.0, 10) # gamma1 

582 self.assertAlmostEqual(float(params[8]), 0.0, 10) # gamma2 

583 self.assertAlmostEqual(float(params[9]), 0.0, 10) # kappa 

584 self.assertAlmostEqual(float(params[10]), 0.0, 10) # delta_ra 

585 self.assertAlmostEqual(float(params[11]), 0.0, 10) # delta_dec 

586 self.assertEqual(params[12], 'point') # source type 

587 dust_msg = ('It is possible you are outputting Milky Way dust parameters before ' 

588 'internal dust parameters; internal dust should come first') 

589 self.assertEqual(params[13], 'none', msg=dust_msg) # internal dust 

590 self.assertEqual(params[14], 'CCM', msg=dust_msg) # Milky Way dust 

591 self.assertGreater(float(params[15]), 0.0, msg=dust_msg) # Av 

592 self.assertAlmostEqual(float(params[16]), 3.1, msg=dust_msg) # Rv 

593 

594 self.assertGreater(n_obj, 0) 

595 

596 def testSersicSchema(self): 

597 """ 

598 Create a PhoSim InstanceCatalog of Sersic profiles (galaxy bulges). Verify 

599 that the schema of the actual objects conforms to what PhoSim expects, 

600 as defined here 

601 

602 https://bitbucket.org/phosim/phosim_release/wiki/Instance%20Catalog 

603 """ 

604 cat = PhoSimCatalogSersic2D(self.bulgeDB, obs_metadata=self.obs_metadata) 

605 cat.phoSimHeaderMap = test_header_map 

606 

607 with lsst.utils.tests.getTempFilePath('.txt') as cat_name: 

608 cat.write_catalog(cat_name) 

609 

610 with open(cat_name, 'r') as input_file: 

611 cat_lines = input_file.readlines() 

612 

613 n_obj = 0 

614 for line in cat_lines: 

615 params = line.split() 

616 if len(params) > 2: 

617 n_obj += 1 

618 self.assertEqual(len(params), 23) 

619 self.assertEqual(params[0], 'object') 

620 self.assertEqual(round(float(params[1])), float(params[1]), 10) # id 

621 float(params[2]) # ra 

622 float(params[3]) # dec 

623 float(params[4]) # mag norm 

624 self.assertIn('galaxySED', params[5]) # sed name 

625 self.assertGreater(float(params[6]), 0.0, 10) # redshift 

626 self.assertAlmostEqual(float(params[7]), 0.0, 10) # gamma1 

627 self.assertAlmostEqual(float(params[8]), 0.0, 10) # gamma2 

628 self.assertAlmostEqual(float(params[9]), 0.0, 10) # kappa 

629 self.assertAlmostEqual(float(params[10]), 0.0, 10) # delta_ra 

630 self.assertAlmostEqual(float(params[11]), 0.0, 10) # delta_dec 

631 self.assertEqual(params[12], 'sersic2d') # source type 

632 self.assertGreater(float(params[13]), 0.0) # major axis 

633 self.assertGreater(float(params[14]), 0.0) # minor axis 

634 self.assertGreater(float(params[15]), 0.0) # position angle 

635 self.assertAlmostEqual(float(params[16]), 4.0, 13) # n_s (bulges have sersic index=4) 

636 self.assertEqual(params[17], 'CCM') # internal dust 

637 dust_msg = ('It is possible you are outputting Milky Way dust parameters before ' 

638 'internal dust parameters; internal dust should come first') 

639 self.assertLess(float(params[18]), 0.31, msg=dust_msg) # Av 

640 self.assertLess(float(params[19]), 2.11, msg=dust_msg) # Rv 

641 self.assertEqual(params[20], 'CCM') # Milky Way dust 

642 self.assertGreater(float(params[21]), 0.0, msg=dust_msg) # Av 

643 self.assertAlmostEqual(float(params[22]), 3.1, msg=dust_msg) # Rv 

644 

645 self.assertGreater(n_obj, 0) 

646 

647 def testZPointSourceSchema(self): 

648 """ 

649 Create a PhoSim InstanceCatalog of extra-galactic point sources (agns). Verify 

650 that the schema of the actual objects conforms to what PhoSim expects, 

651 as defined here 

652 

653 https://bitbucket.org/phosim/phosim_release/wiki/Instance%20Catalog 

654 """ 

655 cat = PhoSimCatalogZPoint(self.agnDB, obs_metadata=self.obs_metadata) 

656 cat.phoSimHeaderMap = test_header_map 

657 

658 with lsst.utils.tests.getTempFilePath('.txt') as cat_name: 

659 cat.write_catalog(cat_name) 

660 

661 with open(cat_name, 'r') as input_file: 

662 cat_lines = input_file.readlines() 

663 

664 n_obj = 0 

665 for line in cat_lines: 

666 params = line.split() 

667 if len(params) > 2: 

668 n_obj += 1 

669 self.assertEqual(len(params), 17) 

670 self.assertEqual(params[0], 'object') 

671 self.assertEqual(round(float(params[1])), float(params[1]), 10) # id 

672 float(params[2]) # ra 

673 float(params[3]) # dec 

674 float(params[4]) # mag norm 

675 self.assertIn('agnSED', params[5]) # sed name 

676 self.assertGreater(float(params[6]), 0.0) # redshift 

677 self.assertAlmostEqual(float(params[7]), 0.0, 10) # gamma1 

678 self.assertAlmostEqual(float(params[8]), 0.0, 10) # gamma2 

679 self.assertAlmostEqual(float(params[9]), 0.0, 10) # kappa 

680 self.assertAlmostEqual(float(params[10]), 0.0, 10) # delta_ra 

681 self.assertAlmostEqual(float(params[11]), 0.0, 10) # delta_dec 

682 self.assertEqual(params[12], 'point') # source type 

683 dust_msg = ('It is possible you are outputting Milky Way dust parameters before ' 

684 'internal dust parameters; internal dust should come first') 

685 self.assertEqual(params[13], 'none', msg=dust_msg) # internal dust 

686 self.assertEqual(params[14], 'CCM', msg=dust_msg) # Milky Way dust 

687 self.assertGreater(float(params[15]), 0.0, msg=dust_msg) # Av 

688 self.assertAlmostEqual(float(params[16]), 3.1, msg=dust_msg) # Rv 

689 

690 self.assertGreater(n_obj, 0) 

691 

692 @unittest.skipIf(_skip_sn_tests, "cannot properly load astropy config dir") 

693 def testSNSchema(self): 

694 """ 

695 Create a PhoSim InstanceCatalog of supernovae. Verify 

696 that the schema of the actual objects conforms to what PhoSim expects, 

697 as defined here 

698 

699 https://bitbucket.org/phosim/phosim_release/wiki/Instance%20Catalog 

700 """ 

701 db, obs = createTestSNDB() 

702 cat = PhoSimCatalogSN(db, obs_metadata=obs) 

703 cat.writeSEDFile = False 

704 cat.phoSimHeaderMap = test_header_map 

705 

706 with lsst.utils.tests.getTempFilePath('.txt') as cat_name: 

707 cat.write_catalog(cat_name) 

708 

709 with open(cat_name, 'r') as input_file: 

710 cat_lines = input_file.readlines() 

711 

712 n_obj = 0 

713 for line in cat_lines: 

714 params = line.split() 

715 if len(params) > 2: 

716 n_obj += 1 

717 self.assertEqual(len(params), 17) 

718 self.assertEqual(params[0], 'object') 

719 self.assertEqual(round(float(params[1])), float(params[1]), 10) # id 

720 float(params[2]) # ra 

721 float(params[3]) # dec 

722 float(params[4]) # mag norm 

723 self.assertIn('%s.dat' % obs.bandpass, params[5]) # sed name 

724 self.assertGreater(float(params[6]), 0.0) # redshift 

725 self.assertAlmostEqual(float(params[7]), 0.0, 10) # gamma1 

726 self.assertAlmostEqual(float(params[8]), 0.0, 10) # gamma2 

727 self.assertAlmostEqual(float(params[9]), 0.0, 10) # kappa 

728 self.assertAlmostEqual(float(params[10]), 0.0, 10) # delta_ra 

729 self.assertAlmostEqual(float(params[11]), 0.0, 10) # delta_dec 

730 self.assertEqual(params[12], 'point') # source type 

731 dust_msg = ('It is possible you are outputting Milky Way dust parameters before ' 

732 'internal dust parameters; internal dust should come first') 

733 self.assertEqual(params[13], 'none', msg=dust_msg) # internal dust 

734 self.assertEqual(params[14], 'CCM', msg=dust_msg) # Milky Way dust 

735 self.assertGreater(float(params[15]), 0.0, msg=dust_msg) # Av 

736 self.assertAlmostEqual(float(params[16]), 3.1, msg=dust_msg) # Rv 

737 

738 self.assertGreater(n_obj, 0) 

739 

740 def testSSMSchema(self): 

741 """ 

742 Create a PhoSim InstanceCatalog of point sources (stars) formatted by the 

743 PhoSimCatalogSSM class. Verify that the schema of the actual objects conforms 

744 to what PhoSim expects, as defined here 

745 

746 https://bitbucket.org/phosim/phosim_release/wiki/Instance%20Catalog 

747 """ 

748 cat = PhoSimCatalogSSM(self.starDB, obs_metadata=self.obs_metadata) 

749 cat.phoSimHeaderMap = test_header_map 

750 

751 with lsst.utils.tests.getTempFilePath('.txt') as cat_name: 

752 cat.write_catalog(cat_name) 

753 

754 with open(cat_name, 'r') as input_file: 

755 cat_lines = input_file.readlines() 

756 

757 n_obj = 0 

758 for line in cat_lines: 

759 params = line.split() 

760 if len(params) > 2: 

761 n_obj += 1 

762 self.assertEqual(len(params), 15) 

763 self.assertEqual(params[0], 'object') 

764 self.assertEqual(round(float(params[1])), float(params[1]), 10) # id 

765 float(params[2]) # ra 

766 float(params[3]) # dec 

767 float(params[4]) # mag norm 

768 self.assertIn('starSED', params[5]) # sed name 

769 self.assertAlmostEqual(float(params[6]), 0.0, 10) # redshift 

770 self.assertAlmostEqual(float(params[7]), 0.0, 10) # gamma1 

771 self.assertAlmostEqual(float(params[8]), 0.0, 10) # gamma2 

772 self.assertAlmostEqual(float(params[9]), 0.0, 10) # kappa 

773 self.assertAlmostEqual(float(params[10]), 0.0, 10) # delta_ra 

774 self.assertAlmostEqual(float(params[11]), 0.0, 10) # delta_dec 

775 self.assertEqual(params[12], 'point') # source type 

776 self.assertEqual(params[13], 'none') # internal dust 

777 self.assertEqual(params[14], 'none') # Milky Way dust 

778 

779 self.assertGreater(n_obj, 0) 

780 

781 

782class MemoryTestClass(lsst.utils.tests.MemoryTestCase): 

783 pass 

784 

785if __name__ == "__main__": 785 ↛ 786line 785 didn't jump to line 786, because the condition on line 785 was never true

786 lsst.utils.tests.init() 

787 unittest.main()