def _login(self, username=None, store_password=False, reenter_password=False): """ Login to the ESO User Portal. Parameters ---------- username : str, optional Username to the ESO Public Portal. If not given, it should be specified in the config file. store_password : bool, optional Stores the password securely in your keyring. Default is False. reenter_password : bool, optional Asks for the password even if it is already stored in the keyring. This is the way to overwrite an already stored passwork on the keyring. Default is False. """ if username is None: if self.USERNAME != "": username = self.USERNAME elif self.username is not None: username = self.username else: raise LoginError("If you do not pass a username to login(), " "you should configure a default one!") else: # store username as we may need it to re-authenticate self.username = username # Get password from keyring or prompt password, password_from_keyring = self._get_password( "astroquery:www.eso.org", username, reenter=reenter_password) # Authenticate log.info("Authenticating {0} on www.eso.org...".format(username)) # Do not cache pieces of the login process login_response = self._request("GET", "https://www.eso.org/sso/login", cache=False) root = BeautifulSoup(login_response.content, 'html5lib') login_input = root.find(name='input', attrs={'name': 'execution'}) if login_input is None: raise ValueError("ESO login page did not have the correct attributes.") execution = login_input.get('value') login_result_response = self._request("POST", "https://www.eso.org/sso/login", data={'username': username, 'password': password, 'execution': execution, '_eventId': 'submit', 'geolocation': '', }) login_result_response.raise_for_status() root = BeautifulSoup(login_result_response.content, 'html5lib') authenticated = root.find('h4').text == 'Login successful' if authenticated: log.info("Authentication successful!") else: log.exception("Authentication failed!") # When authenticated, save password in keyring if needed if authenticated and password_from_keyring is None and store_password: keyring.set_password("astroquery:www.eso.org", username, password) return authenticated
def download_file(self, uri, *, local_path=None, base_url=None, cache=True, cloud_only=False): """ Downloads a single file based on the data URI Parameters ---------- uri : str The product dataURI, e.g. mast:JWST/product/jw00736-o039_t001_miri_ch1-long_x1d.fits local_path : str Directory in which the files will be downloaded. Defaults to current working directory. base_url: str A base url to use when downloading. Default is the MAST Portal API cache : bool Default is True. If file is found on disk it will not be downloaded again. cloud_only : bool, optional Default False. If set to True and cloud data access is enabled (see `enable_cloud_dataset`) files that are not found in the cloud will be skipped rather than downloaded from MAST as is the default behavior. If cloud access is not enables this argument as no affect. Returns ------- status: str download status message. Either COMPLETE, SKIPPED, or ERROR. msg : str An error status message, if any. url : str The full url download path """ # create the full data URL base_url = base_url if base_url else self._portal_api_connection.MAST_DOWNLOAD_URL data_url = base_url + "?uri=" + uri # create a local file path if none is input. Use current directory as default. if not local_path: filename = os.path.basename(uri) local_path = os.path.join(os.path.abspath('.'), filename) # recreate the data_product key for cloud connection check data_product = {'dataURI': uri} status = "COMPLETE" msg = None url = None try: if self._cloud_connection is not None and self._cloud_connection.is_supported(data_product): try: self._cloud_connection.download_file(data_product, local_path, cache) except Exception as ex: log.exception("Error pulling from S3 bucket: {}".format(ex)) if cloud_only: log.warn("Skipping file...") local_path = "" status = "SKIPPED" else: log.warn("Falling back to mast download...") self._download_file(data_url, local_path, cache=cache, head_safe=True, continuation=False) else: self._download_file(data_url, local_path, cache=cache, head_safe=True, continuation=False) # check if file exists also this is where would perform md5, # and also check the filesize if the database reliably reported file sizes if (not os.path.isfile(local_path)) and (status != "SKIPPED"): status = "ERROR" msg = "File was not downloaded" url = data_url except HTTPError as err: status = "ERROR" msg = "HTTPError: {0}".format(err) url = data_url return status, msg, url
def _login(self, username=None, store_password=False, reenter_password=False): """ Login to the NRAO archive Parameters ---------- username : str, optional Username to the NRAO archive. If not given, it should be specified in the config file. store_password : bool, optional Stores the password securely in your keyring. Default is False. reenter_password : bool, optional Asks for the password even if it is already stored in the keyring. This is the way to overwrite an already stored passwork on the keyring. Default is False. """ # Developer notes: # Login via https://my.nrao.edu/cas/login # # this can be added to auto-redirect back to the query tool: # ?service=https://archive.nrao.edu/archive/advquery.jsp if username is None: if not self.USERNAME: raise LoginError("If you do not pass a username to login(), " "you should configure a default one!") else: username = self.USERNAME # Check if already logged in loginpage = self._request("GET", "https://my.nrao.edu/cas/login", cache=False) root = BeautifulSoup(loginpage.content, 'html5lib') if root.find('div', class_='success'): log.info("Already logged in.") return True # Get password from keyring or prompt password, password_from_keyring = self._get_password( "astroquery:my.nrao.edu", username, reenter=reenter_password) # Authenticate log.info("Authenticating {0} on my.nrao.edu ...".format(username)) # Do not cache pieces of the login process data = { kw: root.find('input', {'name': kw})['value'] for kw in ('lt', '_eventId', 'execution') } data['username'] = username data['password'] = password data['execution'] = 'e1s1' # not sure if needed data['_eventId'] = 'submit' data['submit'] = 'LOGIN' login_response = self._request("POST", "https://my.nrao.edu/cas/login", data=data, cache=False) authenticated = ('You have successfully logged in' in login_response.text) if authenticated: log.info("Authentication successful!") self.USERNAME = username else: log.exception("Authentication failed!") # When authenticated, save password in keyring if needed if authenticated and password_from_keyring is None and store_password: keyring.set_password("astroquery:my.nrao.edu", username, password) return authenticated
def _login(self, username=None, store_password=False, reenter_password=False, auth_urls=auth_urls): """ Login to the ALMA Science Portal. Parameters ---------- username : str, optional Username to the ALMA Science Portal. If not given, it should be specified in the config file. store_password : bool, optional Stores the password securely in your keyring. Default is False. reenter_password : bool, optional Asks for the password even if it is already stored in the keyring. This is the way to overwrite an already stored passwork on the keyring. Default is False. """ success = False for auth_url in auth_urls: # set session cookies (they do not get set otherwise) cookiesetpage = self._request("GET", urljoin(self._get_dataarchive_url(), 'rh/forceAuthentication'), cache=False) self._login_cookiepage = cookiesetpage cookiesetpage.raise_for_status() if (auth_url+'/cas/login' in cookiesetpage.request.url): # we've hit a target, we're good success = True break if not success: raise LoginError("Could not log in to any of the known ALMA " "authorization portals: {0}".format(auth_urls)) # Check if already logged in loginpage = self._request("GET", "https://{auth_url}/cas/login".format(auth_url=auth_url), cache=False) root = BeautifulSoup(loginpage.content, 'html5lib') if root.find('div', class_='success'): log.info("Already logged in.") return True self._auth_url = auth_url username, password = self._get_auth_info(username=username, store_password=store_password, reenter_password=reenter_password) # Authenticate log.info("Authenticating {0} on {1} ...".format(username, auth_url)) # Do not cache pieces of the login process data = {kw: root.find('input', {'name': kw})['value'] for kw in ('execution', '_eventId')} data['username'] = username data['password'] = password data['submit'] = 'LOGIN' login_response = self._request("POST", "https://{0}/cas/login".format(auth_url), params={'service': self._get_dataarchive_url()}, data=data, cache=False) # save the login response for debugging purposes self._login_response = login_response # do not expose password back to user del data['password'] # but save the parameters for debug purposes self._login_parameters = data authenticated = ('You have successfully logged in' in login_response.text) if authenticated: log.info("Authentication successful!") self.USERNAME = username else: log.exception("Authentication failed!") return authenticated