{"record":{"id":"c5ba3aec2286ce96","repo":"projectdiscovery/katana","slug":"erremptypage","errorCode":"ErrEmptyPage","errorMessage":"page is empty","messagePattern":"page is empty","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"info","filePath":"pkg/engine/headless/crawler/state.go","lineNumber":65,"sourceCode":"\t\t\treturn originPageState.UniqueID, pageState, nil\n\t\t}\n\t}\n\n\treturn \"\", pageState, fmt.Errorf(\"failed to navigate back to origin page: %s != %s\", currentPageHash, action.OriginID)\n}\n\nfunc getPageHash(page *browser.BrowserPage) (string, *types.PageState, error) {\n\tpageState, err := newPageState(page, nil)\n\tif err == ErrEmptyPage {\n\t\treturn emptyPageHash, nil, nil\n\t}\n\tif err != nil {\n\t\treturn \"\", nil, errors.Wrap(err, \"could not get page state\")\n\t}\n\treturn pageState.UniqueID, pageState, nil\n}\n\nvar ErrEmptyPage = errors.New(\"page is empty\")\n\nfunc newPageState(page *browser.BrowserPage, action *types.Action) (*types.PageState, error) {\n\tpageInfo, err := page.Info()\n\tif err != nil {\n\t\treturn nil, errors.Wrap(err, \"could not get page info\")\n\t}\n\tif pageInfo.URL == \"\" || pageInfo.URL == \"about:blank\" {\n\t\treturn nil, ErrEmptyPage\n\t}\n\n\touterHTML, err := page.HTML()\n\tif err != nil {\n\t\treturn nil, errors.Wrap(err, \"could not get html content\")\n\t}\n\n\tstate := &types.PageState{\n\t\tURL:              pageInfo.URL,\n\t\tDOM:              outerHTML,","sourceCodeStart":47,"sourceCodeEnd":83,"githubUrl":"https://github.com/projectdiscovery/katana/blob/e3e742739c3746f085943ce918fb4e2b8daf6fe6/pkg/engine/headless/crawler/state.go#L47-L83","documentation":"ErrEmptyPage is produced by newPageState when page.Info() returns an empty URL or 'about:blank', meaning the browser tab holds no real page to snapshot. getPageHash treats it specially and returns the sentinel emptyPageHash instead of failing. It prevents blank tabs from being recorded as crawl states.","triggerScenarios":"newPageState called on a page whose Info().URL is \"\" or \"about:blank\" (state.go:73) — e.g. a freshly opened tab, a navigation that landed on about:blank, or a popup/target that never loaded.","commonSituations":"Popup-heavy sites opening about:blank windows before redirecting; SPA routes that briefly blank the document; timing races where the crawler snapshots the tab between navigations.","solutions":["Nothing to fix — the crawler silently uses emptyPageHash for such pages","If seen frequently, add navigation wait/delay so pages finish loading before state capture","Check hooks or custom navigations that might open new tabs that remain on about:blank"],"exampleFix":"// before: navigating then immediately snapshotting\npage.Navigate(url); state := newPageState(page, action)\n// after\npage.Navigate(url); page.WaitLoad(); state := newPageState(page, action)","handlingStrategy":"type-guard","validationCode":"info, err := page.Info()\nif err != nil || info.URL == \"\" || info.URL == \"about:blank\" {\n    page.WaitLoad() // or skip capturing this state\n}","typeGuard":"func isEmptyPage(err error) bool { return errors.Is(err, crawler.ErrEmptyPage) }","tryCatchPattern":"pageState, err := newPageState(page, action)\nif errors.Is(err, crawler.ErrEmptyPage) {\n    return emptyPageHash, nil, nil // mirror library behavior\n}","preventionTips":["Call page.WaitLoad() / navigation waits before snapshotting state","Configure popup blocking for popup-heavy sites","Ignore this error — the library already maps it to emptyPageHash"],"tags":["headless-browser","page-state","blank-page"],"backgroundTag":"empty-blank-page","analyzedSha":"e3e742739c3746f085943ce918fb4e2b8daf6fe6","analyzedAt":"2026-09-03T14:55:13.248Z","contentChangedAt":"2026-09-03T14:55:13.248Z","schemaVersion":2},"datasetVersion":"2026-09-10T17:17:09.494Z"}