def test_named(): frb121102 = FRB('FRB121102', 'J053158.7+330852.5', 558.1 * units.pc / units.cm**3, z_frb=0.19273) # Error ellipse frb121102.set_ee(0.1, 0.1, 0., 95.) assert isinstance(frb121102.eellipse, dict) # Pulse -- These are made up frb121102.set_pulse(1 * units.GHz, time_res=0.054 * units.ms, t0=0.66 * units.ms, Wi=1.1 * units.ms, tscatt=0.041 * units.ms, tscatt_err=0.002 * units.ms, scatt_index=-3.84, scatt_index_err=0.77) assert np.isclose(frb121102.pulse['freq'].value, 1.) # Test writing frb121102.write_to_json() assert np.isclose(frb121102.pulse['freq'].value, 1.) # Test load tst = FRB.from_json('FRB121102.json') assert np.isclose(tst.pulse['freq'].value, 1.)
def host_obj(): # VLT photom = Table() photom['Name'] = ['G_TEST'] photom['ra'] = 123.422 photom['dec'] = 23.222 # These are observed photom['LRISb_V'] = 25.86 photom['LRISb_V_err'] = 0.25 photom['GMOS_S_r'] = 23.61 photom['GMOS_S_r_err'] = 0.15 photom['LRISr_I'] = 23.09 photom['LRISr_I_err'] = 0.1 photom['NOT_z'] = 23.35 photom['NOT_z_err'] = 0.3 photom['NIRI_J'] = 21.75 + 0.91 photom['NIRI_J_err'] = 0.2 # host190613A = FRBHost(photom['ra'], photom['dec'], FRB.by_name('FRB20121102')) host190613A.parse_photom(photom) host190613A.name = 'G_TEST' return host190613A
def test_get_spectra(): """ Check grabbing spectra from the specDB Note: This requires that specdb be installed.. """ try: import specdb except ImportError: assert True return # Check for specDB file if utils.load_specdb() is None: assert True return # Do it! frb180924 = FRB.by_name('FRB180924') host180924 = frb180924.grab_host() meta, xspec = host180924.get_metaspec() # Test assert isinstance(meta, Table) assert isinstance(xspec, xspectrum1d.XSpectrum1D) assert xspec.nspec == 1 # meta, xspec = host180924.get_metaspec(instr='MUSE') # Test assert isinstance(xspec, xspectrum1d.XSpectrum1D) assert xspec.nspec == 1 # meta, xspecs = host180924.get_metaspec(return_all=True) assert xspecs.nspec == 2
def test_luminosity(): frb121102 = FRB.by_name('FRB121102') host121102 = frbgalaxy.FRBHost.from_json(frb121102, data_path('test_frbhost.json')) Lum_Ha, Lum_Ha_err = host121102.calc_nebular_lum('Halpha') # Test assert Lum_Ha.unit == units.erg/units.s assert np.isclose(Lum_Ha.value, 2.93961853e+40)
def test_read_frbhost(): # This test will fail if the previous failed frb121102 = FRB.by_name('FRB121102') host121102 = frbgalaxy.FRBHost.from_json(frb121102, data_path('test_frbhost.json')) # Test assert host121102.frb.frb_name == 'FRB121102' assert np.isclose(host121102.morphology['b/a'], 0.25) assert host121102.vet_all()
def test_parse_galfit(): frb = FRB.by_name("FRB20121102A") host = frb.grab_host() galfit_outfile = resource_filename('frb', 'tests/files/HG121102_galfit.fits') # Test two components host.parse_galfit(galfit_outfile, twocomponent=True) assert type(host.morphology['PA']) == np.ndarray assert len(host.morphology['PA']) == 2 # Test a single component host.parse_galfit(galfit_outfile, twocomponent=False) assert type(host.morphology['PA']) == np.float64
def test_luminosity(): # This test will fail if the previous failed outfile = data_path('test_frbhost.json') frb121102 = FRB.by_name('FRB20121102A') host121102 = frbgalaxy.FRBHost.from_json(frb121102, outfile) Lum_Ha, Lum_Ha_err = host121102.calc_nebular_lum('Halpha') # Test assert Lum_Ha.unit == units.erg / units.s assert np.isclose(Lum_Ha.value, 2.9447660789951146e+40) # Remove os.remove(outfile)
def test_frbhost(): repeater_coord = SkyCoord('05h31m58.698s +33d8m52.59s', frame='icrs') # Use as host here # Instantiate frb121102 = FRB.by_name('FRB20121102A') host121102 = frbgalaxy.FRBHost(repeater_coord.ra.value, repeater_coord.dec.value, frb121102) # Redshift host121102.set_z(0.19273, 'spec', err=0.00008) # Add a few nebular lines (Tendulkar+17) neb_lines = {} neb_lines['Halpha'] = 0.652e-16 neb_lines['Halpha_err'] = 0.009e-16 neb_lines['Halpha_Al'] = 0.622 # neb_lines['Hbeta'] = 0.118e-16 neb_lines['Hbeta_err'] = 0.011e-16 neb_lines['Hbeta_Al'] = 0.941 AV = 2.42 # Deal with Galactic extinction for key in neb_lines.keys(): if '_err' in key: continue if 'Al' in key: continue # Ingest host121102.neb_lines[key] = neb_lines[key] * 10**( neb_lines[key + '_Al'] * AV / 2.5) host121102.neb_lines[key + '_err'] = neb_lines[key + '_err'] * 10**( neb_lines[key + '_Al'] * AV / 2.5) # Vette for key in host121102.neb_lines.keys(): if '_err' in key: continue assert key in defs.valid_neb_lines # Morphology host121102.morphology['reff_ang'] = 0.41 host121102.morphology['reff_ang_err'] = 0.06 # host121102.morphology['n'] = 2.2 host121102.morphology['n_err'] = 1.5 # host121102.morphology['b/a'] = 0.25 host121102.morphology['b/a_err'] = 0.13 # Vet assert host121102.vet_one('morphology') # Vet all assert host121102.vet_all() # Write outfile = data_path('test_frbhost.json') host121102.write_to_json(outfile=outfile)
def test_named(): frb121102 = FRB('FRB121102', 'J053158.7+330852.5', 558.1 * units.pc / units.cm**3, z_frb=0.19273) # Error ellipse frb121102.set_ee(0.1, 0.1, 0., 95.) assert isinstance(frb121102.eellipse, dict) # Test writing frb121102.write_to_json() # Test load tst = FRB.from_json('FRB121102.json') # By name tst = FRB.by_name('FRB121102')
def test_offset(): ifrb = FRB.by_name('FRB20121102A') host = ifrb.grab_host() ra_sig_source = host.positional_error['ra_source'] ra_sig_astro = host.positional_error['ra_astrometric'] dec_sig_source = host.positional_error['dec_source'] dec_sig_astro = host.positional_error['dec_astrometric'] host_ra_sig = np.sqrt(ra_sig_astro**2 + ra_sig_source**2) host_dec_sig = np.sqrt(dec_sig_astro**2 + dec_sig_source**2) ang_avg, avg_err, ang_best, best_err = frb_offsets.angular_offset( ifrb, host, gal_sig=(host_ra_sig, host_dec_sig)) assert np.isclose(ang_best, 0.22687, rtol=1e-5)
def test_host_build(): outfile = data_path('FRB20180924_host.json') if os.path.isfile(outfile): os.remove(outfile) # Requires a file on disk that is too slow to generate in CI pargs = build.parser(['Hosts', '--frb', 'FRB20180924']) frbs = pargs.frb.split(',') frbs = [ifrb.strip() for ifrb in frbs] out_path = data_path('') build_hosts.main(frbs, options=pargs.options, hosts_file=pargs.data_file, lit_refs=pargs.lit_refs, override=pargs.override, out_path=out_path) # Check frb20180924 = FRB.by_name('FRB20180924') host = frbgalaxy.FRBHost.from_json(frb20180924, outfile) # Clean up os.remove(outfile)
new_pa_gal = pa_gal + dtheta * units.deg # x, y gal x_gal = -r.value * np.sin(new_pa_gal).value y_gal = r.value * np.cos(new_pa_gal).value # Offset ang_off = np.sqrt((xx - x_gal)**2 + (yy - y_gal)**2) p_xy = np.exp(-xx**2 / (2 * sig_a**2)) * np.exp(-yy**2 / (2 * sig_b**2)) # Best offset best_off = r.value var_best = np.sum((ang_off - best_off)**2 * p_xy) / np.sum(p_xy) sig_best = np.sqrt(var_best) # Average over the grid avg_off = np.sum(ang_off * p_xy) / np.sum(p_xy) var_off = np.sum((ang_off - avg_off)**2 * p_xy) / np.sum(p_xy) sig_off = np.sqrt(var_off) # Return return avg_off, sig_off, best_off, sig_best if __name__ == '__main__': from frb.frb import FRB ifrb = FRB.by_name('FRB200430') host = ifrb.grab_host() angular_offset(ifrb, host)
def build_fg_181112(build_photom=False): """ Data taken from Prochaska et al. 2019, Science, in press Args: build_photom (bool, optional): Generate the photometry table """ # Coord from DES fg_coord = SkyCoord('J214923.89-525810.43', unit=(units.hourangle, units.deg)) # from DES frb181112 = FRB.by_name('FRB181112') # Instantiate fg_13_5 = frbgalaxy.FGGalaxy(fg_coord.ra.value, fg_coord.dec.value, '181112') fg_13_5.frb_coord = frb181112.coord # Redshift fg_13_5.set_z(0.36738, 'spec', err=7e-5) # Photometry photom_file = os.path.join(db_path, 'CRAFT', 'Prochaska2019', 'prochaska2019_photom.ascii') if build_photom: # DES # Grab the table (requires internet) search_r = 2 * units.arcsec des_srvy = des.DES_Survey(fg_coord, search_r) des_tbl = des_srvy.get_catalog(print_query=True) fg_13_5.parse_photom(des_tbl) # VLT -- Lochlan 2019-05-02 # VLT -- Lochlan 2019-06-18 fg_13_5.photom['VLT_g'] = 21.20 fg_13_5.photom['VLT_g_err'] = 0.04 fg_13_5.photom['VLT_I'] = 19.20 fg_13_5.photom['VLT_I_err'] = 0.02 # Build a Table photom = Table() photom['Name'] = ['FG181112_13_5'] # JXP internal name photom['ra'] = fg_13_5.coord.ra.value photom['dec'] = fg_13_5.coord.dec.value # Add in for key in fg_13_5.photom.keys(): photom[key] = fg_13_5.photom[key] # Merge # Merge/write photom = frbphotom.merge_photom_tables(photom, photom_file) photom.write(photom_file, format=frbphotom.table_format, overwrite=True) # Either way read it fg_13_5.parse_photom(Table.read(photom_file, format=frbphotom.table_format)) # Nebular lines fg_13_5.parse_ppxf(os.path.join(db_path, 'CRAFT', 'Prochaska2019', 'FG181112_13_5_FORS2_ppxf.ecsv')) # Derived quantities fg_13_5.calc_nebular_AV('Ha/Hb') # This will be an upper limit fg_13_5.calc_nebular_SFR('Ha') fg_13_5.derived['SFR_nebular_err'] = -999. # CIGALE fg_13_5.parse_cigale(os.path.join(db_path, 'CRAFT', 'Prochaska2019', 'FG181112_13_5_CIGALE.fits')) # Write path = resource_filename('frb', 'data/Galaxies/181112') fg_13_5.write_to_json(path=path)
def run(frb_input: pandas.core.series.Series, lit_refs: str = None, override: bool = False, out_path: str = None, outfile: str = None): """Main method for generating a Host JSON file Args: frb_input (pandas.core.series.Series): Row of the CVS file providing the frb items lit_refs (str, optional): File of literature references. Defaults to None. override (bool, optional): Attempt to over-ride errors. Mainly for time-outs of public data. Defaults to False. outfile (str, optional): Over-ride default outfile [not recommended; mainly for testing] out_path (str, optional): Over-ride default outfile [not recommended; mainly for testing] Raises: e: [description] ValueError: [description] """ print("--------------------------------------") print(f"Building FRB JSON file for {frb_input.Name}") # Instantiate ifrb = FRB(frb_input.Name, (frb_input.ra, frb_input.dec), frb_input.DM * units.pc / units.cm**3, z_frb=frb_input.z if np.isfinite(frb_input.z) else None, repeater=frb_input.repeater) # DM_err if np.isfinite(frb_input['DM_err']): ifrb.DM_err = frb_input.DM_err * units.pc / units.cm**3 # RM for key in ['RM', 'RM_err']: if np.isfinite(frb_input[key]): setattr(ifrb, key, frb_input[key] * units.rad / units.m**2) # Fluence for key in ['fluence', 'fluence_err']: if np.isfinite(frb_input[key]): setattr(ifrb, key, frb_input[key] * units.Jy * units.ms) # Error ellipse ifrb.set_ee(a=frb_input.ee_a, b=frb_input.ee_b, theta=frb_input.ee_theta, cl=68.) if np.isfinite(frb_input.ee_a_sys): ifrb.set_ee(a=frb_input.ee_a_sys, b=frb_input.ee_b_sys, theta=frb_input.ee_theta, cl=68., stat=False) # Add DM_ISM from NE2001 ifrb.set_DMISM() # Refs ifrb.refs = frb_input.refs.split(',') # Pulses path = os.path.join(resource_filename('frb', 'data'), 'FRBs') tbl_file = os.path.join(path, 'FRB_pulses.csv') frb_pulses = pandas.read_csv(tbl_file) idx = np.where(frb_pulses.Name == frb_input.Name)[0] if len(idx) == 1: frb_pulse = frb_pulses.iloc[idx[0]] # Pulse properties pulse_dict = {} # Width and scattering for key in ['Wi', 'Wi_err', 'tscatt', 'tscatt_err']: if np.isfinite(frb_pulse[key]): pulse_dict[key] = frb_pulse[key] * units.ms ifrb.set_pulse(frb_pulse.freq * units.GHz, **pulse_dict) # References prefs = frb_pulse.refs.split(',') for pref in prefs: if pref not in ifrb.refs: ifrb.refs.append(pref) # Write if out_path is None: out_path = os.path.join(resource_filename('frb', 'data'), 'FRBs') ifrb.write_to_json( path=out_path ) #'/home/xavier/Projects/FRB_Software/FRB/frb/tests/files')
def _instantiate_intepolators(datafolder: str = DEFAULT_DATA_FOLDER, dmfilename: str = None, frb_name: str = "FRB180924") -> list: """ Produce interpolator functions for key quantities required for the analysis. Args: datfolder(str, optional): Folder where the interpolation data files exist dmfilename(str, optional): file name (within datafolder) for the DM interpolation data. frb_name(str, optional): Assumes "FRB180924" by default. Returns: dm_interpolator (RegularGridInterpolator): DM(z, offset_kpc, log_mhalo) mean_interp (interp2d): <log_mhalo(log_mstar, z)> (based on SHMR) stddev_interp (interp2d): std.dev. log_mhalo(log_mstar, z) (based on SHMR) ang_dia_interp (interp1d): angular_diameter_distance(z) (default Repo cosmology) """ # DM for a variety of halo parameters. if not dmfilename: dmfilename = "halo_dm_data.npz" dmdata = np.load(dmfilename) redshifts = dmdata['redshifts'] offsets = dmdata['offsets'] log_mhalos = dmdata['m_halo'] dm_grid = dmdata['dm'] dm_interpolator = RegularGridInterpolator((redshifts, offsets, log_mhalos), dm_grid, bounds_error=False, fill_value=0.) # Halo mass mean and variance from stellar mass frb = FRB.by_name(frb_name) realization_files = glob.glob( os.path.join(datafolder, "mhalo_realization_z*.npz")) realization_files.sort() # Define redshift grid zgrid = np.linspace(0, frb.z, 10) # Now initialize arrays to store mean and std.dev. mean_arrays = [] stddev_arrays = [] # Loop through files, compute mean & std.dev of log_mhalo for log_mstar for file in realization_files: loaded = np.load(file) log_mhalo = loaded['MHALO'] mean_mhalo, _, stddev_mhalo = sigma_clipped_stats(log_mhalo, sigma=20, axis=1) mean_arrays.append(mean_mhalo) stddev_arrays.append(stddev_mhalo) # laoded is going to be from the last file in the loop. The first entry contains # a stellar mass array. log_mstar = loaded['MSTAR'] mean_interp = interp2d(log_mstar, zgrid, np.array(mean_arrays), bounds_error=False) stddev_interp = interp2d(log_mstar, zgrid, np.array(stddev_arrays), bounds_error=False) # Angular diameter distance z = np.linspace(0, 7, 10000) ang_dia_dist = defs.frb_cosmo.angular_diameter_distance(z).to('kpc').value ang_dia_interp = interp1d(z, ang_dia_dist, bounds_error=False, fill_value='extrapolate') # Return interpolators return dm_interpolator, mean_interp, stddev_interp, ang_dia_interp