Exemplo n.º 1
0
def get_spice_target(body_name):
    """
    Return the HelioPy target object

    Parameters
    ----------
    body_name : `~str`
        The name of the SPICE target object.

    Returns
    -------
    `~heliopy.space.Trajectory`

    """
    # Parker Solar Probe (also sometimes referred to as Solar Probe Plus or SPP)
    if body_name == 'psp':
        spacecraft_kernels.load('psp')
        target = spice.Trajectory('SPP')
    elif body_name == 'stereo_a':
        spacecraft_kernels.load('stereo_a')
        target = spice.Trajectory('STEREO AHEAD')
    elif body_name == 'stereo_b':
        spacecraft_kernels.load('stereo_b')
        target = spice.Trajectory('STEREO BEHIND')
    elif body_name == 'soho':
        spacecraft_kernels.load('soho')
        target = spice.Trajectory('SOHO')
    else:
        target = None

    return target
Exemplo n.º 2
0
def get_sc_lonlat_test(kernel, scname, frame, starttime, endtime, res_in_days):
    '''
 make spacecraft positions
 
 kernel,scname,frame,starttime, endtime,res_in_days
 'psp_pred','SPP','HEEQ',datetime(2018, 8,13),'datetime(2024, 8,13), 1

 kernels: psp_pred, stereoa_pred, 
 frames: ECLIPJ2000 HEE HEEQ, HCI
 frames https://naif.jpl.nasa.gov/pub/naif/toolkit_docs/C/req/frames.html  Appendix. ``Built in'' Inertial Reference Frames

 '''
    spice.furnish(spicedata.get_kernel(kernel))
    sc = spice.Trajectory(scname)
    sc_time = []
    while starttime < endtime:
        sc_time.append(starttime)
        starttime += timedelta(days=res_in_days)

    sc_time_num = mdates.date2num(sc_time)
    sc.generate_positions(sc_time, 'Sun', frame)
    sc.change_units(astropy.units.AU)
    sc_r, sc_lat, sc_lon = cart2sphere(sc.x, sc.y, sc.z)
    screc = np.rec.array([sc_time_num, sc_r, sc_lon, sc_lat, sc.x, sc.y, sc.z],
                         dtype=[('time', 'f8'), ('r', 'f8'), ('lon', 'f8'),
                                ('lat', 'f8'), ('x', 'f8'), ('y', 'f8'),
                                ('z', 'f8')])

    return screc
Exemplo n.º 3
0
def get_insitu_position_time(time1,insitu_location_string,insitu_str,insitu_kernel):
    
    
    insitu_exist=True
    
    if insitu_location_string=='PSP': 
        #exclude if time before launch time
        if parse_time(time1).plot_date < parse_time(datetime.datetime(2018, 8, 13)).plot_date:
            insitu_exist=False 

    if insitu_location_string=='Solo': 
        if parse_time(time1).plot_date < parse_time(datetime.datetime(2020, 3, 1)).plot_date:
            insitu_exist=False 
        
    if insitu_location_string=='Bepi': 
        if parse_time(time1).plot_date < parse_time(datetime.datetime(2018, 10, 24)).plot_date:
            insitu_exist=False
                    
    if insitu_location_string=='STB': 
        if parse_time(time1).plot_date > parse_time(datetime.datetime(2014, 9, 27)).plot_date:
            insitu_exist=False  
            
                               
    if insitu_location_string=='Ulysses': 
        #cut off ulysses when no decent in situ data is available anymore
        if parse_time(time1).plot_date > parse_time(datetime.datetime(2008, 5, 1)).plot_date:
            insitu_exist=False              

            
    if insitu_exist == True:
        #insitu_kernel=spicedata.get_kernel('insitu_trajectories')

        #this needs to be an array, so make two similar times and take the first entry later
        insitu_time=[parse_time(time1).datetime,parse_time(time1).datetime]
        insitu=spice.Trajectory(insitu_str)  
        frame='HEEQ'
        insitu.generate_positions(insitu_time,'Sun',frame)  
        insitu.change_units(astropy.units.AU)  
        [insitu_r, insitu_lat, insitu_lon]=hd.cart2sphere(insitu.x,insitu.y,insitu.z)
        
        #Earth position to Earth L1
        if insitu_str=='3': insitu_r[0]=insitu_r[0]-1.5*1e6/AU
       

        insitu_time=np.array(insitu_time)[0]
        insitu_r=np.array(insitu_r)[0]
        insitu_lat=np.array(insitu_lat)[0]
        insitu_lon=np.array(insitu_lon)[0]
        
    else:
        insitu_time=np.nan
        insitu_r=np.nan
        insitu_lat=np.nan
        insitu_lon=np.nan    

    return [insitu_time,insitu_r,np.degrees(insitu_lat),np.degrees(insitu_lon)]
