def test_filter_catalogue(self): """Test filtering of catalogues.""" cat = katpoint.Catalogue(add_specials=True, add_stars=True) cat = cat.filter(tags=['special', '~radec']) self.assertEqual(len(cat.targets), len(katpoint.specials), 'Number of targets incorrect') cat.add(self.flux_target) cat2 = cat.filter(flux_limit_Jy=50.0, flux_freq_MHz=1.5) self.assertEqual(len(cat2.targets), 1, 'Number of targets with sufficient flux should be 1') self.assertNotEqual(cat, cat2, 'Catalogues should be inequal') cat.add(katpoint.Target('Zenith, azel, 0, 90')) cat3 = cat.filter(az_limit_deg=[0, 180], timestamp=self.timestamp, antenna=self.antenna) self.assertEqual(len(cat3.targets), 2, 'Number of targets rising should be 2') cat4 = cat.filter(az_limit_deg=[180, 0], timestamp=self.timestamp, antenna=self.antenna) self.assertEqual(len(cat4.targets), 10, 'Number of targets setting should be 10') cat5 = cat.filter(el_limit_deg=85, timestamp=self.timestamp, antenna=self.antenna) self.assertEqual(len(cat5.targets), 1, 'Number of targets close to zenith should be 1') sun = katpoint.Target('Sun, special') cat6 = cat.filter(dist_limit_deg=[0.0, 1.0], proximity_targets=sun, timestamp=self.timestamp, antenna=self.antenna) self.assertEqual(len(cat6.targets), 1, 'Number of targets close to Sun should be 1')
def setUp(self): self.flux_model = katpoint.FluxDensityModel( '(1.0 2.0 2.0 0.0 0.0 0.0 0.0 0.0)') self.too_many_params = katpoint.FluxDensityModel( '(1.0 2.0 2.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0 0.0)') self.too_few_params = katpoint.FluxDensityModel('(1.0 2.0 2.0)') self.flux_target = katpoint.Target('radec, 0.0, 0.0, ' + self.flux_model.description) self.no_flux_target = katpoint.Target('radec, 0.0, 0.0')
def test_that_equality_and_hash_ignore_order(self): a = katpoint.Catalogue() b = katpoint.Catalogue() t1 = katpoint.Target('Nothing, special') t2 = katpoint.Target('Sun, special') a.add(t1) a.add(t2) b.add(t2) b.add(t1) self.assertEqual(a, b, 'Shuffled catalogues are not equal') self.assertEqual(hash(a), hash(b), 'Shuffled catalogues have different hashes')
def setUp(self): self.unit_model = katpoint.FluxDensityModel(100., 200., [0.]) self.unit_model2 = katpoint.FluxDensityModel(100., 200., [0.]) self.flux_model = katpoint.FluxDensityModel( '(1.0 2.0 2.0 0.0 0.0 0.0 0.0 0.0 2.0 0.5 0.25 -0.75)') with self.assertWarns(FutureWarning): self.too_many_params = katpoint.FluxDensityModel( '(1.0 2.0 2.0 0.0 0.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 0.0 0.0 0.0)' ) self.too_few_params = katpoint.FluxDensityModel('(1.0 2.0 2.0)') self.flux_target = katpoint.Target('radec, 0.0, 0.0, ' + self.flux_model.description) self.no_flux_target = katpoint.Target('radec, 0.0, 0.0')
def get_scan_area_extents(self, test_date): # Test Antenna: 0-m dish at lat 0:00:00.0, long 0:00:00.0, alt 0.0 m antenna = katpoint.Antenna("Test Antenna", 0, 0, 0) target_list = [ katpoint.Target("t1, radec, 05:16:00.0, -25:42:00.0", antenna=antenna), katpoint.Target("t2, radec, 05:16:00.0, -35:36:00.0", antenna=antenna), katpoint.Target("t3, radec, 06:44:00.0, -35:36:00.0", antenna=antenna), katpoint.Target("t4, radec, 06:44:00.0, -25:42:00.0", antenna=antenna), ] el, az_min, az_max, t_start, t_end = scans._get_scan_area_extents(target_list, antenna, test_date) return el, az_min, az_max, t_start, t_end
def test_present(self): catalogue = catalogue_from_telstate(self.telstate, self.cbid, self.continuum, katpoint.Target(_TRG_A)) assert_equal(len(catalogue), 2) assert_equal(catalogue.targets[0], katpoint.Target(_TRG_A)) assert_equal(catalogue.targets[1], katpoint.Target(_TRG_C)) catalogue = catalogue_from_telstate(self.telstate, self.cbid, self.continuum, katpoint.Target(_TRG_B)) assert_equal(len(catalogue), 1) assert_equal(catalogue.targets[0], katpoint.Target(_TRG_B))
def setUp(self): self.nchan = 32 self.spws = [{ 'centre_freq': .856e9 + .856e9 / 2., 'num_chans': self.nchan, 'channel_width': .856e9 / self.nchan, 'sideband': 1, 'band': 'L', }] self.target_names = ['Gunther Lord of the Gibichungs', 'Gunther\\Lord/of%the Gibichungs', 'Gutrune', 'Hagen'] # Construct 4 targets self.targets = [katpoint.Target("%s, radec, 100.0, -35.0" % t) for t in self.target_names] # Construct a 5th target with repeated name self.targets += [katpoint.Target("%s | %s, radec, 100.0, -35.0" % (self.target_names[2], self.target_names[3]))] # Set up varying scans self.scans = [('slew', 1, self.targets[0]), ('track', 3, self.targets[0]), ('slew', 2, self.targets[1]), ('track', 5, self.targets[1]), ('slew', 1, self.targets[2]), ('track', 8, self.targets[2]), ('slew', 2, self.targets[3]), ('track', 9, self.targets[3]), ('slew', 1, self.targets[4]), ('track', 10, self.targets[4])] # Setup the katdal selection, convert it to a string # accepted by our command line parser function, which # converts it back to a dict. select = { 'scans': 'track', 'corrprods': 'cross', 'pol': 'HH,VV', 'channels': slice(0, self.nchan), } assign_str = '; '.join('%s=%s' % (k, repr(v)) for k, v in select.items()) self.select = parse_python_assigns(assign_str) # Do some baseline averaging for funsies self.uvblavg_params = parse_python_assigns("FOV=1.0; avgFreq=1; " "chAvg=2; maxInt=2.0") # Run with imaging defaults self.mfimage_params = {'doGPU': False} # Expected target name in file output for the list of targets # constructed via normalise_target_name self.sanitised_target_names = ['Gunther_Lord_of_the_Gibichungs', 'Gunther_Lord_of_the_Gibichungs_1', 'Gutrune', 'Hagen', 'Gutrune_1']
def test_sequence(ants, disable_corrections=False, dry_run=False): # Disable ACU pointing corrections if disable_corrections: ants.req.ap_enable_point_error_systematic(False) ants.req.ap_enable_point_error_tiltmeter(False) if not dry_run: try: ants.wait('ap.enable-point-error-systematic', False, timeout=1) ants.wait('ap.enable-point-error-tiltmeter', False, timeout=1) except: user_logger.error( "Failed to disable ACU pointing corrections.") raise user_logger.warning("ACU pointing corrections have been disabled.") for azim in [-45, 45, 135, 225]: # Start at low elevation elev = 20 # Set this target for the receptor target sensor target = katpoint.Target('Name, azel, %s, %s' % (azim, elev)) user_logger.info("Starting position: '%s' ", target.description) if not dry_run: move_antennas(ants, azim, elev) # Move to high elevation elev = 80 # Set this target for the receptor target sensor target = katpoint.Target('Name, azel, %s, %s' % (azim, elev)) user_logger.info("Move to high elevation: '%s' ", target.description) if not dry_run: move_antennas(ants, azim, elev) # Wait for 10 minutes before moving to next position user_logger.info( "Dwell at high elevation for 10 minutes to check if indexer slips." ) time.sleep(600) # Return to low elevation elev = 20 # Set this target for the receptor target sensor target = katpoint.Target('Name, azel, %s, %s' % (azim, elev)) user_logger.info("Return to low elevation: '%s' ", target.description) if not dry_run: move_antennas(ants, azim, elev) user_logger.info("Sequence Completed!")
def test_construct_catalogue(self): """Test construction of catalogues.""" cat = katpoint.Catalogue(add_specials=True, add_stars=True, antenna=self.antenna) num_targets_original = len(cat) self.assertEqual(num_targets_original, len(katpoint.specials) + 1 + len(ephem.stars.stars), 'Number of targets incorrect') # Add target already in catalogue - no action cat.add(katpoint.Target('Sun, special')) num_targets = len(cat) self.assertEqual(num_targets, num_targets_original, 'Number of targets incorrect') cat2 = katpoint.Catalogue(add_specials=True, add_stars=True) cat2.add(katpoint.Target('Sun, special')) self.assertEqual(cat, cat2, 'Catalogues not equal') try: self.assertEqual(hash(cat), hash(cat2), 'Catalogue hashes not equal') except TypeError: self.fail('Catalogue object not hashable') # Add different targets with the same name cat2.add(katpoint.Target('Sun, special hot')) cat2.add(katpoint.Target('Sun | Sol, special')) self.assertEqual(len(cat2), num_targets_original + 2, 'Number of targets incorrect') cat2.remove('Sol') self.assertEqual(len(cat2), num_targets_original + 1, 'Number of targets incorrect') self.assertTrue(cat != cat2, 'Catalogues should not be equal') test_target = cat.targets[-1] self.assertEqual(test_target.description, cat[test_target.name].description, 'Lookup failed') self.assertEqual(cat['Non-existent'], None, 'Lookup of non-existent target failed') cat.add_tle(self.tle_lines, 'tle') cat.add_edb(self.edb_lines, 'edb') self.assertEqual(len(cat.targets), num_targets + 2, 'Number of targets incorrect') cat.remove(cat.targets[-1].name) self.assertEqual(len(cat.targets), num_targets + 1, 'Number of targets incorrect') closest_target, dist = cat.closest_to(test_target) self.assertEqual(closest_target.description, test_target.description, 'Closest target incorrect') self.assertAlmostEqual(dist, 0.0, places=5, msg='Target should be on top of itself')
def test_empty_dataset(self): """Test that a completely flagged dataset is exported without error""" nchan = 16 spws = [{ 'centre_freq': .856e9 + .856e9 / 2., 'num_chans': nchan, 'channel_width': .856e9 / nchan, 'sideband': 1, 'band': 'L', }] targets = [katpoint.Target("Flosshilde, radec, 0.0, -30.0")] # Set up a scan scans = [('track', 10, targets[0])] # Flag the data def mock_flags(dataset): return np.ones(dataset.shape, dtype=np.bool) # Create Mock dataset and wrap it in a KatdalAdapter ds = MockDataSet(timestamps=DEFAULT_TIMESTAMPS, subarrays=DEFAULT_SUBARRAYS, spws=spws, dumps=scans, flags=mock_flags) with obit_context(): pipeline = pipeline_factory('offline', ds) pipeline._select_and_infer_files() pipeline._export_and_merge_scans()
def raster_scan(ants,target, num_scans=3, scan_duration=30.0, scan_extent=6.0, scan_spacing=0.5, scan_in_azimuth=True, projection=('ARC', 0., 0.), dry_run=False): # Create references to allow easy copy-and-pasting from this function # Convert description string to target object, or keep object as is if not isinstance(target, katpoint.Target): target = katpoint.Target(target) user_logger.info("Initiating raster scan (%d %g-second scans extending %g degrees) on target '%s'" % (num_scans, scan_duration, scan_extent, target.name)) # Create start and end positions of each scan, based on scan parameters scan_levels = np.arange(-(num_scans // 2), num_scans // 2 + 1) scanning_coord = (scan_extent / 2.0) * (-1) ** scan_levels stepping_coord = scan_spacing * scan_levels # Flip sign of elevation offsets to ensure that the first scan always # starts at the top left of target scan_starts = zip(scanning_coord, -stepping_coord) if scan_in_azimuth else zip(stepping_coord, -scanning_coord) scan_ends = zip(-scanning_coord, -stepping_coord) if scan_in_azimuth else zip(stepping_coord, scanning_coord) # Perform multiple scans across the target for scan_index, (start, end) in enumerate(zip(scan_starts, scan_ends)): scan(ants,target, duration=scan_duration, start=start, end=end, index=scan_index, projection=projection,) return True
def creatBeamMatrix(antennaCoords, sourceCoord, observeTime, frequencies, duration, overlap, beamNum, size, resolution, subarray): if subarray != []: antennaKat = makeKatPointAntenna( [antennaCoords[int(ant)] for ant in subarray]) else: antennaKat = makeKatPointAntenna(antennaCoords) # boresight = sourceCoord boresight = katpoint.Target('boresight, radec, {}, {}'.format( sourceCoord[0], sourceCoord[1])) reference = makeKatPointAntenna([ "ref, -30:42:39.8, 21:26:38.0, 1035.0", ])[0] psf = PsfSim(antennaKat, frequencies[0]) beamShape = psf.get_beam_shape(boresight, observeTime, size * size, resolution) beamShape.plot_psf("beamWithFit.png", shape_overlay=True) beamShape.psf.write_fits('psf.fits') beamShape.plot_interferometry("interferometry.png") tiling = generate_nbeams_tiling(beamShape, beamNum, overlap=overlap) tiling_coordinats = tiling.get_equatorial_coordinates() tiling.plot_tiling("tiling.svg", index=True) np.savetxt("tilingCoord", tiling_coordinats) np.savetxt("tilingCoord_pixel", tiling.coordinates)
def test_catalogue_same_name(self): """"Test add() and remove() of targets with the same name.""" cat = katpoint.Catalogue() targets = ['Sun, special', 'Sun | Sol, special', 'Sun, special hot'] # Add various targets called Sun cat.add(targets[0]) self.assertEqual(cat['Sun'].description, targets[0]) cat.add(targets[0]) self.assertEqual(len(cat), 1, 'Did not ignore duplicate target') cat.add(targets[1]) self.assertEqual(cat['Sun'].description, targets[1]) cat.add(targets[2]) self.assertEqual(cat['Sun'].description, targets[2]) # Check length, iteration, membership self.assertEqual(len(cat), len(targets)) for n, t in enumerate(cat): self.assertEqual(t.description, targets[n]) self.assertIn('Sun', cat) self.assertIn('Sol', cat) for t in targets: self.assertIn(katpoint.Target(t), cat) # Remove targets one by one cat.remove('Sun') self.assertEqual(cat['Sun'].description, targets[1]) cat.remove('Sun') self.assertEqual(cat['Sun'].description, targets[0]) cat.remove('Sun') self.assertTrue( len(cat) == len(cat.targets) == len(cat.lookup) == 0, 'Catalogue not empty')
def test_construct_catalogue(self): """Test construction of catalogues.""" cat = katpoint.Catalogue(add_specials=True, add_stars=True, antenna=self.antenna) cat.add(katpoint.Target('Sun, special')) num_targets = len(cat) self.assertEqual(num_targets, len(katpoint.specials) + 1 + 94, 'Number of targets incorrect') self.assertEqual(cat, cat, 'Catalogue not equal to itself') test_target = cat.targets[0] self.assertEqual(test_target.description, cat[test_target.name].description, 'Lookup failed') self.assertEqual(cat['Non-existent'], None, 'Lookup of non-existent target failed') cat.add_tle(self.tle_lines, 'tle') cat.add_edb(self.edb_lines, 'edb') self.assertEqual(len(cat.targets), num_targets + 2, 'Number of targets incorrect') cat.remove(cat.targets[-1].name) self.assertEqual(len(cat.targets), num_targets + 1, 'Number of targets incorrect') closest_target, dist = cat.closest_to(test_target) self.assertEqual(closest_target.description, test_target.description, 'Closest target incorrect')
def setUp(self): self.nchan = 16 self.spws = [{ 'centre_freq': .856e9 + .856e9 / 2., 'num_chans': self.nchan, 'channel_width': .856e9 / self.nchan, 'sideband': 1, 'band': 'L', }] # Construct a target self.target_name = 'Beckmesser' self.target = katpoint.Target("%s, radec, 100.0, -35.0" % self.target_name) # Set up a track self.scans = [('track', 3, self.target), ('track', 3, self.target)] # Setup the katdal selection, convert it to a string # accepted by our command line parser function, which # converts it back to a dict. self.select = {'corrprods': 'cross', 'pol': 'HH,VV'} # Baseline averaging defaults self.uvblavg_params = parse_python_assigns("FOV=1.0; avgFreq=0; " "chAvg=1; maxInt=2.0") # Run with imaging defaults self.mfimage_params = {'doGPU': False, 'maxFBW': 0.25}
def targetlst(target_str): target = ",".join(["radec target"] + target_str) target = katpoint.Target(target).body rise_lst, set_lst = Observatory().target_rise_and_set_times(target) return ("Target ({}) rises at LST {} and sets at LST {}" .format(" ".join(target_str), rise_lst, set_lst))
def setUp(self): self.flux_target = katpoint.Target( 'flux, radec, 0.0, 0.0, (1.0 2.0 2.0 0.0 0.0)') self.antenna = katpoint.Antenna( 'XDM, -25:53:23.05075, 27:41:03.36453, 1406.1086, 15.0') self.antenna2 = katpoint.Antenna( 'XDM2, -25:53:23.05075, 27:41:03.36453, 1406.1086, 15.0, 100.0 0.0 0.0' ) self.timestamp = time.mktime( time.strptime('2009/06/14 12:34:56', '%Y/%m/%d %H:%M:%S'))
def setUp(self): self.target1 = katpoint.construct_azel_target('45:00:00.0', '75:00:00.0') self.target2 = katpoint.Target('Sun, special') self.ant1 = katpoint.Antenna('A1, -31.0, 18.0, 0.0, 12.0, 0.0 0.0 0.0') self.ant2 = katpoint.Antenna( 'A2, -31.0, 18.0, 0.0, 12.0, 10.0 -10.0 0.0') self.ant3 = katpoint.Antenna( 'A3, -31.0, 18.0, 0.0, 12.0, 5.0 10.0 3.0') self.ts = katpoint.Timestamp('2013-08-14 08:25') self.delays = katpoint.DelayCorrection([self.ant2, self.ant3], self.ant1, 1.285e9)
def stow_test(ants, taz, tel, dry_run=False): # send this target to the antenna. target = katpoint.Target('Name, azel, %s, %s' % (taz, tel)) if not dry_run: # Use slew to bypass pointing model ants.req.ap_slew(taz, tel) # Since we are not using the proxy mode we will have to explicitly wait # for the servo brakes to open and on-target sensor to update. time.sleep(4) user_logger.info("Starting target description: '%s' ", target.description) if not dry_run: try: ants.wait('ap.on-target', True, timeout=300) time.sleep(2) # Track for a bit to allow deacceleration except: user_logger.error("Timed out while waiting for AP to reach " "starting position.") raise user_logger.info("AP has reached start position, beginning stow test") user_logger.info("Activating receptor windstows") ants.req.set_windstow(1) ants.wait('ap.mode', 'stowed', timeout=120) # Wait a bit before clearing user_logger.info("Stow position reached. Monitoring for 20 seconds.") time.sleep(20) user_logger.info("Clearing receptor windstow condition") ants.req.set_windstow(0) ants.wait('mode', 'STOP', timeout=120) # Wait a bit and issue the windstow again to simulate wind picking up user_logger.info("Waiting 30 seconds before next 'gust'.") time.sleep(30) user_logger.info("Triggering 2nd windstow event.") ants.req.set_windstow(1) ants.wait('mode', 'STOW', timeout=120) user_logger.info("Montitoring for 20 seconds") # Reduced this time since we should already be up at stow position time.sleep(20) user_logger.info("Test concluded. Clearing windstow.") # Restore system to normal ants.req.set_windstow(0) ants.wait('mode', 'STOP', timeout=120)
def set_target(self, target): """Set the target. MeerKAT Wrapper around a PyEphem.Body object, target is an object that can be pointed at by an antenna. Parameters ---------- target: str A comma-separated description which contains parameters such as the target name, position, flux model. """ target = katpoint.Target(target) target.body.compute(self.observer) return target
def scan(ants, target, duration=30.0, start=(-3.0, 0.0), end=(3.0, 0.0), index=-1, dry_run=False,projection = ('ARC', 0., 0.)): # Convert description string to target object, or keep object as is if not isinstance(target, katpoint.Target): target = katpoint.Target(target) scan_name = 'scan' if index < 0 else 'scan %d' % (index,) user_logger.info("Initiating %g-second scan across target '%s'" % (duration, target.name)) # This already sets antennas in motion if in mode POINT set_target(ants, target) user_logger.info('slewing to start of %s', scan_name) # Move each antenna to the start position of the scan ants.req.scan_asym(start[0], start[1], end[0], end[1],duration, projection) ants.req.mode('POINT') # Wait until they are all in position (with 5 minute timeout) locks = 0 if not dry_run : for ant_x in ants: if ant_x.wait('lock', True, timeout=300): locks +=1 print "locks status:", ant_x.name , locks,len(ants) else: locks = len(ants) if len(ants)==locks: user_logger.info('start of %s reached' % (scan_name,)) if not dry_run : #time.sleep(duration) user_logger.info('performing %s' % (scan_name,)) # Start scanning the antennas ants.req.mode('SCAN') # Wait until they are all finished scanning (with 5 minute timeout) scanc = 0 for ant_x in ants: if ant_x.wait('scan_status', 'after', timeout=300): scanc +=1 print "scan status:", ant_x.name , scanc,len(ants) user_logger.info('%s complete' % (scan_name,)) return True else: user_logger.warning("Unable to Scan Target : %r Check %s sensors " % (target,','.join([ant.name for ant in ants]))) return False return True
def set_target(self, target, slew_only=False): """Set the target. MeerKAT Wrapper around a PyEphem.Body object, target is an object that can be pointed at by an antenna. Parameters ---------- target: str A comma-separated description which contains parameters such as the target name, position, flux model. slew_only : bool, optional True if only the antenna slews should be performed. """ target = katpoint.Target(target) target.body.compute(self.observer) return target
def source_solar_angle(catalogue, ref_antenna): date = ref_antenna.observer.date horizon = numpy.degrees(ref_antenna.observer.horizon) date = date.datetime().replace(hour=0, minute=0, second=0, microsecond=0) numdays = 365 date_list = [date - timedelta(days=x) for x in range(0, numdays)] sun = katpoint.Target('Sun, special') katpt_targets = catalogue.filter( ['~bpcal', '~fluxcal', '~polcal', '~gaincal', '~delaycal']) for cnt, katpt_target in enumerate(katpt_targets): plt.figure(figsize=(17, 7), facecolor='white') ax = plt.subplot(111) plt.subplots_adjust(right=0.8) fontP = FontProperties() fontP.set_size('small') solar_angle = [] for the_date in date_list: ref_antenna.observer.date = the_date sun.body.compute(ref_antenna.observer) katpt_target.body.compute(ref_antenna.observer) solar_angle.append( numpy.degrees(ephem.separation(sun.body, katpt_target.body))) myplot, = plt.plot_date(date_list, solar_angle, fmt='.', linewidth=0, label='{}'.format(katpt_target.name)) ax.axhspan(0., horizon, facecolor='k', alpha=0.2) box = ax.get_position() ax.set_position([box.x0, box.y0, box.width * 0.95, box.height]) plt.grid() plt.legend(loc='center left', bbox_to_anchor=(1, 0.5), prop={'size': 10}, numpoints=1) plt.ylabel('Solar Separation Angle (degrees)') ax.set_xticklabels(date_list[0::20], rotation=30, fontsize=10) ax.xaxis.set_major_formatter(mdates.DateFormatter("%b %d")) ax.xaxis.set_major_locator( mdates.DayLocator(bymonthday=range(30), interval=10)) ax.set_xlabel('Date')
def _create_test_metadata(target_names): targets = [katpoint.Target(f'{t}, radec, {100.0 + i}, -35') for i, t in enumerate(target_names)] target_metadata = {} used = [] for t in targets: target = normalise_target_name(t.name, used) used.append(target) with mock.patch('katacomb.aips_export._integration_time', return_value=80): with mock.patch('katacomb.img_facade.ImageFacade', autospec=True) as MockImage: MockImage.FArray.RMS = 1e-3 _update_target_metadata(target_metadata, MockImage, t, target, 'katds', target) scans = [('track', 3, targets[0]), ('track', 3, targets[1])] ds = MockDataSet(dumps=scans) metadata = _metadata(ds, '1234', target_metadata) return metadata
def get_stats(dataset: katdal.DataSet, telstate: katsdptelstate.TelescopeState) -> Tuple[CommonStats, List[TargetStats]]: common = CommonStats(dataset, telstate) stats = [TargetStats(dataset, common, katpoint.Target(target)) for target in telstate.get('targets', {})] stats_lookup = {target.description: target for target in stats} for ((target_desc, channel), status) in telstate.get('status', {}).items(): stats_lookup[target_desc].status[channel] = status for ((target_desc, channel), peak) in telstate.get('peak', {}).items(): stats_lookup[target_desc].peak[channel] = peak * (u.Jy / u.beam) for ((target_desc, channel, pol), total) in telstate.get('total', {}).items(): stats_lookup[target_desc].totals[pol][channel] = total * u.Jy for ((target_desc, channel), noise) in telstate.get('noise', {}).items(): stats_lookup[target_desc].noise[channel] = noise * (u.Jy / u.beam) for ((target_desc, channel), noise) in telstate.get('weights_noise', {}).items(): stats_lookup[target_desc].weights_noise[channel] = noise * (u.Jy / u.beam) for ((target_desc, channel), normalized_noise) in telstate.get('normalized_noise', {}).items(): stats_lookup[target_desc].normalized_noise[channel] = normalized_noise return common, stats
def select_and_average(filename, average_time): # Read a file into katdal, and average the data to the prescribed averaging time # Returns the weather data and timestamps with the correct averaging interval data = katdal.open(filename) raw_timestamps = data.sensor.timestamps raw_wind_speed = data.wind_speed raw_temperature = data.temperature raw_dumptime = data.dump_period # Get azel of each antenna and separation of each antenna sun = katpoint.Target('Sun, special', antenna=data.ants[0]) alltimestamps = data.timestamps[:] solar_seps = np.zeros_like(alltimestamps) for dumpnum, timestamp in enumerate(alltimestamps): azeltarget = katpoint.construct_azel_target( katpoint.deg2rad(data.az[dumpnum, 0]), katpoint.deg2rad(data.el[dumpnum, 0])) azeltarget.antenna = data.ants[0] solar_seps[dumpnum] = katpoint.rad2deg( azeltarget.separation(sun, timestamp)) #Determine number of dumps to average num_average = max(int(np.round(average_time / raw_dumptime)), 1) #Array of block indices indices = list( range(min(num_average, raw_timestamps.shape[0]), raw_timestamps.shape[0] + 1, min(num_average, raw_timestamps.shape[0]))) timestamps = np.average(np.array(np.split(raw_timestamps, indices)[:-1]), axis=1) wind_speed = np.average(np.array(np.split(raw_wind_speed, indices)[:-1]), axis=1) temperature = np.average(np.array(np.split(raw_temperature, indices)[:-1]), axis=1) dump_time = raw_dumptime * num_average return (timestamps, alltimestamps, wind_speed, temperature, dump_time, solar_seps, data.ants[0])
def make_katpoint_target(sources): """ check the the data type of the source. If the values are in (RA, DEC) pair, they will be converted to katpoint target object arguments: source -- source in either (RA, DEC) pairs or katpoint target objects return: katpoint target objects """ targets = [] for source in sources: target_string = ",".join([ 'radec', coord.angleToHour(source[0]), coord.angleToDEC(source[1]) ]) targets.append(katpoint.Target(target_string)) return targets
def make_pbeam_images(metadata, in_dir, write_tag): """Write primary beam corrected images. Make a single plane FITS image, a PNG and a thumbnail in a new directory per target. Write a new metadata file per target. Parameters ---------- metadata : dict dictionary containing pipeline metadata in_dir : str path containing pipeline output files write_tag : str tag appended to directory name to indicate it is still being written to """ filenames = metadata['FITSImageFilename'] for i, in_file in enumerate(filenames): kat_target = katpoint.Target(metadata['KatpointTargets'][i]) out_filebase = os.path.splitext(in_file)[0] out_filebase_pb = out_filebase + '_PB' log.info('Write primary beam corrected FITS output: %s', out_filebase_pb + FITS_EXT) in_path = os.path.join(in_dir + write_tag, in_file) pb_dir = _productdir(metadata, in_dir, i, '_PB', write_tag) os.mkdir(pb_dir) pbc_path = os.path.join(pb_dir, out_filebase_pb + FITS_EXT) bp = pbc.beam_pattern(in_path) raw_image = pbc.read_fits(in_path) pbc_image = pbc.primary_beam_correction(bp, raw_image, px_cut=0.1) pbc.write_new_fits(pbc_image, in_path, outputFilename=pbc_path) log.info('Write primary beam corrected PNG output: %s', out_filebase_pb + PNG_EXT) _caption_pngs(pb_dir, out_filebase_pb, kat_target, 'PB Corrected', contrast=PB_CONTRAST)
def validate_target(target_file): """ Validate all target strings from the supplied CSV file using katpoint.Target. Non-Ascii characters are shown as '?' and their positions are shown graphically. All separators are shown graphically if the maximum field count is exceeded. Parameters ---------- target_file : string A CSV file with multiple target strings Returns ------- target_validation_pass : bool Target validation status. """ target_validation_pass = True with open(target_file, 'r') as csv_file: for line in csv_file: if not line.strip().startswith('#') and (len(line.strip()) != 0): try: katpoint.Target(line) except katpoint.NonAsciiError: show_non_ascii(line) target_validation_pass = False except katpoint.FluxError as exception: show_separators(line, ',', exception) target_validation_pass = False except ValueError as exception: if line.strip() in str(exception): print("\nParsing Error!\n{}".format(exception)) else: print("\nParsing Error!\n{}\n{}".format( line, exception)) target_validation_pass = False return target_validation_pass
def test_multiple_ifs(self): """ Test splitting the band into multiple IFs. """ # One scan on a single target with a 16 channel band nchan = 16 spws = [{ 'centre_freq': .856e9 + .856e9 / 2., 'num_chans': nchan, 'channel_width': .856e9 / nchan, 'sideband': 1, 'band': 'L', }] targets = [katpoint.Target("Flosshilde, radec, 0.0, -30.0")] # Set up a scan scans = [('track', 10, targets[0])] ds = MockDataSet(timestamps=DEFAULT_TIMESTAMPS, subarrays=DEFAULT_SUBARRAYS, spws=spws, dumps=scans) ka = KatdalAdapter(ds) # Check ValueError is raised with indivisible number of Ifs. def check_bad_if(): ka.select(nif=5) def check_bad_if_export(): self._test_export_implementation(nif=3) self.assertRaises(ValueError, check_bad_if) self.assertRaises(ValueError, check_bad_if_export) # Test uv_export with 4 IFs self._test_export_implementation("uv_export", nif=4) self._test_export_implementation("continuum_export", nif=4)