Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add cutouts for casda #2366

Merged
merged 13 commits into from
Apr 22, 2022
Merged

Conversation

jd-au
Copy link
Contributor

@jd-au jd-au commented Apr 19, 2022

Added the ability to produce spatial and spectral cutouts from ASKAP images and cubes using CASDA's SODA implementation.

@pep8speaks
Copy link

pep8speaks commented Apr 19, 2022

Hello @jd-au! Thanks for updating this PR. We checked the lines you've touched for PEP 8 issues, and found:

There are currently no PEP 8 issues detected in this Pull Request. Cheers! 🍻

Comment last updated at 2022-04-22 07:32:51 UTC

Copy link
Member

@bsipocz bsipocz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I mostly have nitpick comments.

The bigger point is that I feel the module would benefit if the baseclass would be updated to be QueryWithLogin to help with admining the authentication, following the API of the other modules that deal with the need of authentication.

right = fk5_coords.ra.degree + (width/2)
pos = 'RANGE {} {} {} {}'.format(left, right, bottom, top)
else:
pos = 'CIRCLE {} {} {}'.format(fk5_coords.ra.degree, fk5_coords.dec.degree, 1*u.arcmin.to(u.deg))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

would it be possible to bring this 1 arcmin default out somewhere to be as a default?

I see that it would change the current API behaviour (there is already a minor change to default from ValueError to this default) to change that height+width takes the first case in the conditional then radius could be defaulted to the 1archmin in the signature?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've moved this to the signature of the query_region_async , _args_to_payload and cutout functions.

Comment on lines 131 to 135
if (band[0] is not None and not isinstance(band[0], u.Quantity)) or (band[1] is not None and not isinstance(band[1], u.Quantity)):
raise ValueError("The 'band' value must be a list of 2 wavelength or frequency values.")
if band[0] is not None and band[1] is not None and band[0].unit.physical_type != band[1].unit.physical_type:
raise ValueError("The 'band' values must have the same kind of units.")
if band[0] is not None or band[1] is not None:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: I feel these could be simplified a bit to not check the same things repeativly? (Though nested conditionals may not be that nice an alternative either).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried out a few approaches to simplifying these but none made it much better. I've pull out the band[0] is not None code into variables to hopefully make it more readable though.

request_payload['BAND'] = '{} {}'.format(min_band, max_band)

if kwargs.get('channel') is not None:
channel = kwargs.get('channel')
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: you could bring this out from the conditional, avoiding calling get() twice. Same for band above.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Change made

Comment on lines 151 to 154
if not isinstance(channel, (list, tuple)) or len(channel) != 2:
raise ValueError("The 'channel' value must be a list of 2 integer values.")
if (not isinstance(channel[0], int)) or (not isinstance(channel[1], int)):
raise ValueError("The 'channel' value must be a list of 2 integer values.")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: Maybe have just one long check to avoid duplicates?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Change made

bottom = fk5_coords.dec.degree + (height/2)
left = fk5_coords.ra.degree - (width/2)
right = fk5_coords.ra.degree + (width/2)
pos = 'RANGE {} {} {} {}'.format(left, right, top, bottom)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: using f-strings maybe easier/nicer to read here and elsewhere?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Change made - that's the first time I have encountered f-strings so thank-you for the suggestion.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, we couldn't really use them for a long time, but fortunately, we now dropped the old python versions that don't have it.

log.info("Adding parameters: " + str(cutout_spec))
resp = self._request('POST', job_location + '/parameters', data=cutout_spec, cache=False)
resp.raise_for_status()
return
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

no need for return here

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Removed

width : str or `astropy.units.Quantity`, optional
the width for a box cutout
band : list of `astropy.units.Quantity` with two elements, optional
the spectral range to be included, may be low and high wavelengths in metres or low and high frequencies in Hertz. Use None for an open bound.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: this is a bit long, please break the line at 120 or shorter

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated all code in this file to be 120 characters or less