Exemplo n.º 4
0
def test_spice_sunpy_equivalence():
    # Check that SPICE coordinates and the sunpy coordinates we associate
    # with those coordinates are the same
    t = ['1992-12-21']
    b0 = Latitude(sunpy.coordinates.sun.B0(t))
    l0 = sunpy.coordinates.sun.L0(t, light_travel_time_correction=False)

    earth = spice.Trajectory('Earth')
    earth.generate_positions(t, 'Sun', 'IAU_SUN')

    assert u.allclose(earth.coords.lon, l0, **_tols)
    assert u.allclose(earth.coords.lat, b0, **_tols)
Exemplo n.º 5
0
    def extractSolOrbit(self):
        """
        Get the SPICE orbit data for SolO and put into coordsCarrington
        """
        import heliopy.data.spice as spicedata
        import heliopy.spice as spice

        spicedata.get_kernel("solo")
        solo = spice.Trajectory("Solar Orbiter")
        times = list(self.df.index.to_pydatetime())
        solo.generate_positions(times, 'Sun', 'IAU_SUN')  # Is in KM
        self.coordsCarrington = solo.coords.transform_to(
            frame=frames.HeliographicCarrington)
Exemplo n.º 6
0
def test_spice():
    orbiter_kernel = spicedata.get_kernel('solo_2020')
    spice.furnish(orbiter_kernel)
    orbiter = spice.Trajectory('Solar Orbiter')

    # Generate 1000 days of data
    starttime = datetime(2020, 3, 1)
    times = [starttime + n * timedelta(days=1) for n in range(1000)]

    orbiter.generate_positions(times, 'Sun', 'ECLIPJ2000')
    assert orbiter.times == times

    # Check it works with numpy arrays too
    times = np.array(times)
    orbiter.generate_positions(times, 'Sun', 'ECLIPJ2000')
Exemplo n.º 7
0
def kernel_loader(spacecraft: Union[int, str] = 2) -> spice.Trajectory:
    """
    :param spacecraft: 1 or 2 for Helios 1  or 2, can also be 'ulysses'
    :return: unfurnished  orbiter
    """
    if spacecraft == 1 or spacecraft == 2:
        if spacecraft == 1:
            orbiter_kernel = spice_data.get_kernel('helios1_rec')
        else:
            orbiter_kernel = spice_data.get_kernel('helios2')
        spice.furnish(orbiter_kernel)
        orbiter = spice.Trajectory('Helios ' + str(spacecraft))

    # elif spacecraft == 'ulysses':
    #     orbiter_kernel = spice_data.get_kernel(str(spacecraft))
    #     spice.furnish(orbiter_kernel)
    #     orbiter = spice.Trajectory(spacecraft)
    else:
        raise NotImplementedError('The only probes that can be imported are Helios 1 , Helios 2 and Ulysses')

    return orbiter
Exemplo n.º 8
0
def get_planet_orbit(planet: str, start_date: str = '20/01/1976', end_date: str = '01/10/1979',
                     interval: float = 1) -> spice.Trajectory:
    """
    Finds the orbiter for a given planet
    :param planet: planet that we want to analyse
    :param start_date: start date of analysis
    :param end_date: end date of analysis
    :param interval: interval between each date in the orbiter, defaults to 1
    :return: orbiter of the planet
    """
    orbiter_kernel = spice_data.get_kernel('planet_trajectories')
    spice.furnish(orbiter_kernel)
    orbiter = spice.Trajectory(planet)
    start_time = datetime.strptime(start_date, '%d/%m/%Y')
    end_time = datetime.strptime(end_date, '%d/%m/%Y')
    times = []
    while start_time < end_time:
        times.append(start_time)
        start_time = start_time + timedelta(days=interval)
    orbiter.generate_positions(times, 'Sun', 'ECLIPJ2000')
    orbiter.change_units(u.au)
    return orbiter
Exemplo n.º 9
0
#sys.exit()

########################################## MAKE TRAJECTORIES ############################

##########################################  PSP

