Spaces:
Sleeping
Sleeping
Download scripts/verify_gdrive.py from StavanShah01/grownxt-server: direct link, hf CLI and curl.
- Browser
- Download file 17.8 kB
-
https://huggingface.co/spaces/StavanShah01/grownxt-server/resolve/main/scripts/verify_gdrive.py
- Command line
-
hf download hf://spaces/StavanShah01/grownxt-server/scripts/verify_gdrive.py
-
curl -L -o verify_gdrive.py https://huggingface.co/spaces/StavanShah01/grownxt-server/resolve/main/scripts/verify_gdrive.py
17.8 kB
| """Verification harness for the Google Drive delivery path. | |
| Every check runs against an in-memory stand-in for Drive, so the whole upload, | |
| sharing, token-refresh and caching path is verified with no credentials, no | |
| network, and nothing uploaded to a real account: | |
| venv/Scripts/python.exe -m scripts.verify_gdrive | |
| The invariants here are the ones that would otherwise fail quietly in | |
| production -- a second copy of every report accumulating in Drive, a report | |
| uploaded but never shared, a link that stops resolving after a rebuild, or a | |
| revoked grant reported as a transient error and retried forever. | |
| """ | |
| import json | |
| import logging | |
| import os | |
| from pathlib import Path | |
| import sys | |
| import tempfile | |
| import time | |
| sys.path.insert(0, str(Path(__file__).resolve().parent.parent)) | |
| from scripts import cli # noqa: E402 | |
| from scripts.checks import Report, banner # noqa: E402 | |
| import core.config as config # noqa: E402 | |
| import storage.gdrive as gdrive # noqa: E402 | |
| from storage.gdrive import ( # noqa: E402 | |
| API_BASE, | |
| TOKEN_URL, | |
| UPLOAD_BASE, | |
| DriveAuthError, | |
| DriveError, | |
| DriveStore, | |
| ensure_uploaded, | |
| ) | |
| PDF_BYTES = b"%PDF-1.7\n" + b"x" * 512 + b"\n%%EOF\n" | |
| class FakeResponse: | |
| """Minimal stand-in for a ``requests`` response.""" | |
| def __init__(self, status_code=200, payload=None, text=""): | |
| self.status_code = status_code | |
| self._payload = payload | |
| self.text = text or (json.dumps(payload) if payload is not None else "") | |
| def json(self): | |
| if self._payload is None: | |
| raise ValueError("no JSON body") | |
| return self._payload | |
| class FakeDrive: | |
| """An in-memory Drive: files with names, bytes, parents and permissions.""" | |
| def __init__(self, token_responses=None): | |
| self.files = {} | |
| self.permissions = {} | |
| self.calls = [] | |
| self.next_id = 1 | |
| self.token_responses = list(token_responses or []) | |
| self.token_calls = 0 | |
| # -- transport --------------------------------------------------------- | |
| def post(self, url, data=None, json=None, timeout=None, headers=None): | |
| """Handles the token endpoint; everything else goes through request().""" | |
| if url == TOKEN_URL: | |
| self.token_calls += 1 | |
| if self.token_responses: | |
| return self.token_responses.pop(0) | |
| return FakeResponse(200, {"access_token": "at-%d" % self.token_calls, "expires_in": 3600}) | |
| return self.request("POST", url, data=data, json=json, headers=headers) | |
| def request(self, method, url, headers=None, params=None, data=None, json=None, timeout=None): | |
| params = params or {} | |
| self.calls.append((method, url, params, headers or {})) | |
| if method == "GET" and url == "%s/files" % API_BASE: | |
| return self._list(params.get("q", "")) | |
| if method == "POST" and url == "%s/files" % UPLOAD_BASE: | |
| return self._create(data) | |
| if method == "PATCH" and url.startswith("%s/files/" % UPLOAD_BASE): | |
| return self._update(url.rsplit("/", 1)[-1], data) | |
| if url.endswith("/permissions"): | |
| file_id = url.rsplit("/", 2)[-2] | |
| if method == "GET": | |
| return FakeResponse(200, {"permissions": self.permissions.get(file_id, [])}) | |
| if method == "POST": | |
| grant = dict(json or {}) | |
| grant["id"] = "perm-%d" % (len(self.permissions.get(file_id, [])) + 1) | |
| self.permissions.setdefault(file_id, []).append(grant) | |
| return FakeResponse(200, {"id": grant["id"]}) | |
| return FakeResponse(404, {"error": {"message": "unrouted %s %s" % (method, url)}}) | |
| # -- behaviour --------------------------------------------------------- | |
| def _list(self, query): | |
| name = None | |
| if "name = '" in query: | |
| name = query.split("name = '", 1)[1].split("'", 1)[0] | |
| parent = None | |
| if " in parents" in query: | |
| parent = query.split("'", 1)[1].split("'", 1)[0] if query.startswith("'") else None | |
| for part in query.split(" and "): | |
| if part.endswith(" in parents"): | |
| parent = part.split("'")[1] | |
| matches = [ | |
| {"id": fid, "name": meta["name"]} | |
| for fid, meta in self.files.items() | |
| if meta["name"] == name and (parent is None or parent in meta.get("parents", [])) | |
| ] | |
| return FakeResponse(200, {"files": matches}) | |
| def _create(self, body): | |
| metadata = {} | |
| if body: | |
| text = body.decode("utf-8", "replace") | |
| start = text.find("{") | |
| end = text.find("}", start) | |
| if start >= 0 and end > start: | |
| metadata = json.loads(text[start:end + 1]) | |
| file_id = "file-%d" % self.next_id | |
| self.next_id += 1 | |
| self.files[file_id] = { | |
| "name": metadata.get("name", "unnamed"), | |
| "parents": metadata.get("parents", []), | |
| "bytes": body or b"", | |
| } | |
| return FakeResponse(200, { | |
| "id": file_id, | |
| "name": self.files[file_id]["name"], | |
| "webViewLink": "https://drive.google.com/file/d/%s/view" % file_id, | |
| }) | |
| def _update(self, file_id, body): | |
| if file_id not in self.files: | |
| return FakeResponse(404, {"error": {"message": "no such file"}}) | |
| self.files[file_id]["bytes"] = body or b"" | |
| self.files[file_id]["updates"] = self.files[file_id].get("updates", 0) + 1 | |
| return FakeResponse(200, { | |
| "id": file_id, | |
| "name": self.files[file_id]["name"], | |
| "webViewLink": "https://drive.google.com/file/d/%s/view" % file_id, | |
| }) | |
| def _store(fake, **kwargs): | |
| """Builds a store wired to a fake Drive.""" | |
| options = { | |
| "client_id": "cid", | |
| "client_secret": "secret", | |
| "refresh_token": "rt-original", | |
| "folder_id": "", | |
| "session": fake, | |
| } | |
| options.update(kwargs) | |
| return DriveStore(**options) | |
| def _write_pdf(directory: Path, body: bytes = PDF_BYTES) -> Path: | |
| """Writes a PDF into a directory and returns its path.""" | |
| directory.mkdir(parents=True, exist_ok=True) | |
| path = directory / "WIPRO_report.pdf" | |
| path.write_bytes(body) | |
| return path | |
| def check_configuration(r: Report) -> None: | |
| """Configuration and credential handling.""" | |
| saved = {k: os.environ.pop(k, None) for k in | |
| ("GDRIVE_CLIENT_ID", "GDRIVE_CLIENT_SECRET", "GDRIVE_REFRESH_TOKEN", "GDRIVE_TOKEN_FILE")} | |
| try: | |
| with tempfile.TemporaryDirectory() as tmp: | |
| os.environ["GDRIVE_TOKEN_FILE"] = str(Path(tmp) / "token.json") | |
| r.check("config.not_configured_reports_false", not gdrive.credentials_present(), | |
| "no credentials present") | |
| r.raises("config.missing_credentials_raise_auth_error", DriveAuthError, | |
| lambda: DriveStore(client_id="", client_secret="", refresh_token="")) | |
| os.environ["GDRIVE_CLIENT_ID"] = "cid" | |
| os.environ["GDRIVE_CLIENT_SECRET"] = "secret" | |
| os.environ["GDRIVE_REFRESH_TOKEN"] = "rt" | |
| r.check("config.env_credentials_detected", gdrive.credentials_present(), | |
| "client id, secret and refresh token seen") | |
| os.environ.pop("GDRIVE_REFRESH_TOKEN") | |
| path = gdrive.save_refresh_token("rt-from-file") | |
| r.check("config.token_file_is_read_back", | |
| gdrive.credentials_present() and gdrive._stored_token() == "rt-from-file", | |
| "token file %s supplies the grant" % Path(path).name) | |
| store = _store(FakeDrive(), refresh_token=None) | |
| r.check("config.token_file_beats_env", store.refresh_token == "rt-from-file", | |
| "the persisted token is preferred over the environment") | |
| finally: | |
| for key, value in saved.items(): | |
| if value is None: | |
| os.environ.pop(key, None) | |
| else: | |
| os.environ[key] = value | |
| def check_tokens(r: Report) -> None: | |
| """Access-token lifecycle: the part that keeps a long-running server alive.""" | |
| fake = FakeDrive() | |
| store = _store(fake) | |
| first = store.access_token() | |
| second = store.access_token() | |
| r.check("token.access_token_is_cached", first == second and fake.token_calls == 1, | |
| "two calls, one refresh (%s)" % first) | |
| store._expires_at = time.time() - 1 | |
| third = store.access_token() | |
| r.check("token.expiry_triggers_refresh", third != first and fake.token_calls == 2, | |
| "expired token replaced without intervention") | |
| fake = FakeDrive(token_responses=[ | |
| FakeResponse(400, {"error": "invalid_grant", | |
| "error_description": "Token has been expired or revoked."}), | |
| ]) | |
| store = _store(fake) | |
| r.raises("token.invalid_grant_is_terminal", DriveAuthError, store.access_token, | |
| "revoked grant surfaces as DriveAuthError") | |
| # A fresh store, because the rejection above consumed the queued response. | |
| store = _store(FakeDrive(token_responses=[ | |
| FakeResponse(400, {"error": "invalid_grant", | |
| "error_description": "Token has been expired or revoked."}), | |
| ])) | |
| message = "" | |
| try: | |
| store.access_token() | |
| except DriveAuthError as exc: | |
| message = str(exc) | |
| r.check("token.invalid_grant_says_how_to_fix", | |
| "scripts.gdrive_auth" in message and "Testing status" in message, | |
| "names the re-auth command and the 7-day cause") | |
| fake = FakeDrive(token_responses=[FakeResponse(503, {}, text="backend error")]) | |
| store = _store(fake) | |
| r.raises("token.transient_failure_is_not_auth_error", DriveError, store.access_token, | |
| "a 503 is retryable, not a lost grant") | |
| fake = FakeDrive(token_responses=[FakeResponse(503, {}, text="backend error")]) | |
| store = _store(fake) | |
| try: | |
| store.access_token() | |
| except DriveAuthError: | |
| r.check("token.transient_failure_not_misreported", False, "503 raised DriveAuthError") | |
| except DriveError: | |
| r.check("token.transient_failure_not_misreported", True, | |
| "DriveError, so the caller may retry") | |
| saved = os.environ.get("GDRIVE_TOKEN_FILE") | |
| with tempfile.TemporaryDirectory() as tmp: | |
| token_file = Path(tmp) / "token.json" | |
| os.environ["GDRIVE_TOKEN_FILE"] = str(token_file) | |
| try: | |
| fake = FakeDrive(token_responses=[FakeResponse(200, { | |
| "access_token": "at-rotated", "expires_in": 3600, "refresh_token": "rt-rotated"})]) | |
| store = _store(fake) | |
| store.access_token() | |
| persisted = json.loads(token_file.read_text(encoding="utf-8")).get("refresh_token") | |
| r.check("token.rotated_refresh_token_persisted", | |
| store.refresh_token == "rt-rotated" and persisted == "rt-rotated", | |
| "a rotated grant survives a restart") | |
| finally: | |
| if saved is None: | |
| os.environ.pop("GDRIVE_TOKEN_FILE", None) | |
| else: | |
| os.environ["GDRIVE_TOKEN_FILE"] = saved | |
| # A 401 mid-session: one silent retry, no error surfaced to the caller. | |
| fake = FakeDrive() | |
| calls = {"n": 0} | |
| original = fake.request | |
| def flaky(method, url, **kwargs): | |
| calls["n"] += 1 | |
| if calls["n"] == 1: | |
| return FakeResponse(401, {"error": {"message": "Invalid Credentials"}}) | |
| return original(method, url, **kwargs) | |
| fake.request = flaky | |
| store = _store(fake) | |
| store.find_by_name("WIPRO_report.pdf") | |
| r.check("token.401_retried_once_with_a_fresh_token", | |
| calls["n"] == 2 and fake.token_calls == 2, | |
| "one retry after re-minting the access token") | |
| def check_upload(r: Report) -> None: | |
| """Upload, replacement and sharing.""" | |
| with tempfile.TemporaryDirectory() as tmp: | |
| pdf = _write_pdf(Path(tmp)) | |
| fake = FakeDrive() | |
| store = _store(fake) | |
| first = store.upload(pdf) | |
| r.check("upload.creates_when_absent", len(fake.files) == 1 and first.file_id in fake.files, | |
| "one file created (%s)" % first.file_id) | |
| body = fake.files[first.file_id]["bytes"] | |
| r.check("upload.multipart_carries_metadata_and_pdf", | |
| b"WIPRO_report.pdf" in body and b"%PDF-1.7" in body, | |
| "%d bytes, metadata part and PDF part present" % len(body)) | |
| second = store.upload(pdf) | |
| r.check("upload.replaces_rather_than_duplicating", | |
| len(fake.files) == 1 and second.file_id == first.file_id, | |
| "second upload reused %s" % second.file_id) | |
| r.check("upload.replacement_is_a_media_patch", | |
| fake.files[first.file_id].get("updates") == 1, | |
| "existing file updated in place, so the link still resolves") | |
| r.check("share.link_sharing_is_the_default", | |
| any(p.get("type") == "anyone" and p.get("role") == "reader" | |
| for p in fake.permissions.get(first.file_id, [])), | |
| "anyone-with-link reader granted on upload") | |
| r.check("share.existing_grant_is_not_recreated", | |
| len(fake.permissions.get(first.file_id, [])) == 1, | |
| "one permission after two uploads") | |
| unshared = _store(FakeDrive()) | |
| result = unshared.upload(pdf, share=False) | |
| r.check("share.can_be_declined_explicitly", result.shared is False, | |
| "share=False leaves the file private") | |
| r.check("links.preview_link_is_embeddable", | |
| first.preview_link == "https://drive.google.com/file/d/%s/preview" % first.file_id, | |
| first.preview_link) | |
| r.check("links.direct_link_points_at_the_file", | |
| first.file_id in first.direct_link and "export=download" in first.direct_link, | |
| first.direct_link) | |
| fake = FakeDrive() | |
| store = _store(fake, folder_id="folder-123") | |
| placed = store.upload(pdf) | |
| r.check("upload.folder_id_is_applied", | |
| fake.files[placed.file_id]["parents"] == ["folder-123"], | |
| "file parented to the configured folder") | |
| fake = FakeDrive() | |
| store = _store(fake) | |
| store.find_by_name("O'Brien & Sons_report.pdf") | |
| query = [c for c in fake.calls if c[0] == "GET"][0][2].get("q", "") | |
| r.check("upload.name_query_escapes_quotes", "O\\'Brien" in query, | |
| "an apostrophe cannot break the query") | |
| missing = _store(FakeDrive()) | |
| r.raises("upload.missing_file_is_refused", DriveError, | |
| lambda: missing.upload(Path(tmp) / "nope.pdf")) | |
| def check_caching(r: Report) -> None: | |
| """The sidecar: what stops every request re-uploading the same report.""" | |
| original_output = config.OUTPUT_DIR | |
| with tempfile.TemporaryDirectory() as tmp: | |
| config.OUTPUT_DIR = Path(tmp) | |
| try: | |
| ticker = "WIPRO" | |
| pdf = _write_pdf(config.stock_dir(ticker)) | |
| fake = FakeDrive() | |
| store = _store(fake) | |
| first = ensure_uploaded(pdf, ticker, store=store) | |
| sidecar = gdrive.sidecar_path(ticker) | |
| record = json.loads(sidecar.read_text(encoding="utf-8")) | |
| r.check("cache.sidecar_written", sidecar.exists() and record.get("file_id") == first.file_id, | |
| "%s records the file id and links" % sidecar.name) | |
| r.check("cache.sidecar_records_content_hash", len(record.get("pdf_sha256", "")) == 64, | |
| "identity is the PDF's own hash") | |
| uploads_before = len(fake.calls) | |
| again = ensure_uploaded(pdf, ticker, store=store) | |
| r.check("cache.unchanged_pdf_is_not_reuploaded", | |
| len(fake.calls) == uploads_before and again.file_id == first.file_id, | |
| "no Drive calls for an unchanged report") | |
| pdf.write_bytes(PDF_BYTES + b"revised\n") | |
| changed = ensure_uploaded(pdf, ticker, store=store) | |
| r.check("cache.changed_pdf_is_reuploaded", | |
| changed.file_id == first.file_id and fake.files[first.file_id].get("updates") == 1, | |
| "same file id, new bytes -- the shared link is stable") | |
| new_record = json.loads(sidecar.read_text(encoding="utf-8")) | |
| r.check("cache.hash_advances_with_the_rebuild", | |
| new_record["pdf_sha256"] != record["pdf_sha256"], | |
| "sidecar tracks the new content") | |
| forced_before = fake.files[first.file_id].get("updates") | |
| ensure_uploaded(pdf, ticker, store=store, force=True) | |
| r.check("cache.force_reuploads_identical_bytes", | |
| fake.files[first.file_id].get("updates") == forced_before + 1, | |
| "force=True bypasses the hash check") | |
| gdrive.sidecar_path(ticker).write_text("{ not json", encoding="utf-8") | |
| recovered = ensure_uploaded(pdf, ticker, store=store) | |
| r.check("cache.corrupt_sidecar_is_survivable", bool(recovered.file_id), | |
| "an unreadable sidecar re-uploads instead of crashing") | |
| finally: | |
| config.OUTPUT_DIR = original_output | |
| def main() -> int: | |
| """Runs every check and returns a process exit code.""" | |
| cli.setup(logging.CRITICAL) | |
| banner("Google Drive delivery verification (offline)") | |
| report = Report() | |
| for title, group in (("Configuration", check_configuration), | |
| ("Token handling", check_tokens), | |
| ("Upload and sharing", check_upload), | |
| ("Upload caching", check_caching)): | |
| report.section(title) | |
| group(report) | |
| print(report.render()) | |
| return report.finish() | |
| if __name__ == "__main__": | |
| sys.exit(main()) | |