How to Capture a Full-Page Screenshot of a Member Portal After Email Magic-Link Login
Sign in through the email link in the browser you will use, confirm the member page, then capture and inspect its full scrollable content.
Complete the email magic-link sign-in in the browser session that can access the member portal. Confirm that the correct member account and page are open, wait for the content you need to load, then capture the full scrollable page. In Playwright, use await page.screenshot({ path: 'member-page.png', fullPage: true }). Inspect the saved image: a successful screenshot call does not confirm the account, page state, or completeness of dynamic content.
1. Sign in and confirm the right page
- Open the portal and request its email sign-in link using its normal login flow.
- Open the link in the browser session you intend to use for the capture. If your email app opens the link on another device or in another browser, that session may not have the portal login; the next step depends on the portal and its identity provider.
- Confirm the member account and exact page. Check that the page is not showing a sign-in prompt, an error, or stale content.
- Wait for the content that matters to appear. A full-page screenshot includes the scrollable page, but it does not guarantee that lazy images, delayed widgets, or content loaded during scrolling have finished rendering.
- Capture the page and inspect the image from top to bottom before storing or sharing it.
Playwright describes a full-page screenshot as capturing the full scrollable page as though it were displayed on a very tall screen. Puppeteer also supports a fullPage screenshot option. These APIs capture a visual record, not a structured export of portal data. See the Playwright screenshot guide and Puppeteer screenshot guide.
2. Capture with Playwright
Use the existing browser context that completed authentication. This example assumes the portal is already open in the Playwright page; it does not attempt to automate an unknown email or magic-link flow.
import { chromium } from 'playwright';
const browser = await chromium.launch({ headless: false });
const context = await browser.newContext();
const page = await context.newPage();
try {
// Complete the portal's email-link sign-in in this browser context,
// then navigate to the member page you intend to capture.
await page.goto('https://portal.example/member', { waitUntil: 'domcontentloaded' });
// Replace this with a selector that identifies content you need.
await page.locator('main').waitFor({ state: 'visible', timeout: 30000 });
await page.screenshot({ path: 'member-page.png', fullPage: true });
} finally {
await browser.close();
}
For a one-off capture, run the browser visibly, complete sign-in manually, and take the screenshot from that same page and context. For a repeatable workflow, persist an authenticated browser context only if the portal permits it and you can protect the stored session data. Do not put a one-time sign-in link or session credentials in source control or logs.
The Playwright API also supports element screenshots, page screenshots, and full-page capture. The CLI offers a full-page option as well. Use full-page mode for a whole page; use an element capture when you only need a specific region.
3. Capture with Puppeteer
Puppeteer uses the same general sequence: authenticate in the browser context, open the target member page, wait for content, and call Page.screenshot() with fullPage: true.
import puppeteer from 'puppeteer';
const browser = await puppeteer.launch({ headless: false });
const page = await browser.newPage();
try {
// Complete sign-in in this browser, then open the member page.
await page.goto('https://portal.example/member', { waitUntil: 'domcontentloaded' });
await page.waitForSelector('main', { visible: true, timeout: 30000 });
await page.screenshot({ path: 'member-page.png', fullPage: true });
} finally {
await browser.close();
}
Consult the Puppeteer screenshot guide and its ScreenshotOptions API for the current option details.
4. Other ways to capture
For a one-time image, a browser’s built-in full-page capture or a capture extension may be more convenient than writing a script. The exact steps and extension privacy practices vary, so check the browser’s current documentation and the extension’s handling of authenticated pages before use. The research sources here verify Playwright and Puppeteer APIs, not a particular browser menu path or extension.
Choose based on whether you need a repeatable script, whether you can sign in in the required browser context, and how you will save and protect the output. Neither Playwright nor Puppeteer can be assumed to complete an unknown portal’s authentication automatically.
5. Firebase email-link details, if the portal uses Firebase
Magic link is a general term; the portal’s provider is not known from the URL alone. Firebase is one documented example. Its web flow checks whether the incoming URL is a sign-in link, then completes sign-in with the user’s email and the link. The email used to finish must match the address that received the link. See the Firebase email-link sign-in guide.
Firebase specifically warns against passing the email address in redirect URL parameters and reusing it to complete sign-in, because that can enable session injection. It recommends HTTPS in production. Invalid or expired codes can also fail. These are Firebase-specific instructions, not universal rules for every portal. Follow the portal’s own sign-in and recovery guidance.
6. Review, privacy, and sharing
- Check the top and bottom: confirm the capture starts and ends where expected.
- Check dynamic areas: look for missing lazy-loaded images, loading placeholders, clipped content, or sections that changed during capture.
- Check identity and sensitive data: verify the account and remove or protect information that should not be distributed.
- Protect the sign-in flow: do not forward the one-time email link as part of sharing the screenshot.
- Follow portal rules: check its terms and policies before storing, publishing, or sharing a member page.
A screenshot is an image of what the browser displayed. It does not prove that the viewer had permission to access the account or that the displayed information is complete or current.
7. Troubleshooting
| Symptom | Likely cause | What to do |
|---|---|---|
| The page shows a login screen after opening the email link | The link opened in a different browser or device, the session was not established, or the link is invalid or expired. | Return to the portal’s normal login flow and complete sign-in in the browser context used for capture. Follow the portal’s instructions if it asks you to request a fresh link. |
| The sign-in link is rejected | The link may be expired, invalid, or handled by a provider-specific flow. | Request a new link through the portal and follow its steps. If the portal uses Firebase, use the same email address that received the link and follow Firebase’s email-link guidance. |
| The screenshot contains only the visible viewport | The full-page option was omitted or not enabled. | Set fullPage: true in Playwright or Puppeteer and capture again. |
| Lower sections or images are blank | Content may be lazy-loaded, delayed, or loaded only as the page scrolls. | Wait for the relevant content or selector, scroll through the page if needed to trigger loading, then capture and inspect again. There is no universal wait condition for every portal. |
| The capture ends early or content is clipped | The page may have changed while capturing, or a dynamic layout may not have settled. | Wait for the page to stabilize, retry, and compare the saved image with the page. Capture separate sections if a very long or changing page cannot be represented reliably in one image. |
| The screenshot is correct but unsafe to share | Authenticated pages can contain personal or account information. | Restrict access to the image, redact information where appropriate, and follow the portal’s policies before sharing. |
8. Performance, reliability, and cost
Full-page images can be much taller and larger than viewport screenshots, so capture time, memory use, and output size depend on page length, rendering, and image content. Keep the browser open until the screenshot call completes. For long pages or unstable content, wait for the specific content you need and inspect the output rather than assuming that a generic network-idle condition means every widget is ready.
For repeat captures, reuse the project’s existing browser tooling where practical and keep authentication handling separate from screenshot logic. Protect any saved browser state and output files as member data. Browser-based capture uses your browser runtime and infrastructure; the cost depends on those resources and your hosting setup.
Or skip the browser setup
If you already have an accessible page URL, ScreenshotNeo can return a screenshot with one GET request. It is a website screenshot API and MCP server for developers, made by Yorker Media. See the ScreenshotNeo website and API documentation. The endpoint captures the URL it can access; it does not sign in to a private portal on your behalf. A page that requires the authenticated browser session described above may still need the browser workflow.
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
import requests
r = requests.get(
"https://api.screenshotneo.com/v1/shot",
params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"},
timeout=90,
)
r.raise_for_status()
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
if (!res.ok) throw new Error(`Screenshot request failed: ${res.status}`);
await Bun.write('shot.webp', res);
Replace the example URL with a page the service can access. ScreenshotNeo removes cookie and consent banners, newsletter popups, and chat widgets before capture; each cleanup step can be turned off. Bot checks, blank pages, timeouts, failed loads, and cache hits cost nothing, and response headers report the page verdict and billing status. Its MCP server gives AI agents tools for screenshots, page information, and PDF capture. The free plan includes 1,000 screenshots each month with no card; paid plans start at $5 for 3,000 shots. Sign up for 1,000 free screenshots a month, no card required.
FAQ
Does a full-page screenshot include content below the fold?
Yes, when using the documented full-page option. Verify that delayed or lazy-loaded content is present in the resulting image.
Can a screenshot confirm that the right member is signed in?
No. Confirm the account in the browser before capture and inspect the image afterward.
Can I use ScreenshotNeo for a page behind a magic-link login?
Only if the target page is accessible to the screenshot request. ScreenshotNeo is not a substitute for completing a private portal’s authentication in its required browser session.
Should I share the screenshot?
Only if the portal’s rules and the information shown allow it. Treat both the image and the one-time sign-in link as sensitive.