The cutout support in AstroQuery allows both spatial and spectral cutouts.
To produce a spatial cutout, pass in a coordinate and either a radius or a height and a width to the :meth:`~astroquery.casda.CasdaClass.cutout` method.
To produce a spectral cutout, pass in either a band or a channel value.
For band, the value must be a list or tuple of two `astropy.units.Quantity` objects specifying a low and high frequency or wavelength. For an open ended range use `None` as the open value.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpick: break the long lines

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated the newly added content to be 120 characters or less

>>> import getpass
>>> centre = coordinates.SkyCoord.from_name('2MASX J08161181-7039447')
>>> username = 'email@somewhere.edu.au'
>>> password = getpass.getpass(str("Enter your OPAL password: "))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Overall it would be beneficial to switch to use the authenticated baseclass: QueryWithLogin, it would help you deal with the password promts to follow the usual way we do it in other modules.


@pytest.mark.skipif(('CASDA_USER' not in os.environ or
'CASDA_PASSWD' not in os.environ),
reason='Requires real CASDA user/password (CASDA_USER '
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Long term it would be nice to figure out some test user that we could use for testing purposes. E.g password stored as a token, or it would have access only some limited test data, etc.

@jd-au
Copy link
Contributor Author

jd-au commented Apr 20, 2022

I mostly have nitpick comments.

The bigger point is that I feel the module would benefit if the baseclass would be updated to be QueryWithLogin to help with admining the authentication, following the API of the other modules that deal with the need of authentication.

It might be best to do that as a separate PR, however I will start on it immediately so that both changes are in the same release

@bsipocz
Copy link
Member

bsipocz commented Apr 20, 2022

The bigger point is that I feel the module would benefit if the baseclass would be updated to be QueryWithLogin to help with admining the authentication, following the API of the other modules that deal with the need of authentication.

It might be best to do that as a separate PR, however I will start on it immediately so that both changes are in the same release

Yes, I agree that it's beyond the scope here and would better be in a separate PR.

@codecov
Copy link

codecov bot commented Apr 20, 2022

Codecov Report

Merging #2366 (aebbb34) into main (1368992) will increase coverage by 0.12%.
The diff coverage is 100.00%.

@@            Coverage Diff             @@
##             main    #2366      +/-   ##
==========================================
+ Coverage   63.17%   63.29%   +0.12%     
==========================================
  Files         132      132              
  Lines       17187    17241      +54     
==========================================
+ Hits        10858    10913      +55     
+ Misses       6329     6328       -1     
Impacted Files Coverage Δ
astroquery/casda/core.py 93.01% <100.00%> (+2.61%) ⬆️
astroquery/esa/hsa/core.py 36.55% <0.00%> (+0.88%) ⬆️

📣 Codecov can now indicate which changes are the most critical in Pull Requests. Learn more

Copy link
Member

@bsipocz bsipocz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you! I'll commit the one misunderstanding in the previous review and merge once tests pass.

bottom = fk5_coords.dec.degree + (height/2)
left = fk5_coords.ra.degree - (width/2)
right = fk5_coords.ra.degree + (width/2)
pos = 'RANGE {} {} {} {}'.format(left, right, top, bottom)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, we couldn't really use them for a long time, but fortunately, we now dropped the old python versions that don't have it.

astroquery/casda/core.py Outdated Show resolved Hide resolved
@bsipocz bsipocz force-pushed the CASDA-6552-Add-cutouts-for-CASDA branch from 944f149 to c69651f Compare April 22, 2022 04:22
@jd-au
Copy link
Contributor Author

jd-au commented Apr 22, 2022

Thank you! I'll commit the one misunderstanding in the previous review and merge once tests pass.

Thanks for the review! If you have an example of the approach you want with kwarg I can make the change

jd-au added 2 commits April 22, 2022 17:23
Also include support for numpy arrays for band and channel, and autocorrect the band and channel values to be in ascending order
@bsipocz bsipocz merged commit 65846ed into astropy:main Apr 22, 2022
@bsipocz
Copy link
Member

bsipocz commented Apr 22, 2022

Thanks @jd-au!

@bsipocz bsipocz added this to the v0.4.7 milestone Apr 22, 2022
@jd-au jd-au deleted the CASDA-6552-Add-cutouts-for-CASDA branch April 22, 2022 22:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants