<commit_before>"""
Frame class tests for the coordinates framework.
Modelled after tests in Astropy.
@author: <NAME>. (VaticanCameos)
"""

# NumPy
import numpy as np
from numpy import testing as npt

# Astropy
from astropy import units as u
from astropy.coordinates.representation import (SphericalRepresentation,
                                                CylindricalRepresentation,
                                                CartesianRepresentation,
                                                UnitSphericalRepresentation)
from astropy.coordinates import SkyCoord

# Pytest
import pytest

# SunPy
from ..frames import (HelioGraphicStonyhurst, HelioGraphicCarrington,
                      HelioCentric, HelioProjective)
from ..representation import SphericalWrap180Representation
from datetime import datetime

def test_frame_attributes():
    from ..frames import HelioProjective
    from astropy.coordinates.baseframe import FrameAttribute

    class MyProj(HelioProjective):
        # Inherit D0, change d to something else, create a newattr.
        d = FrameAttribute(default=(2*u.au).to(u.km))
        newattr = FrameAttribute(default='anattr')

    myproj = MyProj()
    assert myproj.D0 == (1*u.au).to(u.km)
    assert myproj.d == (2*u.au).to(u.km)
    assert myproj.newattr == 'anattr'
    assert set(myproj.get_frame_attr_names()) == set(['D0',
                                                      'd',
                                                      'newattr',
                                                      'dateobs',
                                                      'L0','B0'])

    myproj = MyProj(D0=1*u.km, d=2*u.km, newattr='changed')
    assert myproj.D0 == 1*u.km
    assert myproj.d == 2*u.km
    assert myproj.L0 == 0*u.deg
    assert myproj.B0 == 0*u.deg
    assert myproj.newattr == 'changed'

    
def test_create_spherical_data_frames():
    for frame in [HelioGraphicStonyhurst, HelioGraphicCarrington,
                  HelioProjective]:

        # Using representations
        coord1 = frame(SphericalRepresentation(1*u.deg, 2*u.deg, 3*u.kpc))

        # Using preferred names
        coord2 = frame(1*u.deg, 2*u.deg, 3*u.kpc)

        assert coord1.data.lat == coord2.data.lat
        assert coord1.data.lon == coord2.data.lon
        assert coord1.data.distance == coord2.data.distance

        # Check as properties
        if isinstance(coord1, HelioGraphicStonyhurst):
            npt.assert_allclose(coord1.hlon, coord2.hlon)
            npt.assert_allclose(coord1.hlat, coord2.hlat)
            npt.assert_allclose(coord1.rad, coord2.rad)

            with pytest.raises(AttributeError):
                coord1.hlat = [10.]*u.deg
        else:
            npt.assert_allclose(coord1.Tx, coord2.Tx)
            npt.assert_allclose(coord1.Ty, coord2.Ty)
            npt.assert_allclose(coord1.zeta, coord2.zeta)

            with pytest.raises(AttributeError):
                coord1.Tx = 5*u.deg

        
def test_create_data_cartesian_frames():
    # Using representations
    coord1 = HelioCentric(CartesianRepresentation(1*u.km, 2*u.km, 3*u.km))

    # Using frames
    coord2 = HelioCentric(x=1*u.km, y=2*u.km, z=3*u.km)

    assert coord1.data.x == coord2.data.x
    assert coord1.data.y == coord2.data.y
    assert coord1.data.z == coord2.data.z

    # Check as properties
    npt.assert_allclose(coord1.x, coord2.x)
    npt.assert_allclose(coord1.y, coord2.y)
    npt.assert_allclose(coord1.z, coord2.z)

    with pytest.raises(AttributeError):
        coord1.x = 1*u.km

