def no_retry_auth(e): if hasattr(e, "exception"): e = e.exception if not isinstance(e, requests.HTTPError): return True # Don't retry bad request errors; raise immediately if e.response.status_code == 400: return False # Retry all non-forbidden/unauthorized/not-found errors. if e.response.status_code not in (401, 403, 404): return True # Crash w/message on forbidden/unauthorized errors. if e.response.status_code == 401: raise CommError("Invalid or missing api_key. Run wandb login") elif wandb.run: raise CommError("Permission denied to access {}".format(wandb.run.path)) else: raise CommError("Permission denied, ask the project owner to grant you access")
def wrapper(*args, **kwargs): message = "Whoa, you found a bug." try: return func(*args, **kwargs) except requests.HTTPError as err: raise CommError(err.response, err) except RetryError as err: if ("response" in dir(err.last_exception) and err.last_exception.response is not None): try: message = err.last_exception.response.json().get( "errors", [{ "message": message }])[0]["message"] except ValueError: message = err.last_exception.response.text else: message = err.last_exception if env.is_debug(): six.reraise(type(err.last_exception), err.last_exception, sys.exc_info()[2]) else: six.reraise(CommError, CommError(message, err.last_exception), sys.exc_info()[2]) except Exception as err: # gql raises server errors with dict's as strings... if len(err.args) > 0: payload = err.args[0] else: payload = err if str(payload).startswith("{"): message = ast.literal_eval(str(payload))["message"] else: message = str(err) if env.is_debug(): six.reraise(*sys.exc_info()) else: six.reraise(CommError, CommError(message, err), sys.exc_info()[2])
def parse_slug(self, slug, project=None, run=None): if slug and "/" in slug: parts = slug.split("/") project = parts[0] run = parts[1] else: project = project or self.settings().get("project") if project is None: raise CommError("No default project configured.") run = run or slug or env.get_run(env=self._environ) if run is None: run = "latest" return (project, run)
def read(self, size=-1): """Read bytes and call the callback""" bites = self.file.read(size) self.bytes_read += len(bites) if not bites and self.bytes_read < self.len: # Files shrinking during uploads causes request timeouts. Maybe # we could avoid those by updating the self.len in real-time, but # files getting truncated while uploading seems like something # that shouldn't really be happening anyway. raise CommError( "File {} size shrank from {} to {} while it was being uploaded." .format(self.file.name, self.len, self.bytes_read)) # Growing files are also likely to be bad, but our code didn't break # on those in the past so it's riskier to make that an error now. self.callback(len(bites), self.bytes_read) return bites
def upload_urls(self, project, files, run=None, entity=None, description=None): """Generate temporary resumeable upload urls Arguments: project (str): The project to download files (list or dict): The filenames to upload run (str): The run to upload to entity (str, optional): The entity to scope this project to. Defaults to wandb models Returns: (bucket_id, file_info) bucket_id: id of bucket we uploaded to file_info: A dict of filenames and urls, also indicates if this revision already has uploaded files. { 'weights.h5': { "url": "https://weights.url" }, 'model.json': { "url": "https://model.json", "updatedAt": '2013-04-26T22:22:23.832Z', 'md5': 'mZFLkyvTelC5g8XnyQrpOw==' }, } """ query = gql(""" query Model($name: String!, $files: [String]!, $entity: String!, $run: String!, $description: String) { model(name: $name, entityName: $entity) { bucket(name: $run, desc: $description) { id files(names: $files) { uploadHeaders edges { node { name url(upload: true) updatedAt } } } } } } """) run_id = run or self.current_run_id assert run, "run must be specified" entity = entity or self.settings("entity") query_result = self.gql( query, variable_values={ "name": project, "run": run_id, "entity": entity, "description": description, "files": [file for file in files], }, ) run = query_result["model"]["bucket"] if run: result = { file["name"]: file for file in self._flatten_edges(run["files"]) } return run["id"], run["files"]["uploadHeaders"], result else: raise CommError("Run does not exist {}/{}/{}.".format( entity, project, run_id))