starttime = datetime(2018, 8, 13)
endtime = datetime(2025, 8, 31)
psp_time = []
while starttime < endtime:
    psp_time.append(starttime)
    starttime += timedelta(days=res_in_days)
psp_time_num = mdates.date2num(psp_time)

spice.furnish(spicedata.get_kernel('psp_pred'))
psp = spice.Trajectory('SPP')
psp.generate_positions(psp_time, 'Sun', frame)
print('PSP pos')

psp.change_units(astropy.units.AU)
[psp_r, psp_lat, psp_lon] = cart2sphere(psp.x, psp.y, psp.z)
print('PSP conv')

############################################## BepiColombo

starttime = datetime(2018, 10, 21)
endtime = datetime(2025, 11, 2)
bepi_time = []
while starttime < endtime:
    bepi_time.append(starttime)
    starttime += timedelta(days=res_in_days)
Exemplo n.º 10
0
def solo_trajectory():
    orbiter_kernel = spicedata.get_kernel('helios1')
    spice.furnish(orbiter_kernel)
    return spice.Trajectory('Helios 1')
Exemplo n.º 11
0
its orbit for the first year.
"""


import heliopy.data.spice as spicedata
import heliopy.spice as spice
from datetime import datetime, timedelta
import astropy.units as u
import numpy as np

###############################################################################
# Load the solar orbiter spice kernel. heliopy will automatically fetch and
# load the latest kernel
spicedata.get_kernel('psp')
spicedata.get_kernel('psp_pred')
psp = spice.Trajectory('SPP')

###############################################################################
# Generate a time for every day between starttime and endtime
starttime = datetime(2018, 8, 14)
endtime = starttime + timedelta(days=365)
times = []
while starttime < endtime:
    times.append(starttime)
    starttime += timedelta(hours=6)

###############################################################################
# Generate positions
psp.generate_positions(times, 'Sun', 'ECLIPJ2000')
psp.change_units(u.au)
Exemplo n.º 12
0
def psp_xyz(dtime):
    psp = spice.Trajectory('SPP')
    psp.generate_positions([dtime], 'Sun', 'IAU_SUN')
    psp.change_units(u.au)
    return np.array([psp.x.value, psp.y.value, psp.z.value])[:, 0]
Exemplo n.º 13
0
def loc(dtime, body):
    traj = spice.Trajectory(body)
    traj.generate_positions([dtime], 'Sun', 'IAU_SUN')
    traj_coord = traj.coords
    traj_coord.representation_type = 'spherical'
    return traj_coord
Exemplo n.º 14
0
# an hourly data cadence.
starttime = '2018-10-22'
endtime = '2018-11-21'
psp_data = psp.merged_mag_plasma(starttime, endtime)
print(psp_data.columns)

###############################################################################
# Generate the PSP trajectory.
#
# We take the timestamps from the previously loaded data, and use `heliopy.spice`
# to generate the trajectory at these times.
times = psp_data.index

spicedata.get_kernel('psp')
spicedata.get_kernel('psp_pred')
psp_traj = spice.Trajectory('SPP')
psp_traj.generate_positions(times, 'Sun', 'IAU_SUN')
psp_coords = psp_traj.coords
print(psp_coords)

###############################################################################
# Take a sample of the radial velocity.
#
# Here we start by getting the radial velocity `Variable` from the model, and
# then use the PSP corodinate information to sample it.
vr_model = model['vr']
vr_sampled = vr_model.sample_at_coords(psp_coords.lon, psp_coords.lat,
                                       psp_coords.radius)

###############################################################################
# We can now plot a comparison between the model and in-situ measurements.
Exemplo n.º 15
0
def solo_trajectory():
    orbiter_kernel = spicedata.get_kernel('solo')
    spice.furnish(orbiter_kernel)
    return spice.Trajectory('Solar Orbiter')
Exemplo n.º 16
0
# - Working with SPICE kernels
# - Built-in support for:
#     - Helios, Juno, **PSP**, **Solar Orbiter**, STEREO, Ulysses
# - Can work with custom SPICE kernels

# ``heliopy.spice`` example
# ---

# In[11]:

from heliopy import spice
import heliopy.data.spice as spicedata

# Download and load Solar Orbiter predicted SPICE kernel
spice.furnish(spicedata.get_kernel('solo_2020'))
solo = spice.Trajectory('Solar Orbiter')

# In[12]:

# Specify times at which to sample the trajectory
from datetime import datetime, timedelta
starttime = datetime(2020, 2, 20)
times = [starttime + timedelta(days=i) for i in range(365)]

# Generate the trajectory
solo.generate_positions(times, 'Sun', 'ECLIPJ2000')

# Print first 3 positions
print('Positions:', solo.x[:3], solo.y[:3], solo.z[:3], sep='\n')

# In[13]:
Exemplo n.º 17
0
def earth_trajectory(times):
    traj = spice.Trajectory('earth')
    traj.generate_positions(times, 'Sun', 'IAU_SUN')
    return traj
Exemplo n.º 18
0
def make_positions():

    ##########################################  PSP

    starttime =datetime(2018, 8,13)
    endtime = datetime(2025, 8, 31)
    psp_time = []
    while starttime < endtime:
        psp_time.append(starttime)
        starttime += timedelta(days=res_in_days)
    psp_time_num=mdates.date2num(psp_time)     

    spice.furnish(spicedata.get_kernel('psp_pred'))
    psp=spice.Trajectory('SPP')
    psp.generate_positions(psp_time,'Sun',frame)
    print('PSP pos')

    psp.change_units(astropy.units.AU)  
    [psp_r, psp_lat, psp_lon]=cart2sphere(psp.x,psp.y,psp.z)
    print('PSP conv')


    ############################################## BepiColombo

    starttime =datetime(2018, 10, 21)
    endtime = datetime(2025, 11, 2)
    bepi_time = []
    while starttime < endtime:
        bepi_time.append(starttime)
        starttime += timedelta(days=res_in_days)
    bepi_time_num=mdates.date2num(bepi_time) 

    spice.furnish(spicedata.get_kernel('bepi_pred'))
    bepi=spice.Trajectory('BEPICOLOMBO MPO') # or BEPICOLOMBO MMO
    bepi.generate_positions(bepi_time,'Sun',frame)
    bepi.change_units(astropy.units.AU)  
    [bepi_r, bepi_lat, bepi_lon]=cart2sphere(bepi.x,bepi.y,bepi.z)
    print('Bepi')



    #################################################### Solar Orbiter

    starttime = datetime(2020, 3, 1)
    endtime = datetime(2026, 1, 1)
    solo_time = []
    while starttime < endtime:
        solo_time.append(starttime)
        starttime += timedelta(days=res_in_days)
    solo_time_num=mdates.date2num(solo_time) 

    spice.furnish(spicedata.get_kernel('solo_2020'))
    solo=spice.Trajectory('Solar Orbiter')
    solo.generate_positions(solo_time, 'Sun',frame)
    solo.change_units(astropy.units.AU)
    [solo_r, solo_lat, solo_lon]=cart2sphere(solo.x,solo.y,solo.z)
    print('Solo')






    plt.figure(1, figsize=(12,9))
    plt.plot_date(psp_time,psp_r,'-', label='R')
    plt.plot_date(psp_time,psp_lat,'-',label='lat')
    plt.plot_date(psp_time,psp_lon,'-',label='lon')
    plt.ylabel('AU / RAD')
    plt.legend()




    plt.figure(2, figsize=(12,9))
    plt.plot_date(bepi_time,bepi_r,'-', label='R')
    plt.plot_date(bepi_time,bepi_lat,'-',label='lat')
    plt.plot_date(bepi_time,bepi_lon,'-',label='lon')
    plt.title('Bepi Colombo position '+frame)
    plt.ylabel('AU / RAD')
    plt.legend()




    plt.figure(3, figsize=(12,9))
    plt.plot_date(solo_time,solo_r,'-', label='R')
    plt.plot_date(solo_time,solo_lat,'-',label='lat')
    plt.plot_date(solo_time,solo_lon,'-',label='lon')
    plt.title('Solar Orbiter position '+frame)
    plt.ylabel('AU / RAD')
    plt.legend()


    ########### plots


    ######## R with all three
    plt.figure(4, figsize=(16,10))
    plt.plot_date(psp_time,psp.r,'-',label='PSP')
    plt.plot_date(bepi_time,bepi.r,'-',label='Bepi Colombo')
    plt.plot_date(solo_time,solo.r,'-',label='Solar Orbiter')
    plt.legend()
    plt.title('Heliocentric distance of heliospheric observatories')
    plt.ylabel('AU')
    plt.savefig('results/positions_plots/bepi_psp_solo_R.png')

    ##### Longitude all three
    plt.figure(5, figsize=(16,10))
    plt.plot_date(psp_time,psp_lon*180/np.pi,'-',label='PSP')
    plt.plot_date(bepi_time,bepi_lon*180/np.pi,'-',label='Bepi Colombo')
    plt.plot_date(solo_time,solo_lon*180/np.pi,'-',label='Solar Orbiter')
    plt.legend()
    plt.title(frame+' longitude')
    plt.ylabel('DEG')
    plt.savefig('results/positions_plots/bepi_psp_solo_longitude_'+frame+'.png')


    ############# Earth for mercury, venusus, STA
    #https://docs.heliopy.org/en/stable/data/spice.html


    planet_kernel=spicedata.get_kernel('planet_trajectories')

    starttime =datetime(2018, 1, 1)
    endtime = datetime(2028, 12, 31)
    earth_time = []
    while starttime < endtime:
        earth_time.append(starttime)
        starttime += timedelta(days=res_in_days)
    earth_time_num=mdates.date2num(earth_time)     

    earth=spice.Trajectory('399')  #399 for Earth, not barycenter (because of moon)
    earth.generate_positions(earth_time,'Sun',frame)
    earth.change_units(astropy.units.AU)  
    [earth_r, earth_lat, earth_lon]=cart2sphere(earth.x,earth.y,earth.z)
    print('Earth')

    ################ mercury
    mercury_time_num=earth_time_num
    mercury=spice.Trajectory('1')  #barycenter
    mercury.generate_positions(earth_time,'Sun',frame)  
    mercury.change_units(astropy.units.AU)  
    [mercury_r, mercury_lat, mercury_lon]=cart2sphere(mercury.x,mercury.y,mercury.z)
    print('mercury') 

    ################# venus
    venus_time_num=earth_time_num
    venus=spice.Trajectory('2')  
    venus.generate_positions(earth_time,'Sun',frame)  
    venus.change_units(astropy.units.AU)  
    [venus_r, venus_lat, venus_lon]=cart2sphere(venus.x,venus.y,venus.z)
    print('venus') 


    ############### Mars

    mars_time_num=earth_time_num
    mars=spice.Trajectory('4')  
    mars.generate_positions(earth_time,'Sun',frame)  
    mars.change_units(astropy.units.AU)  
    [mars_r, mars_lat, mars_lon]=cart2sphere(mars.x,mars.y,mars.z)
    print('mars') 

    #############stereo-A
    sta_time_num=earth_time_num
    spice.furnish(spicedata.get_kernel('stereo_a_pred'))
    sta=spice.Trajectory('-234')  
    sta.generate_positions(earth_time,'Sun',frame)  
    sta.change_units(astropy.units.AU)  
    [sta_r, sta_lat, sta_lon]=cart2sphere(sta.x,sta.y,sta.z)
    print('STEREO-A') 



    #save positions 
    if high_res_mode:
     pickle.dump([psp_time,psp_time_num,psp_r,psp_lon,psp_lat,bepi_time,bepi_time_num,bepi_r,bepi_lon,bepi_lat,solo_time,solo_time_num,solo_r,solo_lon,solo_lat], open( 'positions_plots/psp_solo_bepi_'+frame+'_1min.p', "wb" ) )
     sys.exit()
    else: 
     psp=np.rec.array([psp_time_num,psp_r,psp_lon,psp_lat, psp.x, psp.y,psp.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     bepi=np.rec.array([bepi_time_num,bepi_r,bepi_lon,bepi_lat,bepi.x, bepi.y,bepi.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     solo=np.rec.array([solo_time_num,solo_r,solo_lon,solo_lat,solo.x, solo.y,solo.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     sta=np.rec.array([sta_time_num,sta_r,sta_lon,sta_lat,sta.x, sta.y,sta.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     earth=np.rec.array([earth_time_num,earth_r,earth_lon,earth_lat, earth.x, earth.y,earth.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     venus=np.rec.array([venus_time_num,venus_r,venus_lon,venus_lat, venus.x, venus.y,venus.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     mars=np.rec.array([mars_time_num,mars_r,mars_lon,mars_lat, mars.x, mars.y,mars.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     mercury=np.rec.array([mercury_time_num,mercury_r,mercury_lon,mercury_lat,mercury.x, mercury.y,mercury.z],dtype=[('time','f8'),('r','f8'),('lon','f8'),('lat','f8'),('x','f8'),('y','f8'),('z','f8')])
     pickle.dump([psp, bepi, solo, sta, earth, venus, mars, mercury,frame], open( 'results/positions_psp_solo_bepi_sta_planets_'+frame+'_2hours.p', "wb" ) )
     #load with [psp, bepi, solo, sta, earth, venus, mars, mercury,frame]=pickle.load( open( 'positions_psp_solo_bepi_sta_planets_HCI_6hours_2018_2025.p', "rb" ) )
 
 
    end=time.time()
    print( 'generate position took time in seconds:', round((end-start),1) )
Exemplo n.º 19
0
def test_coord_err():
    t = ['1992-12-21']
    earth = spice.Trajectory('Earth')
    earth.generate_positions(t, 'Sun', 'IAU_SUN', abcorr='LT')
    with pytest.raises(NotImplementedError):
        earth.coords
Exemplo n.º 20
0
from datetime import datetime, timedelta

import matplotlib.pyplot as plt
import numpy as np

import astropy.units as u
import heliopy.data.spice as spicedata
import heliopy.spice as spice

###############################################################################
# Load the Solar Orbiter spice kernel. HelioPy will automatically fetch and
# load the latest kernel. We can then inspect the kernel to check what the
# date coverage is for Solar Orbiter.
kernels = spicedata.get_kernel('solo')
solo = spice.Trajectory('Solar Orbiter')
coverage = kernels[0].coverage(spice.Body('Solar Orbiter'))
print(coverage)

###############################################################################
# Next we define a set of times at which to sample the orbit.
starttime = coverage[0]
times = [starttime + timedelta(days=i) for i in range(1, 5 * 365)]

###############################################################################
# Generate positions. "IAU_SUN" is a Carrington frame of reference.
solo.generate_positions(times, 'Sun', 'IAU_SUN')
coords = solo.coords

###############################################################################
# Plot radial distance and elevation as a function of time
Exemplo n.º 21
0
def get_satellite_position_heliopy(satname,
                                   timestamp,
                                   refframe='J2000',
                                   refobject='Sun',
                                   rlonlat=False,
                                   returnobj=False):
    """Uses Heliopy's spice to get position information. Will automatically download
    required kernels. Returns positions in km.

    Parameters
    ==========
    satname : str
        Satellite name. Currently available: ['stereo_a', 'stereo_a_pred', 'earth']
    timestamp : datetime / list of datetimes
        Datetime objects to iterate through and return positions for.
    refframe : str
        String denoting reference frame to use for position.
    refobject : str (default='Sun')
        String for reference onject, e.g. 'Sun' or 'Earth'
    rlonlat : bool (default=False)
        If True, returns coordinates in (r, lon, lat) format, not (x,y,z).
    returnobj : bool (default=False)
        If True, returns heliopy.Trajectory object instead of arrays.

    Returns
    =======
    If returnobj: returns heliopy.spice.Trajectory object.
    else: returns tuple of (x,y,z) or (r,lon,lat) if rlonlat=True
    """

    if isinstance(timestamp, datetime):
        timestamp = [timestamp]
    elif isinstance(timestamp, list):
        pass
    else:
        logger.warning(
            "get_satellite_position_heliopy: Don't recognise input timestamp format!"
        )

    if 'stereoa' in satname.lower().replace('-', '').replace('_', ''):
        if 'pred' in satname.lower():
            heliostr = 'stereo_a_pred'
        else:
            heliostr = 'stereo_a'
        satstr = 'STEREO AHEAD'
    elif 'stereob' in satname.lower().replace('-', '').replace('_', ''):
        if 'pred' in satname.lower():
            heliostr = 'stereo_b_pred'
        else:
            heliostr = 'stereo_b'
        satstr = 'STEREO BEHIND'
    elif satname.lower() in [
            'mercury', 'venus', 'earth', 'mars', 'jupiter', 'saturn', 'uranus',
            'neptune'
    ]:
        heliostr = 'planet_trajectories'
        satstr = satname

    hspice.furnish(spicedata.get_kernel(heliostr))
    pos = hspice.Trajectory(satstr)
    pos.generate_positions(timestamp, refobject, refframe)

    if returnobj:
        return pos

    #pos.change_units('AU')
    if rlonlat:
        r, theta, phi = cart2sphere(pos.x, pos.y, pos.z)
        return (r, phi, theta)
    else:
        return (pos.x, pos.y, pos.z)