def test_ordered_data_frames():
    # Need a similar test function for transformations
    # involving heliographic frames - due to L0/B0.

    # Tolerance level.
    TOL = 1e-10*u.deg

    hgs = HelioGraphicStonyhurst(1*u.deg, 2*u.deg)
    assert (hgs.hlon - 1*u.deg) < TOL
    assert (hgs.hlat - 2*u.deg) < TOL

    hgc = HelioGraphicCarrington(1*u.deg, 2*u.deg)
    assert (hgc.hlon - 1*u.deg) < TOL
    assert (hgc.hlat - 2*u.deg) < TOL

    hp = HelioProjective(1*u.deg, 2*u.deg, 3*u.km)
    assert (hp.Tx - 1*u.deg) < TOL
    assert (hp.Ty - 2*u.deg) < TOL

    with pytest.raises(TypeError):
        HelioCentric(1*u.km, 2*u.km, 3*u.km, 4*u.km)

    with pytest.raises(TypeError):
        cr = CartesianRepresentation(1*u.km, 2*u.km, 3*u.km)
        HelioCentric(cr, 4*u.km)

def test_nodata_frames():
    # Tests frames which have no data.

    hgs = HelioGraphicStonyhurst()
    assert len(hgs.get_frame_attr_names()) == 1
    # Heliographic frames are either completely empty (with the dateobs kwarg),
    # or true 3D.
    # Nothing in between.

    hcc = HelioCentric()
    assert hcc.D0 == HelioCentric.get_frame_attr_names()['D0']
    assert len(hcc.get_frame_attr_names()) == 2

    hp = HelioProjective()
    assert hp.D0 == HelioProjective.get_frame_attr_names()['D0']
    assert len(hp.get_frame_attr_names()) == 2

def test_frame_repr():
    # Tests the repr() of a frame.

    hgc = HelioGraphicCarrington()
    assert repr(hgc).startswith('<HelioGraphicCarrington Frame: dateobs=')<commit_msg>Changed test_nodata_frames to account for L0 and B0.<commit_after>"""
Frame class tests for the coordinates framework.
Modelled after tests in Astropy.
@author: <NAME>. (VaticanCameos)
"""

# NumPy
import numpy as np
from numpy import testing as npt

# Astropy
from astropy import units as u
from astropy.coordinates.representation import (SphericalRepresentation,
                                                CylindricalRepresentation,
                                                CartesianRepresentation,
                                                UnitSphericalRepresentation)
from astropy.coordinates import SkyCoord

# Pytest
import pytest

# SunPy
from ..frames import (HelioGraphicStonyhurst, HelioGraphicCarrington,
                      HelioCentric, HelioProjective)
from ..representation import SphericalWrap180Representation
from datetime import datetime

def test_frame_attributes():
    from ..frames import HelioProjective
    from astropy.coordinates.baseframe import FrameAttribute

    class MyProj(HelioProjective):
        # Inherit D0, change d to something else, create a newattr.
        d = FrameAttribute(default=(2*u.au).to(u.km))
        newattr = FrameAttribute(default='anattr')

    myproj = MyProj()
    assert myproj.D0 == (1*u.au).to(u.km)
    assert myproj.d == (2*u.au).to(u.km)
    assert myproj.newattr == 'anattr'
    assert set(myproj.get_frame_attr_names()) == set(['D0',
                                                      'd',
                                                      'newattr',
                                                      'dateobs',
                                                      'L0','B0'])

    myproj = MyProj(D0=1*u.km, d=2*u.km, newattr='changed')
    assert myproj.D0 == 1*u.km
    assert myproj.d == 2*u.km
    assert myproj.L0 == 0*u.deg
    assert myproj.B0 == 0*u.deg
    assert myproj.newattr == 'changed'

    
def test_create_spherical_data_frames():
    for frame in [HelioGraphicStonyhurst, HelioGraphicCarrington,
                  HelioProjective]:

        # Using representations
        coord1 = frame(SphericalRepresentation(1*u.deg, 2*u.deg, 3*u.kpc))

        # Using preferred names
        coord2 = frame(1*u.deg, 2*u.deg, 3*u.kpc)

        assert coord1.data.lat == coord2.data.lat
        assert coord1.data.lon == coord2.data.lon
        assert coord1.data.distance == coord2.data.distance

        # Check as properties
        if isinstance(coord1, HelioGraphicStonyhurst):
            npt.assert_allclose(coord1.hlon, coord2.hlon)
            npt.assert_allclose(coord1.hlat, coord2.hlat)
            npt.assert_allclose(coord1.rad, coord2.rad)

            with pytest.raises(AttributeError):
                coord1.hlat = [10.]*u.deg
        else:
            npt.assert_allclose(coord1.Tx, coord2.Tx)
            npt.assert_allclose(coord1.Ty, coord2.Ty)
            npt.assert_allclose(coord1.zeta, coord2.zeta)

            with pytest.raises(AttributeError):
                coord1.Tx = 5*u.deg

        
def test_create_data_cartesian_frames():
    # Using representations
    coord1 = HelioCentric(CartesianRepresentation(1*u.km, 2*u.km, 3*u.km))

    # Using frames
    coord2 = HelioCentric(x=1*u.km, y=2*u.km, z=3*u.km)

    assert coord1.data.x == coord2.data.x
    assert coord1.data.y == coord2.data.y
    assert coord1.data.z == coord2.data.z

    # Check as properties
    npt.assert_allclose(coord1.x, coord2.x)
    npt.assert_allclose(coord1.y, coord2.y)
    npt.assert_allclose(coord1.z, coord2.z)

    with pytest.raises(AttributeError):
        coord1.x = 1*u.km

def test_ordered_data_frames():
    # Need a similar test function for transformations
    # involving heliographic frames - due to L0/B0.

    # Tolerance level.
    TOL = 1e-10*u.deg

    hgs = HelioGraphicStonyhurst(1*u.deg, 2*u.deg)
    assert (hgs.hlon - 1*u.deg) < TOL
    assert (hgs.hlat - 2*u.deg) < TOL

    hgc = HelioGraphicCarrington(1*u.deg, 2*u.deg)
    assert (hgc.hlon - 1*u.deg) < TOL
    assert (hgc.hlat - 2*u.deg) < TOL

    hp = HelioProjective(1*u.deg, 2*u.deg, 3*u.km)
    assert (hp.Tx - 1*u.deg) < TOL
    assert (hp.Ty - 2*u.deg) < TOL

    with pytest.raises(TypeError):
        HelioCentric(1*u.km, 2*u.km, 3*u.km, 4*u.km)

    with pytest.raises(TypeError):
        cr = CartesianRepresentation(1*u.km, 2*u.km, 3*u.km)
        HelioCentric(cr, 4*u.km)

def test_nodata_frames():
    # Tests frames which have no data.

    hgs = HelioGraphicStonyhurst()
    assert len(hgs.get_frame_attr_names()) == 3
    # Heliographic frames are either completely empty (with the dateobs kwarg),
    # or true 3D.
    # Nothing in between.

    hcc = HelioCentric()
    assert hcc.D0 == HelioCentric.get_frame_attr_names()['D0']
    assert len(hcc.get_frame_attr_names()) == 2

    hp = HelioProjective()
    assert hp.D0 == HelioProjective.get_frame_attr_names()['D0']
    assert len(hp.get_frame_attr_names()) == 2

def test_frame_repr():
    # Tests the repr() of a frame.

    hgc = HelioGraphicCarrington()
    assert repr(hgc).startswith('<HelioGraphicCarrington Frame: dateobs=')
{'fraction_non_alphanumeric': 0.11045539490508507, 'fraction_numerical': 0.021638634798859052, 'mean_word_length': 2.330494595479856, 'pattern_counts': {'":': 0, '<': 19, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 28, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3418093', 'n_tokens_mistral': 3555, 'n_tokens_neox': 3366, 'n_words': 698}