mcp-scraper 0.93.3 → 0.93.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +34 -27
- package/README.md +3 -3
- package/THIRD_PARTY_NOTICES.html +203 -0
- package/dist/bin/api-server.js +1 -1
- package/dist/bin/mcp-scraper-cli.js +1 -1
- package/dist/bin/mcp-scraper-core.js +1 -1
- package/dist/bin/mcp-scraper-install.js +1 -1
- package/dist/bin/mcp-stdio-server.js +1 -1
- package/dist/bin/paa-harvest.js +1 -1
- package/dist/chunk-2SP57VCG.js +15 -15
- package/dist/{chunk-BS4V4CVX.js → chunk-4O2FOBZR.js} +1 -1
- package/dist/chunk-DT2FYN6N.js +1 -1
- package/dist/chunk-M5QHXNFZ.js +3 -3
- package/dist/chunk-M5VZVMPC.js +3 -3
- package/dist/chunk-ORB4RHCK.js +4 -4
- package/dist/{chunk-4FGLXXZ2.js → chunk-OYJ4HES6.js} +4 -4
- package/dist/chunk-POASCYQ7.js +1 -0
- package/dist/chunk-SH5KB4P7.js +1 -1
- package/dist/chunk-WJ4XFLS4.js +15 -15
- package/dist/chunk-Y6MKMSOC.js +1 -1
- package/dist/chunk-ZG52SKGD.js +3 -3
- package/dist/index.cjs +21 -21
- package/dist/index.d.cts +14 -14
- package/dist/index.d.ts +14 -14
- package/dist/{server-G2ZCSWXW.js → server-HAV33FP7.js} +42 -42
- package/package.json +17 -136
- package/dist/chunk-SWCAKYBP.js +0 -1
package/dist/index.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
"use strict";var xo=Object.create;var cn=Object.defineProperty;var Oo=Object.getOwnPropertyDescriptor;var Ro=Object.getOwnPropertyNames;var Wo=Object.getPrototypeOf,Ho=Object.prototype.hasOwnProperty;var Bo=(e,t)=>{for(var n in t)cn(e,n,{get:t[n],enumerable:!0})},ui=(e,t,n,a)=>{if(t&&typeof t=="object"||typeof t=="function")for(let i of Ro(t))!Ho.call(e,i)&&i!==n&&cn(e,i,{get:()=>t[i],enumerable:!(a=Oo(t,i))||a.enumerable});return e};var hn=(e,t,n)=>(n=e!=null?xo(Wo(e)):{},ui(t||!e||!e.__esModule?cn(n,"default",{value:e,enumerable:!0}):n,e)),Do=e=>ui(cn({},"__esModule",{value:!0}),e);var tS={};Bo(tS,{VideoGenerator:()=>Zn,buildClipPrompts:()=>Xn,harvest:()=>ko});module.exports=Do(tS);var v=require("zod"),gn="none",Fo="none";function De(e){switch(e){case"day":return"qdr:d";case"week":return"qdr:w";case"month":return"qdr:m";case"year":return"qdr:y";default:return}}var aS=v.z.object({businessName:v.z.string().min(1),location:v.z.string().min(1),gl:v.z.string().length(2).default("us"),hl:v.z.string().length(2).default("en"),includeReviews:v.z.boolean().default(!1),maxReviews:v.z.number().int().min(1).max(500).default(50),includeServices:v.z.boolean().default(!1),includeImages:v.z.boolean().default(!1),imageScope:v.z.enum(["owner","all"]).default("all"),maxImages:v.z.number().int().min(1).max(250).default(100),maxInlineImages:v.z.number().int().min(0).max(5).default(3),kernelApiKey:v.z.string().optional(),kernelProxyId:v.z.string().optional(),headless:v.z.boolean().default(!0)}),iS=v.z.object({query:v.z.string().min(1),location:v.z.string().optional(),gl:v.z.string().length(2).default("us"),hl:v.z.string().length(2).default("en"),maxResults:v.z.number().int().min(1).max(50).default(10),includeServices:v.z.boolean().default(!1),proxyMode:v.z.enum(["location","configured","none"]).default(Fo),proxyZip:v.z.string().regex(/^\d{5}$/).optional(),serpRedirect:v.z.boolean().optional(),forceDirectEgress:v.z.boolean().optional(),debug:v.z.boolean().default(!1),kernelApiKey:v.z.string().optional(),kernelProxyId:v.z.string().optional(),kernelProxyResolution:v.z.unknown().optional(),headless:v.z.boolean().default(!0)}),sS=v.z.object({name:v.z.string().nullable(),rating:v.z.string().nullable(),reviewCount:v.z.string().nullable(),category:v.z.string().nullable(),address:v.z.string().nullable(),hoursSummary:v.z.string().nullable(),phone:v.z.string().nullable(),phoneDisplay:v.z.string().nullable(),website:v.z.string().nullable(),plusCode:v.z.string().nullable(),bookingUrl:v.z.string().nullable()}),oS=v.z.object({day:v.z.string(),hours:v.z.string()}),rS=v.z.object({reviewHistogram:v.z.array(v.z.object({stars:v.z.number(),count:v.z.string()})),reviewTopics:v.z.array(v.z.object({label:v.z.string(),count:v.z.string()}))}),dS=v.z.object({reviewId:v.z.string(),author:v.z.string().nullable(),stars:v.z.string().nullable(),date:v.z.string().nullable(),text:v.z.string().nullable(),ownerResponse:v.z.string().nullable()}),lS=v.z.object({section:v.z.string(),attribute:v.z.string()});var A=require("zod");var ea=A.z.object({query:A.z.string().min(1),location:A.z.string().optional(),gl:A.z.string().length(2).default("us"),hl:A.z.string().length(2).default("en"),device:A.z.enum(["desktop","mobile"]).default("desktop"),proxyMode:A.z.enum(["location","configured","none"]).default(gn),proxyZip:A.z.string().regex(/^\d{5}$/).optional(),keepDefaultProxy:A.z.boolean().optional(),requireUsEgress:A.z.boolean().optional(),maxAttempts:A.z.number().int().min(1).max(12).optional(),debug:A.z.boolean().default(!1),depth:A.z.number().int().min(1).max(30).default(3),maxQuestions:A.z.number().int().min(1).max(100).default(100),headless:A.z.boolean().default(!1),profileDir:A.z.string().optional(),proxy:A.z.string().url().optional(),kernelApiKey:A.z.string().optional(),kernelProxyId:A.z.string().optional(),kernelProfileName:A.z.string().optional(),kernelProfileSaveChanges:A.z.boolean().optional(),kernelStealth:A.z.boolean().optional(),serpIdentity:A.z.string().regex(/^[a-z0-9][a-z0-9_-]{0,63}$/).optional(),kernelProxyResolution:A.z.unknown().optional(),outputDir:A.z.string().default("./paa-output"),format:A.z.enum(["json","csv","both"]).default("both"),serpOnly:A.z.boolean().default(!1),questionsOnly:A.z.boolean().default(!1),questionGrowthRecoveryRounds:A.z.number().int().min(0).max(4).default(2),pages:A.z.number().int().min(1).max(2).default(1),includeAllSerpFeatures:A.z.boolean().default(!1),includeLocalPack:A.z.boolean().default(!1),includeForums:A.z.boolean().default(!1),includeVideos:A.z.boolean().default(!1),includeAiOverview:A.z.boolean().default(!1),includeWhatPeopleSaying:A.z.boolean().default(!1),includeShortVideos:A.z.boolean().default(!1),recency:A.z.enum(["day","week","month","year"]).optional(),softDeadlineMs:A.z.number().optional()}),ci=A.z.object({questionId:A.z.string().min(1),googleLinkId:A.z.string().nullable(),googleEvidenceId:A.z.string().nullable(),question:A.z.string().min(1),answer:A.z.string().optional(),sourceTitle:A.z.string().optional(),sourceSite:A.z.string().optional(),sourceCite:A.z.string().optional(),sources:A.z.array(A.z.object({title:A.z.string().nullable(),site:A.z.string().nullable(),url:A.z.string().min(1),rawUrl:A.z.string().min(1),resolvedUrl:A.z.string().nullable(),linkType:A.z.enum(["plain","google_url_redirect","google_goto_redirect"]),resolutionStatus:A.z.enum(["not_needed","resolved","unresolved","rejected"])})).default([])});function hi(){return(process.env.BROWSER_SERVICE_API_KEY??process.env.KERNEL_API_KEY)?.trim()||void 0}var Rn=require("playwright-extra"),Ts=hn(require("puppeteer-extra-plugin-stealth"),1),ks=require("playwright");function tt(e,t,n,a,i){if(a==="m")throw new TypeError("Private method is not writable");if(a==="a"&&!i)throw new TypeError("Private accessor was defined without a setter");if(typeof t=="function"?e!==t||!i:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return a==="a"?i.call(e,n):i?i.value=n:t.set(e,n),n}function K(e,t,n,a){if(n==="a"&&!a)throw new TypeError("Private accessor was defined without a getter");if(typeof t=="function"?e!==t||!a:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return n==="m"?a:n==="a"?a.call(e):a?a.value:t.get(e)}var na=function(){let{crypto:e}=globalThis;if(e?.randomUUID)return na=e.randomUUID.bind(e),e.randomUUID();let t=new Uint8Array(1),n=e?()=>e.getRandomValues(t)[0]:()=>Math.random()*255&255;return"10000000-1000-4000-8000-100000000000".replace(/[018]/g,a=>(+a^n()&15>>+a/4).toString(16))};function Fe(e){return typeof e=="object"&&e!==null&&("name"in e&&e.name==="AbortError"||"message"in e&&String(e.message).includes("FetchRequestCanceledException"))}var Ge=e=>{if(e instanceof Error)return e;if(typeof e=="object"&&e!==null){try{if(Object.prototype.toString.call(e)==="[object Error]"){let t=new Error(e.message,e.cause?{cause:e.cause}:{});return e.stack&&(t.stack=e.stack),e.cause&&!t.cause&&(t.cause=e.cause),e.name&&(t.name=e.name),t}}catch{}try{return new Error(JSON.stringify(e))}catch{}}return new Error(e)};var Y=class extends Error{},nt=class e extends Y{constructor(t,n,a,i){super(`${e.makeMessage(t,n,a)}`),this.status=t,this.headers=i,this.error=n}static makeMessage(t,n,a){let i=n?.message?typeof n.message=="string"?n.message:JSON.stringify(n.message):n?JSON.stringify(n):a;return t&&i?`${t} ${i}`:t?`${t} status code (no body)`:i||"(no status code or body)"}static generate(t,n,a,i){if(!t||!i)return new Et({message:a,cause:Ge(n)});let s=n;return t===400?new de(t,s,a,i):t===401?new le(t,s,a,i):t===403?new Se(t,s,a,i):t===404?new Ue(t,s,a,i):t===409?new ue(t,s,a,i):t===422?new ce(t,s,a,i):t===429?new he(t,s,a,i):t>=500?new ge(t,s,a,i):new e(t,s,a,i)}},ot=class extends nt{constructor({message:t}={}){super(void 0,void 0,t||"Request was aborted.",void 0)}},Et=class extends nt{constructor({message:t,cause:n}){super(void 0,void 0,t||"Connection error.",void 0),n&&(this.cause=n)}},ft=class extends Et{constructor({message:t}={}){super({message:t??"Request timed out."})}},de=class extends nt{},le=class extends nt{},Se=class extends nt{},Ue=class extends nt{},ue=class extends nt{},ce=class extends nt{},he=class extends nt{},ge=class extends nt{};var Yo=/^[a-z][a-z0-9+.-]*:/i,gi=e=>Yo.test(e),at=e=>(at=Array.isArray,at(e)),aa=at;function ia(e){return typeof e!="object"?{}:e??{}}function sa(e){if(!e)return!0;for(let t in e)return!1;return!0}function pi(e,t){return Object.prototype.hasOwnProperty.call(e,t)}var wi=(e,t)=>{if(typeof t!="number"||!Number.isInteger(t))throw new Y(`${e} must be an integer`);if(t<0)throw new Y(`${e} must be a positive integer`);return t},Ko=e=>{if(typeof e=="number")return Math.round(e);if(typeof e=="string")return parseInt(e,10);throw new Y(`Could not coerce ${e} (type: ${typeof e}) into a number`)};var Jo=e=>typeof e=="boolean"?e:typeof e=="string"?e==="true":!!e,mi=e=>{if(e!=null)return Ko(e)};var oa=e=>{if(e!=null)return Jo(e)},yi=e=>{try{return JSON.parse(e)}catch{return}};var Ci=e=>new Promise(t=>setTimeout(t,e));var Pt="0.93.0";function qo(){return typeof Deno<"u"&&Deno.build!=null?"deno":typeof EdgeRuntime<"u"?"edge":Object.prototype.toString.call(typeof globalThis.process<"u"?globalThis.process:0)==="[object process]"?"node":"unknown"}var Xo=()=>{let e=qo();if(e==="deno")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":ki(Deno.build.os),"X-Stainless-Arch":Ti(Deno.build.arch),"X-Stainless-Runtime":"deno","X-Stainless-Runtime-Version":typeof Deno.version=="string"?Deno.version:Deno.version?.deno??"unknown"};if(typeof EdgeRuntime<"u")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":`other:${EdgeRuntime}`,"X-Stainless-Runtime":"edge","X-Stainless-Runtime-Version":globalThis.process.version};if(e==="node")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":ki(globalThis.process.platform??"unknown"),"X-Stainless-Arch":Ti(globalThis.process.arch??"unknown"),"X-Stainless-Runtime":"node","X-Stainless-Runtime-Version":globalThis.process.version??"unknown"};let t=jo();return t?{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":"unknown","X-Stainless-Runtime":`browser:${t.browser}`,"X-Stainless-Runtime-Version":t.version}:{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":"unknown","X-Stainless-Runtime":"unknown","X-Stainless-Runtime-Version":"unknown"}};function jo(){if(typeof navigator>"u"||!navigator)return null;let e=[{key:"edge",pattern:/Edge(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"ie",pattern:/MSIE(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"ie",pattern:/Trident(?:.*rv\:(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"chrome",pattern:/Chrome(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"firefox",pattern:/Firefox(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"safari",pattern:/(?:Version\W+(\d+)\.(\d+)(?:\.(\d+))?)?(?:\W+Mobile\S*)?\W+Safari/}];for(let{key:t,pattern:n}of e){let a=n.exec(navigator.userAgent);if(a){let i=a[1]||0,s=a[2]||0,o=a[3]||0;return{browser:t,version:`${i}.${s}.${o}`}}}return null}var Ti=e=>e==="x32"?"x32":e==="x86_64"||e==="x64"?"x64":e==="arm"?"arm":e==="aarch64"||e==="arm64"?"arm64":e?`other:${e}`:"unknown",ki=e=>(e=e.toLowerCase(),e.includes("ios")?"iOS":e==="android"?"Android":e==="darwin"?"MacOS":e==="win32"?"Windows":e==="freebsd"?"FreeBSD":e==="openbsd"?"OpenBSD":e==="linux"?"Linux":e?`Other:${e}`:"Unknown"),fi,Mi=()=>fi??(fi=Xo());function Ni(){if(typeof fetch<"u")return fetch;throw new Error("`fetch` is not defined as a global; Either pass `fetch` to the client, `new Kernel({ fetch })` or polyfill the global, `globalThis.fetch = fetch`")}function ra(...e){let t=globalThis.ReadableStream;if(typeof t>"u")throw new Error("`ReadableStream` is not defined as a global; You will need to polyfill it, `globalThis.ReadableStream = ReadableStream`");return new t(...e)}function pn(e){let t=Symbol.asyncIterator in e?e[Symbol.asyncIterator]():e[Symbol.iterator]();return ra({start(){},async pull(n){let{done:a,value:i}=await t.next();a?n.close():n.enqueue(i)},async cancel(){await t.return?.()}})}function da(e){if(e[Symbol.asyncIterator])return e;let t=e.getReader();return{async next(){try{let n=await t.read();return n?.done&&t.releaseLock(),n}catch(n){throw t.releaseLock(),n}},async return(){let n=t.cancel();return t.releaseLock(),await n,{done:!0,value:void 0}},[Symbol.asyncIterator](){return this}}}async function vi(e){if(e===null||typeof e!="object")return;if(e[Symbol.asyncIterator]){await e[Symbol.asyncIterator]().return?.();return}let t=e.getReader(),n=t.cancel();t.releaseLock(),await n}var _i=({headers:e,body:t})=>({bodyHeaders:{"content-type":"application/json"},body:JSON.stringify(t)});var la="RFC3986",Sa=e=>String(e),Ua={RFC1738:e=>String(e).replace(/%20/g,"+"),RFC3986:Sa},bi="RFC1738";var wn=(e,t)=>(wn=Object.hasOwn??Function.prototype.call.bind(Object.prototype.hasOwnProperty),wn(e,t)),yt=(()=>{let e=[];for(let t=0;t<256;++t)e.push("%"+((t<16?"0":"")+t.toString(16)).toUpperCase());return e})();var ua=1024,Ei=(e,t,n,a,i)=>{if(e.length===0)return e;let s=e;if(typeof e=="symbol"?s=Symbol.prototype.toString.call(e):typeof e!="string"&&(s=String(e)),n==="iso-8859-1")return escape(s).replace(/%u[0-9a-f]{4}/gi,function(d){return"%26%23"+parseInt(d.slice(2),16)+"%3B"});let o="";for(let d=0;d<s.length;d+=ua){let l=s.length>=ua?s.slice(d,d+ua):s,U=[];for(let S=0;S<l.length;++S){let r=l.charCodeAt(S);if(r===45||r===46||r===95||r===126||r>=48&&r<=57||r>=65&&r<=90||r>=97&&r<=122||i===bi&&(r===40||r===41)){U[U.length]=l.charAt(S);continue}if(r<128){U[U.length]=yt[r];continue}if(r<2048){U[U.length]=yt[192|r>>6]+yt[128|r&63];continue}if(r<55296||r>=57344){U[U.length]=yt[224|r>>12]+yt[128|r>>6&63]+yt[128|r&63];continue}S+=1,r=65536+((r&1023)<<10|l.charCodeAt(S)&1023),U[U.length]=yt[240|r>>18]+yt[128|r>>12&63]+yt[128|r>>6&63]+yt[128|r&63]}o+=U.join("")}return o};function Pi(e){return!e||typeof e!="object"?!1:!!(e.constructor&&e.constructor.isBuffer&&e.constructor.isBuffer(e))}function ca(e,t){if(at(e)){let n=[];for(let a=0;a<e.length;a+=1)n.push(t(e[a]));return n}return t(e)}var Ai={brackets(e){return String(e)+"[]"},comma:"comma",indices(e,t){return String(e)+"["+t+"]"},repeat(e){return String(e)}},Li=function(e,t){Array.prototype.push.apply(e,at(t)?t:[t])},Ii,z={addQueryPrefix:!1,allowDots:!1,allowEmptyArrays:!1,arrayFormat:"indices",charset:"utf-8",charsetSentinel:!1,delimiter:"&",encode:!0,encodeDotInKeys:!1,encoder:Ei,encodeValuesOnly:!1,format:la,formatter:Sa,indices:!1,serializeDate(e){return(Ii??(Ii=Function.prototype.call.bind(Date.prototype.toISOString)))(e)},skipNulls:!1,strictNullHandling:!1};function Qo(e){return typeof e=="string"||typeof e=="number"||typeof e=="boolean"||typeof e=="symbol"||typeof e=="bigint"}var ha={};function xi(e,t,n,a,i,s,o,d,l,U,S,r,u,c,h,w,k,f){let m=e,L=f,R=0,D=!1;for(;(L=L.get(ha))!==void 0&&!D;){let y=L.get(e);if(R+=1,typeof y<"u"){if(y===R)throw new RangeError("Cyclic object value");D=!0}typeof L.get(ha)>"u"&&(R=0)}if(typeof U=="function"?m=U(t,m):m instanceof Date?m=u?.(m):n==="comma"&&at(m)&&(m=ca(m,function(y){return y instanceof Date?u?.(y):y})),m===null){if(s)return l&&!w?l(t,z.encoder,k,"key",c):t;m=""}if(Qo(m)||Pi(m)){if(l){let y=w?t:l(t,z.encoder,k,"key",c);return[h?.(y)+"="+h?.(l(m,z.encoder,k,"value",c))]}return[h?.(t)+"="+h?.(String(m))]}let _=[];if(typeof m>"u")return _;let M;if(n==="comma"&&at(m))w&&l&&(m=ca(m,l)),M=[{value:m.length>0?m.join(",")||null:void 0}];else if(at(U))M=U;else{let y=Object.keys(m);M=S?y.sort(S):y}let H=d?String(t).replace(/\./g,"%2E"):String(t),P=a&&at(m)&&m.length===1?H+"[]":H;if(i&&at(m)&&m.length===0)return P+"[]";for(let y=0;y<M.length;++y){let E=M[y],p=typeof E=="object"&&typeof E.value<"u"?E.value:m[E];if(o&&p===null)continue;let T=r&&d?E.replace(/\./g,"%2E"):E,N=at(m)?typeof n=="function"?n(P,T):P:P+(r?"."+T:"["+T+"]");f.set(e,R);let I=new WeakMap;I.set(ha,f),Li(_,xi(p,N,n,a,i,s,o,d,n==="comma"&&w&&at(m)?null:l,U,S,r,u,c,h,w,k,I))}return _}function Zo(e=z){if(typeof e.allowEmptyArrays<"u"&&typeof e.allowEmptyArrays!="boolean")throw new TypeError("`allowEmptyArrays` option can only be `true` or `false`, when provided");if(typeof e.encodeDotInKeys<"u"&&typeof e.encodeDotInKeys!="boolean")throw new TypeError("`encodeDotInKeys` option can only be `true` or `false`, when provided");if(e.encoder!==null&&typeof e.encoder<"u"&&typeof e.encoder!="function")throw new TypeError("Encoder has to be a function.");let t=e.charset||z.charset;if(typeof e.charset<"u"&&e.charset!=="utf-8"&&e.charset!=="iso-8859-1")throw new TypeError("The charset option must be either utf-8, iso-8859-1, or undefined");let n=la;if(typeof e.format<"u"){if(!wn(Ua,e.format))throw new TypeError("Unknown format option provided.");n=e.format}let a=Ua[n],i=z.filter;(typeof e.filter=="function"||at(e.filter))&&(i=e.filter);let s;if(e.arrayFormat&&e.arrayFormat in Ai?s=e.arrayFormat:"indices"in e?s=e.indices?"indices":"repeat":s=z.arrayFormat,"commaRoundTrip"in e&&typeof e.commaRoundTrip!="boolean")throw new TypeError("`commaRoundTrip` must be a boolean, or absent");let o=typeof e.allowDots>"u"?e.encodeDotInKeys?!0:z.allowDots:!!e.allowDots;return{addQueryPrefix:typeof e.addQueryPrefix=="boolean"?e.addQueryPrefix:z.addQueryPrefix,allowDots:o,allowEmptyArrays:typeof e.allowEmptyArrays=="boolean"?!!e.allowEmptyArrays:z.allowEmptyArrays,arrayFormat:s,charset:t,charsetSentinel:typeof e.charsetSentinel=="boolean"?e.charsetSentinel:z.charsetSentinel,commaRoundTrip:!!e.commaRoundTrip,delimiter:typeof e.delimiter>"u"?z.delimiter:e.delimiter,encode:typeof e.encode=="boolean"?e.encode:z.encode,encodeDotInKeys:typeof e.encodeDotInKeys=="boolean"?e.encodeDotInKeys:z.encodeDotInKeys,encoder:typeof e.encoder=="function"?e.encoder:z.encoder,encodeValuesOnly:typeof e.encodeValuesOnly=="boolean"?e.encodeValuesOnly:z.encodeValuesOnly,filter:i,format:n,formatter:a,serializeDate:typeof e.serializeDate=="function"?e.serializeDate:z.serializeDate,skipNulls:typeof e.skipNulls=="boolean"?e.skipNulls:z.skipNulls,sort:typeof e.sort=="function"?e.sort:null,strictNullHandling:typeof e.strictNullHandling=="boolean"?e.strictNullHandling:z.strictNullHandling}}function Oi(e,t={}){let n=e,a=Zo(t),i,s;typeof a.filter=="function"?(s=a.filter,n=s("",n)):at(a.filter)&&(s=a.filter,i=s);let o=[];if(typeof n!="object"||n===null)return"";let d=Ai[a.arrayFormat],l=d==="comma"&&a.commaRoundTrip;i||(i=Object.keys(n)),a.sort&&i.sort(a.sort);let U=new WeakMap;for(let u=0;u<i.length;++u){let c=i[u];a.skipNulls&&n[c]===null||Li(o,xi(n[c],c,d,l,a.allowEmptyArrays,a.strictNullHandling,a.skipNulls,a.encodeDotInKeys,a.encode?a.encoder:null,a.filter,a.sort,a.allowDots,a.serializeDate,a.format,a.formatter,a.encodeValuesOnly,a.charset,U))}let S=o.join(a.delimiter),r=a.addQueryPrefix===!0?"?":"";return a.charsetSentinel&&(a.charset==="iso-8859-1"?r+="utf8=%26%2310003%3B&":r+="utf8=%E2%9C%93&"),S.length>0?r+S:""}function Ri(e){return Oi(e,{arrayFormat:"comma"})}function Bi(e){let t=0;for(let i of e)t+=i.length;let n=new Uint8Array(t),a=0;for(let i of e)n.set(i,a),a+=i.length;return n}var Wi;function Ve(e){let t;return(Wi??(t=new globalThis.TextEncoder,Wi=t.encode.bind(t)))(e)}var Hi;function ga(e){let t;return(Hi??(t=new globalThis.TextDecoder,Hi=t.decode.bind(t)))(e)}var Ut,ut,Bt=class{constructor(){Ut.set(this,void 0),ut.set(this,void 0),tt(this,Ut,new Uint8Array,"f"),tt(this,ut,null,"f")}decode(t){if(t==null)return[];let n=t instanceof ArrayBuffer?new Uint8Array(t):typeof t=="string"?Ve(t):t;tt(this,Ut,Bi([K(this,Ut,"f"),n]),"f");let a=[],i;for(;(i=er(K(this,Ut,"f"),K(this,ut,"f")))!=null;){if(i.carriage&&K(this,ut,"f")==null){tt(this,ut,i.index,"f");continue}if(K(this,ut,"f")!=null&&(i.index!==K(this,ut,"f")+1||i.carriage)){a.push(ga(K(this,Ut,"f").subarray(0,K(this,ut,"f")-1))),tt(this,Ut,K(this,Ut,"f").subarray(K(this,ut,"f")),"f"),tt(this,ut,null,"f");continue}let s=K(this,ut,"f")!==null?i.preceding-1:i.preceding,o=ga(K(this,Ut,"f").subarray(0,s));a.push(o),tt(this,Ut,K(this,Ut,"f").subarray(i.index),"f"),tt(this,ut,null,"f")}return a}flush(){return K(this,Ut,"f").length?this.decode(`
|
|
1
|
+
"use strict";var xo=Object.create;var cn=Object.defineProperty;var Oo=Object.getOwnPropertyDescriptor;var Ro=Object.getOwnPropertyNames;var Wo=Object.getPrototypeOf,Ho=Object.prototype.hasOwnProperty;var Bo=(e,t)=>{for(var n in t)cn(e,n,{get:t[n],enumerable:!0})},ui=(e,t,n,a)=>{if(t&&typeof t=="object"||typeof t=="function")for(let i of Ro(t))!Ho.call(e,i)&&i!==n&&cn(e,i,{get:()=>t[i],enumerable:!(a=Oo(t,i))||a.enumerable});return e};var hn=(e,t,n)=>(n=e!=null?xo(Wo(e)):{},ui(t||!e||!e.__esModule?cn(n,"default",{value:e,enumerable:!0}):n,e)),Do=e=>ui(cn({},"__esModule",{value:!0}),e);var tS={};Bo(tS,{VideoGenerator:()=>Zn,buildClipPrompts:()=>Xn,harvest:()=>ko});module.exports=Do(tS);var v=require("zod"),gn="none",Fo="none";function De(e){switch(e){case"day":return"qdr:d";case"week":return"qdr:w";case"month":return"qdr:m";case"year":return"qdr:y";default:return}}var aS=v.z.object({businessName:v.z.string().min(1),location:v.z.string().min(1),gl:v.z.string().length(2).default("us"),hl:v.z.string().length(2).default("en"),includeReviews:v.z.boolean().default(!1),maxReviews:v.z.number().int().min(1).max(500).default(50),includeServices:v.z.boolean().default(!1),includeImages:v.z.boolean().default(!1),imageScope:v.z.enum(["owner","all"]).default("all"),maxImages:v.z.number().int().min(1).max(250).default(100),maxInlineImages:v.z.number().int().min(0).max(5).default(3),\u006b\u0065\u0072\u006e\u0065\u006cApiKey:v.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProxyId:v.z.string().optional(),headless:v.z.boolean().default(!0)}),iS=v.z.object({query:v.z.string().min(1),location:v.z.string().optional(),gl:v.z.string().length(2).default("us"),hl:v.z.string().length(2).default("en"),maxResults:v.z.number().int().min(1).max(50).default(10),includeServices:v.z.boolean().default(!1),proxyMode:v.z.enum(["location","configured","none"]).default(Fo),proxyZip:v.z.string().regex(/^\d{5}$/).optional(),serpRedirect:v.z.boolean().optional(),forceDirectEgress:v.z.boolean().optional(),debug:v.z.boolean().default(!1),\u006b\u0065\u0072\u006e\u0065\u006cApiKey:v.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProxyId:v.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution:v.z.unknown().optional(),headless:v.z.boolean().default(!0)}),sS=v.z.object({name:v.z.string().nullable(),rating:v.z.string().nullable(),reviewCount:v.z.string().nullable(),category:v.z.string().nullable(),address:v.z.string().nullable(),hoursSummary:v.z.string().nullable(),phone:v.z.string().nullable(),phoneDisplay:v.z.string().nullable(),website:v.z.string().nullable(),plusCode:v.z.string().nullable(),bookingUrl:v.z.string().nullable()}),oS=v.z.object({day:v.z.string(),hours:v.z.string()}),rS=v.z.object({reviewHistogram:v.z.array(v.z.object({stars:v.z.number(),count:v.z.string()})),reviewTopics:v.z.array(v.z.object({label:v.z.string(),count:v.z.string()}))}),dS=v.z.object({reviewId:v.z.string(),author:v.z.string().nullable(),stars:v.z.string().nullable(),date:v.z.string().nullable(),text:v.z.string().nullable(),ownerResponse:v.z.string().nullable()}),lS=v.z.object({section:v.z.string(),attribute:v.z.string()});var A=require("zod");var ea=A.z.object({query:A.z.string().min(1),location:A.z.string().optional(),gl:A.z.string().length(2).default("us"),hl:A.z.string().length(2).default("en"),device:A.z.enum(["desktop","mobile"]).default("desktop"),proxyMode:A.z.enum(["location","configured","none"]).default(gn),proxyZip:A.z.string().regex(/^\d{5}$/).optional(),keepDefaultProxy:A.z.boolean().optional(),requireUsEgress:A.z.boolean().optional(),maxAttempts:A.z.number().int().min(1).max(12).optional(),debug:A.z.boolean().default(!1),depth:A.z.number().int().min(1).max(30).default(3),maxQuestions:A.z.number().int().min(1).max(100).default(100),headless:A.z.boolean().default(!1),profileDir:A.z.string().optional(),proxy:A.z.string().url().optional(),\u006b\u0065\u0072\u006e\u0065\u006cApiKey:A.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProxyId:A.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProfileName:A.z.string().optional(),\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges:A.z.boolean().optional(),\u006b\u0065\u0072\u006e\u0065\u006cStealth:A.z.boolean().optional(),serpIdentity:A.z.string().regex(/^[a-z0-9][a-z0-9_-]{0,63}$/).optional(),\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution:A.z.unknown().optional(),outputDir:A.z.string().default("./paa-output"),format:A.z.enum(["json","csv","both"]).default("both"),serpOnly:A.z.boolean().default(!1),questionsOnly:A.z.boolean().default(!1),questionGrowthRecoveryRounds:A.z.number().int().min(0).max(4).default(2),pages:A.z.number().int().min(1).max(2).default(1),includeAllSerpFeatures:A.z.boolean().default(!1),includeLocalPack:A.z.boolean().default(!1),includeForums:A.z.boolean().default(!1),includeVideos:A.z.boolean().default(!1),includeAiOverview:A.z.boolean().default(!1),includeWhatPeopleSaying:A.z.boolean().default(!1),includeShortVideos:A.z.boolean().default(!1),recency:A.z.enum(["day","week","month","year"]).optional(),softDeadlineMs:A.z.number().optional()}),ci=A.z.object({questionId:A.z.string().min(1),googleLinkId:A.z.string().nullable(),googleEvidenceId:A.z.string().nullable(),question:A.z.string().min(1),answer:A.z.string().optional(),sourceTitle:A.z.string().optional(),sourceSite:A.z.string().optional(),sourceCite:A.z.string().optional(),sources:A.z.array(A.z.object({title:A.z.string().nullable(),site:A.z.string().nullable(),url:A.z.string().min(1),rawUrl:A.z.string().min(1),resolvedUrl:A.z.string().nullable(),linkType:A.z.enum(["plain","google_url_redirect","google_goto_redirect"]),resolutionStatus:A.z.enum(["not_needed","resolved","unresolved","rejected"])})).default([])});function hi(){return(process.env.BROWSER_SERVICE_API_KEY??process.env.\u004b\u0045\u0052\u004e\u0045\u004c_API_KEY)?.trim()||void 0}var Rn=require("playwright-extra"),Ts=hn(require("puppeteer-extra-plugin-stealth"),1),ks=require("playwright");function tt(e,t,n,a,i){if(a==="m")throw new TypeError("Private method is not writable");if(a==="a"&&!i)throw new TypeError("Private accessor was defined without a setter");if(typeof t=="function"?e!==t||!i:!t.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return a==="a"?i.call(e,n):i?i.value=n:t.set(e,n),n}function K(e,t,n,a){if(n==="a"&&!a)throw new TypeError("Private accessor was defined without a getter");if(typeof t=="function"?e!==t||!a:!t.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return n==="m"?a:n==="a"?a.call(e):a?a.value:t.get(e)}var na=function(){let{crypto:e}=globalThis;if(e?.randomUUID)return na=e.randomUUID.bind(e),e.randomUUID();let t=new Uint8Array(1),n=e?()=>e.getRandomValues(t)[0]:()=>Math.random()*255&255;return"10000000-1000-4000-8000-100000000000".replace(/[018]/g,a=>(+a^n()&15>>+a/4).toString(16))};function Fe(e){return typeof e=="object"&&e!==null&&("name"in e&&e.name==="AbortError"||"message"in e&&String(e.message).includes("FetchRequestCanceledException"))}var Ge=e=>{if(e instanceof Error)return e;if(typeof e=="object"&&e!==null){try{if(Object.prototype.toString.call(e)==="[object Error]"){let t=new Error(e.message,e.cause?{cause:e.cause}:{});return e.stack&&(t.stack=e.stack),e.cause&&!t.cause&&(t.cause=e.cause),e.name&&(t.name=e.name),t}}catch{}try{return new Error(JSON.stringify(e))}catch{}}return new Error(e)};var Y=class extends Error{},nt=class e extends Y{constructor(t,n,a,i){super(`${e.makeMessage(t,n,a)}`),this.status=t,this.headers=i,this.error=n}static makeMessage(t,n,a){let i=n?.message?typeof n.message=="string"?n.message:JSON.stringify(n.message):n?JSON.stringify(n):a;return t&&i?`${t} ${i}`:t?`${t} status code (no body)`:i||"(no status code or body)"}static generate(t,n,a,i){if(!t||!i)return new Et({message:a,cause:Ge(n)});let s=n;return t===400?new de(t,s,a,i):t===401?new le(t,s,a,i):t===403?new Se(t,s,a,i):t===404?new Ue(t,s,a,i):t===409?new ue(t,s,a,i):t===422?new ce(t,s,a,i):t===429?new he(t,s,a,i):t>=500?new ge(t,s,a,i):new e(t,s,a,i)}},ot=class extends nt{constructor({message:t}={}){super(void 0,void 0,t||"Request was aborted.",void 0)}},Et=class extends nt{constructor({message:t,cause:n}){super(void 0,void 0,t||"Connection error.",void 0),n&&(this.cause=n)}},ft=class extends Et{constructor({message:t}={}){super({message:t??"Request timed out."})}},de=class extends nt{},le=class extends nt{},Se=class extends nt{},Ue=class extends nt{},ue=class extends nt{},ce=class extends nt{},he=class extends nt{},ge=class extends nt{};var Yo=/^[a-z][a-z0-9+.-]*:/i,gi=e=>Yo.test(e),at=e=>(at=Array.isArray,at(e)),aa=at;function ia(e){return typeof e!="object"?{}:e??{}}function sa(e){if(!e)return!0;for(let t in e)return!1;return!0}function pi(e,t){return Object.prototype.hasOwnProperty.call(e,t)}var wi=(e,t)=>{if(typeof t!="number"||!Number.isInteger(t))throw new Y(`${e} must be an integer`);if(t<0)throw new Y(`${e} must be a positive integer`);return t},Ko=e=>{if(typeof e=="number")return Math.round(e);if(typeof e=="string")return parseInt(e,10);throw new Y(`Could not coerce ${e} (type: ${typeof e}) into a number`)};var Jo=e=>typeof e=="boolean"?e:typeof e=="string"?e==="true":!!e,mi=e=>{if(e!=null)return Ko(e)};var oa=e=>{if(e!=null)return Jo(e)},yi=e=>{try{return JSON.parse(e)}catch{return}};var Ci=e=>new Promise(t=>setTimeout(t,e));var Pt="0.93.0";function qo(){return typeof Deno<"u"&&Deno.build!=null?"deno":typeof EdgeRuntime<"u"?"edge":Object.prototype.toString.call(typeof globalThis.process<"u"?globalThis.process:0)==="[object process]"?"node":"unknown"}var Xo=()=>{let e=qo();if(e==="deno")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":ki(Deno.build.os),"X-Stainless-Arch":Ti(Deno.build.arch),"X-Stainless-Runtime":"deno","X-Stainless-Runtime-Version":typeof Deno.version=="string"?Deno.version:Deno.version?.deno??"unknown"};if(typeof EdgeRuntime<"u")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":`other:${EdgeRuntime}`,"X-Stainless-Runtime":"edge","X-Stainless-Runtime-Version":globalThis.process.version};if(e==="node")return{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":ki(globalThis.process.platform??"unknown"),"X-Stainless-Arch":Ti(globalThis.process.arch??"unknown"),"X-Stainless-Runtime":"node","X-Stainless-Runtime-Version":globalThis.process.version??"unknown"};let t=jo();return t?{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":"unknown","X-Stainless-Runtime":`browser:${t.browser}`,"X-Stainless-Runtime-Version":t.version}:{"X-Stainless-Lang":"js","X-Stainless-Package-Version":Pt,"X-Stainless-OS":"Unknown","X-Stainless-Arch":"unknown","X-Stainless-Runtime":"unknown","X-Stainless-Runtime-Version":"unknown"}};function jo(){if(typeof navigator>"u"||!navigator)return null;let e=[{key:"edge",pattern:/Edge(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"ie",pattern:/MSIE(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"ie",pattern:/Trident(?:.*rv\:(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"chrome",pattern:/Chrome(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"firefox",pattern:/Firefox(?:\W+(\d+)\.(\d+)(?:\.(\d+))?)?/},{key:"safari",pattern:/(?:Version\W+(\d+)\.(\d+)(?:\.(\d+))?)?(?:\W+Mobile\S*)?\W+Safari/}];for(let{key:t,pattern:n}of e){let a=n.exec(navigator.userAgent);if(a){let i=a[1]||0,s=a[2]||0,o=a[3]||0;return{browser:t,version:`${i}.${s}.${o}`}}}return null}var Ti=e=>e==="x32"?"x32":e==="x86_64"||e==="x64"?"x64":e==="arm"?"arm":e==="aarch64"||e==="arm64"?"arm64":e?`other:${e}`:"unknown",ki=e=>(e=e.toLowerCase(),e.includes("ios")?"iOS":e==="android"?"Android":e==="darwin"?"MacOS":e==="win32"?"Windows":e==="freebsd"?"FreeBSD":e==="openbsd"?"OpenBSD":e==="linux"?"Linux":e?`Other:${e}`:"Unknown"),fi,Mi=()=>fi??(fi=Xo());function Ni(){if(typeof fetch<"u")return fetch;throw new Error("`fetch` is not defined as a global; Either pass `fetch` to the client, `new \u004b\u0065\u0072\u006e\u0065\u006c({ fetch })` or polyfill the global, `globalThis.fetch = fetch`")}function ra(...e){let t=globalThis.ReadableStream;if(typeof t>"u")throw new Error("`ReadableStream` is not defined as a global; You will need to polyfill it, `globalThis.ReadableStream = ReadableStream`");return new t(...e)}function pn(e){let t=Symbol.asyncIterator in e?e[Symbol.asyncIterator]():e[Symbol.iterator]();return ra({start(){},async pull(n){let{done:a,value:i}=await t.next();a?n.close():n.enqueue(i)},async cancel(){await t.return?.()}})}function da(e){if(e[Symbol.asyncIterator])return e;let t=e.getReader();return{async next(){try{let n=await t.read();return n?.done&&t.releaseLock(),n}catch(n){throw t.releaseLock(),n}},async return(){let n=t.cancel();return t.releaseLock(),await n,{done:!0,value:void 0}},[Symbol.asyncIterator](){return this}}}async function vi(e){if(e===null||typeof e!="object")return;if(e[Symbol.asyncIterator]){await e[Symbol.asyncIterator]().return?.();return}let t=e.getReader(),n=t.cancel();t.releaseLock(),await n}var _i=({headers:e,body:t})=>({bodyHeaders:{"content-type":"application/json"},body:JSON.stringify(t)});var la="RFC3986",Sa=e=>String(e),Ua={RFC1738:e=>String(e).replace(/%20/g,"+"),RFC3986:Sa},bi="RFC1738";var wn=(e,t)=>(wn=Object.hasOwn??Function.prototype.call.bind(Object.prototype.hasOwnProperty),wn(e,t)),yt=(()=>{let e=[];for(let t=0;t<256;++t)e.push("%"+((t<16?"0":"")+t.toString(16)).toUpperCase());return e})();var ua=1024,Ei=(e,t,n,a,i)=>{if(e.length===0)return e;let s=e;if(typeof e=="symbol"?s=Symbol.prototype.toString.call(e):typeof e!="string"&&(s=String(e)),n==="iso-8859-1")return escape(s).replace(/%u[0-9a-f]{4}/gi,function(d){return"%26%23"+parseInt(d.slice(2),16)+"%3B"});let o="";for(let d=0;d<s.length;d+=ua){let l=s.length>=ua?s.slice(d,d+ua):s,U=[];for(let S=0;S<l.length;++S){let r=l.charCodeAt(S);if(r===45||r===46||r===95||r===126||r>=48&&r<=57||r>=65&&r<=90||r>=97&&r<=122||i===bi&&(r===40||r===41)){U[U.length]=l.charAt(S);continue}if(r<128){U[U.length]=yt[r];continue}if(r<2048){U[U.length]=yt[192|r>>6]+yt[128|r&63];continue}if(r<55296||r>=57344){U[U.length]=yt[224|r>>12]+yt[128|r>>6&63]+yt[128|r&63];continue}S+=1,r=65536+((r&1023)<<10|l.charCodeAt(S)&1023),U[U.length]=yt[240|r>>18]+yt[128|r>>12&63]+yt[128|r>>6&63]+yt[128|r&63]}o+=U.join("")}return o};function Pi(e){return!e||typeof e!="object"?!1:!!(e.constructor&&e.constructor.isBuffer&&e.constructor.isBuffer(e))}function ca(e,t){if(at(e)){let n=[];for(let a=0;a<e.length;a+=1)n.push(t(e[a]));return n}return t(e)}var Ai={brackets(e){return String(e)+"[]"},comma:"comma",indices(e,t){return String(e)+"["+t+"]"},repeat(e){return String(e)}},Li=function(e,t){Array.prototype.push.apply(e,at(t)?t:[t])},Ii,z={addQueryPrefix:!1,allowDots:!1,allowEmptyArrays:!1,arrayFormat:"indices",charset:"utf-8",charsetSentinel:!1,delimiter:"&",encode:!0,encodeDotInKeys:!1,encoder:Ei,encodeValuesOnly:!1,format:la,formatter:Sa,indices:!1,serializeDate(e){return(Ii??(Ii=Function.prototype.call.bind(Date.prototype.toISOString)))(e)},skipNulls:!1,strictNullHandling:!1};function Qo(e){return typeof e=="string"||typeof e=="number"||typeof e=="boolean"||typeof e=="symbol"||typeof e=="bigint"}var ha={};function xi(e,t,n,a,i,s,o,d,l,U,S,r,u,c,h,w,k,f){let m=e,L=f,R=0,D=!1;for(;(L=L.get(ha))!==void 0&&!D;){let y=L.get(e);if(R+=1,typeof y<"u"){if(y===R)throw new RangeError("Cyclic object value");D=!0}typeof L.get(ha)>"u"&&(R=0)}if(typeof U=="function"?m=U(t,m):m instanceof Date?m=u?.(m):n==="comma"&&at(m)&&(m=ca(m,function(y){return y instanceof Date?u?.(y):y})),m===null){if(s)return l&&!w?l(t,z.encoder,k,"key",c):t;m=""}if(Qo(m)||Pi(m)){if(l){let y=w?t:l(t,z.encoder,k,"key",c);return[h?.(y)+"="+h?.(l(m,z.encoder,k,"value",c))]}return[h?.(t)+"="+h?.(String(m))]}let _=[];if(typeof m>"u")return _;let M;if(n==="comma"&&at(m))w&&l&&(m=ca(m,l)),M=[{value:m.length>0?m.join(",")||null:void 0}];else if(at(U))M=U;else{let y=Object.keys(m);M=S?y.sort(S):y}let H=d?String(t).replace(/\./g,"%2E"):String(t),P=a&&at(m)&&m.length===1?H+"[]":H;if(i&&at(m)&&m.length===0)return P+"[]";for(let y=0;y<M.length;++y){let E=M[y],p=typeof E=="object"&&typeof E.value<"u"?E.value:m[E];if(o&&p===null)continue;let T=r&&d?E.replace(/\./g,"%2E"):E,N=at(m)?typeof n=="function"?n(P,T):P:P+(r?"."+T:"["+T+"]");f.set(e,R);let I=new WeakMap;I.set(ha,f),Li(_,xi(p,N,n,a,i,s,o,d,n==="comma"&&w&&at(m)?null:l,U,S,r,u,c,h,w,k,I))}return _}function Zo(e=z){if(typeof e.allowEmptyArrays<"u"&&typeof e.allowEmptyArrays!="boolean")throw new TypeError("`allowEmptyArrays` option can only be `true` or `false`, when provided");if(typeof e.encodeDotInKeys<"u"&&typeof e.encodeDotInKeys!="boolean")throw new TypeError("`encodeDotInKeys` option can only be `true` or `false`, when provided");if(e.encoder!==null&&typeof e.encoder<"u"&&typeof e.encoder!="function")throw new TypeError("Encoder has to be a function.");let t=e.charset||z.charset;if(typeof e.charset<"u"&&e.charset!=="utf-8"&&e.charset!=="iso-8859-1")throw new TypeError("The charset option must be either utf-8, iso-8859-1, or undefined");let n=la;if(typeof e.format<"u"){if(!wn(Ua,e.format))throw new TypeError("Unknown format option provided.");n=e.format}let a=Ua[n],i=z.filter;(typeof e.filter=="function"||at(e.filter))&&(i=e.filter);let s;if(e.arrayFormat&&e.arrayFormat in Ai?s=e.arrayFormat:"indices"in e?s=e.indices?"indices":"repeat":s=z.arrayFormat,"commaRoundTrip"in e&&typeof e.commaRoundTrip!="boolean")throw new TypeError("`commaRoundTrip` must be a boolean, or absent");let o=typeof e.allowDots>"u"?e.encodeDotInKeys?!0:z.allowDots:!!e.allowDots;return{addQueryPrefix:typeof e.addQueryPrefix=="boolean"?e.addQueryPrefix:z.addQueryPrefix,allowDots:o,allowEmptyArrays:typeof e.allowEmptyArrays=="boolean"?!!e.allowEmptyArrays:z.allowEmptyArrays,arrayFormat:s,charset:t,charsetSentinel:typeof e.charsetSentinel=="boolean"?e.charsetSentinel:z.charsetSentinel,commaRoundTrip:!!e.commaRoundTrip,delimiter:typeof e.delimiter>"u"?z.delimiter:e.delimiter,encode:typeof e.encode=="boolean"?e.encode:z.encode,encodeDotInKeys:typeof e.encodeDotInKeys=="boolean"?e.encodeDotInKeys:z.encodeDotInKeys,encoder:typeof e.encoder=="function"?e.encoder:z.encoder,encodeValuesOnly:typeof e.encodeValuesOnly=="boolean"?e.encodeValuesOnly:z.encodeValuesOnly,filter:i,format:n,formatter:a,serializeDate:typeof e.serializeDate=="function"?e.serializeDate:z.serializeDate,skipNulls:typeof e.skipNulls=="boolean"?e.skipNulls:z.skipNulls,sort:typeof e.sort=="function"?e.sort:null,strictNullHandling:typeof e.strictNullHandling=="boolean"?e.strictNullHandling:z.strictNullHandling}}function Oi(e,t={}){let n=e,a=Zo(t),i,s;typeof a.filter=="function"?(s=a.filter,n=s("",n)):at(a.filter)&&(s=a.filter,i=s);let o=[];if(typeof n!="object"||n===null)return"";let d=Ai[a.arrayFormat],l=d==="comma"&&a.commaRoundTrip;i||(i=Object.keys(n)),a.sort&&i.sort(a.sort);let U=new WeakMap;for(let u=0;u<i.length;++u){let c=i[u];a.skipNulls&&n[c]===null||Li(o,xi(n[c],c,d,l,a.allowEmptyArrays,a.strictNullHandling,a.skipNulls,a.encodeDotInKeys,a.encode?a.encoder:null,a.filter,a.sort,a.allowDots,a.serializeDate,a.format,a.formatter,a.encodeValuesOnly,a.charset,U))}let S=o.join(a.delimiter),r=a.addQueryPrefix===!0?"?":"";return a.charsetSentinel&&(a.charset==="iso-8859-1"?r+="utf8=%26%2310003%3B&":r+="utf8=%E2%9C%93&"),S.length>0?r+S:""}function Ri(e){return Oi(e,{arrayFormat:"comma"})}function Bi(e){let t=0;for(let i of e)t+=i.length;let n=new Uint8Array(t),a=0;for(let i of e)n.set(i,a),a+=i.length;return n}var Wi;function Ve(e){let t;return(Wi??(t=new globalThis.TextEncoder,Wi=t.encode.bind(t)))(e)}var Hi;function ga(e){let t;return(Hi??(t=new globalThis.TextDecoder,Hi=t.decode.bind(t)))(e)}var Ut,ut,Bt=class{constructor(){Ut.set(this,void 0),ut.set(this,void 0),tt(this,Ut,new Uint8Array,"f"),tt(this,ut,null,"f")}decode(t){if(t==null)return[];let n=t instanceof ArrayBuffer?new Uint8Array(t):typeof t=="string"?Ve(t):t;tt(this,Ut,Bi([K(this,Ut,"f"),n]),"f");let a=[],i;for(;(i=er(K(this,Ut,"f"),K(this,ut,"f")))!=null;){if(i.carriage&&K(this,ut,"f")==null){tt(this,ut,i.index,"f");continue}if(K(this,ut,"f")!=null&&(i.index!==K(this,ut,"f")+1||i.carriage)){a.push(ga(K(this,Ut,"f").subarray(0,K(this,ut,"f")-1))),tt(this,Ut,K(this,Ut,"f").subarray(K(this,ut,"f")),"f"),tt(this,ut,null,"f");continue}let s=K(this,ut,"f")!==null?i.preceding-1:i.preceding,o=ga(K(this,Ut,"f").subarray(0,s));a.push(o),tt(this,Ut,K(this,Ut,"f").subarray(i.index),"f"),tt(this,ut,null,"f")}return a}flush(){return K(this,Ut,"f").length?this.decode(`
|
|
2
2
|
`):[]}};Ut=new WeakMap,ut=new WeakMap;Bt.NEWLINE_CHARS=new Set([`
|
|
3
3
|
`,"\r"]);Bt.NEWLINE_REGEXP=/\r\n|[\n\r]/g;function er(e,t){for(let i=t??0;i<e.length;i++){if(e[i]===10)return{preceding:i,index:i+1,carriage:!1};if(e[i]===13)return{preceding:i,index:i+1,carriage:!0}}return null}function Di(e){for(let a=0;a<e.length-1;a++){if(e[a]===10&&e[a+1]===10||e[a]===13&&e[a+1]===13)return a+2;if(e[a]===13&&e[a+1]===10&&a+3<e.length&&e[a+2]===13&&e[a+3]===10)return a+4}return-1}var yn={off:0,error:200,warn:300,info:400,debug:500},pa=(e,t,n)=>{if(e){if(pi(yn,e))return e;$(n).warn(`${t} was set to ${JSON.stringify(e)}, expected one of ${JSON.stringify(Object.keys(yn))}`)}};function Ye(){}function mn(e,t,n){return!t||yn[e]>yn[n]?Ye:t[e].bind(t)}var nr={error:Ye,warn:Ye,info:Ye,debug:Ye},Fi=new WeakMap;function $(e){let t=e.logger,n=e.logLevel??"off";if(!t)return nr;let a=Fi.get(t);if(a&&a[0]===n)return a[1];let i={error:mn("error",t,n),warn:mn("warn",t,n),info:mn("info",t,n),debug:mn("debug",t,n)};return Fi.set(t,[n,i]),i}var Mt=e=>(e.options&&(e.options={...e.options},delete e.options.headers),e.headers&&(e.headers=Object.fromEntries((e.headers instanceof Headers?[...e.headers]:Object.entries(e.headers)).map(([t,n])=>[t,t.toLowerCase()==="authorization"||t.toLowerCase()==="api-key"||t.toLowerCase()==="x-api-key"||t.toLowerCase()==="cookie"||t.toLowerCase()==="set-cookie"?"***":n]))),"retryOfRequestLogID"in e&&(e.retryOfRequestLogID&&(e.retryOf=e.retryOfRequestLogID),delete e.retryOfRequestLogID),e);var Ke,Cn=class e{constructor(t,n,a){this.iterator=t,Ke.set(this,void 0),this.controller=n,tt(this,Ke,a,"f")}static fromSSEResponse(t,n,a){let i=!1,s=a?$(a):console;async function*o(){if(i)throw new Y("Cannot iterate over a consumed stream, use `.tee()` to split the stream.");i=!0;let d=!1;try{for await(let l of ar(t,n))try{yield JSON.parse(l.data)}catch(U){throw s.error("Could not parse message into JSON:",l.data),s.error("From chunk:",l.raw),U}d=!0}catch(l){if(Fe(l))return;throw l}finally{d||n.abort()}}return new e(o,n,a)}static fromReadableStream(t,n,a){let i=!1;async function*s(){let d=new Bt,l=da(t);for await(let U of l)for(let S of d.decode(U))yield S;for(let U of d.flush())yield U}async function*o(){if(i)throw new Y("Cannot iterate over a consumed stream, use `.tee()` to split the stream.");i=!0;let d=!1;try{for await(let l of s())d||l&&(yield JSON.parse(l));d=!0}catch(l){if(Fe(l))return;throw l}finally{d||n.abort()}}return new e(o,n,a)}[(Ke=new WeakMap,Symbol.asyncIterator)](){return this.iterator()}tee(){let t=[],n=[],a=this.iterator(),i=s=>({next:()=>{if(s.length===0){let o=a.next();t.push(o),n.push(o)}return s.shift()}});return[new e(()=>i(t),this.controller,K(this,Ke,"f")),new e(()=>i(n),this.controller,K(this,Ke,"f"))]}toReadableStream(){let t=this,n;return ra({async start(){n=t[Symbol.asyncIterator]()},async pull(a){try{let{value:i,done:s}=await n.next();if(s)return a.close();let o=Ve(JSON.stringify(i)+`
|
|
4
4
|
`);a.enqueue(o)}catch(i){a.error(i)}},async cancel(){await n.return?.()}})}};async function*ar(e,t){if(!e.body)throw t.abort(),typeof globalThis.navigator<"u"&&globalThis.navigator.product==="ReactNative"?new Y("The default react-native fetch implementation does not support streaming. Please use expo/fetch: https://docs.expo.dev/versions/latest/sdk/expo/#expofetch-api"):new Y("Attempted to iterate over a response with no body");let n=new wa,a=new Bt,i=da(e.body);for await(let s of ir(i))for(let o of a.decode(s)){let d=n.decode(o);d&&(yield d)}for(let s of a.flush()){let o=n.decode(s);o&&(yield o)}}async function*ir(e){let t=new Uint8Array;for await(let n of e){if(n==null)continue;let a=n instanceof ArrayBuffer?new Uint8Array(n):typeof n=="string"?Ve(n):n,i=new Uint8Array(t.length+a.length);i.set(t),i.set(a,t.length),t=i;let s;for(;(s=Di(t))!==-1;)yield t.slice(0,s),t=t.slice(s)}t.length>0&&(yield t)}var wa=class{constructor(){this.event=null,this.data=[],this.chunks=[]}decode(t){if(t.endsWith("\r")&&(t=t.substring(0,t.length-1)),!t){if(!this.event&&!this.data.length)return null;let s={event:this.event,data:this.data.join(`
|
|
@@ -6,8 +6,8 @@
|
|
|
6
6
|
${s.map(u=>u.error).join(`
|
|
7
7
|
`)}
|
|
8
8
|
${o}
|
|
9
|
-
${r}`)}return o},g=gr(qi);var Ft=class extends b{create(t,n){return this._client.post("/org/api_keys",{body:t,...n})}retrieve(t,n={},a){return this._client.get(g`/org/api_keys/${t}`,{query:n,...a})}update(t,n,a){return this._client.patch(g`/org/api_keys/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/api_keys",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/api_keys/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}rotate(t,n={},a){return this._client.post(g`/org/api_keys/${t}/rotate`,{body:n,...a})}};var Gt=class extends b{list(t={},n){return this._client.getAPIList("/apps",F,{query:t,...n})}};var we=class extends b{create(t,n){return this._client.post("/audit-logs/export/destinations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/audit-logs/export/destinations/${t}`,n)}update(t,n,a){return this._client.patch(g`/audit-logs/export/destinations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/audit-logs/export/destinations",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/audit-logs/export/destinations/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}test(t,n){return this._client.post(g`/audit-logs/export/destinations/${t}/test`,n)}};var wr=6,mr=5e4,yr=8e3,gt=class extends Y{};async function ji(e,t,n,a,i={}){if(!n||typeof n.write!="function")throw new TypeError("audit log download destination must provide write()");let{onProgress:s,maxTransferRetries:o=wr,...d}=i;if(!Number.isInteger(o)||o<0)throw new TypeError("maxTransferRetries must be a non-negative integer");let l=d.timeout??a,U,S={bytesWritten:0,chunks:0,rows:0},r=new Set;for(;;){let u=await Cr(e,U?{...t,cursor:U}:t,d,o,l),{nextCursor:c,hasMore:h,rows:w}=Tr(u.headers,U);if(h&&c){if(r.has(c))throw new gt("response repeated X-Next-Cursor header");r.add(c)}if(await Mr(n,u.body),U=c,S.bytesWritten+=u.body.byteLength,S.chunks+=1,S.rows+=w,s&&await s({...S,chunkRows:w}),!h)return S}}async function Cr(e,t,n,a,i){for(let s=0;;s+=1){let o=new AbortController,d=()=>o.abort();n.signal?.aborted?o.abort():n.signal?.addEventListener("abort",d,{once:!0});let l;try{l=await e(t,{...n,signal:o.signal})}catch(r){throw n.signal?.removeEventListener("abort",d),r}let U=!1,S=setTimeout(()=>{U=!0,o.abort()},i);try{let r=new Uint8Array(await l.arrayBuffer());if(clearTimeout(S),n.signal?.aborted)throw new ot;if(U)throw new ft;let u=l.headers.get("x-content-sha256");if(!u)throw new gt("response missing X-Content-Sha256 header");let c=await kr(r);if(n.signal?.aborted)throw new ot;if(c!==u)throw new gt(`audit log chunk checksum mismatch (got ${c}, want ${u})`);return{body:r,headers:l.headers}}catch(r){if(n.signal?.aborted&&!(r instanceof ot)?r=new ot:U&&(r=new ft),s===a||r instanceof ot)throw r;await fr(s+1,n.signal)}finally{clearTimeout(S),n.signal?.removeEventListener("abort",d)}}}function Tr(e,t){let n=e.get("x-has-more");if(n!=="true"&&n!=="false")throw new gt("response missing or invalid X-Has-More header");let a=n==="true",i=e.get("x-row-count");if(i===null||!/^[0-9]+$/.test(i))throw new gt("response missing or invalid X-Row-Count header");let s=Number(i);if(!Number.isSafeInteger(s)||s>mr)throw new gt("response missing or invalid X-Row-Count header");let o=e.get("x-next-cursor")||void 0;if(a&&(!o||o===t))throw new gt("response has invalid X-Next-Cursor header");if(!a&&o)throw new gt("response returned a cursor after the final chunk");return{rows:s,nextCursor:o,hasMore:a}}async function kr(e){let t=await globalThis.crypto.subtle.digest("SHA-256",e);return Array.from(new Uint8Array(t),n=>n.toString(16).padStart(2,"0")).join("")}async function fr(e,t){let n=Math.min(1e3*2**(e-1),yr);await new Promise((a,i)=>{if(t?.aborted){i(new ot);return}let s=()=>{clearTimeout(o),i(new ot)},o=setTimeout(()=>{t?.removeEventListener("abort",s),a()},n);t?.addEventListener("abort",s,{once:!0})})}async function Mr(e,t){let n=0;for(;n<t.byteLength;){let a=await e.write(n===0?t:t.subarray(n));if(typeof a=="number"){n+=Xi(a,t.byteLength-n);continue}if(a&&typeof a=="object"&&"bytesWritten"in a){let i=a.bytesWritten;n+=Xi(i,t.byteLength-n);continue}return}}function Xi(e,t){if(!Number.isSafeInteger(e)||e<=0||e>t)throw new gt("audit log download destination performed a short write");return e}var It=class extends b{constructor(){super(...arguments),this.exportDestinations=new we(this._client)}list(t,n){return this._client.getAPIList("/audit-logs",Mn,{query:t,...n})}exportChunk(t,n){return this._client.get("/audit-logs/export/chunk",{query:t,...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}download(t,n,a){return ji((i,s)=>this.exportChunk(i,s),t,n,this._client.timeout,a)}};It.ExportDestinations=we;var me=class extends b{create(t,n){return this._client.post("/auth/connections",{body:t,...n})}retrieve(t,n){return this._client.get(g`/auth/connections/${t}`,n)}update(t,n,a){return this._client.patch(g`/auth/connections/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/auth/connections",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/auth/connections/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n){return this._client.get(g`/auth/connections/${t}/events`,{...n,headers:C([{Accept:"text/event-stream"},n?.headers]),stream:!0})}login(t,n={},a){return this._client.post(g`/auth/connections/${t}/login`,{body:n,...a})}submit(t,n,a){return this._client.post(g`/auth/connections/${t}/submit`,{body:n,...a})}timeline(t,n={},a){return this._client.getAPIList(g`/auth/connections/${t}/timeline`,F,{query:n,...a})}};var ye=class extends b{retrieve(t){return this._client.get("/auth/context",t)}};var vt=class extends b{constructor(){super(...arguments),this.context=new ye(this._client),this.connections=new me(this._client)}};vt.Context=ye;vt.Connections=me;var Vt=class extends b{create(t,n){return this._client.post("/browser_pools",{body:t,...n})}retrieve(t,n){return this._client.get(g`/browser_pools/${t}`,n)}update(t,n,a){return this._client.patch(g`/browser_pools/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/browser_pools",F,{query:t,...n})}delete(t,n={},a){return this._client.delete(g`/browser_pools/${t}`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}acquire(t,n,a){return this._client.post(g`/browser_pools/${t}/acquire`,{body:n,...a})}flush(t,n){return this._client.post(g`/browser_pools/${t}/flush`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}release(t,n,a){return this._client.post(g`/browser_pools/${t}/release`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Ce=class extends b{batch(t,n,a){return this._client.post(g`/browsers/${t}/computer/batch`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}captureScreenshot(t,n={},a){return this._client.post(g`/browsers/${t}/computer/screenshot`,{body:n,...a,headers:C([{Accept:"image/png"},a?.headers]),__binaryResponse:!0})}clickMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/click_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}dragMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/drag_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}getMousePosition(t,n){return this._client.post(g`/browsers/${t}/computer/get_mouse_position`,n)}moveMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/move_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}pressKey(t,n,a){return this._client.post(g`/browsers/${t}/computer/press_key`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}readClipboard(t,n){return this._client.post(g`/browsers/${t}/computer/clipboard/read`,n)}scroll(t,n,a){return this._client.post(g`/browsers/${t}/computer/scroll`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}setCursorVisibility(t,n,a){return this._client.post(g`/browsers/${t}/computer/cursor`,{body:n,...a})}typeText(t,n,a){return this._client.post(g`/browsers/${t}/computer/type`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}writeClipboard(t,n,a){return this._client.post(g`/browsers/${t}/computer/clipboard/write`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Te=class extends b{stream(t,n,a){return this._client.get(g`/browsers/${t}/logs/stream`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var ke=class extends b{execute(t,n,a){return this._client.post(g`/browsers/${t}/playwright/execute`,{body:n,...a})}};var fe=class extends b{exec(t,n,a){return this._client.post(g`/browsers/${t}/process/exec`,{body:n,...a})}kill(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/kill`,{body:s,...a})}resize(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/resize`,{body:s,...a})}spawn(t,n,a){return this._client.post(g`/browsers/${t}/process/spawn`,{body:n,...a})}status(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/process/${t}/status`,a)}stdin(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/stdin`,{body:s,...a})}stdoutStream(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/process/${t}/stdout/stream`,{...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var Me=class extends b{list(t,n){return this._client.get(g`/browsers/${t}/replays`,n)}download(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/replays/${t}`,{...a,headers:C([{Accept:"video/mp4"},a?.headers]),__binaryResponse:!0})}start(t,n={},a){return this._client.post(g`/browsers/${t}/replays`,{body:n,...a})}stop(t,n,a){let{id:i}=n;return this._client.post(g`/browsers/${i}/replays/${t}/stop`,{...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Ne=class extends b{events(t,n={},a){return this._client.getAPIList(g`/browsers/${t}/telemetry/events`,F,{query:n,...a})}stream(t,n={},a){let{"Last-Event-ID":i,...s}=n??{};return this._client.get(g`/browsers/${t}/telemetry/stream`,{query:s,...a,headers:C([{Accept:"text/event-stream",...i!=null?{"Last-Event-ID":i}:void 0},a?.headers]),stream:!0})}};var ve=class extends b{events(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/fs/watch/${t}/events`,{...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}start(t,n,a){return this._client.post(g`/browsers/${t}/fs/watch`,{body:n,...a})}stop(t,n,a){let{id:i}=n;return this._client.delete(g`/browsers/${i}/fs/watch/${t}`,{...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Yt=class extends b{constructor(){super(...arguments),this.watch=new ve(this._client)}createDirectory(t,n,a){return this._client.put(g`/browsers/${t}/fs/create_directory`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}deleteDirectory(t,n,a){return this._client.put(g`/browsers/${t}/fs/delete_directory`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}deleteFile(t,n,a){return this._client.put(g`/browsers/${t}/fs/delete_file`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}downloadDirZip(t,n,a){return this._client.get(g`/browsers/${t}/fs/download_dir_zip`,{query:n,...a,headers:C([{Accept:"application/zip"},a?.headers]),__binaryResponse:!0})}fileInfo(t,n,a){return this._client.get(g`/browsers/${t}/fs/file_info`,{query:n,...a})}listFiles(t,n,a){return this._client.get(g`/browsers/${t}/fs/list_files`,{query:n,...a})}move(t,n,a){return this._client.put(g`/browsers/${t}/fs/move`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}readFile(t,n,a){return this._client.get(g`/browsers/${t}/fs/read_file`,{query:n,...a,headers:C([{Accept:"application/octet-stream"},a?.headers]),__binaryResponse:!0})}setFilePermissions(t,n,a){return this._client.put(g`/browsers/${t}/fs/set_file_permissions`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}upload(t,n,a){return this._client.post(g`/browsers/${t}/fs/upload`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}uploadZip(t,n,a){return this._client.post(g`/browsers/${t}/fs/upload_zip`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}writeFile(t,n,a,i){let{path:s,mode:o}=a;return this._client.put(g`/browsers/${t}/fs/write_file`,{body:n,query:{path:s,mode:o},...i,headers:C([{"Content-Type":"application/octet-stream",Accept:"*/*"},i?.headers])})}};Yt.Watch=ve;function _n(e,t){return`${e.replace(/\/+$/,"")}${t.startsWith("/")?t:`/${t}`}`}async function zi(e,t,n,a){let i=e.browserRouteCache.get(t);if(!i)throw new Y(`browser route cache does not contain session ${t}; create, retrieve, or list the browser before calling browser.fetch`);let{url:s,method:o,headers:d,body:l,signal:U,duplex:S,timeout_ms:r}=Rr(n,a);Wr(s);let u={url:s,jwt:i.jwt};r!==void 0&&(u.timeout_ms=r);let c=d.get("accept"),h={method:Or(o),path:_n(i.baseURL,"/curl/raw"),query:u,body:l,headers:C([{Authorization:null},c?{Accept:c}:{Accept:"*/*"},Hr(d)]),signal:U??null,__binaryResponse:!0};return S&&(h.fetchOptions={duplex:S}),e.request(h).asResponse()}function Or(e){let t=e.toLowerCase();if(!new Set(["get","post","put","patch","delete"]).has(t))throw new Y(`browser.fetch unsupported HTTP method: ${e}`);return t}function Rr(e,t){let n=t&&"timeout_ms"in t?t.timeout_ms:void 0;if(e instanceof Request){let i=new Headers(e.headers);t?.headers&&new Headers(t.headers).forEach((U,S)=>{i.set(S,U)});let s={url:e.url,method:(t?.method??e.method)?.toUpperCase()||"GET",headers:i},o=t?.body??e.body;o!=null&&(s.body=o);let d=t?.signal??e.signal;return d!==void 0&&(s.signal=d),t?.duplex!==void 0&&(s.duplex=t.duplex),n!==void 0&&(s.timeout_ms=n),s}let a={url:e instanceof URL?e.href:String(e),method:(t?.method??"GET").toUpperCase(),headers:new Headers(t?.headers)};return t?.body!==void 0&&(a.body=t.body),t?.signal!==void 0&&(a.signal=t.signal),t?.duplex!==void 0&&(a.duplex=t.duplex),n!==void 0&&(a.timeout_ms=n),a}function Wr(e){let t;try{t=new URL(e)}catch{throw new Y(`browser.fetch target must be an absolute URL; received: ${e}`)}if(t.protocol!=="http:"&&t.protocol!=="https:")throw new Y(`browser.fetch only supports http(s) URLs; received: ${t.protocol}`)}function Hr(e){let t={};return e.forEach((n,a)=>{switch(a.toLowerCase()){case"accept":case"content-length":case"connection":case"keep-alive":case"proxy-authenticate":case"proxy-authorization":case"te":case"trailers":case"transfer-encoding":case"upgrade":return;default:t[a]=n}}),t}var lt=class extends b{constructor(){super(...arguments),this.telemetry=new Ne(this._client),this.replays=new Me(this._client),this.fs=new Yt(this._client),this.process=new fe(this._client),this.logs=new Te(this._client),this.computer=new Ce(this._client),this.playwright=new ke(this._client)}create(t={},n){return this._client.post("/browsers",{body:t,...n})}retrieve(t,n={},a){return this._client.get(g`/browsers/${t}`,{query:n,...a})}update(t,n,a){return this._client.patch(g`/browsers/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/browsers",F,{query:t,...n})}curl(t,n,a){return this._client.post(g`/browsers/${t}/curl`,{body:n,...a})}fetch(t,n,a){return zi(this._client,t,n,a)}deleteByID(t,n){return this._client.delete(g`/browsers/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}loadExtensions(t,n,a){return this._client.post(g`/browsers/${t}/extensions`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}};lt.Telemetry=Ne;lt.Replays=Me;lt.Fs=Yt;lt.Process=fe;lt.Logs=Te;lt.Computer=Ce;lt.Playwright=ke;var Kt=class extends b{create(t,n){return this._client.post("/org/credential_providers",{body:t,...n})}retrieve(t,n){return this._client.get(g`/org/credential_providers/${t}`,n)}update(t,n,a){return this._client.patch(g`/org/credential_providers/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/credential_providers",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/credential_providers/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}listItems(t,n){return this._client.get(g`/org/credential_providers/${t}/items`,n)}test(t,n){return this._client.post(g`/org/credential_providers/${t}/test`,n)}};var Jt=class extends b{create(t,n){return this._client.post("/credentials",{body:t,...n})}retrieve(t,n){return this._client.get(g`/credentials/${t}`,n)}update(t,n,a){return this._client.patch(g`/credentials/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/credentials",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/credentials/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}totpCode(t,n){return this._client.get(g`/credentials/${t}/totp-code`,n)}};var qt=class extends b{create(t,n){return this._client.post("/deployments",Nt({body:t,...n},this._client))}retrieve(t,n){return this._client.get(g`/deployments/${t}`,n)}list(t={},n){return this._client.getAPIList("/deployments",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/deployments/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n={},a){return this._client.get(g`/deployments/${t}/events`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var Xt=class extends b{list(t={},n){return this._client.getAPIList("/extensions",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/extensions/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}download(t,n){return this._client.get(g`/extensions/${t}`,{...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}downloadFromChromeStore(t,n){return this._client.get("/extensions/from_chrome_store",{query:t,...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}get(t,n){return this._client.get(g`/extensions/${t}/metadata`,n)}upload(t,n){return this._client.post("/extensions",Nt({body:t,...n},this._client))}};var jt=class extends b{create(t,n){return this._client.post("/invocations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/invocations/${t}`,n)}update(t,n,a){return this._client.patch(g`/invocations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/invocations",F,{query:t,...n})}deleteBrowsers(t,n){return this._client.delete(g`/invocations/${t}/browsers`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n={},a){return this._client.get(g`/invocations/${t}/events`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}listBrowsers(t,n){return this._client.get(g`/invocations/${t}/browsers`,n)}};var _e=class extends b{retrieve(t){return this._client.get("/org/entitlements",t)}};var be=class extends b{retrieve(t){return this._client.get("/org/limits",t)}update(t,n){return this._client.patch("/org/limits",{body:t,...n})}};var _t=class extends b{constructor(){super(...arguments),this.entitlements=new _e(this._client),this.limits=new be(this._client)}};_t.Entitlements=_e;_t.Limits=be;var zt=class extends b{create(t,n){return this._client.post("/profiles",{body:t,...n})}retrieve(t,n){return this._client.get(g`/profiles/${t}`,n)}update(t,n,a){return this._client.patch(g`/profiles/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/profiles",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/profiles/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}download(t,n={},a){return this._client.get(g`/profiles/${t}/download`,{query:n,...a,headers:C([{Accept:"application/octet-stream"},a?.headers]),__binaryResponse:!0})}};var Ee=class extends b{retrieve(t,n){return this._client.get(g`/org/projects/${t}/limits`,n)}update(t,n,a){return this._client.patch(g`/org/projects/${t}/limits`,{body:n,...a})}};var At=class extends b{constructor(){super(...arguments),this.limits=new Ee(this._client)}create(t,n){return this._client.post("/org/projects",{body:t,...n})}retrieve(t,n){return this._client.get(g`/org/projects/${t}`,n)}update(t,n,a){return this._client.patch(g`/org/projects/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/projects",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/projects/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}};At.Limits=Ee;var $t=class extends b{create(t,n){return this._client.post("/proxies",{body:t,...n})}retrieve(t,n){return this._client.get(g`/proxies/${t}`,n)}update(t,n,a){return this._client.patch(g`/proxies/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/proxies",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/proxies/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}check(t,n={},a){return this._client.post(g`/proxies/${t}/check`,{body:n,...a})}};var Pe=class extends b{create(t,n){return this._client.post("/telemetry/destinations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/telemetry/destinations/${t}`,n)}update(t,n,a){return this._client.patch(g`/telemetry/destinations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/telemetry/destinations",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/telemetry/destinations/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}};var Lt=class extends b{constructor(){super(...arguments),this.destinations=new Pe(this._client)}};Lt.Destinations=Pe;var je=class{constructor(){this.entries=new Map}get(t){return this.entries.get(t)}set(t){this.entries.set(t.sessionId,t)}delete(t){this.entries.delete(t)}clear(){this.entries.clear()}},$i="KERNEL_BROWSER_ROUTING_SUBRESOURCES",Yr=["curl","telemetry/stream"],Kr=/^\/(?:v\d+\/)?browsers(?:\/[^/]+)?\/?$/,Jr=/^\/(?:v\d+\/)?browser_pools\/[^/]+\/acquire\/?$/,qr=/^\/(?:v\d+\/)?browsers\/([^/]+)\/?$/,Xr=/^\/(?:v\d+\/)?browser_pools\/[^/]+\/release\/?$/;function fa(){let e=rd();return e===void 0?[...Yr]:e.trim()===""?[]:e.split(",").map(t=>t.trim()).filter(Boolean)}function Ma(e,{apiBaseURL:t,subresources:n,cache:a}){let i=[...n].map(o=>o.trim().replace(/^\/+|\/+$/g,"")).filter(Boolean),s=new URL(t).origin;return async(o,d)=>{let l=new Request(o,d),U=jr(l,s),S=await nd(e,{input:o,init:d,request:l},s,i,a);return U&&await td(S,a),await zr(l,S,s,a),S}}function jr(e,t){let n=new URL(e.url);return n.origin===t&&(Kr.test(n.pathname)||Jr.test(n.pathname))}async function zr(e,t,n,a){if(!t.ok)return;let i=new URL(e.url);if(i.origin!==n)return;let s=$r(e,i.pathname)??await Qr(e,i.pathname);s&&a.delete(s)}function $r(e,t){if(e.method.toUpperCase()!=="DELETE")return;let n=t.match(qr);return n&&decodeURIComponent(n[1]??"")||void 0}async function Qr(e,t){if(!(e.method.toUpperCase()!=="POST"||!Xr.test(t)))try{let n=await e.clone().json();if(!n||typeof n!="object")return;let a=n.session_id;return typeof a=="string"&&a.trim()?a.trim():void 0}catch{return}}function Zr(e){if(!e||typeof e!="object")return;let t=e,n=typeof t.session_id=="string"?t.session_id.trim():"",a=typeof t.base_url=="string"?t.base_url.trim():"";if(!n||!a)return;let i=typeof t.jwt=="string"?t.jwt.trim():"",s=typeof t.cdp_ws_url=="string"?t.cdp_ws_url:void 0,o=i||od(s)||"";if(o)return{sessionId:n,baseURL:a,jwt:o}}async function td(e,t){if((e.headers.get("content-type")?.toLowerCase()??"").includes("application/json"))try{ka(await e.clone().json(),t)}catch{}}function ka(e,t){let n=Zr(e);if(n&&t.set(n),Array.isArray(e)){for(let a of e)ka(a,t);return}if(!(!e||typeof e!="object"))for(let a of Object.values(e))typeof a=="object"&&a!==null&&ka(a,t)}function ed(e,t){let n=e.replace(/^\/+|\/+$/g,"");return t.some(a=>n===a||n.startsWith(a+"/"))}async function nd(e,{input:t,init:n,request:a},i,s,o){let d=new URL(a.url);if(d.origin!==i)return e(t,n);let l=d.pathname.match(/^\/(?:v\d+\/)?browsers\/([^/]+)\/([^/]+)(\/.*)?$/);if(!l)return e(t,n);let U=decodeURIComponent(l[1]??""),S=l[2]??"";if(!U||!ed(S+(l[3]??""),s))return e(t,n);let r=o.get(U);if(r===void 0)return e(t,n);let u=new URL(_n(r.baseURL,`/${S}${l[3]??""}`));d.searchParams.forEach((h,w)=>{w!=="jwt"&&u.searchParams.append(w,h)}),u.searchParams.get("jwt")||u.searchParams.set("jwt",r.jwt);let c=new Headers(a.headers);return c.delete("authorization"),e(u.toString(),ad(t,a,n,c))}function ad(e,t,n,a){let i=t.method.toUpperCase(),s={...n??{},method:i,headers:a,redirect:t.redirect,signal:n?.signal??(e instanceof Request?e.signal:void 0)};if(delete s.body,delete s.duplex,i!=="GET"&&i!=="HEAD"){let o=id(t,n);o!==void 0&&(s.body=o),n?.duplex!==void 0?s.duplex=n.duplex:sd(o)&&(s.duplex="half")}return s}function id(e,t){return t?.body!==void 0&&t.body!==null?t.body:e.body??void 0}function sd(e){return globalThis.ReadableStream&&e instanceof globalThis.ReadableStream||typeof e=="object"&&e!==null&&Symbol.asyncIterator in e}function od(e){if(e)try{return new URL(e).searchParams.get("jwt")??void 0}catch{return}}function rd(){if(typeof globalThis.process<"u"){let e=globalThis.process.env?.[$i];return typeof e=="string"?e:void 0}if(typeof globalThis.Deno<"u"){let e=globalThis.Deno.env?.get?.($i);return typeof e=="string"?e:void 0}}var bn=class{constructor(t){this.actions=new Map,this.name=t,Qi.registerApp(this)}action(t,n){let a;if(n.length===0)throw new Error("Action handlers must accept at least the context parameter");if(n.length===1){let i=n;a=async(s,o)=>i(s)}else a=n;return this.actions.set(t,{name:t,handler:a}),a}getActions(){return Array.from(this.actions.values())}getAction(t){return this.actions.get(t)}toJSON(){return{name:this.name,actions:this.getActions().map(t=>({name:t.name}))}}},Na=class{constructor(){this.apps=new Map}registerApp(t){this.apps.set(t.name,t)}getApps(){return Array.from(this.apps.values())}getAppByName(t){return this.apps.get(t)}export(){return{apps:this.getApps().map(t=>t.toJSON())}}exportJSON(){return JSON.stringify(this.export(),null,2)}},Qi=new Na;var Ie=e=>{if(typeof globalThis.process<"u")return globalThis.process.env?.[e]?.trim()||void 0;if(typeof globalThis.Deno<"u")return globalThis.Deno.env?.get?.(e)?.trim()||void 0};var va,_a,ze,Zi,ts={production:"https://api.onkernel.com/",development:"https://localhost:3001/"},B=class{constructor({baseURL:t=Ie("KERNEL_BASE_URL"),apiKey:n=Ie("KERNEL_API_KEY"),projectID:a=null,project:i=null,...s}={}){if(va.add(this),ze.set(this,void 0),this.deployments=new qt(this),this.apps=new Gt(this),this.invocations=new jt(this),this.browsers=new lt(this),this.profiles=new zt(this),this.auth=new vt(this),this.telemetry=new Lt(this),this.proxies=new $t(this),this.extensions=new Xt(this),this.browserPools=new Vt(this),this.credentials=new Jt(this),this.projects=new At(this),this.organization=new _t(this),this.auditLogs=new It(this),this.apiKeys=new Ft(this),this.credentialProviders=new Kt(this),typeof globalThis<"u"&&typeof globalThis.Bun<"u"&&globalThis.Bun.version&&!Ie("KERNEL_SUPPRESS_BUN_WARNING")&&$(this).warn("The Bun runtime was detected. Playwright may have CDP connection issues, proceed with caution. Suppress this warning by setting the KERNEL_SUPPRESS_BUN_WARNING environment variable to true"),n===void 0)throw new Y("The KERNEL_API_KEY environment variable is missing or empty; either provide it, or instantiate the Kernel client with an apiKey option, like new Kernel({ apiKey: 'My API Key' }).");let o={apiKey:n,projectID:a,project:i,...s,baseURL:t,environment:s.environment??"production"};if(t&&s.environment)throw new Y("Ambiguous URL; The `baseURL` option (or KERNEL_BASE_URL env var) and the `environment` option are given. If you want to use the environment you must pass baseURL: null");this.baseURL=o.baseURL||ts[o.environment||"production"],this.timeout=o.timeout??_a.DEFAULT_TIMEOUT,this.logger=o.logger??console;let d="warn";this.logLevel=d,this.logLevel=pa(o.logLevel,"ClientOptions.logLevel",this)??pa(Ie("KERNEL_LOG"),"process.env['KERNEL_LOG']",this)??d,this.fetchOptions=o.fetchOptions,this.maxRetries=o.maxRetries??2,this.rawFetch=o.fetch??Ni(),this.browserRouteCache=new je,this.fetch=Ma(this.rawFetch,{apiBaseURL:this.baseURL,subresources:fa(),cache:this.browserRouteCache}),tt(this,ze,_i,"f");let l=Ie("KERNEL_CUSTOM_HEADERS");if(l){let U={};for(let S of l.split(`
|
|
10
|
-
`)){let r=S.indexOf(":");r>=0&&(U[S.substring(0,r).trim()]=S.substring(r+1).trim())}o.defaultHeaders={...U,...o.defaultHeaders}}this._options=o,this.apiKey=n,this.projectID=a,this.project=i}withOptions(t){let n=new this.constructor({...this._options,environment:t.environment?t.environment:void 0,baseURL:t.environment?void 0:this.baseURL,maxRetries:this.maxRetries,timeout:this.timeout,logger:this.logger,logLevel:this.logLevel,fetch:this.rawFetch,fetchOptions:this.fetchOptions,apiKey:this.apiKey,projectID:this.projectID,project:this.project,...t});return n.browserRouteCache=this.browserRouteCache,n.fetch=Ma(n.rawFetch,{apiBaseURL:n.baseURL,subresources:fa(),cache:n.browserRouteCache}),n}defaultQuery(){return this._options.defaultQuery}validateHeaders({values:t,nulls:n}){}async authHeaders(t){return C([{Authorization:`Bearer ${this.apiKey}`}])}stringifyQuery(t){return Ri(t)}getUserAgent(){return`${this.constructor.name}/JS ${Pt}`}defaultIdempotencyKey(){return`stainless-node-retry-${na()}`}makeStatusError(t,n,a,i){return nt.generate(t,n,a,i)}buildURL(t,n,a){let i=!K(this,va,"m",Zi).call(this)&&a||this.baseURL,s=gi(t)?new URL(t):new URL(i+(i.endsWith("/")&&t.startsWith("/")?t.slice(1):t)),o=this.defaultQuery(),d=Object.fromEntries(s.searchParams);return(!sa(o)||!sa(d))&&(n={...d,...o,...n}),typeof n=="object"&&n&&!Array.isArray(n)&&(s.search=this.stringifyQuery(n)),s.toString()}async prepareOptions(t){}async prepareRequest(t,{url:n,options:a}){}get(t,n){return this.methodRequest("get",t,n)}post(t,n){return this.methodRequest("post",t,n)}patch(t,n){return this.methodRequest("patch",t,n)}put(t,n){return this.methodRequest("put",t,n)}delete(t,n){return this.methodRequest("delete",t,n)}methodRequest(t,n,a){return this.request(Promise.resolve(a).then(i=>({method:t,path:n,...i})))}request(t,n=null){return new Dt(this,this.makeRequest(t,n,void 0))}async makeRequest(t,n,a){let i=await t,s=i.maxRetries??this.maxRetries;n==null&&(n=s),await this.prepareOptions(i);let{req:o,url:d,timeout:l}=await this.buildRequest(i,{retryCount:s-n});await this.prepareRequest(o,{url:d,options:i});let U="log_"+(Math.random()*(1<<24)|0).toString(16).padStart(6,"0"),S=a===void 0?"":`, retryOf: ${a}`,r=Date.now();if($(this).debug(`[${U}] sending request`,Mt({retryOfRequestLogID:a,method:i.method,url:d,options:i,headers:o.headers})),i.signal?.aborted)throw new ot;let u=new AbortController,c=await this.fetchWithTimeout(d,o,l,u).catch(Ge),h=Date.now();if(c instanceof globalThis.Error){let k=`retrying, ${n} attempts remaining`;if(i.signal?.aborted)throw new ot;let f=Fe(c)||/timed? ?out/i.test(String(c)+("cause"in c?String(c.cause):""));if(n)return $(this).info(`[${U}] connection ${f?"timed out":"failed"} - ${k}`),$(this).debug(`[${U}] connection ${f?"timed out":"failed"} (${k})`,Mt({retryOfRequestLogID:a,url:d,durationMs:h-r,message:c.message})),this.retryRequest(i,n,a??U);throw $(this).info(`[${U}] connection ${f?"timed out":"failed"} - error; no more retries left`),$(this).debug(`[${U}] connection ${f?"timed out":"failed"} (error; no more retries left)`,Mt({retryOfRequestLogID:a,url:d,durationMs:h-r,message:c.message})),f?new ft:new Et({cause:c})}let w=`[${U}${S}] ${o.method} ${d} ${c.ok?"succeeded":"failed"} with status ${c.status} in ${h-r}ms`;if(!c.ok){let k=await this.shouldRetry(c);if(n&&k){let _=`retrying, ${n} attempts remaining`;return await vi(c.body),$(this).info(`${w} - ${_}`),$(this).debug(`[${U}] response error (${_})`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,durationMs:h-r})),this.retryRequest(i,n,a??U,c.headers)}let f=k?"error; no more retries left":"error; not retryable";$(this).info(`${w} - ${f}`);let m=await c.text().catch(_=>Ge(_).message),L=yi(m),R=L?void 0:m;throw $(this).debug(`[${U}] response error (${f})`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,message:R,durationMs:Date.now()-r})),this.makeStatusError(c.status,L,R,c.headers)}return $(this).info(w),$(this).debug(`[${U}] response start`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,durationMs:h-r})),{response:c,options:i,controller:u,requestLogID:U,retryOfRequestLogID:a,startTime:r}}getAPIList(t,n,a){return this.requestAPIList(n,a&&"then"in a?a.then(i=>({method:"get",path:t,...i})):{method:"get",path:t,...a})}requestAPIList(t,n){let a=this.makeRequest(n,null,void 0);return new qe(this,a,t)}async fetchWithTimeout(t,n,a,i){let{signal:s,method:o,...d}=n||{},l=this._makeAbort(i);s&&s.addEventListener("abort",l,{once:!0});let U=setTimeout(l,a),S=globalThis.ReadableStream&&d.body instanceof globalThis.ReadableStream||typeof d.body=="object"&&d.body!==null&&Symbol.asyncIterator in d.body,r={signal:i.signal,...S?{duplex:"half"}:{},method:"GET",...d};o&&(r.method=o.toUpperCase());try{return await this.fetch.call(void 0,t,r)}finally{clearTimeout(U)}}async shouldRetry(t){let n=t.headers.get("x-should-retry");return n==="true"?!0:n==="false"?!1:t.status===408||t.status===409||t.status===429||t.status>=500}async retryRequest(t,n,a,i){let s,o=i?.get("retry-after-ms");if(o){let l=parseFloat(o);Number.isNaN(l)||(s=l)}let d=i?.get("retry-after");if(d&&!s){let l=parseFloat(d);Number.isNaN(l)?s=Date.parse(d)-Date.now():s=l*1e3}if(s===void 0){let l=t.maxRetries??this.maxRetries;s=this.calculateDefaultRetryTimeoutMillis(n,l)}return await Ci(s),this.makeRequest(t,n-1,a)}calculateDefaultRetryTimeoutMillis(t,n){let s=n-t,o=Math.min(.5*Math.pow(2,s),8),d=1-Math.random()*.25;return o*d*1e3}async buildRequest(t,{retryCount:n=0}={}){let a={...t},{method:i,path:s,query:o,defaultBaseURL:d}=a,l=this.buildURL(s,o,d);"timeout"in a&&wi("timeout",a.timeout),a.timeout=a.timeout??this.timeout;let{bodyHeaders:U,body:S}=this.buildBody({options:a}),r=await this.buildHeaders({options:t,method:i,bodyHeaders:U,retryCount:n});return{req:{method:i,headers:r,...a.signal&&{signal:a.signal},...globalThis.ReadableStream&&S instanceof globalThis.ReadableStream&&{duplex:"half"},...S&&{body:S},...this.fetchOptions??{},...a.fetchOptions??{}},url:l,timeout:a.timeout}}async buildHeaders({options:t,method:n,bodyHeaders:a,retryCount:i}){let s={};this.idempotencyHeader&&n!=="get"&&(t.idempotencyKey||(t.idempotencyKey=this.defaultIdempotencyKey()),s[this.idempotencyHeader]=t.idempotencyKey);let o=C([s,{Accept:"application/json","User-Agent":this.getUserAgent(),"X-Stainless-Retry-Count":String(i),...t.timeout?{"X-Stainless-Timeout":String(Math.trunc(t.timeout/1e3))}:{},...Mi(),"X-Kernel-Project-Id":this.projectID,"X-Kernel-Project":this.project},await this.authHeaders(t),this._options.defaultHeaders,a,t.headers]);return this.validateHeaders(o),o.values}_makeAbort(t){return()=>t.abort()}buildBody({options:t}){let{body:n,headers:a}=t;if(!n)return n==null&&"body"in t?K(this,ze,"f").call(this,{body:n,headers:C([a])}):{bodyHeaders:void 0,body:void 0};let i=C([a]);return ArrayBuffer.isView(n)||n instanceof ArrayBuffer||n instanceof DataView||typeof n=="string"&&i.values.has("content-type")||globalThis.Blob&&n instanceof globalThis.Blob||n instanceof FormData||n instanceof URLSearchParams||globalThis.ReadableStream&&n instanceof globalThis.ReadableStream?{bodyHeaders:void 0,body:n}:typeof n=="object"&&(Symbol.asyncIterator in n||Symbol.iterator in n&&"next"in n&&typeof n.next=="function")?{bodyHeaders:void 0,body:pn(n)}:typeof n=="object"&&i.values.get("content-type")==="application/x-www-form-urlencoded"?{bodyHeaders:{"content-type":"application/x-www-form-urlencoded"},body:this.stringifyQuery(n)}:K(this,ze,"f").call(this,{body:n,headers:i})}app(t){return new bn(t)}};_a=B,ze=new WeakMap,va=new WeakSet,Zi=function(){return this.baseURL!==ts[this._options.environment||"production"]};B.Kernel=_a;B.DEFAULT_TIMEOUT=6e4;B.KernelError=Y;B.APIError=nt;B.APIConnectionError=Et;B.APIConnectionTimeoutError=ft;B.APIUserAbortError=ot;B.NotFoundError=Ue;B.ConflictError=ue;B.RateLimitError=he;B.BadRequestError=de;B.AuthenticationError=le;B.InternalServerError=ge;B.PermissionDeniedError=Se;B.UnprocessableEntityError=ce;B.toFile=vn;B.Deployments=qt;B.Apps=Gt;B.Invocations=jt;B.Browsers=lt;B.Profiles=zt;B.Auth=vt;B.Telemetry=Lt;B.Proxies=$t;B.Extensions=Xt;B.BrowserPools=Vt;B.Credentials=Jt;B.Projects=At;B.Organization=_t;B.AuditLogs=It;B.APIKeys=Ft;B.CredentialProviders=Kt;var mt={paaItem:".related-question-pair",captchaMarker:'#captcha-form, #recaptcha, form[action*="/sorry/"], .g-recaptcha, [data-sitekey]'},es={container:'div[jscontroller="HWk0Gf"]',sectionHeading:'.mgAbYb[role="heading"]',item:"a.rIRoqf"},En={udm:"39",item:"a.rIRoqf",durationPattern:/^\d+:\d+$/,platforms:["YouTube","TikTok","Instagram","Facebook","X"]},ns={section:".ULSxyf",item:"a.KYg7td.INpicf",title:".hyYc0c",source:".K4ETW"},as={sectionTag:"g-section-with-header",sectionHeadingText:"What people are saying",card:'.dRzkFf[role="listitem"]',cardLink:'a.WlydOe[jsname="YKoRaf"]',titleH1:"h1.WQWxe",titleDiv:".eAaXgc",popularCommentLabel:".qgdis",source:".sTl1Td",platformBadge:".appd0, .KrMNbf",ytChannel:".sjVJQd",ytDate:".PLq9Je",authorNote:".nDgy9d"},is={root:"[data-lhcontainer][data-streaming-container][eid]",legacyRoot:'[data-hveid="CBMQAA"]',wrapper:".Fgyi2e",controller:'[jscontroller="AkrxPe"]',contentSubtree:'[data-subtree="mfc"]',header:".heWuVc",heading:".Fzsovc.cwYVJe.RJPOee",showMoreButton:'[aria-label="Show more AI Overview"]',sourcesPanel:".OZ9ddf.WAUd4",disclaimer:".DuQANe.MSJHRb"},ss={root:'[data-hveid="CAUQAA"]',wrapper:".Fgyi2e",citations:'.Fgyi2e [data-hveid] a[jsname="pxBnId"]'},os={result:".wHYlTd.tF2Cxc",title:"h3.LC20lb",siteName:".VuuXrf",cite:"cite.tjvcx",snippet:".VwiC3b",redditCite:"cite.qLRx3b",ratingWrap:".Y0A0hc",ratingValue:".yi40Hd",reviewCount:".RDApEe"},rs={headingText:"Businesses",card:".w7Dbne",name:".OSrXXb",ratingValue:".yi40Hd",reviewCount:".RDApEe"},ds="2026-05-07";var ls="Google returned a CAPTCHA. Run with --headless=false to re-warm the browser profile, then retry.";var dd=["request_aborted","captcha_exhausted","captcha_or_blocked","location_mismatch","proxy_tunnel_failed","proxy_unavailable","harvest_timeout","mcp_request_timeout","mcp_http_error","extraction_failed","concurrency_limit_exceeded","unauthorized","forbidden","invalid_request","rate_limited","upstream_rate_limited","insufficient_balance","service_unavailable","response_lost","vendor_unavailable","page_not_found","page_forbidden","page_rate_limited","page_server_error","page_http_error","bot_check_unresolved","page_too_large","page_unreachable","browser_session_interrupted","site_export_not_found","site_export_format_unavailable","site_export_read_failed","site_export_image_not_found","image_url_invalid","image_url_not_https","image_host_unresolvable","image_host_blocked","image_redirect_invalid","image_source_unavailable","image_too_large","image_redirect_limit","image_base64_invalid","image_source_missing","image_source_ambiguous","image_source_type_invalid","image_artifact_not_found","image_page_too_large","page_image_not_found","page_image_candidates_unusable","image_format_unsupported","image_storage_unconfigured","featured_image_unhostable"],ld=["request_aborted","captcha","location_mismatch","connection","timeout","extraction","concurrency_limit","unauthorized","forbidden","invalid_request","rate_limit","billing","service_unavailable"];var ng=new Set(dd),ag=new Set(ld);function Ss(e){return e.replace(/https?:\/\/[^\s]*(?:brightdata|onkernel|kernel\.sh)[^\s]*/gi,"the service").replace(/bright\s*data/gi,"the service").replace(/brightdata/gi,"the service").replace(/kernel\.sh\s+sessions?/gi,"sessions").replace(/kernel\.sh\s+session/gi,"this session").replace(/kernel\.sh/gi,"the service").replace(/kernel\s+sessions?/gi,"sessions").replace(/kernel\s+session/gi,"this session").replace(/\b(?:sub|cus|sess|proxy)_[A-Za-z0-9_-]+\b/g,"[redacted]").replace(/\b(?:KERNEL|BRIGHTDATA|BRIGHT_DATA)_[A-Z0-9_]*API_KEY\b/g,"BROWSER_SERVICE_API_KEY").replace(/\bkernel\b/gi,"the service").replace(/ +/g," ").trim()}var it=class extends Error{constructor(n){super(`CAPTCHA detected. ${n}`);this.instructions=n}instructions;name="CaptchaError"},Ae=class extends Error{constructor(n,a){super(n);this.cause=a}cause;name="ExtractionError"};var pt=class extends Error{name="RequestAbortedError";constructor(t="Request aborted before harvest completed"){super(t)}},Qt=class extends Error{name="PaaInteractionInterruptedError"},$e=class extends Error{name="LocationMismatchError";constructor(t="Google returned results for a different location than requested"){super(t)}};async function Pn(e,t,n,a){let i,s=!1,o,d=()=>{},l=()=>a?.reason instanceof DOMException&&a.reason.name==="TimeoutError"?a.reason:new pt,U=()=>d(l()),S=new Promise((u,c)=>{d=c}),r=async u=>{let c;try{await Promise.race([u.close().catch(()=>{}),new Promise(h=>{c=setTimeout(h,2e3)})])}finally{c&&clearTimeout(c)}};if(a?.aborted)throw l();a?.addEventListener("abort",U,{once:!0}),o=setTimeout(()=>d(new DOMException("Optional pagination timed out","TimeoutError")),3e4);try{return await Promise.race([(async()=>{let u=await e.newPage();if(s)throw await r(u),new pt;if(i=u,await t(u),s)throw new pt;return n(u)})(),S])}finally{s=!0,o&&clearTimeout(o),a?.removeEventListener("abort",U),i&&await r(i)}}var Ia=require("crypto");var Us=require("@libsql/client/http"),Qe=require("crypto"),Z=require("zod");var bt="strftime('%Y-%m-%dT%H:%M:%fZ','now')";var Sd=[`CREATE TABLE IF NOT EXISTS oauth_store_metadata (
|
|
9
|
+
${r}`)}return o},g=gr(qi);var Ft=class extends b{create(t,n){return this._client.post("/org/api_keys",{body:t,...n})}retrieve(t,n={},a){return this._client.get(g`/org/api_keys/${t}`,{query:n,...a})}update(t,n,a){return this._client.patch(g`/org/api_keys/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/api_keys",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/api_keys/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}rotate(t,n={},a){return this._client.post(g`/org/api_keys/${t}/rotate`,{body:n,...a})}};var Gt=class extends b{list(t={},n){return this._client.getAPIList("/apps",F,{query:t,...n})}};var we=class extends b{create(t,n){return this._client.post("/audit-logs/export/destinations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/audit-logs/export/destinations/${t}`,n)}update(t,n,a){return this._client.patch(g`/audit-logs/export/destinations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/audit-logs/export/destinations",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/audit-logs/export/destinations/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}test(t,n){return this._client.post(g`/audit-logs/export/destinations/${t}/test`,n)}};var wr=6,mr=5e4,yr=8e3,gt=class extends Y{};async function ji(e,t,n,a,i={}){if(!n||typeof n.write!="function")throw new TypeError("audit log download destination must provide write()");let{onProgress:s,maxTransferRetries:o=wr,...d}=i;if(!Number.isInteger(o)||o<0)throw new TypeError("maxTransferRetries must be a non-negative integer");let l=d.timeout??a,U,S={bytesWritten:0,chunks:0,rows:0},r=new Set;for(;;){let u=await Cr(e,U?{...t,cursor:U}:t,d,o,l),{nextCursor:c,hasMore:h,rows:w}=Tr(u.headers,U);if(h&&c){if(r.has(c))throw new gt("response repeated X-Next-Cursor header");r.add(c)}if(await Mr(n,u.body),U=c,S.bytesWritten+=u.body.byteLength,S.chunks+=1,S.rows+=w,s&&await s({...S,chunkRows:w}),!h)return S}}async function Cr(e,t,n,a,i){for(let s=0;;s+=1){let o=new AbortController,d=()=>o.abort();n.signal?.aborted?o.abort():n.signal?.addEventListener("abort",d,{once:!0});let l;try{l=await e(t,{...n,signal:o.signal})}catch(r){throw n.signal?.removeEventListener("abort",d),r}let U=!1,S=setTimeout(()=>{U=!0,o.abort()},i);try{let r=new Uint8Array(await l.arrayBuffer());if(clearTimeout(S),n.signal?.aborted)throw new ot;if(U)throw new ft;let u=l.headers.get("x-content-sha256");if(!u)throw new gt("response missing X-Content-Sha256 header");let c=await kr(r);if(n.signal?.aborted)throw new ot;if(c!==u)throw new gt(`audit log chunk checksum mismatch (got ${c}, want ${u})`);return{body:r,headers:l.headers}}catch(r){if(n.signal?.aborted&&!(r instanceof ot)?r=new ot:U&&(r=new ft),s===a||r instanceof ot)throw r;await fr(s+1,n.signal)}finally{clearTimeout(S),n.signal?.removeEventListener("abort",d)}}}function Tr(e,t){let n=e.get("x-has-more");if(n!=="true"&&n!=="false")throw new gt("response missing or invalid X-Has-More header");let a=n==="true",i=e.get("x-row-count");if(i===null||!/^[0-9]+$/.test(i))throw new gt("response missing or invalid X-Row-Count header");let s=Number(i);if(!Number.isSafeInteger(s)||s>mr)throw new gt("response missing or invalid X-Row-Count header");let o=e.get("x-next-cursor")||void 0;if(a&&(!o||o===t))throw new gt("response has invalid X-Next-Cursor header");if(!a&&o)throw new gt("response returned a cursor after the final chunk");return{rows:s,nextCursor:o,hasMore:a}}async function kr(e){let t=await globalThis.crypto.subtle.digest("SHA-256",e);return Array.from(new Uint8Array(t),n=>n.toString(16).padStart(2,"0")).join("")}async function fr(e,t){let n=Math.min(1e3*2**(e-1),yr);await new Promise((a,i)=>{if(t?.aborted){i(new ot);return}let s=()=>{clearTimeout(o),i(new ot)},o=setTimeout(()=>{t?.removeEventListener("abort",s),a()},n);t?.addEventListener("abort",s,{once:!0})})}async function Mr(e,t){let n=0;for(;n<t.byteLength;){let a=await e.write(n===0?t:t.subarray(n));if(typeof a=="number"){n+=Xi(a,t.byteLength-n);continue}if(a&&typeof a=="object"&&"bytesWritten"in a){let i=a.bytesWritten;n+=Xi(i,t.byteLength-n);continue}return}}function Xi(e,t){if(!Number.isSafeInteger(e)||e<=0||e>t)throw new gt("audit log download destination performed a short write");return e}var It=class extends b{constructor(){super(...arguments),this.exportDestinations=new we(this._client)}list(t,n){return this._client.getAPIList("/audit-logs",Mn,{query:t,...n})}exportChunk(t,n){return this._client.get("/audit-logs/export/chunk",{query:t,...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}download(t,n,a){return ji((i,s)=>this.exportChunk(i,s),t,n,this._client.timeout,a)}};It.ExportDestinations=we;var me=class extends b{create(t,n){return this._client.post("/auth/connections",{body:t,...n})}retrieve(t,n){return this._client.get(g`/auth/connections/${t}`,n)}update(t,n,a){return this._client.patch(g`/auth/connections/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/auth/connections",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/auth/connections/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n){return this._client.get(g`/auth/connections/${t}/events`,{...n,headers:C([{Accept:"text/event-stream"},n?.headers]),stream:!0})}login(t,n={},a){return this._client.post(g`/auth/connections/${t}/login`,{body:n,...a})}submit(t,n,a){return this._client.post(g`/auth/connections/${t}/submit`,{body:n,...a})}timeline(t,n={},a){return this._client.getAPIList(g`/auth/connections/${t}/timeline`,F,{query:n,...a})}};var ye=class extends b{retrieve(t){return this._client.get("/auth/context",t)}};var vt=class extends b{constructor(){super(...arguments),this.context=new ye(this._client),this.connections=new me(this._client)}};vt.Context=ye;vt.Connections=me;var Vt=class extends b{create(t,n){return this._client.post("/browser_pools",{body:t,...n})}retrieve(t,n){return this._client.get(g`/browser_pools/${t}`,n)}update(t,n,a){return this._client.patch(g`/browser_pools/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/browser_pools",F,{query:t,...n})}delete(t,n={},a){return this._client.delete(g`/browser_pools/${t}`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}acquire(t,n,a){return this._client.post(g`/browser_pools/${t}/acquire`,{body:n,...a})}flush(t,n){return this._client.post(g`/browser_pools/${t}/flush`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}release(t,n,a){return this._client.post(g`/browser_pools/${t}/release`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Ce=class extends b{batch(t,n,a){return this._client.post(g`/browsers/${t}/computer/batch`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}captureScreenshot(t,n={},a){return this._client.post(g`/browsers/${t}/computer/screenshot`,{body:n,...a,headers:C([{Accept:"image/png"},a?.headers]),__binaryResponse:!0})}clickMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/click_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}dragMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/drag_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}getMousePosition(t,n){return this._client.post(g`/browsers/${t}/computer/get_mouse_position`,n)}moveMouse(t,n,a){return this._client.post(g`/browsers/${t}/computer/move_mouse`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}pressKey(t,n,a){return this._client.post(g`/browsers/${t}/computer/press_key`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}readClipboard(t,n){return this._client.post(g`/browsers/${t}/computer/clipboard/read`,n)}scroll(t,n,a){return this._client.post(g`/browsers/${t}/computer/scroll`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}setCursorVisibility(t,n,a){return this._client.post(g`/browsers/${t}/computer/cursor`,{body:n,...a})}typeText(t,n,a){return this._client.post(g`/browsers/${t}/computer/type`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}writeClipboard(t,n,a){return this._client.post(g`/browsers/${t}/computer/clipboard/write`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Te=class extends b{stream(t,n,a){return this._client.get(g`/browsers/${t}/logs/stream`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var ke=class extends b{execute(t,n,a){return this._client.post(g`/browsers/${t}/playwright/execute`,{body:n,...a})}};var fe=class extends b{exec(t,n,a){return this._client.post(g`/browsers/${t}/process/exec`,{body:n,...a})}kill(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/kill`,{body:s,...a})}resize(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/resize`,{body:s,...a})}spawn(t,n,a){return this._client.post(g`/browsers/${t}/process/spawn`,{body:n,...a})}status(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/process/${t}/status`,a)}stdin(t,n,a){let{id:i,...s}=n;return this._client.post(g`/browsers/${i}/process/${t}/stdin`,{body:s,...a})}stdoutStream(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/process/${t}/stdout/stream`,{...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var Me=class extends b{list(t,n){return this._client.get(g`/browsers/${t}/replays`,n)}download(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/replays/${t}`,{...a,headers:C([{Accept:"video/mp4"},a?.headers]),__binaryResponse:!0})}start(t,n={},a){return this._client.post(g`/browsers/${t}/replays`,{body:n,...a})}stop(t,n,a){let{id:i}=n;return this._client.post(g`/browsers/${i}/replays/${t}/stop`,{...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Ne=class extends b{events(t,n={},a){return this._client.getAPIList(g`/browsers/${t}/telemetry/events`,F,{query:n,...a})}stream(t,n={},a){let{"Last-Event-ID":i,...s}=n??{};return this._client.get(g`/browsers/${t}/telemetry/stream`,{query:s,...a,headers:C([{Accept:"text/event-stream",...i!=null?{"Last-Event-ID":i}:void 0},a?.headers]),stream:!0})}};var ve=class extends b{events(t,n,a){let{id:i}=n;return this._client.get(g`/browsers/${i}/fs/watch/${t}/events`,{...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}start(t,n,a){return this._client.post(g`/browsers/${t}/fs/watch`,{body:n,...a})}stop(t,n,a){let{id:i}=n;return this._client.delete(g`/browsers/${i}/fs/watch/${t}`,{...a,headers:C([{Accept:"*/*"},a?.headers])})}};var Yt=class extends b{constructor(){super(...arguments),this.watch=new ve(this._client)}createDirectory(t,n,a){return this._client.put(g`/browsers/${t}/fs/create_directory`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}deleteDirectory(t,n,a){return this._client.put(g`/browsers/${t}/fs/delete_directory`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}deleteFile(t,n,a){return this._client.put(g`/browsers/${t}/fs/delete_file`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}downloadDirZip(t,n,a){return this._client.get(g`/browsers/${t}/fs/download_dir_zip`,{query:n,...a,headers:C([{Accept:"application/zip"},a?.headers]),__binaryResponse:!0})}fileInfo(t,n,a){return this._client.get(g`/browsers/${t}/fs/file_info`,{query:n,...a})}listFiles(t,n,a){return this._client.get(g`/browsers/${t}/fs/list_files`,{query:n,...a})}move(t,n,a){return this._client.put(g`/browsers/${t}/fs/move`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}readFile(t,n,a){return this._client.get(g`/browsers/${t}/fs/read_file`,{query:n,...a,headers:C([{Accept:"application/octet-stream"},a?.headers]),__binaryResponse:!0})}setFilePermissions(t,n,a){return this._client.put(g`/browsers/${t}/fs/set_file_permissions`,{body:n,...a,headers:C([{Accept:"*/*"},a?.headers])})}upload(t,n,a){return this._client.post(g`/browsers/${t}/fs/upload`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}uploadZip(t,n,a){return this._client.post(g`/browsers/${t}/fs/upload_zip`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}writeFile(t,n,a,i){let{path:s,mode:o}=a;return this._client.put(g`/browsers/${t}/fs/write_file`,{body:n,query:{path:s,mode:o},...i,headers:C([{"Content-Type":"application/octet-stream",Accept:"*/*"},i?.headers])})}};Yt.Watch=ve;function _n(e,t){return`${e.replace(/\/+$/,"")}${t.startsWith("/")?t:`/${t}`}`}async function zi(e,t,n,a){let i=e.browserRouteCache.get(t);if(!i)throw new Y(`browser route cache does not contain session ${t}; create, retrieve, or list the browser before calling browser.fetch`);let{url:s,method:o,headers:d,body:l,signal:U,duplex:S,timeout_ms:r}=Rr(n,a);Wr(s);let u={url:s,jwt:i.jwt};r!==void 0&&(u.timeout_ms=r);let c=d.get("accept"),h={method:Or(o),path:_n(i.baseURL,"/curl/raw"),query:u,body:l,headers:C([{Authorization:null},c?{Accept:c}:{Accept:"*/*"},Hr(d)]),signal:U??null,__binaryResponse:!0};return S&&(h.fetchOptions={duplex:S}),e.request(h).asResponse()}function Or(e){let t=e.toLowerCase();if(!new Set(["get","post","put","patch","delete"]).has(t))throw new Y(`browser.fetch unsupported HTTP method: ${e}`);return t}function Rr(e,t){let n=t&&"timeout_ms"in t?t.timeout_ms:void 0;if(e instanceof Request){let i=new Headers(e.headers);t?.headers&&new Headers(t.headers).forEach((U,S)=>{i.set(S,U)});let s={url:e.url,method:(t?.method??e.method)?.toUpperCase()||"GET",headers:i},o=t?.body??e.body;o!=null&&(s.body=o);let d=t?.signal??e.signal;return d!==void 0&&(s.signal=d),t?.duplex!==void 0&&(s.duplex=t.duplex),n!==void 0&&(s.timeout_ms=n),s}let a={url:e instanceof URL?e.href:String(e),method:(t?.method??"GET").toUpperCase(),headers:new Headers(t?.headers)};return t?.body!==void 0&&(a.body=t.body),t?.signal!==void 0&&(a.signal=t.signal),t?.duplex!==void 0&&(a.duplex=t.duplex),n!==void 0&&(a.timeout_ms=n),a}function Wr(e){let t;try{t=new URL(e)}catch{throw new Y(`browser.fetch target must be an absolute URL; received: ${e}`)}if(t.protocol!=="http:"&&t.protocol!=="https:")throw new Y(`browser.fetch only supports http(s) URLs; received: ${t.protocol}`)}function Hr(e){let t={};return e.forEach((n,a)=>{switch(a.toLowerCase()){case"accept":case"content-length":case"connection":case"keep-alive":case"proxy-authenticate":case"proxy-authorization":case"te":case"trailers":case"transfer-encoding":case"upgrade":return;default:t[a]=n}}),t}var lt=class extends b{constructor(){super(...arguments),this.telemetry=new Ne(this._client),this.replays=new Me(this._client),this.fs=new Yt(this._client),this.process=new fe(this._client),this.logs=new Te(this._client),this.computer=new Ce(this._client),this.playwright=new ke(this._client)}create(t={},n){return this._client.post("/browsers",{body:t,...n})}retrieve(t,n={},a){return this._client.get(g`/browsers/${t}`,{query:n,...a})}update(t,n,a){return this._client.patch(g`/browsers/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/browsers",F,{query:t,...n})}curl(t,n,a){return this._client.post(g`/browsers/${t}/curl`,{body:n,...a})}fetch(t,n,a){return zi(this._client,t,n,a)}deleteByID(t,n){return this._client.delete(g`/browsers/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}loadExtensions(t,n,a){return this._client.post(g`/browsers/${t}/extensions`,Nt({body:n,...a,headers:C([{Accept:"*/*"},a?.headers])},this._client))}};lt.Telemetry=Ne;lt.Replays=Me;lt.Fs=Yt;lt.Process=fe;lt.Logs=Te;lt.Computer=Ce;lt.Playwright=ke;var Kt=class extends b{create(t,n){return this._client.post("/org/credential_providers",{body:t,...n})}retrieve(t,n){return this._client.get(g`/org/credential_providers/${t}`,n)}update(t,n,a){return this._client.patch(g`/org/credential_providers/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/credential_providers",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/credential_providers/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}listItems(t,n){return this._client.get(g`/org/credential_providers/${t}/items`,n)}test(t,n){return this._client.post(g`/org/credential_providers/${t}/test`,n)}};var Jt=class extends b{create(t,n){return this._client.post("/credentials",{body:t,...n})}retrieve(t,n){return this._client.get(g`/credentials/${t}`,n)}update(t,n,a){return this._client.patch(g`/credentials/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/credentials",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/credentials/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}totpCode(t,n){return this._client.get(g`/credentials/${t}/totp-code`,n)}};var qt=class extends b{create(t,n){return this._client.post("/deployments",Nt({body:t,...n},this._client))}retrieve(t,n){return this._client.get(g`/deployments/${t}`,n)}list(t={},n){return this._client.getAPIList("/deployments",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/deployments/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n={},a){return this._client.get(g`/deployments/${t}/events`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}};var Xt=class extends b{list(t={},n){return this._client.getAPIList("/extensions",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/extensions/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}download(t,n){return this._client.get(g`/extensions/${t}`,{...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}downloadFromChromeStore(t,n){return this._client.get("/extensions/from_chrome_store",{query:t,...n,headers:C([{Accept:"application/octet-stream"},n?.headers]),__binaryResponse:!0})}get(t,n){return this._client.get(g`/extensions/${t}/metadata`,n)}upload(t,n){return this._client.post("/extensions",Nt({body:t,...n},this._client))}};var jt=class extends b{create(t,n){return this._client.post("/invocations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/invocations/${t}`,n)}update(t,n,a){return this._client.patch(g`/invocations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/invocations",F,{query:t,...n})}deleteBrowsers(t,n){return this._client.delete(g`/invocations/${t}/browsers`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}follow(t,n={},a){return this._client.get(g`/invocations/${t}/events`,{query:n,...a,headers:C([{Accept:"text/event-stream"},a?.headers]),stream:!0})}listBrowsers(t,n){return this._client.get(g`/invocations/${t}/browsers`,n)}};var _e=class extends b{retrieve(t){return this._client.get("/org/entitlements",t)}};var be=class extends b{retrieve(t){return this._client.get("/org/limits",t)}update(t,n){return this._client.patch("/org/limits",{body:t,...n})}};var _t=class extends b{constructor(){super(...arguments),this.entitlements=new _e(this._client),this.limits=new be(this._client)}};_t.Entitlements=_e;_t.Limits=be;var zt=class extends b{create(t,n){return this._client.post("/profiles",{body:t,...n})}retrieve(t,n){return this._client.get(g`/profiles/${t}`,n)}update(t,n,a){return this._client.patch(g`/profiles/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/profiles",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/profiles/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}download(t,n={},a){return this._client.get(g`/profiles/${t}/download`,{query:n,...a,headers:C([{Accept:"application/octet-stream"},a?.headers]),__binaryResponse:!0})}};var Ee=class extends b{retrieve(t,n){return this._client.get(g`/org/projects/${t}/limits`,n)}update(t,n,a){return this._client.patch(g`/org/projects/${t}/limits`,{body:n,...a})}};var At=class extends b{constructor(){super(...arguments),this.limits=new Ee(this._client)}create(t,n){return this._client.post("/org/projects",{body:t,...n})}retrieve(t,n){return this._client.get(g`/org/projects/${t}`,n)}update(t,n,a){return this._client.patch(g`/org/projects/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/org/projects",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/org/projects/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}};At.Limits=Ee;var $t=class extends b{create(t,n){return this._client.post("/proxies",{body:t,...n})}retrieve(t,n){return this._client.get(g`/proxies/${t}`,n)}update(t,n,a){return this._client.patch(g`/proxies/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/proxies",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/proxies/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}check(t,n={},a){return this._client.post(g`/proxies/${t}/check`,{body:n,...a})}};var Pe=class extends b{create(t,n){return this._client.post("/telemetry/destinations",{body:t,...n})}retrieve(t,n){return this._client.get(g`/telemetry/destinations/${t}`,n)}update(t,n,a){return this._client.patch(g`/telemetry/destinations/${t}`,{body:n,...a})}list(t={},n){return this._client.getAPIList("/telemetry/destinations",F,{query:t,...n})}delete(t,n){return this._client.delete(g`/telemetry/destinations/${t}`,{...n,headers:C([{Accept:"*/*"},n?.headers])})}};var Lt=class extends b{constructor(){super(...arguments),this.destinations=new Pe(this._client)}};Lt.Destinations=Pe;var je=class{constructor(){this.entries=new Map}get(t){return this.entries.get(t)}set(t){this.entries.set(t.sessionId,t)}delete(t){this.entries.delete(t)}clear(){this.entries.clear()}},$i="\u004b\u0045\u0052\u004e\u0045\u004c_BROWSER_ROUTING_SUBRESOURCES",Yr=["curl","telemetry/stream"],Kr=/^\/(?:v\d+\/)?browsers(?:\/[^/]+)?\/?$/,Jr=/^\/(?:v\d+\/)?browser_pools\/[^/]+\/acquire\/?$/,qr=/^\/(?:v\d+\/)?browsers\/([^/]+)\/?$/,Xr=/^\/(?:v\d+\/)?browser_pools\/[^/]+\/release\/?$/;function fa(){let e=rd();return e===void 0?[...Yr]:e.trim()===""?[]:e.split(",").map(t=>t.trim()).filter(Boolean)}function Ma(e,{apiBaseURL:t,subresources:n,cache:a}){let i=[...n].map(o=>o.trim().replace(/^\/+|\/+$/g,"")).filter(Boolean),s=new URL(t).origin;return async(o,d)=>{let l=new Request(o,d),U=jr(l,s),S=await nd(e,{input:o,init:d,request:l},s,i,a);return U&&await td(S,a),await zr(l,S,s,a),S}}function jr(e,t){let n=new URL(e.url);return n.origin===t&&(Kr.test(n.pathname)||Jr.test(n.pathname))}async function zr(e,t,n,a){if(!t.ok)return;let i=new URL(e.url);if(i.origin!==n)return;let s=$r(e,i.pathname)??await Qr(e,i.pathname);s&&a.delete(s)}function $r(e,t){if(e.method.toUpperCase()!=="DELETE")return;let n=t.match(qr);return n&&decodeURIComponent(n[1]??"")||void 0}async function Qr(e,t){if(!(e.method.toUpperCase()!=="POST"||!Xr.test(t)))try{let n=await e.clone().json();if(!n||typeof n!="object")return;let a=n.session_id;return typeof a=="string"&&a.trim()?a.trim():void 0}catch{return}}function Zr(e){if(!e||typeof e!="object")return;let t=e,n=typeof t.session_id=="string"?t.session_id.trim():"",a=typeof t.base_url=="string"?t.base_url.trim():"";if(!n||!a)return;let i=typeof t.jwt=="string"?t.jwt.trim():"",s=typeof t.cdp_ws_url=="string"?t.cdp_ws_url:void 0,o=i||od(s)||"";if(o)return{sessionId:n,baseURL:a,jwt:o}}async function td(e,t){if((e.headers.get("content-type")?.toLowerCase()??"").includes("application/json"))try{ka(await e.clone().json(),t)}catch{}}function ka(e,t){let n=Zr(e);if(n&&t.set(n),Array.isArray(e)){for(let a of e)ka(a,t);return}if(!(!e||typeof e!="object"))for(let a of Object.values(e))typeof a=="object"&&a!==null&&ka(a,t)}function ed(e,t){let n=e.replace(/^\/+|\/+$/g,"");return t.some(a=>n===a||n.startsWith(a+"/"))}async function nd(e,{input:t,init:n,request:a},i,s,o){let d=new URL(a.url);if(d.origin!==i)return e(t,n);let l=d.pathname.match(/^\/(?:v\d+\/)?browsers\/([^/]+)\/([^/]+)(\/.*)?$/);if(!l)return e(t,n);let U=decodeURIComponent(l[1]??""),S=l[2]??"";if(!U||!ed(S+(l[3]??""),s))return e(t,n);let r=o.get(U);if(r===void 0)return e(t,n);let u=new URL(_n(r.baseURL,`/${S}${l[3]??""}`));d.searchParams.forEach((h,w)=>{w!=="jwt"&&u.searchParams.append(w,h)}),u.searchParams.get("jwt")||u.searchParams.set("jwt",r.jwt);let c=new Headers(a.headers);return c.delete("authorization"),e(u.toString(),ad(t,a,n,c))}function ad(e,t,n,a){let i=t.method.toUpperCase(),s={...n??{},method:i,headers:a,redirect:t.redirect,signal:n?.signal??(e instanceof Request?e.signal:void 0)};if(delete s.body,delete s.duplex,i!=="GET"&&i!=="HEAD"){let o=id(t,n);o!==void 0&&(s.body=o),n?.duplex!==void 0?s.duplex=n.duplex:sd(o)&&(s.duplex="half")}return s}function id(e,t){return t?.body!==void 0&&t.body!==null?t.body:e.body??void 0}function sd(e){return globalThis.ReadableStream&&e instanceof globalThis.ReadableStream||typeof e=="object"&&e!==null&&Symbol.asyncIterator in e}function od(e){if(e)try{return new URL(e).searchParams.get("jwt")??void 0}catch{return}}function rd(){if(typeof globalThis.process<"u"){let e=globalThis.process.env?.[$i];return typeof e=="string"?e:void 0}if(typeof globalThis.Deno<"u"){let e=globalThis.Deno.env?.get?.($i);return typeof e=="string"?e:void 0}}var bn=class{constructor(t){this.actions=new Map,this.name=t,Qi.registerApp(this)}action(t,n){let a;if(n.length===0)throw new Error("Action handlers must accept at least the context parameter");if(n.length===1){let i=n;a=async(s,o)=>i(s)}else a=n;return this.actions.set(t,{name:t,handler:a}),a}getActions(){return Array.from(this.actions.values())}getAction(t){return this.actions.get(t)}toJSON(){return{name:this.name,actions:this.getActions().map(t=>({name:t.name}))}}},Na=class{constructor(){this.apps=new Map}registerApp(t){this.apps.set(t.name,t)}getApps(){return Array.from(this.apps.values())}getAppByName(t){return this.apps.get(t)}export(){return{apps:this.getApps().map(t=>t.toJSON())}}exportJSON(){return JSON.stringify(this.export(),null,2)}},Qi=new Na;var Ie=e=>{if(typeof globalThis.process<"u")return globalThis.process.env?.[e]?.trim()||void 0;if(typeof globalThis.Deno<"u")return globalThis.Deno.env?.get?.(e)?.trim()||void 0};var va,_a,ze,Zi,ts={production:"https://api.on\u006b\u0065\u0072\u006e\u0065\u006c.com/",development:"https://localhost:3001/"},B=class{constructor({baseURL:t=Ie("\u004b\u0045\u0052\u004e\u0045\u004c_BASE_URL"),apiKey:n=Ie("\u004b\u0045\u0052\u004e\u0045\u004c_API_KEY"),projectID:a=null,project:i=null,...s}={}){if(va.add(this),ze.set(this,void 0),this.deployments=new qt(this),this.apps=new Gt(this),this.invocations=new jt(this),this.browsers=new lt(this),this.profiles=new zt(this),this.auth=new vt(this),this.telemetry=new Lt(this),this.proxies=new $t(this),this.extensions=new Xt(this),this.browserPools=new Vt(this),this.credentials=new Jt(this),this.projects=new At(this),this.organization=new _t(this),this.auditLogs=new It(this),this.apiKeys=new Ft(this),this.credentialProviders=new Kt(this),typeof globalThis<"u"&&typeof globalThis.Bun<"u"&&globalThis.Bun.version&&!Ie("\u004b\u0045\u0052\u004e\u0045\u004c_SUPPRESS_BUN_WARNING")&&$(this).warn("The Bun runtime was detected. Playwright may have CDP connection issues, proceed with caution. Suppress this warning by setting the \u004b\u0045\u0052\u004e\u0045\u004c_SUPPRESS_BUN_WARNING environment variable to true"),n===void 0)throw new Y("The \u004b\u0045\u0052\u004e\u0045\u004c_API_KEY environment variable is missing or empty; either provide it, or instantiate the \u004b\u0065\u0072\u006e\u0065\u006c client with an apiKey option, like new \u004b\u0065\u0072\u006e\u0065\u006c({ apiKey: 'My API Key' }).");let o={apiKey:n,projectID:a,project:i,...s,baseURL:t,environment:s.environment??"production"};if(t&&s.environment)throw new Y("Ambiguous URL; The `baseURL` option (or \u004b\u0045\u0052\u004e\u0045\u004c_BASE_URL env var) and the `environment` option are given. If you want to use the environment you must pass baseURL: null");this.baseURL=o.baseURL||ts[o.environment||"production"],this.timeout=o.timeout??_a.DEFAULT_TIMEOUT,this.logger=o.logger??console;let d="warn";this.logLevel=d,this.logLevel=pa(o.logLevel,"ClientOptions.logLevel",this)??pa(Ie("\u004b\u0045\u0052\u004e\u0045\u004c_LOG"),"process.env['\u004b\u0045\u0052\u004e\u0045\u004c_LOG']",this)??d,this.fetchOptions=o.fetchOptions,this.maxRetries=o.maxRetries??2,this.rawFetch=o.fetch??Ni(),this.browserRouteCache=new je,this.fetch=Ma(this.rawFetch,{apiBaseURL:this.baseURL,subresources:fa(),cache:this.browserRouteCache}),tt(this,ze,_i,"f");let l=Ie("\u004b\u0045\u0052\u004e\u0045\u004c_CUSTOM_HEADERS");if(l){let U={};for(let S of l.split(`
|
|
10
|
+
`)){let r=S.indexOf(":");r>=0&&(U[S.substring(0,r).trim()]=S.substring(r+1).trim())}o.defaultHeaders={...U,...o.defaultHeaders}}this._options=o,this.apiKey=n,this.projectID=a,this.project=i}withOptions(t){let n=new this.constructor({...this._options,environment:t.environment?t.environment:void 0,baseURL:t.environment?void 0:this.baseURL,maxRetries:this.maxRetries,timeout:this.timeout,logger:this.logger,logLevel:this.logLevel,fetch:this.rawFetch,fetchOptions:this.fetchOptions,apiKey:this.apiKey,projectID:this.projectID,project:this.project,...t});return n.browserRouteCache=this.browserRouteCache,n.fetch=Ma(n.rawFetch,{apiBaseURL:n.baseURL,subresources:fa(),cache:n.browserRouteCache}),n}defaultQuery(){return this._options.defaultQuery}validateHeaders({values:t,nulls:n}){}async authHeaders(t){return C([{Authorization:`Bearer ${this.apiKey}`}])}stringifyQuery(t){return Ri(t)}getUserAgent(){return`${this.constructor.name}/JS ${Pt}`}defaultIdempotencyKey(){return`stainless-node-retry-${na()}`}makeStatusError(t,n,a,i){return nt.generate(t,n,a,i)}buildURL(t,n,a){let i=!K(this,va,"m",Zi).call(this)&&a||this.baseURL,s=gi(t)?new URL(t):new URL(i+(i.endsWith("/")&&t.startsWith("/")?t.slice(1):t)),o=this.defaultQuery(),d=Object.fromEntries(s.searchParams);return(!sa(o)||!sa(d))&&(n={...d,...o,...n}),typeof n=="object"&&n&&!Array.isArray(n)&&(s.search=this.stringifyQuery(n)),s.toString()}async prepareOptions(t){}async prepareRequest(t,{url:n,options:a}){}get(t,n){return this.methodRequest("get",t,n)}post(t,n){return this.methodRequest("post",t,n)}patch(t,n){return this.methodRequest("patch",t,n)}put(t,n){return this.methodRequest("put",t,n)}delete(t,n){return this.methodRequest("delete",t,n)}methodRequest(t,n,a){return this.request(Promise.resolve(a).then(i=>({method:t,path:n,...i})))}request(t,n=null){return new Dt(this,this.makeRequest(t,n,void 0))}async makeRequest(t,n,a){let i=await t,s=i.maxRetries??this.maxRetries;n==null&&(n=s),await this.prepareOptions(i);let{req:o,url:d,timeout:l}=await this.buildRequest(i,{retryCount:s-n});await this.prepareRequest(o,{url:d,options:i});let U="log_"+(Math.random()*(1<<24)|0).toString(16).padStart(6,"0"),S=a===void 0?"":`, retryOf: ${a}`,r=Date.now();if($(this).debug(`[${U}] sending request`,Mt({retryOfRequestLogID:a,method:i.method,url:d,options:i,headers:o.headers})),i.signal?.aborted)throw new ot;let u=new AbortController,c=await this.fetchWithTimeout(d,o,l,u).catch(Ge),h=Date.now();if(c instanceof globalThis.Error){let k=`retrying, ${n} attempts remaining`;if(i.signal?.aborted)throw new ot;let f=Fe(c)||/timed? ?out/i.test(String(c)+("cause"in c?String(c.cause):""));if(n)return $(this).info(`[${U}] connection ${f?"timed out":"failed"} - ${k}`),$(this).debug(`[${U}] connection ${f?"timed out":"failed"} (${k})`,Mt({retryOfRequestLogID:a,url:d,durationMs:h-r,message:c.message})),this.retryRequest(i,n,a??U);throw $(this).info(`[${U}] connection ${f?"timed out":"failed"} - error; no more retries left`),$(this).debug(`[${U}] connection ${f?"timed out":"failed"} (error; no more retries left)`,Mt({retryOfRequestLogID:a,url:d,durationMs:h-r,message:c.message})),f?new ft:new Et({cause:c})}let w=`[${U}${S}] ${o.method} ${d} ${c.ok?"succeeded":"failed"} with status ${c.status} in ${h-r}ms`;if(!c.ok){let k=await this.shouldRetry(c);if(n&&k){let _=`retrying, ${n} attempts remaining`;return await vi(c.body),$(this).info(`${w} - ${_}`),$(this).debug(`[${U}] response error (${_})`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,durationMs:h-r})),this.retryRequest(i,n,a??U,c.headers)}let f=k?"error; no more retries left":"error; not retryable";$(this).info(`${w} - ${f}`);let m=await c.text().catch(_=>Ge(_).message),L=yi(m),R=L?void 0:m;throw $(this).debug(`[${U}] response error (${f})`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,message:R,durationMs:Date.now()-r})),this.makeStatusError(c.status,L,R,c.headers)}return $(this).info(w),$(this).debug(`[${U}] response start`,Mt({retryOfRequestLogID:a,url:c.url,status:c.status,headers:c.headers,durationMs:h-r})),{response:c,options:i,controller:u,requestLogID:U,retryOfRequestLogID:a,startTime:r}}getAPIList(t,n,a){return this.requestAPIList(n,a&&"then"in a?a.then(i=>({method:"get",path:t,...i})):{method:"get",path:t,...a})}requestAPIList(t,n){let a=this.makeRequest(n,null,void 0);return new qe(this,a,t)}async fetchWithTimeout(t,n,a,i){let{signal:s,method:o,...d}=n||{},l=this._makeAbort(i);s&&s.addEventListener("abort",l,{once:!0});let U=setTimeout(l,a),S=globalThis.ReadableStream&&d.body instanceof globalThis.ReadableStream||typeof d.body=="object"&&d.body!==null&&Symbol.asyncIterator in d.body,r={signal:i.signal,...S?{duplex:"half"}:{},method:"GET",...d};o&&(r.method=o.toUpperCase());try{return await this.fetch.call(void 0,t,r)}finally{clearTimeout(U)}}async shouldRetry(t){let n=t.headers.get("x-should-retry");return n==="true"?!0:n==="false"?!1:t.status===408||t.status===409||t.status===429||t.status>=500}async retryRequest(t,n,a,i){let s,o=i?.get("retry-after-ms");if(o){let l=parseFloat(o);Number.isNaN(l)||(s=l)}let d=i?.get("retry-after");if(d&&!s){let l=parseFloat(d);Number.isNaN(l)?s=Date.parse(d)-Date.now():s=l*1e3}if(s===void 0){let l=t.maxRetries??this.maxRetries;s=this.calculateDefaultRetryTimeoutMillis(n,l)}return await Ci(s),this.makeRequest(t,n-1,a)}calculateDefaultRetryTimeoutMillis(t,n){let s=n-t,o=Math.min(.5*Math.pow(2,s),8),d=1-Math.random()*.25;return o*d*1e3}async buildRequest(t,{retryCount:n=0}={}){let a={...t},{method:i,path:s,query:o,defaultBaseURL:d}=a,l=this.buildURL(s,o,d);"timeout"in a&&wi("timeout",a.timeout),a.timeout=a.timeout??this.timeout;let{bodyHeaders:U,body:S}=this.buildBody({options:a}),r=await this.buildHeaders({options:t,method:i,bodyHeaders:U,retryCount:n});return{req:{method:i,headers:r,...a.signal&&{signal:a.signal},...globalThis.ReadableStream&&S instanceof globalThis.ReadableStream&&{duplex:"half"},...S&&{body:S},...this.fetchOptions??{},...a.fetchOptions??{}},url:l,timeout:a.timeout}}async buildHeaders({options:t,method:n,bodyHeaders:a,retryCount:i}){let s={};this.idempotencyHeader&&n!=="get"&&(t.idempotencyKey||(t.idempotencyKey=this.defaultIdempotencyKey()),s[this.idempotencyHeader]=t.idempotencyKey);let o=C([s,{Accept:"application/json","User-Agent":this.getUserAgent(),"X-Stainless-Retry-Count":String(i),...t.timeout?{"X-Stainless-Timeout":String(Math.trunc(t.timeout/1e3))}:{},...Mi(),"X-\u004b\u0065\u0072\u006e\u0065\u006c-Project-Id":this.projectID,"X-\u004b\u0065\u0072\u006e\u0065\u006c-Project":this.project},await this.authHeaders(t),this._options.defaultHeaders,a,t.headers]);return this.validateHeaders(o),o.values}_makeAbort(t){return()=>t.abort()}buildBody({options:t}){let{body:n,headers:a}=t;if(!n)return n==null&&"body"in t?K(this,ze,"f").call(this,{body:n,headers:C([a])}):{bodyHeaders:void 0,body:void 0};let i=C([a]);return ArrayBuffer.isView(n)||n instanceof ArrayBuffer||n instanceof DataView||typeof n=="string"&&i.values.has("content-type")||globalThis.Blob&&n instanceof globalThis.Blob||n instanceof FormData||n instanceof URLSearchParams||globalThis.ReadableStream&&n instanceof globalThis.ReadableStream?{bodyHeaders:void 0,body:n}:typeof n=="object"&&(Symbol.asyncIterator in n||Symbol.iterator in n&&"next"in n&&typeof n.next=="function")?{bodyHeaders:void 0,body:pn(n)}:typeof n=="object"&&i.values.get("content-type")==="application/x-www-form-urlencoded"?{bodyHeaders:{"content-type":"application/x-www-form-urlencoded"},body:this.stringifyQuery(n)}:K(this,ze,"f").call(this,{body:n,headers:i})}app(t){return new bn(t)}};_a=B,ze=new WeakMap,va=new WeakSet,Zi=function(){return this.baseURL!==ts[this._options.environment||"production"]};B.\u004b\u0065\u0072\u006e\u0065\u006c=_a;B.DEFAULT_TIMEOUT=6e4;B.\u004b\u0065\u0072\u006e\u0065\u006cError=Y;B.APIError=nt;B.APIConnectionError=Et;B.APIConnectionTimeoutError=ft;B.APIUserAbortError=ot;B.NotFoundError=Ue;B.ConflictError=ue;B.RateLimitError=he;B.BadRequestError=de;B.AuthenticationError=le;B.InternalServerError=ge;B.PermissionDeniedError=Se;B.UnprocessableEntityError=ce;B.toFile=vn;B.Deployments=qt;B.Apps=Gt;B.Invocations=jt;B.Browsers=lt;B.Profiles=zt;B.Auth=vt;B.Telemetry=Lt;B.Proxies=$t;B.Extensions=Xt;B.BrowserPools=Vt;B.Credentials=Jt;B.Projects=At;B.Organization=_t;B.AuditLogs=It;B.APIKeys=Ft;B.CredentialProviders=Kt;var mt={paaItem:".related-question-pair",captchaMarker:'#captcha-form, #recaptcha, form[action*="/sorry/"], .g-recaptcha, [data-sitekey]'},es={container:'div[jscontroller="HWk0Gf"]',sectionHeading:'.mgAbYb[role="heading"]',item:"a.rIRoqf"},En={udm:"39",item:"a.rIRoqf",durationPattern:/^\d+:\d+$/,platforms:["YouTube","TikTok","Instagram","Facebook","X"]},ns={section:".ULSxyf",item:"a.KYg7td.INpicf",title:".hyYc0c",source:".K4ETW"},as={sectionTag:"g-section-with-header",sectionHeadingText:"What people are saying",card:'.dRzkFf[role="listitem"]',cardLink:'a.WlydOe[jsname="YKoRaf"]',titleH1:"h1.WQWxe",titleDiv:".eAaXgc",popularCommentLabel:".qgdis",source:".sTl1Td",platformBadge:".appd0, .KrMNbf",ytChannel:".sjVJQd",ytDate:".PLq9Je",authorNote:".nDgy9d"},is={root:"[data-lhcontainer][data-streaming-container][eid]",legacyRoot:'[data-hveid="CBMQAA"]',wrapper:".Fgyi2e",controller:'[jscontroller="AkrxPe"]',contentSubtree:'[data-subtree="mfc"]',header:".heWuVc",heading:".Fzsovc.cwYVJe.RJPOee",showMoreButton:'[aria-label="Show more AI Overview"]',sourcesPanel:".OZ9ddf.WAUd4",disclaimer:".DuQANe.MSJHRb"},ss={root:'[data-hveid="CAUQAA"]',wrapper:".Fgyi2e",citations:'.Fgyi2e [data-hveid] a[jsname="pxBnId"]'},os={result:".wHYlTd.tF2Cxc",title:"h3.LC20lb",siteName:".VuuXrf",cite:"cite.tjvcx",snippet:".VwiC3b",redditCite:"cite.qLRx3b",ratingWrap:".Y0A0hc",ratingValue:".yi40Hd",reviewCount:".RDApEe"},rs={headingText:"Businesses",card:".w7Dbne",name:".OSrXXb",ratingValue:".yi40Hd",reviewCount:".RDApEe"},ds="2026-05-07";var ls="Google returned a CAPTCHA. Run with --headless=false to re-warm the browser profile, then retry.";var dd=["request_aborted","captcha_exhausted","captcha_or_blocked","location_mismatch","proxy_tunnel_failed","proxy_unavailable","harvest_timeout","mcp_request_timeout","mcp_http_error","extraction_failed","concurrency_limit_exceeded","unauthorized","forbidden","invalid_request","rate_limited","upstream_rate_limited","insufficient_balance","service_unavailable","response_lost","vendor_unavailable","page_not_found","page_forbidden","page_rate_limited","page_server_error","page_http_error","bot_check_unresolved","page_too_large","page_unreachable","browser_session_interrupted","site_export_not_found","site_export_format_unavailable","site_export_read_failed","site_export_image_not_found","image_url_invalid","image_url_not_https","image_host_unresolvable","image_host_blocked","image_redirect_invalid","image_source_unavailable","image_too_large","image_redirect_limit","image_base64_invalid","image_source_missing","image_source_ambiguous","image_source_type_invalid","image_artifact_not_found","image_page_too_large","page_image_not_found","page_image_candidates_unusable","image_format_unsupported","image_storage_unconfigured","featured_image_unhostable"],ld=["request_aborted","captcha","location_mismatch","connection","timeout","extraction","concurrency_limit","unauthorized","forbidden","invalid_request","rate_limit","billing","service_unavailable"];var ng=new Set(dd),ag=new Set(ld);function Ss(e){return e.replace((new RegExp("https?:\\/\\/[^\\s]*(?:\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061|on\u006b\u0065\u0072\u006e\u0065\u006c|\u006b\u0065\u0072\u006e\u0065\u006c\\.sh)[^\\s]*", "gi")),"the service").replace(/bright\s*data/gi,"the service").replace((new RegExp("\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061", "gi")),"the service").replace((new RegExp("\u006b\u0065\u0072\u006e\u0065\u006c\\.sh\\s+sessions?", "gi")),"sessions").replace((new RegExp("\u006b\u0065\u0072\u006e\u0065\u006c\\.sh\\s+session", "gi")),"this session").replace((new RegExp("\u006b\u0065\u0072\u006e\u0065\u006c\\.sh", "gi")),"the service").replace((new RegExp("\u006b\u0065\u0072\u006e\u0065\u006c\\s+sessions?", "gi")),"sessions").replace((new RegExp("\u006b\u0065\u0072\u006e\u0065\u006c\\s+session", "gi")),"this session").replace(/\b(?:sub|cus|sess|proxy)_[A-Za-z0-9_-]+\b/g,"[redacted]").replace((new RegExp("\\b(?:\u004b\u0045\u0052\u004e\u0045\u004c|\u0042\u0052\u0049\u0047\u0048\u0054\u0044\u0041\u0054\u0041|\u0042\u0052\u0049\u0047\u0048\u0054_\u0044\u0041\u0054\u0041)_[A-Z0-9_]*API_KEY\\b", "g")),"BROWSER_SERVICE_API_KEY").replace((new RegExp("\\b\u006b\u0065\u0072\u006e\u0065\u006c\\b", "gi")),"the service").replace(/ +/g," ").trim()}var it=class extends Error{constructor(n){super(`CAPTCHA detected. ${n}`);this.instructions=n}instructions;name="CaptchaError"},Ae=class extends Error{constructor(n,a){super(n);this.cause=a}cause;name="ExtractionError"};var pt=class extends Error{name="RequestAbortedError";constructor(t="Request aborted before harvest completed"){super(t)}},Qt=class extends Error{name="PaaInteractionInterruptedError"},$e=class extends Error{name="LocationMismatchError";constructor(t="Google returned results for a different location than requested"){super(t)}};async function Pn(e,t,n,a){let i,s=!1,o,d=()=>{},l=()=>a?.reason instanceof DOMException&&a.reason.name==="TimeoutError"?a.reason:new pt,U=()=>d(l()),S=new Promise((u,c)=>{d=c}),r=async u=>{let c;try{await Promise.race([u.close().catch(()=>{}),new Promise(h=>{c=setTimeout(h,2e3)})])}finally{c&&clearTimeout(c)}};if(a?.aborted)throw l();a?.addEventListener("abort",U,{once:!0}),o=setTimeout(()=>d(new DOMException("Optional pagination timed out","TimeoutError")),3e4);try{return await Promise.race([(async()=>{let u=await e.newPage();if(s)throw await r(u),new pt;if(i=u,await t(u),s)throw new pt;return n(u)})(),S])}finally{s=!0,o&&clearTimeout(o),a?.removeEventListener("abort",U),i&&await r(i)}}var Ia=require("crypto");var Us=require("@libsql/client/http"),Qe=require("crypto"),Z=require("zod");var bt="strftime('%Y-%m-%dT%H:%M:%fZ','now')";var Sd=[`CREATE TABLE IF NOT EXISTS oauth_store_metadata (
|
|
11
11
|
id INTEGER PRIMARY KEY CHECK (id = 1),
|
|
12
12
|
store_id TEXT NOT NULL UNIQUE,
|
|
13
13
|
schema_version INTEGER NOT NULL CHECK (schema_version > 0),
|
|
@@ -118,18 +118,18 @@ ${r}`)}return o},g=gr(qi);var Ft=class extends b{create(t,n){return this._client
|
|
|
118
118
|
updated_at TEXT NOT NULL DEFAULT (${bt}),
|
|
119
119
|
PRIMARY KEY (scope, key_digest, window_start, window_seconds)
|
|
120
120
|
) STRICT`,`CREATE INDEX IF NOT EXISTS oauth_rate_limit_buckets_expiry_idx
|
|
121
|
-
ON oauth_rate_limit_buckets(expires_at, scope, key_digest, window_start, window_seconds)`],dg=[...Sd,...Ud,...ud];var hd=process.env.TURSO_DATABASE_URL??"file:./paa-api.db",gd=process.env.TURSO_AUTH_TOKEN,ba=null;function In(){return ba||(ba=(0,Us.createClient)({url:hd,authToken:gd})),ba}var wg=32*1024;var mg=Z.z.object({id:Z.z.string(),user_id:Z.z.number(),status:Z.z.string().default("pending"),client_domain:Z.z.string(),session_path:Z.z.string(),request:Z.z.string(),result:Z.z.string().nullable(),error:Z.z.string().nullable(),created_at:Z.z.string(),updated_at:Z.z.string()}),yg=Z.z.object({id:Z.z.number(),job_id:Z.z.string(),phase:Z.z.string(),completed_at:Z.z.string(),output_summary:Z.z.string()});var us=require("async_hooks"),cs="MCP_SCRAPER_ALLOW_HEADLESS_HARVEST_TEST",hs=new us.AsyncLocalStorage;function gs(e,t){return hs.run(e,t)}function Zt(){return hs.getStore()}var pd=166667e-10,wd=.0001333336,ps=new Set(["serp","fb_search","fb_ad","instagram"]),md=.00111,yd=4,Cd=4e-4;function Le(e,t){let n=process.env[e]?.trim();if(!n)return t;let a=Number(n);return Number.isFinite(a)&&a>=0?a:t}var Td=Le("NANGO_USD_PER_CONNECTION_MONTH",1),kd=Le("NANGO_USD_PER_FUNCTION_RUN",1e-4),fd=Le("NANGO_USD_PER_PROXY_REQUEST",1e-4),Md=Le("NANGO_USD_PER_COMPUTE_SEC",2e-4),Nd=Le("
|
|
121
|
+
ON oauth_rate_limit_buckets(expires_at, scope, key_digest, window_start, window_seconds)`],dg=[...Sd,...Ud,...ud];var hd=process.env.TURSO_DATABASE_URL??"file:./paa-api.db",gd=process.env.TURSO_AUTH_TOKEN,ba=null;function In(){return ba||(ba=(0,Us.createClient)({url:hd,authToken:gd})),ba}var wg=32*1024;var mg=Z.z.object({id:Z.z.string(),user_id:Z.z.number(),status:Z.z.string().default("pending"),client_domain:Z.z.string(),session_path:Z.z.string(),request:Z.z.string(),result:Z.z.string().nullable(),error:Z.z.string().nullable(),created_at:Z.z.string(),updated_at:Z.z.string()}),yg=Z.z.object({id:Z.z.number(),job_id:Z.z.string(),phase:Z.z.string(),completed_at:Z.z.string(),output_summary:Z.z.string()});var us=require("async_hooks"),cs="MCP_SCRAPER_ALLOW_HEADLESS_HARVEST_TEST",hs=new us.AsyncLocalStorage;function gs(e,t){return hs.run(e,t)}function Zt(){return hs.getStore()}var pd=166667e-10,wd=.0001333336,ps=new Set(["serp","fb_search","fb_ad","instagram"]),md=.00111,yd=4,Cd=4e-4;function Le(e,t){let n=process.env[e]?.trim();if(!n)return t;let a=Number(n);return Number.isFinite(a)&&a>=0?a:t}var Td=Le("NANGO_USD_PER_CONNECTION_MONTH",1),kd=Le("NANGO_USD_PER_FUNCTION_RUN",1e-4),fd=Le("NANGO_USD_PER_PROXY_REQUEST",1e-4),Md=Le("NANGO_USD_PER_COMPUTE_SEC",2e-4),Nd=Le("\u0042\u0052\u0049\u0047\u0048\u0054\u0044\u0041\u0054\u0041_BROWSER_USD_PER_GB",8),fg=Le("\u0042\u0052\u0049\u0047\u0048\u0054\u0044\u0041\u0054\u0041_SERP_USD_PER_REQUEST",.002836168);function Ea(e,t){return Math.max(0,e)/1e3*(t?wd:pd)}function ws(e,t){return e==="fal_wizper"?Math.max(0,t)/yd*md:e==="deepinfra_qwen"?Math.max(0,t)/1e3*Cd:e==="openrouter"||e==="mcp_memory_video"||e==="mcp_memory_ai"?Math.max(0,t):e==="nango_connection"?Math.max(0,t)*Td:e==="nango_function_run"?Math.max(0,t)*kd:e==="nango_proxy_request"?Math.max(0,t)*fd:e==="nango_compute"?Math.max(0,t)*Md:e==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061_browser_api"?Math.max(0,t)/1e9*Nd:0}var Pa=!1,Ze=null;async function ms(){if(!Pa)return Ze||(Ze=vd().finally(()=>{Ze=null}),Ze)}async function vd(){let e=In(),t=await e.execute(`
|
|
122
122
|
SELECT
|
|
123
|
-
(SELECT COUNT(*) FROM sqlite_master WHERE type = 'table' AND name IN ('
|
|
124
|
-
AND (SELECT COUNT(*) FROM pragma_table_info('
|
|
123
|
+
(SELECT COUNT(*) FROM sqlite_master WHERE type = 'table' AND name IN ('\u006b\u0065\u0072\u006e\u0065\u006c_session_log', 'vendor_usage_log', 'cost_probe_runs')) = 3
|
|
124
|
+
AND (SELECT COUNT(*) FROM pragma_table_info('\u006b\u0065\u0072\u006e\u0065\u006c_session_log') WHERE name IN ('proxy_source', 'proxy_type', 'method')) = 3
|
|
125
125
|
AND (SELECT COUNT(*) FROM pragma_table_info('vendor_usage_log') WHERE name IN ('method', 'source_key', 'provider_duration_ms', 'provider_captcha', 'provider_status')) = 5
|
|
126
126
|
AND (SELECT COUNT(*) FROM sqlite_master WHERE type = 'index' AND name = 'vendor_usage_log_vendor_source_key') = 1
|
|
127
127
|
AND (SELECT COUNT(*) FROM pragma_table_info('cost_probe_runs') WHERE name IN ('units', 'unit_type', 'mode')) = 3
|
|
128
128
|
AS ready
|
|
129
129
|
`);if(Number(t.rows[0]?.ready??0)===1){Pa=!0;return}await e.execute(`
|
|
130
|
-
CREATE TABLE IF NOT EXISTS
|
|
130
|
+
CREATE TABLE IF NOT EXISTS \u006b\u0065\u0072\u006e\u0065\u006c_session_log (
|
|
131
131
|
id TEXT PRIMARY KEY,
|
|
132
|
-
|
|
132
|
+
\u006b\u0065\u0072\u006e\u0065\u006c_session_id TEXT,
|
|
133
133
|
op TEXT,
|
|
134
134
|
source TEXT NOT NULL,
|
|
135
135
|
probe_run_id TEXT,
|
|
@@ -146,7 +146,7 @@ ${r}`)}return o},g=gr(qi);var Ft=class extends b{create(t,n){return this._client
|
|
|
146
146
|
error TEXT,
|
|
147
147
|
created_at TEXT NOT NULL DEFAULT (datetime('now'))
|
|
148
148
|
)
|
|
149
|
-
`),await e.execute("CREATE INDEX IF NOT EXISTS
|
|
149
|
+
`),await e.execute("CREATE INDEX IF NOT EXISTS \u006b\u0065\u0072\u006e\u0065\u006c_session_log_op ON \u006b\u0065\u0072\u006e\u0065\u006c_session_log(op)"),await e.execute("CREATE INDEX IF NOT EXISTS \u006b\u0065\u0072\u006e\u0065\u006c_session_log_probe ON \u006b\u0065\u0072\u006e\u0065\u006c_session_log(probe_run_id)"),await e.execute("CREATE INDEX IF NOT EXISTS \u006b\u0065\u0072\u006e\u0065\u006c_session_log_created ON \u006b\u0065\u0072\u006e\u0065\u006c_session_log(created_at)");try{await e.execute("ALTER TABLE \u006b\u0065\u0072\u006e\u0065\u006c_session_log ADD COLUMN proxy_source TEXT")}catch{}try{await e.execute("ALTER TABLE \u006b\u0065\u0072\u006e\u0065\u006c_session_log ADD COLUMN proxy_type TEXT")}catch{}try{await e.execute("ALTER TABLE \u006b\u0065\u0072\u006e\u0065\u006c_session_log ADD COLUMN method TEXT")}catch{}await e.execute(`
|
|
150
150
|
CREATE TABLE IF NOT EXISTS vendor_usage_log (
|
|
151
151
|
id TEXT PRIMARY KEY,
|
|
152
152
|
op TEXT,
|
|
@@ -174,23 +174,23 @@ ${r}`)}return o},g=gr(qi);var Ft=class extends b{create(t,n){return this._client
|
|
|
174
174
|
success INTEGER NOT NULL DEFAULT 0,
|
|
175
175
|
error TEXT,
|
|
176
176
|
http_only INTEGER NOT NULL DEFAULT 0,
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
177
|
+
\u006b\u0065\u0072\u006e\u0065\u006c_used INTEGER NOT NULL DEFAULT 0,
|
|
178
|
+
\u006b\u0065\u0072\u006e\u0065\u006c_sessions INTEGER NOT NULL DEFAULT 0,
|
|
179
|
+
\u006b\u0065\u0072\u006e\u0065\u006c_seconds_total REAL NOT NULL DEFAULT 0,
|
|
180
|
+
\u006b\u0065\u0072\u006e\u0065\u006c_tier_observed TEXT,
|
|
181
|
+
est_\u006b\u0065\u0072\u006e\u0065\u006c_cost_usd_headless REAL NOT NULL DEFAULT 0,
|
|
182
|
+
est_\u006b\u0065\u0072\u006e\u0065\u006c_cost_usd_headful REAL NOT NULL DEFAULT 0,
|
|
183
183
|
vendor_cost_usd REAL NOT NULL DEFAULT 0,
|
|
184
184
|
charged_credits REAL NOT NULL DEFAULT 0,
|
|
185
185
|
margin_usd_headless_starter REAL NOT NULL DEFAULT 0,
|
|
186
186
|
margin_usd_headful_starter REAL NOT NULL DEFAULT 0,
|
|
187
187
|
notes TEXT
|
|
188
188
|
)
|
|
189
|
-
`),await e.execute("CREATE INDEX IF NOT EXISTS cost_probe_runs_tool ON cost_probe_runs(tool)");try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN units REAL")}catch{}try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN unit_type TEXT")}catch{}try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN mode TEXT")}catch{}Pa=!0}async function ys(e){try{await ms();let t=Zt(),n=Math.max(0,e.closedAtMs-e.openedAtMs);await In().execute({sql:`INSERT INTO
|
|
190
|
-
(id,
|
|
191
|
-
VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,args:[(0,Ia.randomUUID)(),e
|
|
189
|
+
`),await e.execute("CREATE INDEX IF NOT EXISTS cost_probe_runs_tool ON cost_probe_runs(tool)");try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN units REAL")}catch{}try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN unit_type TEXT")}catch{}try{await e.execute("ALTER TABLE cost_probe_runs ADD COLUMN mode TEXT")}catch{}Pa=!0}async function ys(e){try{await ms();let t=Zt(),n=Math.max(0,e.closedAtMs-e.openedAtMs);await In().execute({sql:`INSERT INTO \u006b\u0065\u0072\u006e\u0065\u006c_session_log
|
|
190
|
+
(id, \u006b\u0065\u0072\u006e\u0065\u006c_session_id, op, source, probe_run_id, user_id, stealth, headless_sent, proxy_used, proxy_source, proxy_type, fallback, opened_at, closed_at, duration_ms, est_cost_usd_headless, est_cost_usd_headful, error, method)
|
|
191
|
+
VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,args:[(0,Ia.randomUUID)(),e.\u006b\u0065\u0072\u006e\u0065\u006cSessionId??null,t?.op??null,e.source,t?.probeRunId??null,t?.userId??null,An(e.stealth),An(e.headlessSent),An(e.proxyUsed),e.proxySource??null,e.proxyType??null,e.fallback?1:0,new Date(e.openedAtMs).toISOString(),new Date(e.closedAtMs).toISOString(),n,Ea(n,!1),Ea(n,!0),e.error??null,t?.subOp??null]})}catch(t){console.warn("[cost-telemetry] record\u004b\u0065\u0072\u006e\u0065\u006cSession failed:",t instanceof Error?t.message:String(t))}}async function Aa(e){try{await ms();let t=Zt();return(await In().execute({sql:`INSERT OR IGNORE INTO vendor_usage_log
|
|
192
192
|
(id, op, probe_run_id, user_id, vendor, model, units, unit_type, est_cost_usd, error, method, source_key, provider_duration_ms, provider_captcha, provider_status)
|
|
193
|
-
VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,args:[(0,Ia.randomUUID)(),e.op??t?.op??null,e.probeRunId??t?.probeRunId??null,e.userId??t?.userId??null,e.vendor,e.model??null,e.units,e.unitType,ws(e.vendor,e.units),e.error??null,e.method??t?.subOp??null,e.sourceKey??null,e.providerDurationMs??null,An(e.providerCaptcha),e.providerStatus??null]})).rowsAffected===1}catch(t){return console.warn("[cost-telemetry] recordVendorUsage failed:",t instanceof Error?t.message:String(t)),!1}}function An(e){return e==null?null:e?1:0}var _d=/\b(?:HeadlessChrome|Chrome|Chromium|Firefox)\/\d+|\bVersion\/\d+.*\bSafari\//;async function Ln(e){try{let t=await e.evaluate(()=>navigator.userAgent);return typeof t=="string"&&_d.test(t)?t:null}catch{return null}}async function xn(e){let t=null;try{let n=e.contexts().flatMap(a=>a.pages())[0];return n||(t=await e.newContext(),n=t.pages()[0]??await t.newPage()),await Ln(n)}catch{return null}finally{t&&await t.close().catch(()=>{})}}Rn.chromium.use((0,Ts.default)());var bd=180,Ed=3e3,Pd=5e3,Id='#search, #rso, a[href] h3, [data-snhf], [role="main"]';function La(e,t){return e?Math.max(1,Math.min(t,e-Date.now())):t}function Ad(e,t){let n=process.env[e];if(!n)return t;let a=Number(n);return Number.isInteger(a)&&a>0?a:t}function xa(e){return e?e.slice(-6):null}function Cs(e,t){let n=(t??process.env.SERP_REDIRECT_BASE)?.trim().replace(/\/+$/,"");return n?`${n}/g/${Buffer.from(e,"utf8").toString("base64url")}`:e}function Ld(e){return e?/united states|u\.?s\.?a?\.?|^us$/i.test(e.trim()):!1}function Oe(e){return e instanceof Error?e.message:String(e)}function xd(e){return/\b409\b|conflict|already exists/i.test(Oe(e))}function Od(e){return/\b404\b|not[ _-]?found|already (?:gone|deleted|closed)|does not exist/i.test(Oe(e))}async function Rd(e,t){try{await e.profiles.create({name:t})}catch(n){if(!xd(n))throw n}}function On(e,t){return{viewport:e.viewport,locale:e.locale,...t?{userAgent:t}:{},...e.deviceScaleFactor?{deviceScaleFactor:e.deviceScaleFactor}:{},...e.isMobile!==void 0?{isMobile:e.isMobile}:{},...e.hasTouch!==void 0?{hasTouch:e.hasTouch}:{}}}async function xe(e,t,n){let a;try{return await Promise.race([e,new Promise((i,s)=>{a=setTimeout(()=>s(new Error(`${n} timed out after ${t}ms`)),t)})])}finally{a&&clearTimeout(a)}}function Wd(e){let t=e.trim();if(!t)throw new Error("channelHandle is required");if(/^https?:\/\//i.test(t)||/^(www\.|m\.)?youtube\.com\//i.test(t)){let o=new URL(/^https?:\/\//i.test(t)?t:`https://${t}`);if(o.hostname.replace(/^www\./,"").replace(/^m\./,"").toLowerCase()!=="youtube.com")throw new Error("channel URL must be on youtube.com");let l=o.pathname.split("/").filter(Boolean),U=l[0]??"",S=l[1]??"";if(U.startsWith("@"))return`https://www.youtube.com/${U}/videos`;if(U==="channel"&&S)return`https://www.youtube.com/channel/${S}/videos`;if((U==="c"||U==="user")&&S)return`https://www.youtube.com/${U}/${S}/videos`;throw new Error("channel URL must be a YouTube handle, /channel/UC..., /c/..., or /user/... URL")}let i=t.replace(/^\/+/,"").replace(/\/+$/,"").replace(/\/videos$/i,"");if(/^UC[\w-]{20,}$/.test(i))return`https://www.youtube.com/channel/${i}/videos`;let s=i.startsWith("@")?i:`@${i}`;if(!/^@[\w.-]+$/.test(s))throw new Error("channelHandle must be an @handle, UC channel ID, or YouTube channel URL");return`https://www.youtube.com/${s}/videos`}var Wn=class{browser=null;context=null;page=null;kernelClient=null;kernelSessionId=null;kernelOpenedAtMs=null;kernelStealth=null;kernelProxyUsed=null;kernelProxySource=null;kernelProxyType=null;kernelHeadlessSent=null;lastKernelBillingMode=null;lastKernelOpenedAtMs=null;lastKernelClosedAtMs=null;debugEnabled=!1;debugSnapshot={kernel:null,context:null,networkLocation:null,serpNavigation:null};async launch(t){this.debugEnabled=t.debug===!0;let n=t.proxyMode??(t.kernelProxyId?"configured":"none"),a=t.isMobile?"mobile":"desktop";if(this.debugSnapshot={kernel:null,context:{viewport:t.viewport,locale:t.locale,device:a,userAgent:null,deviceScaleFactor:t.deviceScaleFactor??null,isMobile:t.isMobile===!0,hasTouch:t.hasTouch===!0},networkLocation:null,serpNavigation:null},t.kernelApiKey){this.kernelClient=new B({apiKey:t.kernelApiKey});let s=Number.isInteger(t.kernelTimeoutSeconds)&&Number(t.kernelTimeoutSeconds)>0?Number(t.kernelTimeoutSeconds):Ad("KERNEL_BROWSER_TIMEOUT_SECONDS",bd),o=Math.min(s,600);t.kernelProfileName&&t.kernelProfileSaveChanges===!0&&await Rd(this.kernelClient,t.kernelProfileName);let d=Zt(),l;t.headlessMode==="headful"||d?.forceHeadful===!0?l=!1:t.headlessMode==="headless"?l=!0:l=d?.forceHeadless===!0||process.env.KERNEL_HEADLESS_DISABLED!=="true"&&!!d?.op&&ps.has(d.op),this.kernelHeadlessSent=l?!0:null,this.lastKernelBillingMode=l?"headless":"headful",d?.headlessSentOut&&(d.headlessSentOut.value=this.kernelHeadlessSent);let U=await this.kernelClient.browsers.create({stealth:t.kernelStealth===!0,timeout_seconds:o,...l?{headless:!0}:{},...t.kernelProxyId?{proxy_id:t.kernelProxyId}:{},...t.kernelProfileName?{profile:{name:t.kernelProfileName,...typeof t.kernelProfileSaveChanges=="boolean"?{save_changes:t.kernelProfileSaveChanges}:{}}}:{}});this.kernelSessionId=U.session_id,this.kernelOpenedAtMs=Date.now(),this.lastKernelOpenedAtMs=this.kernelOpenedAtMs,this.lastKernelClosedAtMs=null,this.kernelStealth=typeof U.stealth=="boolean"?U.stealth:null,this.kernelProxyUsed=typeof U.proxy_id=="string"?!!U.proxy_id:!!t.kernelProxyId,this.kernelProxySource=t.kernelProxyResolution?.source??null,this.kernelProxyType=t.kernelProxyResolution?.proxyType??null;let S=null,r=null;if(!t.kernelProxyId&&!t.keepDefaultProxy)try{await xe(this.kernelClient.browsers.update(this.kernelSessionId,{disable_default_proxy:!0}),5e3,`Kernel session ${this.kernelSessionId} disable default proxy`),S=!0}catch(c){S=!1,r=Oe(c)}let u={sessionId:this.kernelSessionId,proxyMode:n,requestedProxyIdPresent:!!t.kernelProxyId,requestedProxyIdSuffix:xa(t.kernelProxyId),createdProxyIdPresent:typeof U.proxy_id=="string"?!!U.proxy_id:null,createdProxyIdSuffix:xa(U.proxy_id),retrievedProxyIdPresent:null,retrievedProxyIdSuffix:null,retrievedProxyIdMatchesRequested:null,defaultProxyDisabled:S,defaultProxyDisableError:r,proxyResolution:t.kernelProxyResolution??null,timeoutSeconds:o,stealth:typeof U.stealth=="boolean"?U.stealth:null,profilePresent:null,poolPresent:null,retrieveError:null};if(this.debugSnapshot.kernel=u,console.info(JSON.stringify({event:"kernel_browser_created",kernel_session_id:this.kernelSessionId,timeout_seconds:o,proxy_mode:n,proxy_id_present:!!t.kernelProxyId,profile_name_present:!!t.kernelProfileName,proxy_resolution_source:t.kernelProxyResolution?.source})),this.debugEnabled&&await this.populateKernelRetrieveDebug(u,t.kernelProxyId),this.browser=await ks.chromium.connectOverCDP(U.cdp_ws_url),t.kernelProfileName||t.preserveKernelContext)this.context=this.browser.contexts()[0]??await this.browser.newContext(On(t)),this.page=this.context.pages()[0]??await this.context.newPage(),this.debugSnapshot.context.userAgent=await Ln(this.page);else{let c=await xn(this.browser);this.debugSnapshot.context.userAgent=c,this.context=await this.browser.newContext(On(t,c)),this.page=await this.context.newPage()}if(await this.installEsbuildHelperShims(this.context),t.preserveKernelContext||await this.page.setViewportSize(t.viewport),(this.debugEnabled||t.requireUsEgress)&&(this.debugSnapshot.networkLocation=await this.captureBrowserNetworkLocation()),t.requireUsEgress){let c=this.debugSnapshot.networkLocation?.country??null;if(!Ld(c))throw new it(`Non-US egress (${c??"unknown"}) \u2014 retrying with a fresh session`)}return}let i={headless:t.headless,proxy:t.proxy?{server:t.proxy}:void 0,...t.browserExecutablePath?{executablePath:t.browserExecutablePath}:{},...t.ignoreDefaultArgs?{ignoreDefaultArgs:t.ignoreDefaultArgs}:{}};if(t.profileDir)this.context=await Rn.chromium.launchPersistentContext(t.profileDir,{...i,...On(t)}),await this.installEsbuildHelperShims(this.context),this.page=await this.context.newPage(),this.debugSnapshot.context.userAgent=await Ln(this.page);else{this.browser=await Rn.chromium.launch(i);let s=await xn(this.browser);this.debugSnapshot.context.userAgent=s,this.context=await this.browser.newContext(On(t,s)),await this.installEsbuildHelperShims(this.context),this.page=await this.context.newPage()}this.debugEnabled&&(this.debugSnapshot.networkLocation=await this.captureBrowserNetworkLocation())}async populateKernelRetrieveDebug(t,n){if(!(!this.kernelClient||!this.kernelSessionId))try{let a=await xe(this.kernelClient.browsers.retrieve(this.kernelSessionId),5e3,`Kernel session ${this.kernelSessionId} retrieve`);t.retrievedProxyIdPresent=typeof a.proxy_id=="string"?!!a.proxy_id:!1,t.retrievedProxyIdSuffix=xa(a.proxy_id),t.retrievedProxyIdMatchesRequested=n?a.proxy_id===n:!a.proxy_id,t.timeoutSeconds=typeof a.timeout_seconds=="number"?a.timeout_seconds:t.timeoutSeconds,t.stealth=typeof a.stealth=="boolean"?a.stealth:t.stealth,t.profilePresent=!!a.profile,t.poolPresent=!!a.pool}catch(a){t.retrieveError=Oe(a)}}async captureBrowserNetworkLocation(){let t=(a,i="ipapi.co")=>({source:i,ip:null,city:null,region:null,country:null,org:null,timezone:null,error:a});if(!this.context)return t("browser context is not available");let n=null;try{n=await this.context.newPage();let a=await this.loadJsonInDebugPage(n,"https://ipwho.is/");if(a){let d=typeof a.connection=="object"&&a.connection!==null?a.connection:{};return{source:"ipwho.is",ip:typeof a.ip=="string"?a.ip:null,city:typeof a.city=="string"?a.city:null,region:typeof a.region=="string"?a.region:null,country:typeof a.country=="string"?a.country:null,org:typeof d.org=="string"?d.org:null,timezone:typeof a.timezone=="object"&&a.timezone!==null&&typeof a.timezone.id=="string"?a.timezone.id:null,error:null}}let i=await this.loadJsonInDebugPage(n,"https://api64.ipify.org?format=json");if(i)return{source:"api64.ipify.org",ip:typeof i.ip=="string"?i.ip:null,city:null,region:null,country:null,org:null,timezone:null,error:null};await xe(n.goto("https://ipapi.co/json/",{waitUntil:"domcontentloaded",timeout:7e3}),8e3,"browser network location navigation");let s=await n.locator("body").innerText({timeout:2e3}),o=JSON.parse(s);return{source:"ipapi.co",ip:typeof o.ip=="string"?o.ip:null,city:typeof o.city=="string"?o.city:null,region:typeof o.region=="string"?o.region:null,country:typeof o.country_name=="string"?o.country_name:typeof o.country=="string"?o.country:null,org:typeof o.org=="string"?o.org:null,timezone:typeof o.timezone=="string"?o.timezone:null,error:null}}catch(a){return t(Oe(a))}finally{await n?.close().catch(()=>{})}}async loadJsonInDebugPage(t,n){try{await xe(t.goto(n,{waitUntil:"domcontentloaded",timeout:7e3}),8e3,`browser network location navigation ${n}`);let a=await t.locator("body").innerText({timeout:2e3});return JSON.parse(a)}catch{return null}}async installEsbuildHelperShims(t){await t.addInitScript(()=>{let n=globalThis;typeof n.__name!="function"&&(n.__name=a=>a),typeof n.__publicField!="function"&&(n.__publicField=(a,i,s)=>(a[i]=s,s))})}async withTemporaryPage(t,n){if(!this.context)throw new Error("Browser context is not available");return Pn(this.context,async()=>{},t,n)}async navigateToSERP(t,n,a,i,s){let o=new URLSearchParams({q:t,gl:a,hl:i,pws:"0"});s?.tbs&&o.set("tbs",s.tbs),n&&o.set("uule",n);let d="https://www.google.com/search?"+o.toString(),l=Cs(d),U=s?.debug?{requestedUrl:d,finalUrl:null,title:null,bodySnippet:null,hasPaa:null,captchaDetected:null,googleSorryUrl:null,redirected:null}:null;U&&(this.debugSnapshot.serpNavigation=U);try{await this.page.goto(l,{waitUntil:"domcontentloaded",timeout:La(s?.deadlineMs,s?.purpose==="serp"?8e3:45e3)})}catch(r){await this.updateSerpNavigationDebug(U,d,{hasPaa:null,captchaDetected:null});let u=await this.captureDiagnostics(d);throw new Ae(`page.goto failed: ${r.message} | ${u}`)}if(await this.isSerpChallengeVisible())throw await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!0}),new it(this.captchaMessage());if(s?.purpose==="serp"){await this.page.waitForSelector(Id,{timeout:La(s.deadlineMs,1500)}).catch(()=>null);let r=await this.page.locator(mt.paaItem).count().catch(()=>0)>0;return await this.updateSerpNavigationDebug(U,d,{hasPaa:r,captchaDetected:!1}),{hasPaa:r}}if(await this.page.waitForSelector(mt.paaItem,{timeout:La(s?.deadlineMs,4e3)}).catch(()=>null))return await this.updateSerpNavigationDebug(U,d,{hasPaa:!0,captchaDetected:!1}),{hasPaa:!0};if(await this.isSerpChallengeVisible())throw await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!0}),new it(this.captchaMessage());for(let r=1;r<=6;r++)if(await this.page.evaluate(c=>{window.scrollTo(0,document.body.scrollHeight*c)},r/6),await this.page.waitForTimeout(600),await this.page.locator(mt.paaItem).count()>0)return await this.updateSerpNavigationDebug(U,d,{hasPaa:!0,captchaDetected:!1}),{hasPaa:!0};return await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!1}),{hasPaa:!1}}async isSerpChallengeVisible(){if(!this.page)return!1;if(await this.page.locator(mt.captchaMarker).count().catch(()=>0)>0)return!0;let n=this.page.url();if(/google\.[^/]+\/sorry\//i.test(n))return!0;let a=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,1e3)).catch(()=>"");return/recaptcha|unusual traffic|are you a robot|about this page|detected unusual traffic/i.test(a)}async updateSerpNavigationDebug(t,n,a){if(!(!t||!this.page))try{let i=this.page.url(),s=await this.page.title().catch(()=>""),o=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,500)).catch(()=>""),d=/recaptcha|unusual traffic|are you a robot/i.test(o);t.finalUrl=i,t.title=s,t.bodySnippet=o,t.hasPaa=a.hasPaa,t.captchaDetected=a.captchaDetected??d,t.googleSorryUrl=/google\.[^/]+\/sorry\//i.test(i),t.redirected=i!==n}catch(i){t.bodySnippet=`debug capture failed: ${Oe(i)}`}}async captureDiagnostics(t){try{let n=this.page.url(),a=await this.page.title().catch(()=>""),i=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,400)).catch(()=>""),s=/consent\.google\./.test(n)||/before you continue/i.test(i),o=/recaptcha|unusual traffic|are you a robot/i.test(i),d=[s?"CONSENT_WALL":"",o?"BOT_CHALLENGE":"",n!==t?"REDIRECTED":""].filter(Boolean).join(",");return`intended=${t} | final=${n} | title="${a}" | flags=[${d}] | body="${i}"`}catch(n){return`diagnostics-failed: ${n.message}`}}captchaMessage(){return this.kernelClient?"Google returned a CAPTCHA on this session \u2014 retrying with a fresh session.":ls}async navigateTo(t){let n=process.env.ADS_ARRIVAL_REDIRECT_BASE?.trim(),a=n?Cs(t,n):t;try{if(await this.page.goto(a,{waitUntil:"domcontentloaded",timeout:45e3}),/google\.[^/]+\/search\?/i.test(t)&&await this.isSerpChallengeVisible())throw new it(this.captchaMessage())}catch(i){if(i instanceof it)throw i;let s=await this.captureDiagnostics(t);throw new Ae(`page.goto failed: ${i.message} | ${s}`)}}async navigateToChannel(t){let n=Wd(t);try{await this.page.goto(n,{waitUntil:"networkidle",timeout:3e4})}catch(a){let i=await this.captureDiagnostics(n);throw new Ae(`navigateToChannel failed: ${a.message} | ${i}`)}}async evaluate(t,n){return this.page.evaluate(t,n)}getPage(){return this.page}getKernelSessionId(){return this.kernelSessionId}getKernelMeteringEvidence(){return{sessionId:this.kernelSessionId??this.debugSnapshot.kernel?.sessionId??null,billingMode:this.lastKernelBillingMode,openedAtMs:this.lastKernelOpenedAtMs,closedAtMs:this.lastKernelClosedAtMs}}getProviderSessionMetadata(){return{provider:this.kernelSessionId?"kernel":"local",providerSessionId:this.kernelSessionId,disconnectObservation:null,billingMode:this.kernelSessionId?this.kernelHeadlessSent?"headless":"headful":null}}getDebugSnapshot(){return this.debugSnapshot}async close(){if(this.browser){let t=this.browser,n=this.kernelSessionId,a=this.kernelClient,i=this.kernelOpenedAtMs,s=this.kernelStealth,o=this.kernelProxyUsed,d=this.kernelProxySource,l=this.kernelProxyType,U=this.kernelHeadlessSent,S=this.getProviderSessionMetadata();if(this.browser=null,this.context=null,this.page=null,this.kernelSessionId=null,this.kernelClient=null,this.kernelOpenedAtMs=null,this.kernelHeadlessSent=null,this.kernelProxySource=null,this.kernelProxyType=null,a&&n){console.info(JSON.stringify({event:"kernel_browser_delete_started",kernel_session_id:n}));let r=xe(a.browsers.deleteByID(n),Pd,`Kernel session ${n} delete`),u=xe(t.close(),Ed,`Kernel browser ${n} close`),[c,h]=await Promise.allSettled([r,u]);this.lastKernelClosedAtMs=Date.now(),i!=null&&ys({kernelSessionId:n,source:"browser_driver",stealth:s,headlessSent:U,proxyUsed:o,proxySource:d,proxyType:l,openedAtMs:i,closedAtMs:this.lastKernelClosedAtMs});let w=c.status==="rejected"&&Od(c.reason),k={kernelSessionId:n,kernelDeleteStarted:!0,kernelDeleteSucceeded:c.status==="fulfilled"||w,kernelDeleteError:c.status==="rejected"&&!w?c.reason instanceof Error?c.reason.message:String(c.reason):null,browserCloseSucceeded:h.status==="fulfilled",browserCloseError:h.status==="rejected"?h.reason instanceof Error?h.reason.message:String(h.reason):null,provider:S.provider,providerSessionId:S.providerSessionId,providerDisconnectObserved:!1,providerDisconnectMessage:null};return c.status==="rejected"&&!w?(console.warn(JSON.stringify({event:"kernel_browser_delete_failed",kernel_session_id:n,message:k.kernelDeleteError})),console.warn(`Kernel session cleanup failed for ${n}:`,c.reason)):console.info(JSON.stringify({event:"kernel_browser_delete_succeeded",kernel_session_id:n})),h.status==="rejected"&&(console.warn(JSON.stringify({event:"kernel_browser_close_failed",kernel_session_id:n,message:k.browserCloseError})),console.warn(`Kernel browser close failed for ${n}:`,h.reason)),k}return await t.close(),{kernelSessionId:null,kernelDeleteStarted:!1,kernelDeleteSucceeded:null,kernelDeleteError:null,browserCloseSucceeded:!0,browserCloseError:null,provider:S.provider,providerSessionId:S.providerSessionId,providerDisconnectObserved:!1,providerDisconnectMessage:null}}else if(this.context){let t=this.context;return this.context=null,this.page=null,await t.close(),{kernelSessionId:null,kernelDeleteStarted:!1,kernelDeleteSucceeded:null,kernelDeleteError:null,browserCloseSucceeded:!0,browserCloseError:null,provider:"local",providerSessionId:null,providerDisconnectObserved:!1,providerDisconnectMessage:null}}return{kernelSessionId:null,kernelDeleteStarted:!1,kernelDeleteSucceeded:null,kernelDeleteError:null,browserCloseSucceeded:null,browserCloseError:null,provider:"local",providerSessionId:null,providerDisconnectObserved:!1,providerDisconnectMessage:null}}};var Es=require("playwright");function Hd(e,t){if(typeof e!="string")return null;let n=e.replace(/[\u0000-\u001f\u007f]+/g," ").replace(/\s+/g," ").trim();return n?n.slice(0,t):null}function fs(e){let t=Hd(e,320);return t?t.replace(/\b(?:wss?|https?):\/\/\S+/gi,"[redacted endpoint]").replace(/\b(?:authorization|proxy-authorization):\s*\S+/gi,"$1: [redacted]").replace(/\bBearer\s+\S+/gi,"Bearer [redacted]").slice(0,320):null}function Ms(e){return fs(e)}function Ns(e){if(typeof e!="string"||e.length===0||e.length>512||e.trim()!==e||/[\s\u0000-\u001f\u007f]/.test(e)||/:\/\//.test(e))throw new Error("Bright Data did not return a valid browser session ID");return e}function Oa(e,t,n=new Date().toISOString()){let a=fs(t);return{source:e,message:a??e.replaceAll("_"," "),observedAt:n}}function Bd(e){return{provider:e.provider,providerDisconnectObserved:e.disconnectObservation!==null,providerDisconnectMessage:e.disconnectObservation?.message??null}}function vs(e){return{...Bd(e),providerSessionId:e.providerSessionId}}function Ra(){return process.env.BRIGHTDATA_BROWSER_WSS?.trim()||null}function _s(){return process.env.SERP_BROWSER_PROVIDER?.trim().toLowerCase()==="kernel"?!1:!!Ra()}var Dd=new Set(["image","media","font","stylesheet","ping"]),Fd=["doubleclick.net","googleadservices.com","googlesyndication.com","google-analytics.com"],Gd='#search, #rso, a[href] h3, [data-snhf], [role="main"]',Vd=3e4,bs=1500;function Hn(e,t){return e?Math.max(1,Math.min(t,e-Date.now())):t}async function Wa(e,t=!1){let n=e.request();try{let a=await n.allHeaders(),i=await fetch(n.url(),{method:n.method(),headers:{accept:a.accept??"*/*","accept-language":a["accept-language"]??"en-US,en;q=0.9","user-agent":a["user-agent"]??"Mozilla/5.0",...t?{cookie:a.cookie??"",referer:a.referer??"https://www.google.com/",...a["x-client-data"]?{"x-client-data":a["x-client-data"]}:{}}:{}},body:n.method()==="GET"||n.method()==="HEAD"?void 0:n.postData()});if(!i.ok)return!1;let s=Buffer.from(await i.arrayBuffer());return await e.fulfill({status:i.status,contentType:i.headers.get("content-type")??"application/octet-stream",headers:{"cache-control":"public, max-age=3600"},body:s}),!0}catch{return!1}}var Bn=class{browser=null;context=null;page=null;cdpSession=null;providerSessionId=null;disconnectObservation=null;closing=!1;observeDisconnect(t,n){this.closing||this.disconnectObservation||(this.disconnectObservation=Oa(t,n))}async launch(t){if(this.page)return;this.closing=!1,this.providerSessionId=null,this.disconnectObservation=null;let n=Ra();if(!n)throw new Error("SERP browser service is not configured");this.browser=await Es.chromium.connectOverCDP(n,{timeout:Hn(t.operationDeadlineMs,Vd)}),this.context=this.browser.contexts()[0]??await this.browser.newContext(),await this.context.addInitScript(()=>{let s=globalThis;typeof s.__name!="function"&&(s.__name=o=>o),typeof s.__publicField!="function"&&(s.__publicField=(o,d,l)=>(o[d]=l,l))}),this.page=this.context.pages()[0]??await this.context.newPage(),this.browser.on("disconnected",()=>this.observeDisconnect("browser_disconnected")),this.context.on("close",()=>this.observeDisconnect("context_closed")),this.page.on("close",()=>this.observeDisconnect("page_closed")),this.page.on("crash",()=>this.observeDisconnect("page_crashed")),this.cdpSession=await this.context.newCDPSession(this.page);let i=await this.cdpSession.send("Browser.getSessionId");this.providerSessionId=Ns(i?.sessionId),await this.setupPage(this.page)}async setupPage(t){await t.route("**/*",async n=>{let a=n.request(),i=a.resourceType(),s;try{s=new URL(a.url())}catch{await n.continue();return}let o=s.hostname.toLowerCase();if(!(s.pathname==="/sgasync"&&await Wa(n,!0))&&!(s.pathname.includes("/shared_dict/")&&await Wa(n))&&!(i==="script"&&(o==="www.google.com"||o==="www.gstatic.com")&&await Wa(n))){if(Dd.has(i)){await n.abort("blockedbyclient");return}if(Fd.some(d=>o===d||o.endsWith(`.${d}`))){await n.abort("blockedbyclient");return}await n.continue()}})}async withTemporaryPage(t,n){if(!this.context||this.closing)throw new Error("Browser context is not available");return Pn(this.context,a=>this.setupPage(a),t,n)}async navigateToSERP(t,n,a,i,s){if(!this.page)throw new Error("Browser page is not available");let o=new URLSearchParams({q:t,gl:a,hl:i,pws:"0"});return s?.tbs&&o.set("tbs",s.tbs),n&&o.set("uule",n),await this.page.goto(`https://www.google.com/search?${o}`,{waitUntil:"domcontentloaded",timeout:Hn(s?.deadlineMs,s?.purpose==="serp"?8e3:45e3)}),s?.purpose==="serp"?(await this.page.waitForSelector(Gd,{timeout:Hn(s.deadlineMs,1500)}).catch(()=>null),{hasPaa:await this.page.locator(mt.paaItem).count().catch(()=>0)>0}):{hasPaa:!!await this.page.waitForSelector(mt.paaItem,{timeout:Hn(s?.deadlineMs,8e3)}).catch(()=>null)}}async navigateTo(t){if(!this.page)throw new Error("Browser page is not available");await this.page.goto(t,{waitUntil:"load",timeout:45e3})}async navigateToChannel(){throw new Error("YouTube navigation is not supported by the SERP browser driver")}async evaluate(t,n){if(!this.page)throw new Error("Browser page is not available");return this.page.evaluate(t,n)}getPage(){if(!this.page)throw new Error("Browser page is not available");return this.page}getKernelSessionId(){return null}getProviderSessionMetadata(){return{provider:"bright_data_browser_api",providerSessionId:this.providerSessionId,disconnectObservation:this.disconnectObservation}}getDebugSnapshot(){return{kernel:null,context:null,networkLocation:null,serpNavigation:null}}async close(){this.closing=!0;let t=null,n;try{let i=this.browser?.close();i&&await Promise.race([i,new Promise((s,o)=>{n=setTimeout(()=>o(new Error(`Browser close acknowledgement exceeded ${bs}ms`)),bs)})])}catch(i){t=Ms(i instanceof Error?i.message:String(i))??"Bright Data browser close failed",this.disconnectObservation??=Oa("browser_close_error",t)}finally{n&&clearTimeout(n)}let a=vs(this.getProviderSessionMetadata());return this.browser=null,this.context=null,this.page=null,this.cdpSession=null,{kernelSessionId:null,kernelDeleteStarted:!1,kernelDeleteSucceeded:null,kernelDeleteError:null,browserCloseSucceeded:t===null,browserCloseError:t,...a}}};function Ps(e){return e.plannedProvider==="brightdata"?new Bn:new Wn}var X={container:".eJH8qe.adDDi",dataInitq:"[data-initq]",item:mt.paaItem,itemDataQ:"data-q",itemDataInitQ:"data-initq",itemQuestionEl:".JlqpRe",answerContainer:".bCOlv, .hgKElc, .wDYxhc, .LGOjhe, .fo7IQd, .fmW3u",aiAnswerBody:".pWvJNd",aiCitation:"a.PMDqCb[href]",aiSourceCard:"a.vIWmYe[href], a.Zbfntb[href]",sourceTitle:"h3",sourceSite:".VuuXrf",sourceCite:"cite",clickTarget:".JlqpRe",expandedClass:"aoRk1c",captchaMarker:mt.captchaMarker};var te={austin:"Austin,Texas,United States","new york":"New York,New York,United States","new york city":"New York,New York,United States",nyc:"New York,New York,United States","los angeles":"Los Angeles,California,United States",la:"Los Angeles,California,United States",chicago:"Chicago,Illinois,United States",houston:"Houston,Texas,United States",phoenix:"Phoenix,Arizona,United States",philadelphia:"Philadelphia,Pennsylvania,United States",philly:"Philadelphia,Pennsylvania,United States","san antonio":"San Antonio,Texas,United States",dallas:"Dallas,Texas,United States",miami:"Miami,Florida,United States",seattle:"Seattle,Washington,United States",denver:"Denver,Colorado,United States",loveland:"Loveland,Colorado,United States","loveland co":"Loveland,Colorado,United States","fort collins":"Fort Collins,Colorado,United States",boulder:"Boulder,Colorado,United States","colorado springs":"Colorado Springs,Colorado,United States",boston:"Boston,Massachusetts,United States",atlanta:"Atlanta,Georgia,United States","san francisco":"San Francisco,California,United States",sf:"San Francisco,California,United States",portland:"Portland,Oregon,United States","las vegas":"Las Vegas,Nevada,United States",minneapolis:"Minneapolis,Minnesota,United States",detroit:"Detroit,Michigan,United States",nashville:"Nashville,Tennessee,United States",charlotte:"Charlotte,North Carolina,United States",orlando:"Orlando,Florida,United States","san diego":"San Diego,California,United States",baltimore:"Baltimore,Maryland,United States",sacramento:"Sacramento,California,United States",columbus:"Columbus,Ohio,United States",indianapolis:"Indianapolis,Indiana,United States","san jose":"San Jose,California,United States","fort worth":"Fort Worth,Texas,United States",jacksonville:"Jacksonville,Florida,United States",memphis:"Memphis,Tennessee,United States",louisville:"Louisville,Kentucky,United States",raleigh:"Raleigh,North Carolina,United States",richmond:"Richmond,Virginia,United States","salt lake city":"Salt Lake City,Utah,United States",toronto:"Toronto,Ontario,Canada",vancouver:"Vancouver,British Columbia,Canada",montreal:"Montreal,Quebec,Canada",calgary:"Calgary,Alberta,Canada",ottawa:"Ottawa,Ontario,Canada",london:"London,England,United Kingdom",manchester:"Manchester,England,United Kingdom",birmingham:"Birmingham,England,United Kingdom",edinburgh:"Edinburgh,Scotland,United Kingdom",glasgow:"Glasgow,Scotland,United Kingdom",leeds:"Leeds,England,United Kingdom",sydney:"Sydney,New South Wales,Australia",melbourne:"Melbourne,Victoria,Australia",brisbane:"Brisbane,Queensland,Australia",perth:"Perth,Western Australia,Australia",adelaide:"Adelaide,South Australia,Australia",dublin:"Dublin,Leinster,Ireland"};var Is=`3, Nanjemoy,Maryland,United States
|
|
193
|
+
VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,args:[(0,Ia.randomUUID)(),e.op??t?.op??null,e.probeRunId??t?.probeRunId??null,e.userId??t?.userId??null,e.vendor,e.model??null,e.units,e.unitType,ws(e.vendor,e.units),e.error??null,e.method??t?.subOp??null,e.sourceKey??null,e.providerDurationMs??null,An(e.providerCaptcha),e.providerStatus??null]})).rowsAffected===1}catch(t){return console.warn("[cost-telemetry] recordVendorUsage failed:",t instanceof Error?t.message:String(t)),!1}}function An(e){return e==null?null:e?1:0}var _d=/\b(?:HeadlessChrome|Chrome|Chromium|Firefox)\/\d+|\bVersion\/\d+.*\bSafari\//;async function Ln(e){try{let t=await e.evaluate(()=>navigator.userAgent);return typeof t=="string"&&_d.test(t)?t:null}catch{return null}}async function xn(e){let t=null;try{let n=e.contexts().flatMap(a=>a.pages())[0];return n||(t=await e.newContext(),n=t.pages()[0]??await t.newPage()),await Ln(n)}catch{return null}finally{t&&await t.close().catch(()=>{})}}Rn.chromium.use((0,Ts.default)());var bd=180,Ed=3e3,Pd=5e3,Id='#search, #rso, a[href] h3, [data-snhf], [role="main"]';function La(e,t){return e?Math.max(1,Math.min(t,e-Date.now())):t}function Ad(e,t){let n=process.env[e];if(!n)return t;let a=Number(n);return Number.isInteger(a)&&a>0?a:t}function xa(e){return e?e.slice(-6):null}function Cs(e,t){let n=(t??process.env.SERP_REDIRECT_BASE)?.trim().replace(/\/+$/,"");return n?`${n}/g/${Buffer.from(e,"utf8").toString("base64url")}`:e}function Ld(e){return e?/united states|u\.?s\.?a?\.?|^us$/i.test(e.trim()):!1}function Oe(e){return e instanceof Error?e.message:String(e)}function xd(e){return/\b409\b|conflict|already exists/i.test(Oe(e))}function Od(e){return/\b404\b|not[ _-]?found|already (?:gone|deleted|closed)|does not exist/i.test(Oe(e))}async function Rd(e,t){try{await e.profiles.create({name:t})}catch(n){if(!xd(n))throw n}}function On(e,t){return{viewport:e.viewport,locale:e.locale,...t?{userAgent:t}:{},...e.deviceScaleFactor?{deviceScaleFactor:e.deviceScaleFactor}:{},...e.isMobile!==void 0?{isMobile:e.isMobile}:{},...e.hasTouch!==void 0?{hasTouch:e.hasTouch}:{}}}async function xe(e,t,n){let a;try{return await Promise.race([e,new Promise((i,s)=>{a=setTimeout(()=>s(new Error(`${n} timed out after ${t}ms`)),t)})])}finally{a&&clearTimeout(a)}}function Wd(e){let t=e.trim();if(!t)throw new Error("channelHandle is required");if(/^https?:\/\//i.test(t)||/^(www\.|m\.)?youtube\.com\//i.test(t)){let o=new URL(/^https?:\/\//i.test(t)?t:`https://${t}`);if(o.hostname.replace(/^www\./,"").replace(/^m\./,"").toLowerCase()!=="youtube.com")throw new Error("channel URL must be on youtube.com");let l=o.pathname.split("/").filter(Boolean),U=l[0]??"",S=l[1]??"";if(U.startsWith("@"))return`https://www.youtube.com/${U}/videos`;if(U==="channel"&&S)return`https://www.youtube.com/channel/${S}/videos`;if((U==="c"||U==="user")&&S)return`https://www.youtube.com/${U}/${S}/videos`;throw new Error("channel URL must be a YouTube handle, /channel/UC..., /c/..., or /user/... URL")}let i=t.replace(/^\/+/,"").replace(/\/+$/,"").replace(/\/videos$/i,"");if(/^UC[\w-]{20,}$/.test(i))return`https://www.youtube.com/channel/${i}/videos`;let s=i.startsWith("@")?i:`@${i}`;if(!/^@[\w.-]+$/.test(s))throw new Error("channelHandle must be an @handle, UC channel ID, or YouTube channel URL");return`https://www.youtube.com/${s}/videos`}var Wn=class{browser=null;context=null;page=null;\u006b\u0065\u0072\u006e\u0065\u006cClient=null;\u006b\u0065\u0072\u006e\u0065\u006cSessionId=null;\u006b\u0065\u0072\u006e\u0065\u006cOpenedAtMs=null;\u006b\u0065\u0072\u006e\u0065\u006cStealth=null;\u006b\u0065\u0072\u006e\u0065\u006cProxyUsed=null;\u006b\u0065\u0072\u006e\u0065\u006cProxySource=null;\u006b\u0065\u0072\u006e\u0065\u006cProxyType=null;\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent=null;last\u004b\u0065\u0072\u006e\u0065\u006cBillingMode=null;last\u004b\u0065\u0072\u006e\u0065\u006cOpenedAtMs=null;last\u004b\u0065\u0072\u006e\u0065\u006cClosedAtMs=null;debugEnabled=!1;debugSnapshot={\u006b\u0065\u0072\u006e\u0065\u006c:null,context:null,networkLocation:null,serpNavigation:null};async launch(t){this.debugEnabled=t.debug===!0;let n=t.proxyMode??(t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId?"configured":"none"),a=t.isMobile?"mobile":"desktop";if(this.debugSnapshot={\u006b\u0065\u0072\u006e\u0065\u006c:null,context:{viewport:t.viewport,locale:t.locale,device:a,userAgent:null,deviceScaleFactor:t.deviceScaleFactor??null,isMobile:t.isMobile===!0,hasTouch:t.hasTouch===!0},networkLocation:null,serpNavigation:null},t.\u006b\u0065\u0072\u006e\u0065\u006cApiKey){this.\u006b\u0065\u0072\u006e\u0065\u006cClient=new B({apiKey:t.\u006b\u0065\u0072\u006e\u0065\u006cApiKey});let s=Number.isInteger(t.\u006b\u0065\u0072\u006e\u0065\u006cTimeoutSeconds)&&Number(t.\u006b\u0065\u0072\u006e\u0065\u006cTimeoutSeconds)>0?Number(t.\u006b\u0065\u0072\u006e\u0065\u006cTimeoutSeconds):Ad("\u004b\u0045\u0052\u004e\u0045\u004c_BROWSER_TIMEOUT_SECONDS",bd),o=Math.min(s,600);t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName&&t.\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges===!0&&await Rd(this.\u006b\u0065\u0072\u006e\u0065\u006cClient,t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName);let d=Zt(),l;t.headlessMode==="headful"||d?.forceHeadful===!0?l=!1:t.headlessMode==="headless"?l=!0:l=d?.forceHeadless===!0||process.env.\u004b\u0045\u0052\u004e\u0045\u004c_HEADLESS_DISABLED!=="true"&&!!d?.op&&ps.has(d.op),this.\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent=l?!0:null,this.last\u004b\u0065\u0072\u006e\u0065\u006cBillingMode=l?"headless":"headful",d?.headlessSentOut&&(d.headlessSentOut.value=this.\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent);let U=await this.\u006b\u0065\u0072\u006e\u0065\u006cClient.browsers.create({stealth:t.\u006b\u0065\u0072\u006e\u0065\u006cStealth===!0,timeout_seconds:o,...l?{headless:!0}:{},...t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId?{proxy_id:t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId}:{},...t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName?{profile:{name:t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName,...typeof t.\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges=="boolean"?{save_changes:t.\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges}:{}}}:{}});this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId=U.session_id,this.\u006b\u0065\u0072\u006e\u0065\u006cOpenedAtMs=Date.now(),this.last\u004b\u0065\u0072\u006e\u0065\u006cOpenedAtMs=this.\u006b\u0065\u0072\u006e\u0065\u006cOpenedAtMs,this.last\u004b\u0065\u0072\u006e\u0065\u006cClosedAtMs=null,this.\u006b\u0065\u0072\u006e\u0065\u006cStealth=typeof U.stealth=="boolean"?U.stealth:null,this.\u006b\u0065\u0072\u006e\u0065\u006cProxyUsed=typeof U.proxy_id=="string"?!!U.proxy_id:!!t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId,this.\u006b\u0065\u0072\u006e\u0065\u006cProxySource=t.\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution?.source??null,this.\u006b\u0065\u0072\u006e\u0065\u006cProxyType=t.\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution?.proxyType??null;let S=null,r=null;if(!t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId&&!t.keepDefaultProxy)try{await xe(this.\u006b\u0065\u0072\u006e\u0065\u006cClient.browsers.update(this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,{disable_default_proxy:!0}),5e3,`\u004b\u0065\u0072\u006e\u0065\u006c session ${this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId} disable default proxy`),S=!0}catch(c){S=!1,r=Oe(c)}let u={sessionId:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,proxyMode:n,requestedProxyIdPresent:!!t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId,requestedProxyIdSuffix:xa(t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId),createdProxyIdPresent:typeof U.proxy_id=="string"?!!U.proxy_id:null,createdProxyIdSuffix:xa(U.proxy_id),retrievedProxyIdPresent:null,retrievedProxyIdSuffix:null,retrievedProxyIdMatchesRequested:null,defaultProxyDisabled:S,defaultProxyDisableError:r,proxyResolution:t.\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution??null,timeoutSeconds:o,stealth:typeof U.stealth=="boolean"?U.stealth:null,profilePresent:null,poolPresent:null,retrieveError:null};if(this.debugSnapshot.\u006b\u0065\u0072\u006e\u0065\u006c=u,console.info(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_browser_created",\u006b\u0065\u0072\u006e\u0065\u006c_session_id:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,timeout_seconds:o,proxy_mode:n,proxy_id_present:!!t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId,profile_name_present:!!t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName,proxy_resolution_source:t.\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution?.source})),this.debugEnabled&&await this.populate\u004b\u0065\u0072\u006e\u0065\u006cRetrieveDebug(u,t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId),this.browser=await ks.chromium.connectOverCDP(U.cdp_ws_url),t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName||t.preserve\u004b\u0065\u0072\u006e\u0065\u006cContext)this.context=this.browser.contexts()[0]??await this.browser.newContext(On(t)),this.page=this.context.pages()[0]??await this.context.newPage(),this.debugSnapshot.context.userAgent=await Ln(this.page);else{let c=await xn(this.browser);this.debugSnapshot.context.userAgent=c,this.context=await this.browser.newContext(On(t,c)),this.page=await this.context.newPage()}if(await this.installEsbuildHelperShims(this.context),t.preserve\u004b\u0065\u0072\u006e\u0065\u006cContext||await this.page.setViewportSize(t.viewport),(this.debugEnabled||t.requireUsEgress)&&(this.debugSnapshot.networkLocation=await this.captureBrowserNetworkLocation()),t.requireUsEgress){let c=this.debugSnapshot.networkLocation?.country??null;if(!Ld(c))throw new it(`Non-US egress (${c??"unknown"}) \u2014 retrying with a fresh session`)}return}let i={headless:t.headless,proxy:t.proxy?{server:t.proxy}:void 0,...t.browserExecutablePath?{executablePath:t.browserExecutablePath}:{},...t.ignoreDefaultArgs?{ignoreDefaultArgs:t.ignoreDefaultArgs}:{}};if(t.profileDir)this.context=await Rn.chromium.launchPersistentContext(t.profileDir,{...i,...On(t)}),await this.installEsbuildHelperShims(this.context),this.page=await this.context.newPage(),this.debugSnapshot.context.userAgent=await Ln(this.page);else{this.browser=await Rn.chromium.launch(i);let s=await xn(this.browser);this.debugSnapshot.context.userAgent=s,this.context=await this.browser.newContext(On(t,s)),await this.installEsbuildHelperShims(this.context),this.page=await this.context.newPage()}this.debugEnabled&&(this.debugSnapshot.networkLocation=await this.captureBrowserNetworkLocation())}async populate\u004b\u0065\u0072\u006e\u0065\u006cRetrieveDebug(t,n){if(!(!this.\u006b\u0065\u0072\u006e\u0065\u006cClient||!this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId))try{let a=await xe(this.\u006b\u0065\u0072\u006e\u0065\u006cClient.browsers.retrieve(this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId),5e3,`\u004b\u0065\u0072\u006e\u0065\u006c session ${this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId} retrieve`);t.retrievedProxyIdPresent=typeof a.proxy_id=="string"?!!a.proxy_id:!1,t.retrievedProxyIdSuffix=xa(a.proxy_id),t.retrievedProxyIdMatchesRequested=n?a.proxy_id===n:!a.proxy_id,t.timeoutSeconds=typeof a.timeout_seconds=="number"?a.timeout_seconds:t.timeoutSeconds,t.stealth=typeof a.stealth=="boolean"?a.stealth:t.stealth,t.profilePresent=!!a.profile,t.poolPresent=!!a.pool}catch(a){t.retrieveError=Oe(a)}}async captureBrowserNetworkLocation(){let t=(a,i="ipapi.co")=>({source:i,ip:null,city:null,region:null,country:null,org:null,timezone:null,error:a});if(!this.context)return t("browser context is not available");let n=null;try{n=await this.context.newPage();let a=await this.loadJsonInDebugPage(n,"https://ipwho.is/");if(a){let d=typeof a.connection=="object"&&a.connection!==null?a.connection:{};return{source:"ipwho.is",ip:typeof a.ip=="string"?a.ip:null,city:typeof a.city=="string"?a.city:null,region:typeof a.region=="string"?a.region:null,country:typeof a.country=="string"?a.country:null,org:typeof d.org=="string"?d.org:null,timezone:typeof a.timezone=="object"&&a.timezone!==null&&typeof a.timezone.id=="string"?a.timezone.id:null,error:null}}let i=await this.loadJsonInDebugPage(n,"https://api64.ipify.org?format=json");if(i)return{source:"api64.ipify.org",ip:typeof i.ip=="string"?i.ip:null,city:null,region:null,country:null,org:null,timezone:null,error:null};await xe(n.goto("https://ipapi.co/json/",{waitUntil:"domcontentloaded",timeout:7e3}),8e3,"browser network location navigation");let s=await n.locator("body").innerText({timeout:2e3}),o=JSON.parse(s);return{source:"ipapi.co",ip:typeof o.ip=="string"?o.ip:null,city:typeof o.city=="string"?o.city:null,region:typeof o.region=="string"?o.region:null,country:typeof o.country_name=="string"?o.country_name:typeof o.country=="string"?o.country:null,org:typeof o.org=="string"?o.org:null,timezone:typeof o.timezone=="string"?o.timezone:null,error:null}}catch(a){return t(Oe(a))}finally{await n?.close().catch(()=>{})}}async loadJsonInDebugPage(t,n){try{await xe(t.goto(n,{waitUntil:"domcontentloaded",timeout:7e3}),8e3,`browser network location navigation ${n}`);let a=await t.locator("body").innerText({timeout:2e3});return JSON.parse(a)}catch{return null}}async installEsbuildHelperShims(t){await t.addInitScript(()=>{let n=globalThis;typeof n.__name!="function"&&(n.__name=a=>a),typeof n.__publicField!="function"&&(n.__publicField=(a,i,s)=>(a[i]=s,s))})}async withTemporaryPage(t,n){if(!this.context)throw new Error("Browser context is not available");return Pn(this.context,async()=>{},t,n)}async navigateToSERP(t,n,a,i,s){let o=new URLSearchParams({q:t,gl:a,hl:i,pws:"0"});s?.tbs&&o.set("tbs",s.tbs),n&&o.set("uule",n);let d="https://www.google.com/search?"+o.toString(),l=Cs(d),U=s?.debug?{requestedUrl:d,finalUrl:null,title:null,bodySnippet:null,hasPaa:null,captchaDetected:null,googleSorryUrl:null,redirected:null}:null;U&&(this.debugSnapshot.serpNavigation=U);try{await this.page.goto(l,{waitUntil:"domcontentloaded",timeout:La(s?.deadlineMs,s?.purpose==="serp"?8e3:45e3)})}catch(r){await this.updateSerpNavigationDebug(U,d,{hasPaa:null,captchaDetected:null});let u=await this.captureDiagnostics(d);throw new Ae(`page.goto failed: ${r.message} | ${u}`)}if(await this.isSerpChallengeVisible())throw await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!0}),new it(this.captchaMessage());if(s?.purpose==="serp"){await this.page.waitForSelector(Id,{timeout:La(s.deadlineMs,1500)}).catch(()=>null);let r=await this.page.locator(mt.paaItem).count().catch(()=>0)>0;return await this.updateSerpNavigationDebug(U,d,{hasPaa:r,captchaDetected:!1}),{hasPaa:r}}if(await this.page.waitForSelector(mt.paaItem,{timeout:La(s?.deadlineMs,4e3)}).catch(()=>null))return await this.updateSerpNavigationDebug(U,d,{hasPaa:!0,captchaDetected:!1}),{hasPaa:!0};if(await this.isSerpChallengeVisible())throw await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!0}),new it(this.captchaMessage());for(let r=1;r<=6;r++)if(await this.page.evaluate(c=>{window.scrollTo(0,document.body.scrollHeight*c)},r/6),await this.page.waitForTimeout(600),await this.page.locator(mt.paaItem).count()>0)return await this.updateSerpNavigationDebug(U,d,{hasPaa:!0,captchaDetected:!1}),{hasPaa:!0};return await this.updateSerpNavigationDebug(U,d,{hasPaa:!1,captchaDetected:!1}),{hasPaa:!1}}async isSerpChallengeVisible(){if(!this.page)return!1;if(await this.page.locator(mt.captchaMarker).count().catch(()=>0)>0)return!0;let n=this.page.url();if(/google\.[^/]+\/sorry\//i.test(n))return!0;let a=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,1e3)).catch(()=>"");return/recaptcha|unusual traffic|are you a robot|about this page|detected unusual traffic/i.test(a)}async updateSerpNavigationDebug(t,n,a){if(!(!t||!this.page))try{let i=this.page.url(),s=await this.page.title().catch(()=>""),o=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,500)).catch(()=>""),d=/recaptcha|unusual traffic|are you a robot/i.test(o);t.finalUrl=i,t.title=s,t.bodySnippet=o,t.hasPaa=a.hasPaa,t.captchaDetected=a.captchaDetected??d,t.googleSorryUrl=/google\.[^/]+\/sorry\//i.test(i),t.redirected=i!==n}catch(i){t.bodySnippet=`debug capture failed: ${Oe(i)}`}}async captureDiagnostics(t){try{let n=this.page.url(),a=await this.page.title().catch(()=>""),i=await this.page.evaluate(()=>(document.body?.innerText??"").replace(/\s+/g," ").trim().slice(0,400)).catch(()=>""),s=/consent\.google\./.test(n)||/before you continue/i.test(i),o=/recaptcha|unusual traffic|are you a robot/i.test(i),d=[s?"CONSENT_WALL":"",o?"BOT_CHALLENGE":"",n!==t?"REDIRECTED":""].filter(Boolean).join(",");return`intended=${t} | final=${n} | title="${a}" | flags=[${d}] | body="${i}"`}catch(n){return`diagnostics-failed: ${n.message}`}}captchaMessage(){return this.\u006b\u0065\u0072\u006e\u0065\u006cClient?"Google returned a CAPTCHA on this session \u2014 retrying with a fresh session.":ls}async navigateTo(t){let n=process.env.ADS_ARRIVAL_REDIRECT_BASE?.trim(),a=n?Cs(t,n):t;try{if(await this.page.goto(a,{waitUntil:"domcontentloaded",timeout:45e3}),/google\.[^/]+\/search\?/i.test(t)&&await this.isSerpChallengeVisible())throw new it(this.captchaMessage())}catch(i){if(i instanceof it)throw i;let s=await this.captureDiagnostics(t);throw new Ae(`page.goto failed: ${i.message} | ${s}`)}}async navigateToChannel(t){let n=Wd(t);try{await this.page.goto(n,{waitUntil:"networkidle",timeout:3e4})}catch(a){let i=await this.captureDiagnostics(n);throw new Ae(`navigateToChannel failed: ${a.message} | ${i}`)}}async evaluate(t,n){return this.page.evaluate(t,n)}getPage(){return this.page}get\u004b\u0065\u0072\u006e\u0065\u006cSessionId(){return this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId}get\u004b\u0065\u0072\u006e\u0065\u006cMeteringEvidence(){return{sessionId:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId??this.debugSnapshot.\u006b\u0065\u0072\u006e\u0065\u006c?.sessionId??null,billingMode:this.last\u004b\u0065\u0072\u006e\u0065\u006cBillingMode,openedAtMs:this.last\u004b\u0065\u0072\u006e\u0065\u006cOpenedAtMs,closedAtMs:this.last\u004b\u0065\u0072\u006e\u0065\u006cClosedAtMs}}getProviderSessionMetadata(){return{provider:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId?"\u006b\u0065\u0072\u006e\u0065\u006c":"local",providerSessionId:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,disconnectObservation:null,billingMode:this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId?this.\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent?"headless":"headful":null}}getDebugSnapshot(){return this.debugSnapshot}async close(){if(this.browser){let t=this.browser,n=this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,a=this.\u006b\u0065\u0072\u006e\u0065\u006cClient,i=this.\u006b\u0065\u0072\u006e\u0065\u006cOpenedAtMs,s=this.\u006b\u0065\u0072\u006e\u0065\u006cStealth,o=this.\u006b\u0065\u0072\u006e\u0065\u006cProxyUsed,d=this.\u006b\u0065\u0072\u006e\u0065\u006cProxySource,l=this.\u006b\u0065\u0072\u006e\u0065\u006cProxyType,U=this.\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent,S=this.getProviderSessionMetadata();if(this.browser=null,this.context=null,this.page=null,this.\u006b\u0065\u0072\u006e\u0065\u006cSessionId=null,this.\u006b\u0065\u0072\u006e\u0065\u006cClient=null,this.\u006b\u0065\u0072\u006e\u0065\u006cOpenedAtMs=null,this.\u006b\u0065\u0072\u006e\u0065\u006cHeadlessSent=null,this.\u006b\u0065\u0072\u006e\u0065\u006cProxySource=null,this.\u006b\u0065\u0072\u006e\u0065\u006cProxyType=null,a&&n){console.info(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_browser_delete_started",\u006b\u0065\u0072\u006e\u0065\u006c_session_id:n}));let r=xe(a.browsers.deleteByID(n),Pd,`\u004b\u0065\u0072\u006e\u0065\u006c session ${n} delete`),u=xe(t.close(),Ed,`\u004b\u0065\u0072\u006e\u0065\u006c browser ${n} close`),[c,h]=await Promise.allSettled([r,u]);this.last\u004b\u0065\u0072\u006e\u0065\u006cClosedAtMs=Date.now(),i!=null&&ys({\u006b\u0065\u0072\u006e\u0065\u006cSessionId:n,source:"browser_driver",stealth:s,headlessSent:U,proxyUsed:o,proxySource:d,proxyType:l,openedAtMs:i,closedAtMs:this.last\u004b\u0065\u0072\u006e\u0065\u006cClosedAtMs});let w=c.status==="rejected"&&Od(c.reason),k={\u006b\u0065\u0072\u006e\u0065\u006cSessionId:n,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!0,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:c.status==="fulfilled"||w,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:c.status==="rejected"&&!w?c.reason instanceof Error?c.reason.message:String(c.reason):null,browserCloseSucceeded:h.status==="fulfilled",browserCloseError:h.status==="rejected"?h.reason instanceof Error?h.reason.message:String(h.reason):null,provider:S.provider,providerSessionId:S.providerSessionId,providerDisconnectObserved:!1,providerDisconnectMessage:null};return c.status==="rejected"&&!w?(console.warn(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_browser_delete_failed",\u006b\u0065\u0072\u006e\u0065\u006c_session_id:n,message:k.\u006b\u0065\u0072\u006e\u0065\u006cDeleteError})),console.warn(`\u004b\u0065\u0072\u006e\u0065\u006c session cleanup failed for ${n}:`,c.reason)):console.info(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_browser_delete_succeeded",\u006b\u0065\u0072\u006e\u0065\u006c_session_id:n})),h.status==="rejected"&&(console.warn(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_browser_close_failed",\u006b\u0065\u0072\u006e\u0065\u006c_session_id:n,message:k.browserCloseError})),console.warn(`\u004b\u0065\u0072\u006e\u0065\u006c browser close failed for ${n}:`,h.reason)),k}return await t.close(),{\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!1,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:null,browserCloseSucceeded:!0,browserCloseError:null,provider:S.provider,providerSessionId:S.providerSessionId,providerDisconnectObserved:!1,providerDisconnectMessage:null}}else if(this.context){let t=this.context;return this.context=null,this.page=null,await t.close(),{\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!1,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:null,browserCloseSucceeded:!0,browserCloseError:null,provider:"local",providerSessionId:null,providerDisconnectObserved:!1,providerDisconnectMessage:null}}return{\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!1,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:null,browserCloseSucceeded:null,browserCloseError:null,provider:"local",providerSessionId:null,providerDisconnectObserved:!1,providerDisconnectMessage:null}}};var Es=require("playwright");function Hd(e,t){if(typeof e!="string")return null;let n=e.replace(/[\u0000-\u001f\u007f]+/g," ").replace(/\s+/g," ").trim();return n?n.slice(0,t):null}function fs(e){let t=Hd(e,320);return t?t.replace(/\b(?:wss?|https?):\/\/\S+/gi,"[redacted endpoint]").replace(/\b(?:authorization|proxy-authorization):\s*\S+/gi,"$1: [redacted]").replace(/\bBearer\s+\S+/gi,"Bearer [redacted]").slice(0,320):null}function Ms(e){return fs(e)}function Ns(e){if(typeof e!="string"||e.length===0||e.length>512||e.trim()!==e||/[\s\u0000-\u001f\u007f]/.test(e)||/:\/\//.test(e))throw new Error("\u0042\u0072\u0069\u0067\u0068\u0074 \u0044\u0061\u0074\u0061 did not return a valid browser session ID");return e}function Oa(e,t,n=new Date().toISOString()){let a=fs(t);return{source:e,message:a??e.replaceAll("_"," "),observedAt:n}}function Bd(e){return{provider:e.provider,providerDisconnectObserved:e.disconnectObservation!==null,providerDisconnectMessage:e.disconnectObservation?.message??null}}function vs(e){return{...Bd(e),providerSessionId:e.providerSessionId}}function Ra(){return process.env.\u0042\u0052\u0049\u0047\u0048\u0054\u0044\u0041\u0054\u0041_BROWSER_WSS?.trim()||null}function _s(){return process.env.SERP_BROWSER_PROVIDER?.trim().toLowerCase()==="\u006b\u0065\u0072\u006e\u0065\u006c"?!1:!!Ra()}var Dd=new Set(["image","media","font","stylesheet","ping"]),Fd=["doubleclick.net","googleadservices.com","googlesyndication.com","google-analytics.com"],Gd='#search, #rso, a[href] h3, [data-snhf], [role="main"]',Vd=3e4,bs=1500;function Hn(e,t){return e?Math.max(1,Math.min(t,e-Date.now())):t}async function Wa(e,t=!1){let n=e.request();try{let a=await n.allHeaders(),i=await fetch(n.url(),{method:n.method(),headers:{accept:a.accept??"*/*","accept-language":a["accept-language"]??"en-US,en;q=0.9","user-agent":a["user-agent"]??"Mozilla/5.0",...t?{cookie:a.cookie??"",referer:a.referer??"https://www.google.com/",...a["x-client-data"]?{"x-client-data":a["x-client-data"]}:{}}:{}},body:n.method()==="GET"||n.method()==="HEAD"?void 0:n.postData()});if(!i.ok)return!1;let s=Buffer.from(await i.arrayBuffer());return await e.fulfill({status:i.status,contentType:i.headers.get("content-type")??"application/octet-stream",headers:{"cache-control":"public, max-age=3600"},body:s}),!0}catch{return!1}}var Bn=class{browser=null;context=null;page=null;cdpSession=null;providerSessionId=null;disconnectObservation=null;closing=!1;observeDisconnect(t,n){this.closing||this.disconnectObservation||(this.disconnectObservation=Oa(t,n))}async launch(t){if(this.page)return;this.closing=!1,this.providerSessionId=null,this.disconnectObservation=null;let n=Ra();if(!n)throw new Error("SERP browser service is not configured");this.browser=await Es.chromium.connectOverCDP(n,{timeout:Hn(t.operationDeadlineMs,Vd)}),this.context=this.browser.contexts()[0]??await this.browser.newContext(),await this.context.addInitScript(()=>{let s=globalThis;typeof s.__name!="function"&&(s.__name=o=>o),typeof s.__publicField!="function"&&(s.__publicField=(o,d,l)=>(o[d]=l,l))}),this.page=this.context.pages()[0]??await this.context.newPage(),this.browser.on("disconnected",()=>this.observeDisconnect("browser_disconnected")),this.context.on("close",()=>this.observeDisconnect("context_closed")),this.page.on("close",()=>this.observeDisconnect("page_closed")),this.page.on("crash",()=>this.observeDisconnect("page_crashed")),this.cdpSession=await this.context.newCDPSession(this.page);let i=await this.cdpSession.send("Browser.getSessionId");this.providerSessionId=Ns(i?.sessionId),await this.setupPage(this.page)}async setupPage(t){await t.route("**/*",async n=>{let a=n.request(),i=a.resourceType(),s;try{s=new URL(a.url())}catch{await n.continue();return}let o=s.hostname.toLowerCase();if(!(s.pathname==="/sgasync"&&await Wa(n,!0))&&!(s.pathname.includes("/shared_dict/")&&await Wa(n))&&!(i==="script"&&(o==="www.google.com"||o==="www.gstatic.com")&&await Wa(n))){if(Dd.has(i)){await n.abort("blockedbyclient");return}if(Fd.some(d=>o===d||o.endsWith(`.${d}`))){await n.abort("blockedbyclient");return}await n.continue()}})}async withTemporaryPage(t,n){if(!this.context||this.closing)throw new Error("Browser context is not available");return Pn(this.context,a=>this.setupPage(a),t,n)}async navigateToSERP(t,n,a,i,s){if(!this.page)throw new Error("Browser page is not available");let o=new URLSearchParams({q:t,gl:a,hl:i,pws:"0"});return s?.tbs&&o.set("tbs",s.tbs),n&&o.set("uule",n),await this.page.goto(`https://www.google.com/search?${o}`,{waitUntil:"domcontentloaded",timeout:Hn(s?.deadlineMs,s?.purpose==="serp"?8e3:45e3)}),s?.purpose==="serp"?(await this.page.waitForSelector(Gd,{timeout:Hn(s.deadlineMs,1500)}).catch(()=>null),{hasPaa:await this.page.locator(mt.paaItem).count().catch(()=>0)>0}):{hasPaa:!!await this.page.waitForSelector(mt.paaItem,{timeout:Hn(s?.deadlineMs,8e3)}).catch(()=>null)}}async navigateTo(t){if(!this.page)throw new Error("Browser page is not available");await this.page.goto(t,{waitUntil:"load",timeout:45e3})}async navigateToChannel(){throw new Error("YouTube navigation is not supported by the SERP browser driver")}async evaluate(t,n){if(!this.page)throw new Error("Browser page is not available");return this.page.evaluate(t,n)}getPage(){if(!this.page)throw new Error("Browser page is not available");return this.page}get\u004b\u0065\u0072\u006e\u0065\u006cSessionId(){return null}getProviderSessionMetadata(){return{provider:"\u0062\u0072\u0069\u0067\u0068\u0074_\u0064\u0061\u0074\u0061_browser_api",providerSessionId:this.providerSessionId,disconnectObservation:this.disconnectObservation}}getDebugSnapshot(){return{\u006b\u0065\u0072\u006e\u0065\u006c:null,context:null,networkLocation:null,serpNavigation:null}}async close(){this.closing=!0;let t=null,n;try{let i=this.browser?.close();i&&await Promise.race([i,new Promise((s,o)=>{n=setTimeout(()=>o(new Error(`Browser close acknowledgement exceeded ${bs}ms`)),bs)})])}catch(i){t=Ms(i instanceof Error?i.message:String(i))??"\u0042\u0072\u0069\u0067\u0068\u0074 \u0044\u0061\u0074\u0061 browser close failed",this.disconnectObservation??=Oa("browser_close_error",t)}finally{n&&clearTimeout(n)}let a=vs(this.getProviderSessionMetadata());return this.browser=null,this.context=null,this.page=null,this.cdpSession=null,{\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!1,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:null,browserCloseSucceeded:t===null,browserCloseError:t,...a}}};function Ps(e){return e.plannedProvider==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"?new Bn:new Wn}var X={container:".eJH8qe.adDDi",dataInitq:"[data-initq]",item:mt.paaItem,itemDataQ:"data-q",itemDataInitQ:"data-initq",itemQuestionEl:".JlqpRe",answerContainer:".bCOlv, .hgKElc, .wDYxhc, .LGOjhe, .fo7IQd, .fmW3u",aiAnswerBody:".pWvJNd",aiCitation:"a.PMDqCb[href]",aiSourceCard:"a.vIWmYe[href], a.Zbfntb[href]",sourceTitle:"h3",sourceSite:".VuuXrf",sourceCite:"cite",clickTarget:".JlqpRe",expandedClass:"aoRk1c",captchaMarker:mt.captchaMarker};var te={austin:"Austin,Texas,United States","new york":"New York,New York,United States","new york city":"New York,New York,United States",nyc:"New York,New York,United States","los angeles":"Los Angeles,California,United States",la:"Los Angeles,California,United States",chicago:"Chicago,Illinois,United States",houston:"Houston,Texas,United States",phoenix:"Phoenix,Arizona,United States",philadelphia:"Philadelphia,Pennsylvania,United States",philly:"Philadelphia,Pennsylvania,United States","san antonio":"San Antonio,Texas,United States",dallas:"Dallas,Texas,United States",miami:"Miami,Florida,United States",seattle:"Seattle,Washington,United States",denver:"Denver,Colorado,United States",loveland:"Loveland,Colorado,United States","loveland co":"Loveland,Colorado,United States","fort collins":"Fort Collins,Colorado,United States",boulder:"Boulder,Colorado,United States","colorado springs":"Colorado Springs,Colorado,United States",boston:"Boston,Massachusetts,United States",atlanta:"Atlanta,Georgia,United States","san francisco":"San Francisco,California,United States",sf:"San Francisco,California,United States",portland:"Portland,Oregon,United States","las vegas":"Las Vegas,Nevada,United States",minneapolis:"Minneapolis,Minnesota,United States",detroit:"Detroit,Michigan,United States",nashville:"Nashville,Tennessee,United States",charlotte:"Charlotte,North Carolina,United States",orlando:"Orlando,Florida,United States","san diego":"San Diego,California,United States",baltimore:"Baltimore,Maryland,United States",sacramento:"Sacramento,California,United States",columbus:"Columbus,Ohio,United States",indianapolis:"Indianapolis,Indiana,United States","san jose":"San Jose,California,United States","fort worth":"Fort Worth,Texas,United States",jacksonville:"Jacksonville,Florida,United States",memphis:"Memphis,Tennessee,United States",louisville:"Louisville,Kentucky,United States",raleigh:"Raleigh,North Carolina,United States",richmond:"Richmond,Virginia,United States","salt lake city":"Salt Lake City,Utah,United States",toronto:"Toronto,Ontario,Canada",vancouver:"Vancouver,British Columbia,Canada",montreal:"Montreal,Quebec,Canada",calgary:"Calgary,Alberta,Canada",ottawa:"Ottawa,Ontario,Canada",london:"London,England,United Kingdom",manchester:"Manchester,England,United Kingdom",birmingham:"Birmingham,England,United Kingdom",edinburgh:"Edinburgh,Scotland,United Kingdom",glasgow:"Glasgow,Scotland,United Kingdom",leeds:"Leeds,England,United Kingdom",sydney:"Sydney,New South Wales,Australia",melbourne:"Melbourne,Victoria,Australia",brisbane:"Brisbane,Queensland,Australia",perth:"Perth,Western Australia,Australia",adelaide:"Adelaide,South Australia,Australia",dublin:"Dublin,Leinster,Ireland"};var Is=`3, Nanjemoy,Maryland,United States
|
|
194
194
|
Aaronsburg,Pennsylvania,United States
|
|
195
195
|
Abbeville,Alabama,United States
|
|
196
196
|
Abbeville,Georgia,United States
|
|
@@ -21893,13 +21893,13 @@ Zwolle,Louisiana,United States`,As={ad:"Andorra",ae:"United Arab Emirates",af:"A
|
|
|
21893
21893
|
|
|
21894
21894
|
`).trim();return!W||/not available|try again|can't generate/i.test(W)?null:W}function U(y){if(!y||y.startsWith("javascript:"))return null;try{let E=new URL(y,window.location.href);return!["http:","https:"].includes(E.protocol)||E.username||E.password?null:{href:E.href,rawHref:E.href}}catch{return null}}function S(y){if(!y)return[];let E=new Set,p=[];for(let T of Array.from(y.querySelectorAll("a[href]"))){let N=U(T.getAttribute("href")??"");if(!N||E.has(N.rawHref))continue;E.add(N.rawHref);let I="";try{I=new URL(N.href).hostname.replace(/^www\./,"")}catch{}p.push({text:i(T)||I||N.href,href:N.href,rawHref:N.rawHref})}return p}async function r(y){let E=y.querySelector(t.aio.showMoreButton);if(!E||E.getAttribute("aria-expanded")!=="false")return!1;E.click();let p=t.expandWaitMs??1500;return p>0&&await new Promise(T=>setTimeout(T,p)),!0}let u=d(),c=null,h=[],w=!1,k=!1,f=[];if(u){w=await r(u);let y=u.querySelector(t.aio.controller),E=u.querySelector(t.aio.contentSubtree),p=u.querySelector(t.aio.showMoreButton);k=y?.getAttribute("data-trnct")==="false"||p?.getAttribute("aria-expanded")==="true"||!p,c=l(E??y??u),f=(c??"").split(`
|
|
21895
21895
|
`).map(T=>T.trim()).filter(T=>/^\d+\.\s+.+/.test(T)),h=S(u)}let m=document.querySelector(t.aim.root),L=a==="aim"&&!!m,R=m?.closest(t.aim.wrapper)??m,D=L?l(R):null,_=L&&s(D),M=_?D:null,H=_?S(R):[],P=!!u&&s(c);return{surface:a,aiOverview:{detected:P,text:P?c:null,citations:P?h:[],expanded:P?w:!1,fullyExpanded:P?k:!1,sections:P?f:[]},aiMode:{detected:_&&M!==null,text:M,citations:H}}}var Vs=require("crypto"),Ys=8e3,Ks=3e3,Js=1e4,il=8;function Ot(e){return/(^|\.)google\.(?:com|[a-z]{2,3}(?:\.[a-z]{2})?)$/i.test(e)}function nn(e){if(!e||e.length>Ys)return null;try{let t=new URL(e);return t.protocol!=="http:"&&t.protocol!=="https:"||t.username||t.password?null:t}catch{return null}}function sl(e,t){if(!e||e.length>Ys||/^javascript:/i.test(e))return null;try{let n=new URL(e,t);return nn(n.href)}catch{return null}}function en(e){let t=nn(e);return!t||t.protocol!=="https:"||!Ot(t.hostname)||t.pathname!=="/goto"?null:t.searchParams.get("url")?t:null}function Ga(e){if(e.linkType!=="google_goto_redirect"||e.resolutionStatus!=="resolved"||!en(e.rawUrl)||!e.resolvedUrl)return!1;let t=nn(e.resolvedUrl);return!!(t&&!Ot(t.hostname)&&t.href===e.resolvedUrl&&e.url===t.href)}function ee(e){let t=e.normalize("NFKC").toLocaleLowerCase("en-US").replace(/[^\p{L}\p{N}\s]/gu,"").replace(/\s+/g," ").trim();return`paa_${(0,Vs.createHash)("sha256").update(t).digest("hex").slice(0,16)}`}function Fn(e,t){let n=sl(e,t);if(!n)return null;let a=n.href;if(!Ot(n.hostname))return{url:a,rawUrl:a,resolvedUrl:a,linkType:"plain",resolutionStatus:"not_needed"};if(n.pathname==="/url"){let i=nn(n.searchParams.get("q")??n.searchParams.get("url")??"");return!i||Ot(i.hostname)?null:{url:i.href,rawUrl:a,resolvedUrl:i.href,linkType:"google_url_redirect",resolutionStatus:"resolved"}}return n.pathname==="/goto"&&n.searchParams.get("url")?{url:a,rawUrl:a,resolvedUrl:null,linkType:"google_goto_redirect",resolutionStatus:"unresolved"}:null}function Va(e){return en(e)?.searchParams.get("url")??null}function qs(e,t){try{let n=new URL(e),a=nn(new URL(t,n).href);return!a||Ot(a.hostname)?null:(!a.hash&&n.hash&&(a.hash=n.hash),a.href)}catch{return null}}async function Xs(e,t={}){let n=[...new Set([...e].flatMap(r=>en(r)?[r]:[]))],a=new Map(n.map(r=>[r,{rawUrl:r,resolvedUrl:null,resolutionStatus:"unresolved"}])),i=typeof globalThis.fetch=="function"?globalThis.fetch.bind(globalThis):null,s=t.fetchImpl??i;if(n.length===0||!s)return{resolutions:[...a.values()],nonGoogleRequestsObserved:0};let o=Math.max(1,t.timeoutMs??Ks),d=Date.now()+Math.max(1,t.totalBudgetMs??Js),l=Math.max(1,Math.min(16,Math.floor(t.concurrency??il))),U=0,S=async()=>{for(;U<n.length;){let r=n[U++],u=en(r),c=u?.searchParams.get("url");if(!u||!c){a.set(r,{rawUrl:r,resolvedUrl:null,resolutionStatus:"rejected"});continue}u.hash="";let h=u.href;for(let w=0;w<2;w++){let k=d-Date.now();if(k<=0)return;let f=new AbortController,m=setTimeout(()=>f.abort(),Math.min(o,k)),L;try{L=await s(h,{method:"GET",redirect:"manual",headers:{accept:"*/*","user-agent":"Mozilla/5.0"},signal:f.signal})}catch{break}finally{clearTimeout(m)}if(L.status<300||L.status>=400)break;let R=L.headers.get("location");if(!R)break;let D=qs(r,R);if(D){a.set(r,{rawUrl:r,resolvedUrl:D,resolutionStatus:"resolved"});break}let _;try{_=new URL(R,h)}catch{a.set(r,{rawUrl:r,resolvedUrl:null,resolutionStatus:"rejected"});break}if(!Ot(_.hostname)||Va(_.href)!==c){a.set(r,{rawUrl:r,resolvedUrl:null,resolutionStatus:"rejected"});break}h=_.href}}};return await Promise.all(Array.from({length:Math.min(l,n.length)},()=>S())),{resolutions:[...a.values()],nonGoogleRequestsObserved:0}}function Gs(e,t){try{return new URL(e.resolvedUrl??e.url).hostname.replace(/^www\./,"")}catch{return t}}async function js(e,t={}){let n=[],a=r=>{for(let u of r)n.push(u),a(u.children??[])};a(e.tree??[]);let i=[...e.flat.flatMap(r=>r.sources??[]),...n.flatMap(r=>r.sources),...e.organicResults??[],...(e.aiOverview?.citations??[]).map(({text:r,href:u,...c})=>({...c,url:u})),...(e.aiMode?.citations??[]).map(({text:r,href:u,...c})=>({...c,url:u}))],s=new Map(i.filter(r=>!!r?.rawUrl).map(r=>[r.rawUrl,r])),o=[...s.values()].filter(r=>r.linkType==="google_goto_redirect"&&r.resolutionStatus!=="resolved").map(r=>r.rawUrl);if(o.length>0){let r=await Xs(o,t);for(let u of r.resolutions){let c=s.get(u.rawUrl);c&&s.set(u.rawUrl,u.resolutionStatus==="resolved"&&u.resolvedUrl?{...c,url:u.resolvedUrl,resolvedUrl:u.resolvedUrl,resolutionStatus:"resolved"}:{...c,resolutionStatus:u.resolutionStatus})}}let d=r=>({...r,...s.get(r.rawUrl)??r}),l=r=>r.map(u=>{let c=d(u);return{...c,site:Gs(c,u.site)}});for(let r of e.flat){r.sources=l(r.sources??[]);let u=r.sources[0];r.source_title=u?.title??r.source_title,r.source_site=u?.site??r.source_site,r.source_cite=u?.url??r.source_cite}for(let r of n){r.sources=l(r.sources??[]);let u=r.sources[0];r.sourceTitle=u?.title??r.sourceTitle,r.sourceSite=u?.site??r.sourceSite,r.sourceCite=u?.url??r.sourceCite}for(let r=0;r<(e.organicResults?.length??0);r++){let u=d(e.organicResults[r]);e.organicResults[r]={...u,domain:Gs(u,e.organicResults[r].domain)??""}}let U=r=>{let u=d({url:r.href,rawUrl:r.rawUrl,resolvedUrl:r.resolvedUrl,linkType:r.linkType,resolutionStatus:r.resolutionStatus}),{url:c,...h}=u;return{...r,...h,href:c}};e.aiOverview&&(e.aiOverview.citations=(e.aiOverview.citations??[]).map(U)),e.aiMode&&(e.aiMode.citations=(e.aiMode.citations??[]).map(U));let S=[...s.values()];return e.diagnostics.links={linkCandidatesObserved:s.size,plainLinksObserved:S.filter(r=>r.linkType==="plain").length,googleUrlRedirectsObserved:S.filter(r=>r.linkType==="google_url_redirect").length,googleGotoRedirectsObserved:S.filter(r=>r.linkType==="google_goto_redirect").length,redirectsResolved:S.filter(r=>r.linkType!=="plain"&&r.resolutionStatus==="resolved").length,redirectsUnresolved:S.filter(r=>r.resolutionStatus==="unresolved").length,redirectsRejected:S.filter(r=>r.resolutionStatus==="rejected").length,resolverNonGoogleRequestsObserved:0,paaSourcesPreserved:e.flat.reduce((r,u)=>r+u.sources.length,0),aiOverviewLabelValidated:e.aiOverview?.detected??!1},e}async function zs(e,t,n={}){let a=new Map;for(let u of t){let c=a.get(u.rawUrl);c&&Ga(c)||a.set(u.rawUrl,u.linkType==="google_goto_redirect"&&!Ga(u)?{...u,url:u.rawUrl,resolvedUrl:null,resolutionStatus:"unresolved"}:u)}let i=[...a.values()].filter(u=>u.linkType==="google_goto_redirect"&&!Ga(u));if(i.length===0)return a;let s=Date.now()+(n.totalBudgetMs??Js),o=await Xs(i.map(u=>u.rawUrl),n);for(let u of o.resolutions){let c=a.get(u.rawUrl);c&&a.set(u.rawUrl,u.resolutionStatus==="resolved"&&u.resolvedUrl?{...c,url:u.resolvedUrl,resolvedUrl:u.resolvedUrl,resolutionStatus:"resolved"}:{...c,resolutionStatus:u.resolutionStatus})}let d=i.filter(u=>a.get(u.rawUrl)?.resolutionStatus==="unresolved");if(d.length===0||n.browserFallback===!1||Date.now()>=s)return n.onNetworkAudit?.({nonGoogleRequestsObserved:0}),a;let l=n.timeoutMs??Ks,U=await e.context().newPage().catch(()=>null);if(!U)return n.onNetworkAudit?.({nonGoogleRequestsObserved:0}),a;let S=null,r=0;try{await U.route("**/*",async u=>{let c=u.request().url();try{Ot(new URL(c).hostname)||(r+=1)}catch{}let h=Va(c);if(!S||h!==S.token){await u.abort("blockedbyclient").catch(()=>{});return}let w=S;try{let k=await u.fetch({maxRedirects:0,timeout:w.timeoutMs});w.location=k.headers().location??null}finally{await u.abort("blockedbyclient").catch(()=>{}),w.finish()}});for(let u of d){let c=s-Date.now();if(c<=0)break;let h=en(u.rawUrl),w=h?.searchParams.get("url");if(!h||!w){a.set(u.rawUrl,{...u,resolutionStatus:"rejected"});continue}let k=Math.min(l,c);h.hash="";let f=h.href,m=!1;for(let L=0;L<2;L++){let R,D=new Promise(y=>{R=y}),_=`mcp-goto-${Math.random().toString(36).slice(2)}`;S={token:w,timeoutMs:k,location:null,finish:R},await U.evaluate(({url:y,id:E})=>{let p=document.createElement("iframe");p.id=E,p.hidden=!0,p.src=y,document.body.append(p)},{url:f,id:_}).catch(()=>null),await Promise.race([D,new Promise(y=>setTimeout(y,k))]);let M=S.location;if(S=null,await U.evaluate(y=>document.getElementById(y)?.remove(),_).catch(()=>null),!M)break;let H=qs(u.rawUrl,M);if(H){a.set(u.rawUrl,{...u,url:H,resolvedUrl:H,resolutionStatus:"resolved"});break}let P;try{P=new URL(M,f)}catch{m=!0;break}if(!Ot(P.hostname)||Va(P.href)!==w){m=!0;break}f=P.href}m&&a.get(u.rawUrl)?.resolutionStatus!=="resolved"&&a.set(u.rawUrl,{...u,resolutionStatus:"rejected"})}}finally{S=null,await U.close().catch(()=>{}),n.onNetworkAudit?.({nonGoogleRequestsObserved:r})}return a}var $s=String.raw`^(?:an error has occurred(?:[.!…]\s*)?(?:please try again later[.!…]?)?|loading|please wait|try again|something went wrong)[.!…\s]*$`,ol=700,rl=1e3,dl=1400,Qs=900,ll=3,Zs=250,Gn=class{constructor(t,n,a,i){this.driver=t;this.reporter=n;this.onPaaProgress=a;this.onProviderSession=i}driver;reporter;onPaaProgress;onProviderSession;completeness={paaWithoutAnswer:0,paaWithoutSource:0,paaAnswersRecovered:0,aioShareCaptured:null};aioShareUrlEarly=null;linkDiagnostics=this.emptyLinkDiagnostics();collectedRows=[];partialContext=null;progressSequence=0;clickedQuestions=new Set;paaLifecycle=this.emptyPaaLifecycle(0);checkpointMaterial=null;interactionObservations=[];phaseTimings={};currentPhaseTimings(t){return{...this.phaseTimings,totalServerMs:Math.max(0,Date.now()-t)}}emptyPaaLifecycle(t){return{requestedQuestions:t,questionsFound:0,targetStatus:"not_met",discoveryStatus:"in_progress",materialStatus:"partial",completionReason:"PAA expansion is still running.",automaticRetries:0,retryBreakdown:{controlRetries:0,browserRetries:0,providerFallbacks:0,runtimeRecoveries:0,idempotentReplays:0},knownQuestions:0,processedQuestions:0,failedInteractions:0,noGrowthConfirmations:0,visibleControls:0,eligibleControls:0,dispatchedInteractions:0,confirmedInteractions:0,unconfirmedInteractions:0}}emptyLinkDiagnostics(){return{linkCandidatesObserved:0,plainLinksObserved:0,googleUrlRedirectsObserved:0,googleGotoRedirectsObserved:0,redirectsResolved:0,redirectsUnresolved:0,redirectsRejected:0,resolverNonGoogleRequestsObserved:0,paaSourcesPreserved:0,aiOverviewLabelValidated:!1}}mergePaaSources(t=[],n=[]){let a=new Map;for(let i of[...t,...n]){let s=a.get(i.rawUrl);if(!s){a.set(i.rawUrl,i);continue}let o=i.resolutionStatus==="resolved"&&s.resolutionStatus!=="resolved"?i:s;a.set(i.rawUrl,{...o,title:o.title??s.title??i.title,site:o.site??s.site??i.site})}return[...a.values()]}normalizeAICitations(t,n){let a=new Set;return n.flatMap(i=>{let s=Fn(i.rawHref??i.href,t);if(!s||a.has(s.rawUrl))return[];a.add(s.rawUrl);let{url:o,...d}=s;return[{...d,text:i.text,href:o}]})}async resolveMaterialLinks(t,n,a,i,s){let o=Date.now(),d=[...n.flatMap(h=>h.sources??[]),...a,...i.citations.map(({text:h,href:w,...k})=>({...k,url:w})),...s.citations.map(({text:h,href:w,...k})=>({...k,url:w}))],l=new Map(d.map(h=>[h.rawUrl,h])),U=0,S=await zs(t,d,{onNetworkAudit:h=>{U=h.nonGoogleRequestsObserved}}),r=h=>({...h,...S.get(h.rawUrl)??h});for(let h of n){h.sources=(h.sources??[]).map(r);let w=h.sources[0];h.source_title=w?.title??h.source_title,h.source_site=w?.site??h.source_site,h.source_cite=w?.url??h.source_cite}for(let h=0;h<a.length;h++){let w=r(a[h]);if(w.resolvedUrl)try{w.domain=new URL(w.resolvedUrl).hostname.replace(/^www\./,"")}catch{}a[h]=w}let u=h=>{let w=r({url:h.href,rawUrl:h.rawUrl,resolvedUrl:h.resolvedUrl,linkType:h.linkType,resolutionStatus:h.resolutionStatus}),{url:k,...f}=w;return{...f,text:h.text,href:k}};i.citations=i.citations.map(u),s.citations=s.citations.map(u);let c=[...S.values()];this.linkDiagnostics={linkCandidatesObserved:l.size,plainLinksObserved:c.filter(h=>h.linkType==="plain").length,googleUrlRedirectsObserved:c.filter(h=>h.linkType==="google_url_redirect").length,googleGotoRedirectsObserved:c.filter(h=>h.linkType==="google_goto_redirect").length,redirectsResolved:c.filter(h=>h.linkType!=="plain"&&h.resolutionStatus==="resolved").length,redirectsUnresolved:c.filter(h=>h.resolutionStatus==="unresolved").length,redirectsRejected:c.filter(h=>h.resolutionStatus==="rejected").length,resolverNonGoogleRequestsObserved:U,paaSourcesPreserved:n.reduce((h,w)=>h+(w.sources??[]).length,0),aiOverviewLabelValidated:i.detected},this.phaseTimings.linkResolutionMs=(this.phaseTimings.linkResolutionMs??0)+(Date.now()-o)}normalizeQuestion(t){return t.toLowerCase().replace(/[^\w\s]/g,"").replace(/\s+/g," ").trim()}throwIfAborted(t){if(t?.aborted)throw t.reason instanceof DOMException&&t.reason.name==="TimeoutError"?t.reason:new pt}async throwIfCaptcha(t,n){if(await t.locator(X.captchaMarker).count().catch(()=>0)>0)throw new it(`${n} returned a CAPTCHA \u2014 retrying with a fresh session.`)}async extractVisibleItems(t,n){let a=X,i=await t.evaluate(({selectors:o,onlyQuestion:d,answerPlaceholderPattern:l})=>{function U(r){if(!r)return"";let u=[];for(let c of r.childNodes)if(c.nodeType===Node.TEXT_NODE){let h=c.textContent?.trim();h&&u.push(h)}else{if(c.tagName==="STYLE"||c.tagName==="SCRIPT")continue;{let h=U(c);h&&u.push(h)}}return u.join(" ").replace(/\s+/g," ").trim()}function S(r){return(r??"").replace(/\s*\(\+\d+\)\s*-\s*View related links.*$/i,"").replace(/\s*-\s*Opens in new tab.*$/i,"").trim()}return Array.from(document.querySelectorAll(o.item)).filter(r=>!d||(r.getAttribute(o.itemDataQ)||r.getAttribute(o.itemDataInitQ)||r.querySelector(o.itemQuestionEl)?.innerText?.trim()||"")===d).map(r=>{let u=r.querySelector(o.clickTarget),c=r.classList.contains(o.expandedClass)||u?.getAttribute("aria-expanded")==="true",h=r.querySelector(o.answerContainer),k=h?.querySelector(o.aiAnswerBody)??h,f=U(k),m=new RegExp(l,"i").test(f),L=[...Array.from((k??r).querySelectorAll("a[href]")),...Array.from(r.querySelectorAll(o.aiCitation)),...Array.from(r.querySelectorAll(o.aiSourceCard))],R=!m&&(c&&f.length>=10||f.length>30&&L.some(H=>/^https?:\/\//.test(H.href))),D=R&&r.querySelector(o.sourceTitle)?.innerText?.trim()||void 0,_=R&&r.querySelector(o.sourceSite)?.innerText?.trim()||void 0,M=[];if(R){let H=new Set;for(let y of L)!/^https?:\/\//.test(y.href)||H.has(y.href)||(H.add(y.href),M.push({title:S(y.getAttribute("aria-label"))||(y.textContent||"").trim(),rawHref:y.href}));let P=M.find(y=>y.title.length>2)??M[0];P&&(D=D||P.title||void 0)}return{googleLinkId:r.getAttribute("data-lk")||r.querySelector("[data-lk]")?.getAttribute("data-lk")||null,googleEvidenceId:r.getAttribute("data-ved")||r.querySelector("[data-ved]")?.getAttribute("data-ved")||null,question:r.getAttribute(o.itemDataQ)||r.getAttribute(o.itemDataInitQ)||r.querySelector(o.itemQuestionEl)?.innerText?.trim()||"",answer:R&&f||void 0,sourceTitle:D,sourceSite:_,sources:M}})},{selectors:a,onlyQuestion:n,answerPlaceholderPattern:$s}),s=typeof t.url=="function"?t.url():"https://www.google.com/";return i.flatMap(o=>{let d=[],l=new Set;for(let u of o.sources){let c=Fn(u.rawHref,s);if(!c||l.has(c.rawUrl))continue;l.add(c.rawUrl);let h=o.sourceSite??null;try{h||=new URL(c.resolvedUrl??c.rawUrl).hostname.replace(/^www\./,"")}catch{}d.push({...c,title:u.title||o.sourceTitle||null,site:h})}let U=d[0],S={questionId:ee(o.question),googleLinkId:o.googleLinkId,googleEvidenceId:o.googleEvidenceId,question:o.question,answer:Ds(o.answer,o.question,o.sourceTitle),sourceTitle:U?.title??o.sourceTitle,sourceSite:U?.site??o.sourceSite,sourceCite:U?.url,sources:d},r=ci.safeParse(S);return r.success?[r.data]:(console.warn("[PAAExtractor] item parse failed:",o.question,r.error.issues[0]?.message),[])})}jitteredDelayMs(t,n){return t+Math.floor(Math.random()*(n-t+1))}async clickItem(t,n){try{await t.locator(`${X.item}[data-q="${n}"], ${X.item}[data-initq="${n}"]`).first().click()}catch{}}toFlatRow(t,n,a,i){return{seed_query:i,question_id:t.questionId??ee(t.question),google_link_id:t.googleLinkId??"",google_evidence_id:t.googleEvidenceId??"",question:t.question,answer:t.answer??"",source_title:t.sourceTitle??"",source_site:t.sourceSite??"",source_cite:t.sourceCite??"",sources:t.sources??[],depth:n,parent_question:a??"",extracted_at:new Date().toISOString()}}upsertCollectedRow(t){let n=this.normalizeQuestion(t.question),a=this.collectedRows.findIndex(d=>this.normalizeQuestion(d.question)===n);if(a<0)return this.collectedRows.push({...t}),!0;let i=this.collectedRows[a],s={...i,...t,answer:t.answer||i.answer,source_title:t.source_title||i.source_title,source_site:t.source_site||i.source_site,source_cite:t.source_cite||i.source_cite,sources:this.mergePaaSources(i.sources,t.sources),extracted_at:t.extracted_at||i.extracted_at},o=s.answer!==i.answer||s.source_title!==i.source_title||s.source_site!==i.source_site||s.source_cite!==i.source_cite||JSON.stringify(s.sources)!==JSON.stringify(i.sources);return o&&(this.collectedRows[a]=s),o}async emitProgress(t){if(!this.onPaaProgress||this.collectedRows.length===0&&!this.checkpointMaterial)return;let n={sequence:++this.progressSequence,observedAt:new Date().toISOString(),clickedQuestions:[...this.clickedQuestions],phase:t,records:this.collectedRows.map(a=>({...a})),lifecycle:{...this.paaLifecycle},...this.checkpointMaterial?{material:structuredClone(this.checkpointMaterial)}:{},interactions:this.interactionObservations.map(a=>({...a,confirmationSignals:[...a.confirmationSignals]}))};try{await this.onPaaProgress(n)}catch(a){console.warn(JSON.stringify({event:"paa_progress_sink_failed",sequence:n.sequence,phase:n.phase,message:a instanceof Error?a.message:String(a)}))}}getPartialResult(){let t=this.partialContext;if(!t||this.collectedRows.length===0&&!this.checkpointMaterial)return null;let n=this.collectedRows.map(d=>({...d})),a=this.checkpointMaterial,i=t.questionsOnly?0:n.filter(d=>!d.answer?.trim()).length,s=t.questionsOnly?0:n.filter(d=>(d.sources??[]).length===0).length,o={seed:t.seed,totalQuestions:n.length,maxDepthReached:n.reduce((d,l)=>Math.max(d,l.depth),0),durationMs:Date.now()-t.startMs,errorCount:0};return{seed:t.seed,location:t.location,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(t.startMs),completionStatus:"paa_found",problem:null,...a?.pagination?{pagination:{...a.pagination}}:{},resultQuality:"partial",degradedResult:!1,retryRecommended:!0,paaLifecycle:{...this.paaLifecycle,questionsFound:n.length,targetStatus:n.length>=(t.maxQuestions??0)?"met":"not_met",discoveryStatus:"interrupted",materialStatus:i>0||s>0?"partial":"complete",completionReason:"The browser attempt ended before frontier exhaustion could be proven."},completeness:{...this.completeness,paaWithoutAnswer:i,paaWithoutSource:s,paaRequested:t.maxQuestions,paaReturned:n.length,paaUnique:n.length},warnings:[{code:"paa_partial",surface:"paa",message:`Harvest stopped before finishing; returning the ${n.length} question(s) collected up to that point.`,retryable:!0}]},totalQuestions:n.length,surface:a?.surface??"web",aiOverview:a?.aiOverview??{detected:!1,text:null,citations:[]},aiMode:a?.aiMode??{detected:!1,text:null,citations:[]},whatPeopleSaying:a?.whatPeopleSaying??[],tree:this.buildTree(n,t.seed),flat:n,videos:a?.videos??[],forums:a?.forums??[],organicResults:a?.organicResults??[],localPack:a?.localPack??[],entityIds:a?.entityIds??{entities:[],kgIds:[],cids:[],gcids:[]},stats:o}}async runBFS(t,n,a){await t.waitForTimeout(700);let i=new Set,s=new Set,o=[];this.clickedQuestions=new Set,this.interactionObservations=[],this.phaseTimings={};let d=new Set,l=new Map,U=new Set,S=new Set,r=new Map,u=2,c=3,h=0,w={sel:X.item,dataQ:X.itemDataQ,dataInitQ:X.itemDataInitQ,questionEl:X.itemQuestionEl,answerSel:X.answerContainer,expandedClass:X.expandedClass,clickTarget:X.clickTarget,answerPlaceholderPattern:$s,questionsOnly:n.questionsOnly,sourceSel:"a[href]"},k=()=>t.evaluate(({sel:_,dataQ:M,dataInitQ:H,questionEl:P,expandedClass:y,clickTarget:E,answerSel:p,answerPlaceholderPattern:T,questionsOnly:N})=>{let I=W=>{if(!W)return"";let x=[];for(let O of W.childNodes){if(O.nodeType===Node.TEXT_NODE){let st=O.textContent?.trim();st&&x.push(st);continue}if(O.nodeType!==Node.ELEMENT_NODE)continue;let j=O;if(j.tagName==="STYLE"||j.tagName==="SCRIPT"||j.getAttribute("aria-hidden")==="true")continue;let ct=I(j);ct&&x.push(ct)}return x.join(" ").replace(/\s+/g," ").trim()};return Array.from(document.querySelectorAll(_)).map((W,x)=>{let O=I(W.querySelector(p)).replace(/An AI Overview is not available for this search/gi," ").replace(/Can't generate an AI overview right now\.?\s*Try again later\.?/gi," ").replace(/\bAI Overview\b/gi," ").replace(/\s+/g," ").trim(),j=W.classList.contains(y)||W.querySelector(E)?.getAttribute("aria-expanded")==="true",ct=O.length>=10&&!new RegExp(T,"i").test(O);return{q:W.getAttribute(M)||W.getAttribute(H)||W.querySelector(P)?.innerText?.trim()||"",done:j&&(N||ct),expanded:j,index:x}}).filter(W=>W.q)},w),f=async(_,M,H,P,y,E)=>{let p=Date.now(),T={id:`${E}:${ee(_)}:${y}`,questionId:ee(_),question:_,batchNumber:E,controlAttempt:y,observedAt:new Date(p).toISOString(),beforeQuestionCount:M,expandedBefore:P},N=H>=0?t.locator(w.sel).nth(H).locator(w.clickTarget):null,I=null,W=N?await(async()=>(P&&(await N.click({timeout:Qs,force:!0}),await t.waitForTimeout(120)),await N.click({timeout:Qs,force:!0}),!0))().catch(G=>(I=G instanceof Error&&(G.name==="TimeoutError"||/timeout/i.test(G.message))?"click_ack_timeout":"click_failed",!1)):!1,x=Date.now()-p;if(!W&&I!=="click_ack_timeout")return{dispatched:!1,confirmed:!1,observation:{...T,dispatched:!1,outcome:"dispatch_failed",confirmationSignals:[],confirmationCheckpointMs:null,confirmedAtMs:null,dispatchDurationMs:x,totalDurationMs:x,afterQuestionCount:M,newQuestionCount:0,expandedAfter:P,answerObserved:!1,sourceCount:0,errorCode:H<0?"control_missing":I??"click_failed"}};let O={exists:!0,expanded:P,answerReady:!1,sourceCount:0,questionCount:M},j=[],ct=null,st=null,q=!1;for(let G of[ol,rl,dl]){let Tt=p+G-Date.now();if(Tt>0&&await t.waitForTimeout(Tt),O=await t.evaluate(({sel:V,dataQ:et,dataInitQ:J,questionEl:Q,expandedClass:wt,clickTarget:kt,answerSel:rn,answerPlaceholderPattern:se,sourceSel:dn,target:Be})=>{let ln=re=>{if(!re)return"";let ta=[];for(let Un of re.childNodes){if(Un.nodeType===Node.TEXT_NODE){let Ui=Un.textContent?.trim();Ui&&ta.push(Ui);continue}if(Un.nodeType!==Node.ELEMENT_NODE)continue;let un=Un;if(un.tagName==="STYLE"||un.tagName==="SCRIPT"||un.getAttribute("aria-hidden")==="true")continue;let Si=ln(un);Si&&ta.push(Si)}return ta.join(" ").replace(/\s+/g," ").trim()},oe=Array.from(document.querySelectorAll(V)),Sn=oe.find(re=>(re.getAttribute(et)||re.getAttribute(J)||re.querySelector(Q)?.innerText?.trim())===Be);if(!Sn)return{exists:!1,expanded:!1,answerReady:!1,sourceCount:0,questionCount:oe.length};let Lo=Sn.classList.contains(wt)||Sn.querySelector(kt)?.getAttribute("aria-expanded")==="true",ri=Sn.querySelector(rn),di=ln(ri).replace(/An AI Overview is not available for this search/gi," ").replace(/Can't generate an AI overview right now\.?\s*Try again later\.?/gi," ").replace(/\bAI Overview\b/gi," ").replace(/\s+/g," ").trim(),li=di.length>=10&&!new RegExp(se,"i").test(di);return{exists:!0,expanded:Lo,answerReady:li,sourceCount:li?ri?.querySelectorAll(dn).length??0:0,questionCount:oe.length}},{...w,target:_}).catch(()=>O),j=[...O.expanded?["expanded"]:[],...O.answerReady?["answer"]:[],...O.sourceCount>0?["source"]:[],...O.questionCount>M?["question_growth"]:[]],O.answerReady||O.sourceCount>0||O.questionCount>M){q=!0,ct=G,st=Date.now()-p;break}}let ht=Date.now()-p,He={...T,dispatched:W,outcome:q?"confirmed":W?"unconfirmed":"dispatch_failed",confirmationSignals:j,confirmationCheckpointMs:ct,confirmedAtMs:st,dispatchDurationMs:x,totalDurationMs:ht,afterQuestionCount:O.questionCount,newQuestionCount:Math.max(0,O.questionCount-M),expandedAfter:O.expanded,answerObserved:O.answerReady,sourceCount:O.sourceCount,errorCode:W?q?null:O.exists?"confirmation_timeout":"control_missing":I};return{dispatched:W,confirmed:q,observation:He}},m=0;t:for(;;){if(n.softDeadlineMs&&Date.now()>=n.softDeadlineMs)throw this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"interrupted",completionReason:"The execution deadline arrived before frontier exhaustion could be proven."},new Qt(this.paaLifecycle.completionReason);this.throwIfAborted(a);let _=await k(),M=!1;for(let p of _)s.has(p.q)||(s.add(p.q),o.push(p.q),o.length<=n.maxQuestions&&(M=this.upsertCollectedRow(this.toFlatRow({questionId:ee(p.q),googleLinkId:null,googleEvidenceId:null,question:p.q,sources:[]},1,null,n.query))||M)),p.done&&U.add(p.q);if(this.paaLifecycle={...this.paaLifecycle,questionsFound:Math.min(o.length,n.maxQuestions),targetStatus:o.length>=n.maxQuestions?"met":"not_met",knownQuestions:o.length,processedQuestions:U.size,failedInteractions:S.size,visibleControls:_.length},M&&await this.emitProgress("discovered"),n.questionsOnly&&s.size>=n.maxQuestions){this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"target_reached",targetStatus:"met",completionReason:"The requested unique-question count was observed."};break}if(!n.questionsOnly&&s.size>=n.maxQuestions){let p=!1,T=new Set(o.slice(0,n.maxQuestions));for(let N of await this.extractVisibleItems(t)){if(!T.has(N.question))continue;let I=r.get(N.question),W={...N,answer:N.answer??I?.answer,sourceTitle:N.sourceTitle??I?.sourceTitle,sourceSite:N.sourceSite??I?.sourceSite,sourceCite:N.sourceCite??I?.sourceCite,sources:this.mergePaaSources(I?.sources,N.sources)};r.set(N.question,W),p=this.upsertCollectedRow(this.toFlatRow(W,1,null,n.query))||p}if(p&&await this.emitProgress("answer_captured"),[...T].every(N=>{let I=r.get(N);return!!(I?.answer?.trim()&&I.sources.length>0)})){S.clear(),this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"target_reached",targetStatus:"met",failedInteractions:0,completionReason:"The requested unique-question count and its answer/source material were observed."};break}}let H=new Set(o.slice(0,n.maxQuestions)),P=_.filter(p=>H.has(p.q)&&!p.done&&(l.get(p.q)??0)<u&&!d.has(p.q)),y=P.slice(-ll);if(this.paaLifecycle={...this.paaLifecycle,eligibleControls:P.length},y.length===0){if(s.size>=n.maxQuestions){this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"target_reached",targetStatus:"met",completionReason:"The requested unique-question count was observed."};break}let p=new Set(_.map(N=>N.q)),T=o.slice(0,n.maxQuestions).filter(N=>!U.has(N)&&(S.has(N)||!p.has(N)));if(T.length>0)throw this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"interrupted",failedInteractions:new Set([...S,...T]).size,completionReason:"At least one known PAA control failed or disappeared before it could be confirmed."},await this.emitProgress("expansion_finished"),new Qt(this.paaLifecycle.completionReason);for(let N=1;N<=c;N++){this.throwIfAborted(a),await this.throwIfCaptcha(t,"Google PAA exhaustion confirmation"),await t.mouse.wheel(0,320);let I=await t.waitForFunction(({sel:x,min:O})=>document.querySelectorAll(x).length>O,{sel:X.item,min:_.length},{timeout:1500,polling:100}).catch(()=>null);if(this.paaLifecycle={...this.paaLifecycle,noGrowthConfirmations:N},I||(await k()).some(x=>!s.has(x.q)))continue t}this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"frontier_exhausted",targetStatus:"not_met",failedInteractions:0,noGrowthConfirmations:c,completionReason:"Every known eligible PAA control was processed and three healthy no-growth confirmations found no additional questions."};break}await this.throwIfCaptcha(t,"Google PAA expansion"),h+=1;for(let p of y){if(this.reporter.onDepth(++m),(l.get(p.q)??0)>0){let T=this.paaLifecycle.retryBreakdown.controlRetries+1;this.paaLifecycle={...this.paaLifecycle,automaticRetries:T+this.paaLifecycle.retryBreakdown.browserRetries+this.paaLifecycle.retryBreakdown.runtimeRecoveries,retryBreakdown:{...this.paaLifecycle.retryBreakdown,controlRetries:T}}}l.set(p.q,(l.get(p.q)??0)+1)}let E=await Promise.all(y.map(async p=>({target:p,result:await f(p.q,_.length,p.index,p.expanded,l.get(p.q)??1,h)})));for(let{target:p,result:T}of E)(T.dispatched||T.confirmed)&&this.clickedQuestions.add(p.q),this.interactionObservations.push(T.observation);if(this.interactionObservations.length>Zs&&this.interactionObservations.splice(0,this.interactionObservations.length-Zs),!n.questionsOnly){let p=new Set(y.map(T=>T.q));for(let T of await this.extractVisibleItems(t))p.has(T.question)&&(r.set(T.question,T),this.upsertCollectedRow(this.toFlatRow(T,1,null,n.query))&&await this.emitProgress("answer_captured"))}for(let{target:p,result:T}of E){let N=r.get(p.q);T.confirmed||N?.answer?.trim()?(U.add(p.q),S.delete(p.q)):(l.get(p.q)??0)>=u&&(S.add(p.q),d.add(p.q))}this.paaLifecycle={...this.paaLifecycle,processedQuestions:U.size,failedInteractions:S.size,noGrowthConfirmations:0,dispatchedInteractions:this.interactionObservations.filter(p=>p.dispatched).length,confirmedInteractions:this.interactionObservations.filter(p=>p.outcome==="confirmed").length,unconfirmedInteractions:this.interactionObservations.filter(p=>p.outcome!=="confirmed").length},await this.emitProgress("click_observed")}let L=n.questionsOnly?new Map:new Map(r);n.questionsOnly||await this.fillIncompleteItems(t,o,L,n,d);let R=[];for(let _ of o){if(R.length>=n.maxQuestions)break;let M=this.normalizeQuestion(_);if(i.has(M))continue;i.add(M);let H=L.get(_);if(H){let P=this.toFlatRow(H,1,null,n.query);this.upsertCollectedRow(P),R.push(P),this.reporter.onQuestion({questionId:H.questionId,googleLinkId:H.googleLinkId,googleEvidenceId:H.googleEvidenceId,question:H.question,answer:H.answer??null,sourceTitle:H.sourceTitle??null,sourceSite:H.sourceSite??null,sourceCite:H.sourceCite??null,sources:H.sources,depth:1,parentQuestion:null,children:[]})}else{let P=this.toFlatRow({questionId:ee(_),googleLinkId:null,googleEvidenceId:null,question:_,answer:void 0,sourceTitle:void 0,sourceSite:void 0,sourceCite:void 0,sources:[]},1,null,n.query);this.upsertCollectedRow(P),R.push(P)}}this.completeness.paaWithoutAnswer=n.questionsOnly?0:R.filter(_=>!_.answer).length,this.completeness.paaWithoutSource=n.questionsOnly?0:R.filter(_=>(_.sources??[]).length===0).length,this.completeness.paaRequested=n.maxQuestions,this.completeness.paaReturned=R.length,this.completeness.paaUnique=i.size;let D=!n.questionsOnly&&(this.completeness.paaWithoutAnswer>0||this.completeness.paaWithoutSource>0);return this.paaLifecycle={...this.paaLifecycle,questionsFound:R.length,targetStatus:R.length>=n.maxQuestions?"met":"not_met",materialStatus:D?"partial":"complete",processedQuestions:U.size,failedInteractions:S.size},await this.emitProgress("fill_incomplete"),await this.emitProgress("expansion_finished"),R}async fillIncompleteItems(t,n,a,i,s){let o=new Set(n.slice(0,i.maxQuestions)),d=S=>!S?.answer||(S.sources??[]).length===0,l=new Set([...o].filter(S=>d(a.get(S)))),U=new Set([...l].filter(S=>!a.get(S)?.answer));if(l.size!==0){for(let S of l){if(i.softDeadlineMs&&Date.now()>=i.softDeadlineMs)break;let r=(await this.extractVisibleItems(t,S))[0];if(!r)continue;let u=a.get(S);a.set(S,{...r,answer:r.answer??u?.answer,sourceTitle:r.sourceTitle??u?.sourceTitle,sourceSite:r.sourceSite??u?.sourceSite,sourceCite:r.sourceCite??u?.sourceCite,sources:this.mergePaaSources(u?.sources,r.sources)});let c=a.get(S);c&&this.upsertCollectedRow(this.toFlatRow(c,1,null,i.query))&&await this.emitProgress("fill_incomplete")}this.completeness.paaAnswersRecovered=[...U].filter(S=>a.get(S)?.answer).length}}async reExpandCollapsedItems(t){let n=`${X.item}:not(.${X.expandedClass}) ${X.clickTarget}`,a=await t.locator(n).count().catch(()=>0);if(a===0)return!1;for(let i=0;i<a;i++)try{let s=t.locator(n).first();await s.scrollIntoViewIfNeeded(),await s.click({force:!0}),await t.waitForTimeout(this.jitteredDelayMs(300,500))}catch{}return!0}async extractVideos(t){let n=es;return t.evaluate(a=>{let i=[],s=Array.from(document.querySelectorAll(a.container));for(let o of s){let U=(o.querySelector(a.sectionHeading)?.textContent?.trim()??"").toLowerCase().includes("short")?"short_video":"video",S=Array.from(o.querySelectorAll(a.item));for(let r of S){let u=r.href;if(!u||!u.includes("youtube")&&!u.includes("youtu.be"))continue;let c=r.textContent?.trim()??"",h=c.indexOf("YouTube");if(h===-1)continue;let w=c.slice(0,h).trim(),f=c.slice(h+7).replace(/^[·\s·]+/,"").match(/^([^·\n]+)/),m=f?f[1].trim():"";w&&i.push({type:U,title:w,channel:m,platform:"YouTube",duration:"",url:u})}}return i},n)}async extractForums(t){let n=ns;return t.evaluate(a=>{let i=[],o=Array.from(document.querySelectorAll(a.section)).find(l=>l.textContent?.includes("Discussions"));if(!o)return i;let d=Array.from(o.querySelectorAll(a.item));for(let l of d){let U=l.href;if(!U)continue;let S=l.querySelector(a.title),r=l.querySelector(a.source),u=S?.textContent?.trim()??"",c=r?.textContent?.trim()??"";u&&i.push({title:u,source:c,url:U})}return i},n)}async extractShortVideos(t,n){try{await t.goto(n,{waitUntil:"domcontentloaded"}),await t.waitForTimeout(1500)}catch{return[]}await this.throwIfCaptcha(t,"Google short video search");let a={item:En.item,platforms:[...En.platforms]};return(await t.evaluate(s=>{let o=new Set,d=[],l=Array.from(document.querySelectorAll(s.item)),U=["youtube.com","youtu.be","tiktok.com","instagram.com","facebook.com","fb.watch"],S=new Map;for(let r of l){let u=r.href;if(!u||!U.some(h=>u.includes(h)))continue;let c=r.textContent?.trim()??"";S.has(u)||S.set(u,[]),S.get(u).push(c)}for(let[r,u]of S.entries()){if(o.has(r))continue;o.add(r);let c=u.find(m=>/^\d+:\d+$/.test(m))??"",h=u.find(m=>!/^\d+:\d+$/.test(m)&&m.length>5)??"";if(!h)continue;let w=h,k="",f="";for(let m of s.platforms){let L=-1,R=0;for(;;){let P=h.indexOf(m,R);if(P===-1)break;L=P,R=P+1}if(L===-1)continue;let D=h.slice(L+m.length);if(!(/^[\s·]/.test(D)||D.trim()===""))continue;w=h.slice(0,L).trim(),k=m;let M=D.replace(/^[\s·]+/,""),H=M.indexOf("\xB7");f=(H===-1?M:M.slice(0,H)).trim();break}w&&d.push({title:w,channel:f,platform:k,duration:c,url:r})}return d},a)).map(s=>({type:"short_video",...s}))}async extractWhatPeopleSaying(t){let n=as;return t.evaluate(a=>{let i=Array.from(document.querySelectorAll(a.sectionTag)).find(s=>s.textContent?.includes(a.sectionHeadingText))??document.querySelector(".yG4QQe.TBC9ub.NbhJ1c");return i?Array.from(i.querySelectorAll(a.card)).map(s=>{let d=s.querySelector(a.cardLink)?.href??"",l=s.querySelector(a.titleH1)?.textContent?.trim(),U=s.querySelector(a.titleDiv)?.textContent?.trim(),S=l??U??"",r=s.querySelector(a.source)?.textContent?.trim()??"",c=s.querySelector(a.platformBadge)?.textContent?.trim()??"",h=s.querySelector(a.ytChannel)?.textContent?.trim()??"",w=s.querySelector(a.ytDate)?.textContent?.trim()??"",k=s.querySelector(a.authorNote)?.textContent?.trim()??null,f=s.querySelector(a.popularCommentLabel),m=null;if(f){let I=f.nextSibling;for(;I;){let W=I.textContent?.trim();if(W){m=W;break}I=I.nextSibling}}let L=Array.from(s.querySelectorAll("span")),R=L.find(I=>/^\d+:\d+$/.test(I.textContent?.trim()??""))?.textContent?.trim()??null,_=L.map(I=>I.textContent?.trim()??"").filter(I=>/\d/.test(I)&&(I.includes("comment")||I.includes("reaction")||I.includes("view")||I.includes("like")||I.includes("share")))[0]??"",M=L.map(I=>I.textContent?.trim()??"").filter(I=>/\d+ (day|week|month|year|hour)s? ago|Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec/.test(I)),H=w||(M[0]??""),P=c||(h?"YouTube":""),y=h||r,E="unknown",p=P.toLowerCase(),T=y.toLowerCase(),N=r.toLowerCase();return p.includes("reddit")||T.startsWith("r/")?E="reddit":p.includes("facebook")||N.includes("facebook")?E="facebook":p.includes("instagram")||N.includes("instagram")?E="instagram":p.includes("tiktok")||N.includes("tiktok")?E="tiktok":p.includes("youtube")||h?E="youtube":E="news",{type:E,title:S,url:d,source:y,platform:P,popularComment:m,engagement:_,date:H,duration:R,authorNote:k}}):[]},n)}async extractOrganicResults(t){let n=os,a=await t.evaluate(s=>{let o=[],d=0;return document.querySelectorAll(s.result).forEach(l=>{let U=l.querySelector(s.title);if(!U)return;let S=U.textContent?.trim()??"",u=U.closest("a")?.href??"";if(!S||!u)return;d++;let c=l.querySelector(s.cite)?.textContent?.trim()??null,h=l.querySelector(s.snippet)?.textContent?.trim()??null,w=!!l.querySelector(s.redditCite),k=l.querySelector(s.ratingWrap),f=k?{value:k.querySelector(s.ratingValue)?.textContent?.trim()??"",count:k.querySelector(s.reviewCount)?.textContent?.trim()??""}:null,m="";try{m=new URL(u).hostname.replace(/^www\./,"")}catch{m=l.querySelector(s.siteName)?.textContent?.trim()??""}o.push({position:d,title:S,url:u,domain:m,cite:c,snippet:h,isRedditStyle:w,inlineRating:f})}),o},n),i=typeof t.url=="function"?t.url():"https://www.google.com/";return a.flatMap(s=>{let o=Fn(s.url,i);if(!o)return[];let d=s.domain;try{d=new URL(o.resolvedUrl??o.rawUrl).hostname.replace(/^www\./,"")}catch{}return[{...s,...o,domain:d}]})}async extractLocalPack(t){let n=rs;return t.evaluate(a=>{let i=[],s=null;return document.querySelectorAll('[role="heading"]').forEach(o=>{!s&&o.textContent?.includes(a.headingText)&&(s=o.closest("[data-hveid]"))}),s&&s.querySelectorAll(a.card).forEach((o,d)=>{let l=o.querySelector(a.name)?.textContent?.trim()??"";if(!l)return;let U=o.querySelector(a.ratingValue)?.textContent?.trim()??null,S=o.querySelector(a.reviewCount)?.textContent?.trim()??null,r=S?S.replace(/[()]/g,"").trim():null,u=o.querySelector("a[data-cid]")?.getAttribute("data-cid")??null;if(!u)for(let f of Array.from(o.querySelectorAll("a[href]"))){let m=f.href.match(/[?&]cid=(\d+)/);if(m){u=m[1];break}let L=f.href.match(/!1s0x[0-9a-f]+:0x([0-9a-f]+)/i);if(L){try{u=BigInt("0x"+L[1]).toString()}catch{}if(u)break}}let c=[];o.querySelectorAll("div, span").forEach(f=>{let m=Array.from(f.childNodes).filter(L=>L.nodeType===3).map(L=>L.textContent?.trim()??"").filter(L=>L.length>1&&L.length<120).join(" ");m&&!c.includes(m)&&c.push(m)});let h=Array.from(o.querySelectorAll("a[href]")),w=h.find(f=>f.href.includes("google.com/maps"))?.href??null,k=h.find(f=>!f.href.includes("google.com")&&f.href.startsWith("http"))?.href??null;i.push({position:d+1,name:l,cid:u,rating:U,reviewCount:r,metadata:c,websiteUrl:k,directionsUrl:w})}),i},n)}async extractEntityIds(t){return t.evaluate(()=>{let n=new Set,a=new Set,i=new Set,s=new Map;function o(l){let U=[".OSrXXb",".dbg0pd",".tzt0oe",'[role="heading"]',"h3"];for(let S of U){let r=l.querySelector(S);if(r?.textContent?.trim())return r.textContent.trim()}return""}document.querySelectorAll('[id^="pv-/g/"]').forEach(l=>{let U=l.getAttribute("id");if(!U)return;let S=U.replace("pv-","");n.add(S);let r=o(l),c=l.querySelector("a[data-cid]")?.getAttribute("data-cid")??null;c&&a.add(c),r&&s.set(S,{name:r,kgId:S,cid:c,gcid:null})}),document.querySelectorAll("[data-mid]").forEach(l=>{let U=l.getAttribute("data-mid");if(U?.startsWith("/g/")&&(n.add(U),!s.has(U))){let S=o(l);S&&s.set(U,{name:S,kgId:U,cid:null,gcid:null})}}),document.querySelectorAll(".w7Dbne").forEach(l=>{let S=l.querySelector("a[data-cid]")?.getAttribute("data-cid")??null;if(!S)return;a.add(S);let r=l.querySelector(".OSrXXb")?.textContent?.trim()??"";if(!r)return;let u=l.querySelector('[id^="pv-/g/"]'),c=u?u.getAttribute("id").replace("pv-",""):null,h=c??`cid:${S}`;if(s.has(h)){let w=s.get(h);w.cid||s.set(h,{...w,cid:S})}else s.set(h,{name:r,kgId:c,cid:S,gcid:null})}),document.querySelectorAll("a[data-cid]").forEach(l=>{let U=l.getAttribute("data-cid");if(!U)return;if(a.add(U),![...s.values()].some(r=>r.cid===U)){let r=l.parentElement,u="";for(let c=0;c<8&&r;c++){let h=r.querySelector('.OSrXXb, .dbg0pd, [role="heading"], h3');if(h?.textContent?.trim()){u=h.textContent.trim();break}r=r.parentElement}u&&s.set(`cid:${U}`,{name:u,kgId:null,cid:U,gcid:null})}});let d=Array.from(document.querySelectorAll("script:not([src])")).map(l=>l.textContent??"").filter(l=>l.length>1e4).join(`
|
|
21896
|
-
`);for(let l of d.matchAll(/\/g\/[a-zA-Z0-9_-]{5,20}/g))n.add(l[0]);for(let l of d.matchAll(/gcid:[a-zA-Z0-9_]+/g))i.add(l[0]);for(let l of d.matchAll(/0x[0-9a-f]+:0x([0-9a-f]+)/gi))try{a.add(BigInt("0x"+l[1]).toString())}catch{}return{entities:[...s.values()],kgIds:[...n],cids:[...a],gcids:[...i]}})}mergeLocalPackIntoEntities(t,n){let a=new Set(t.cids),i=t.entities.map(s=>({...s}));for(let s of n){if(!s.cid)continue;a.add(s.cid);let o=s.name.toLowerCase().trim(),d=i.find(l=>l.name.toLowerCase().trim()===o);d?d.cid||(d.cid=s.cid):i.find(l=>l.cid===s.cid)||i.push({name:s.name,kgId:null,cid:s.cid,gcid:null})}return{...t,entities:i,cids:[...a]}}async extractAISurfaces(t,n){let a=await t.evaluate(Fs,{aio:is,aim:ss,expandWaitMs:1500}),i=typeof t.url=="function"?t.url():"https://www.google.com/",s={surface:a.surface,aiOverview:{...a.aiOverview,citations:this.normalizeAICitations(i,a.aiOverview.citations)},aiMode:{...a.aiMode,citations:this.normalizeAICitations(i,a.aiMode.citations)}};if(!s.aiOverview.detected)return this.completeness.aioShareCaptured=null,s;let o=this.aioShareUrlEarly??await this.captureAIOverviewShareUrl(t,n).catch(()=>null);return this.completeness.aioShareCaptured=o!==null,{...s,aiOverview:{...s.aiOverview,shareUrl:o}}}async captureAIOverviewShareUrl(t,n){if(n?.softDeadlineMs&&Date.now()>=n.softDeadlineMs||!await t.evaluate(()=>{let s=Array.from(document.querySelectorAll('h1,h2,h3,[role="heading"],div')).filter(o=>(o.textContent||"").trim()==="AI Overview");for(let o of s){let d=o;for(let l=0;l<8&&d;l++){let U=d.querySelector('[aria-label="Share"]');if(U)return U.scrollIntoView({block:"center"}),U.click(),!0;d=d.parentElement}}return!1}).catch(()=>!1))return null;let i=null;try{i=await(await t.waitForFunction(()=>{let o=document.createTreeWalker(document.body,NodeFilter.SHOW_TEXT);for(;o.nextNode();){let d=(o.currentNode.textContent||"").match(/https:\/\/share\.google\/aimode\/\S+/);if(d)return d[0]}return!1},void 0,{timeout:4500,polling:250})).jsonValue()}catch{i=null}return await t.keyboard.press("Escape").catch(()=>{}),i}buildTree(t,n){let a=[],i=new Map;for(let s of t){let o={questionId:s.question_id,googleLinkId:s.google_link_id||null,googleEvidenceId:s.google_evidence_id||null,question:s.question,answer:s.answer||null,sourceTitle:s.source_title||null,sourceSite:s.source_site||null,sourceCite:s.source_cite||null,sources:s.sources??[],depth:s.depth,parentQuestion:s.parent_question||null,children:[]};i.set(s.question,o)}for(let s of i.values())s.parentQuestion&&i.has(s.parentQuestion)?i.get(s.parentQuestion).children.push(s):a.push(s);return a}getBrowserDebugSnapshot(){return this.driver.getDebugSnapshot()}buildHarvestDebugSnapshot(t,n,a,i,s){if(t.debug)return{enabled:!0,request:{query:t.query,locationInput:t.location??null,canonicalLocation:n,locationResolved:s?s.matched:null,locationMatchSource:s?s.source:null,locationAmbiguousCandidates:s?s.ambiguousCandidates:null,uule:a,gl:t.gl,hl:t.hl,device:t.device,proxyMode:t.proxyMode,proxyZip:t.proxyZip??null,serpIdentity:t.serpIdentity??null,serpOnly:t.serpOnly,pages:t.pages??1},browser:this.getBrowserDebugSnapshot(),...i?{locationEvidence:i}:{}}}async captureSecondOrganicPage(t,n,a){if(this.throwIfAborted(a),!this.driver.withTemporaryPage)return{organic:[],status:"failed",failureCode:"unsupported_driver"};let i;try{let s=new URL(t.url()),o=U=>{try{let S=new URL(U,s);return s.origin==="https://www.google.com"&&S.origin===s.origin&&!S.username&&!S.password&&S.pathname==="/search"&&S.searchParams.getAll("q").length===1&&S.searchParams.get("q")===n.query&&S.searchParams.getAll("start").length===1&&S.searchParams.get("start")==="10"&&(!S.searchParams.has("num")||S.searchParams.get("num")==="10")&&["gl","hl"].every(r=>!S.searchParams.has(r)||S.searchParams.getAll(r).length===1&&S.searchParams.get(r)===n[r])&&["uule","tbs","udm","tbm","pws"].every(r=>S.searchParams.getAll(r).length<=1&&S.searchParams.get(r)===s.searchParams.get(r))}catch{return!1}},d=await t.evaluate(()=>document.querySelector('a#pnnext, a[rel="next"]')?.getAttribute("href")??null);if(!d)return{organic:[],status:"unavailable",failureCode:"missing_next"};if(!o(d))return{organic:[],status:"unavailable",failureCode:"invalid_next"};let l=await this.driver.withTemporaryPage(async U=>{if(await U.route("**/*",async S=>{let r=S.request();r.isNavigationRequest()&&r.frame()===U.mainFrame()&&!o(r.url())?(i=/^https:\/\/www\.google\.com\/sorry(?:\/|\?)/.test(r.url())?"captcha":"invalid_next",await S.abort("blockedbyclient")):await S.fallback()}),await U.goto(new URL(d,s).href,{waitUntil:"domcontentloaded",timeout:2e4}),this.throwIfAborted(a),await this.throwIfCaptcha(U,"Google SERP page 2"),!o(U.url()))throw i="invalid_next",new Error("Invalid pagination landing");return this.extractOrganicResults(U)},a);return this.throwIfAborted(a),l.length>0?{organic:l.map(U=>({...U,position:U.position+10})),status:"captured"}:{organic:[],status:"unavailable",failureCode:"empty_page"}}catch(s){if(this.throwIfAborted(a),s instanceof pt)throw s;return{organic:[],status:"failed",failureCode:i??(s instanceof it?"captcha":s instanceof Error&&(s.name==="TimeoutError"||/timed? ?out/i.test(s.message))?"timeout":"navigation_error")}}}async extract(t,n){let a=Date.now();this.completeness={paaWithoutAnswer:0,paaWithoutSource:0,paaAnswersRecovered:0,aioShareCaptured:null},this.linkDiagnostics=this.emptyLinkDiagnostics(),this.aioShareUrlEarly=null,this.collectedRows=[],this.progressSequence=0,this.checkpointMaterial=null,this.clickedQuestions=new Set,this.paaLifecycle=this.emptyPaaLifecycle(t.maxQuestions),this.partialContext={seed:t.query,location:t.location??null,startMs:a,maxQuestions:t.maxQuestions,questionsOnly:t.questionsOnly};let i=t.device==="mobile",s={headless:t.headless,profileDir:t.profileDir,proxy:t.proxy,kernelApiKey:t.kernelApiKey,kernelProxyId:t.kernelProxyId,kernelProfileName:t.kernelProfileName,kernelProfileSaveChanges:t.kernelProfileSaveChanges,kernelStealth:t.kernelStealth,kernelProxyResolution:t.kernelProxyResolution,proxyMode:t.proxyMode,keepDefaultProxy:t.keepDefaultProxy,requireUsEgress:t.requireUsEgress,viewport:i?{width:390,height:844}:{width:1280,height:800},locale:`${t.hl}-${t.gl.toUpperCase()}`,deviceScaleFactor:i?3:1,isMobile:i,hasTouch:i,debug:t.debug,operationDeadlineMs:t.softDeadlineMs},o=0,d=[];try{this.throwIfAborted(n);let l=Date.now();await this.driver.launch(s),this.phaseTimings.providerConnectMs=Date.now()-l;let U=this.driver.getProviderSessionMetadata();if(U?.providerSessionId&&this.onProviderSession)try{await this.onProviderSession(U)}catch(V){console.warn(JSON.stringify({event:"paa_provider_session_sink_failed",provider:U.provider,message:V instanceof Error?V.message:String(V)}))}this.throwIfAborted(n);let S=t.location?Da(t.location):null,r=t.location?S?.canonical??t.location:null,u=r?Os(r):null,c=t,h=t.includeAllSerpFeatures,w=h||t.includeLocalPack,k=h||t.includeForums,f=h||t.includeVideos,m=h||t.includeAiOverview,L=h||t.includeWhatPeopleSaying,R={surface:"web",aiOverview:{detected:!1,text:null,citations:[]},aiMode:{detected:!1,text:null,citations:[]}},D=Date.now(),{hasPaa:_}=await this.driver.navigateToSERP(c.query,u,t.gl,t.hl,{...De(t.recency)?{tbs:De(t.recency)}:{},debug:t.debug,purpose:t.serpOnly?"serp":"paa",...t.softDeadlineMs?{deadlineMs:t.softDeadlineMs}:{}});this.phaseTimings.navigationMs=Date.now()-D,this.throwIfAborted(n);let M=this.driver.getPage();if(await this.throwIfCaptcha(M,"Google SERP"),_||(this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"no_paa_observed",materialStatus:"complete",completionReason:"A readable Google SERP was observed without a People Also Ask block."}),t.questionsOnly){let V=Date.now(),et=_?await this.runBFS(M,c,n):[];this.phaseTimings.paaExpansionMs=Date.now()-V,await this.resolveMaterialLinks(M,et,[],R.aiOverview,R.aiMode);let J={seed:c.query,totalQuestions:et.length,maxDepthReached:et.reduce((Q,wt)=>Math.max(Q,wt.depth),0),durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(J),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:_?"paa_found":"no_paa",..._?{}:{noPaaObserved:!0},problem:null,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,void 0,S)}:{}},totalQuestions:et.length,surface:"web",aiOverview:{detected:!1,text:null,citations:[]},aiMode:{detected:!1,text:null,citations:[]},whatPeopleSaying:[],tree:this.buildTree(et,c.query),flat:et,videos:[],forums:[],organicResults:[],localPack:[],entityIds:{entities:[],kgIds:[],cids:[],gcids:[]},stats:J}}if(m&&(this.aioShareUrlEarly=await this.captureAIOverviewShareUrl(M,t).catch(()=>null)),t.serpOnly){let V=Date.now(),[et,J,Q]=await Promise.all([this.extractOrganicResults(M),w?this.extractLocalPack(M):Promise.resolve([]),this.extractEntityIds(M)]),wt=this.mergeLocalPackIntoEntities(Q,J),kt=m?await this.extractAISurfaces(M,t):R;this.phaseTimings.serpParseMs=Date.now()-V;let rn=t.debug?tn(r,et,J):void 0,se=et;if((t.pages??1)>=2){let Be=new URLSearchParams({q:c.query,gl:t.gl,hl:t.hl,pws:"0",start:"10"});De(t.recency)&&Be.set("tbs",De(t.recency)),u&&Be.set("uule",u),await this.driver.navigateTo("https://www.google.com/search?"+Be.toString()),await this.throwIfCaptcha(M,"Google SERP page 2");let ln=await this.extractOrganicResults(M);se=[...et,...ln.map(oe=>({...oe,position:oe.position+10}))],t.debug&&(rn=tn(r,se,J))}await this.resolveMaterialLinks(M,[],se,kt.aiOverview,kt.aiMode);let dn={seed:c.query,totalQuestions:0,maxDepthReached:0,durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(dn),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"serp_only",problem:null,completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,rn,S)}:{}},totalQuestions:0,surface:kt.surface,aiOverview:kt.aiOverview,aiMode:kt.aiMode,whatPeopleSaying:[],tree:[],flat:[],videos:[],forums:[],organicResults:se,localPack:J,entityIds:wt,stats:dn}}let[H,P,y,E,p,T]=await Promise.all([f?this.extractVideos(M):Promise.resolve([]),k?this.extractForums(M):Promise.resolve([]),L?this.extractWhatPeopleSaying(M):Promise.resolve([]),this.extractEntityIds(M),this.extractOrganicResults(M),w?this.extractLocalPack(M):Promise.resolve([])]),N=this.mergeLocalPackIntoEntities(E,T),I=t.debug?tn(r,p,T):void 0;this.reporter.onVideos(H),this.reporter.onForums(P);let W=m?await this.extractAISurfaces(M,t):R,x={requestedPages:(t.pages??1)>=2?2:1,capturedPages:1,page2Status:(t.pages??1)>=2?"not_attempted":"not_requested",page1OrganicCount:p.length,page2OrganicCount:0},O=p;if(this.checkpointMaterial={surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,videos:H,forums:P,organicResults:O,localPack:T,entityIds:N,pagination:x},await this.emitProgress("serp_captured"),x.requestedPages===2){let V=await this.captureSecondOrganicPage(M,c,n);O=[...p,...V.organic],x={...x,capturedPages:V.status==="captured"?2:1,page2Status:V.status,page2OrganicCount:V.organic.length,...V.failureCode?{failureCode:V.failureCode}:{}},this.checkpointMaterial={...this.checkpointMaterial,organicResults:O,pagination:x},await this.emitProgress("serp_captured"),await this.resolveMaterialLinks(M,[],O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,organicResults:O},await this.emitProgress("serp_captured")}let j=t.debug?tn(r,O,T):I;if(!_){await this.resolveMaterialLinks(M,[],O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,organicResults:O},await this.emitProgress("serp_captured");let V={seed:c.query,totalQuestions:0,maxDepthReached:0,durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(V),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"no_paa",noPaaObserved:!0,problem:null,pagination:x,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,j,S)}:{}},totalQuestions:0,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,tree:[],flat:[],videos:H,forums:P,organicResults:O,localPack:T,entityIds:N,stats:V}}let ct=Date.now(),st=await this.runBFS(M,c,n);this.phaseTimings.paaExpansionMs=Date.now()-ct,this.throwIfAborted(n);let q=new URLSearchParams({q:c.query,gl:t.gl,hl:t.hl,pws:"0",udm:En.udm});u&&q.set("uule",u);let ht=[];if(t.includeShortVideos!==!1)try{ht=await this.extractShortVideos(M,"https://www.google.com/search?"+q.toString())}catch(V){if(!(V instanceof it))throw V;o++,d.push({code:"short_videos_captcha_skipped",surface:"short_videos",message:V.message,retryable:!0})}this.reporter.onVideos(ht),await this.resolveMaterialLinks(M,st,O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,videos:[...H,...ht],organicResults:O},await this.emitProgress("expansion_finished");let He=[...H,...ht],G=this.buildTree(st,c.query),Tt={seed:c.query,totalQuestions:st.length,maxDepthReached:st.reduce((V,et)=>Math.max(V,et.depth),0),durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(Tt),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"paa_found",problem:null,pagination:x,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...d.length>0?{warnings:d}:{},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,j,S)}:{}},totalQuestions:st.length,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,tree:G,flat:st,videos:He,forums:P,organicResults:O,localPack:T,entityIds:N,stats:Tt}}catch(l){throw o++,this.paaLifecycle.discoveryStatus==="in_progress"&&(this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"interrupted",completionReason:"The browser attempt ended before frontier exhaustion could be proven."}),await this.emitProgress("attempt_ending").catch(()=>{}),this.reporter.onError(l instanceof Error?l:new Error(String(l))),l}}};var rt=require("fs"),Rt=hn(require("path"),1),ne=hn(require("papaparse"),1);async function to(e){if((process.env.NODE_ENV==="test"||process.env.VITEST)&&process.env.MCP_SCRAPER_ENABLE_MEMORY_LIBRARY_SINK_IN_TESTS!=="1")return;let t=process.env.MCP_SCRAPER_API_KEY?.trim(),n=(process.env.MCP_SCRAPER_BASE_URL??"https://mcpscraper.dev").replace(/\/$/,"");if(t)try{let a=await fetch(`${n}/memory/mcp-call`,{method:"POST",headers:{"content-type":"application/json","x-api-key":t},body:JSON.stringify({toolName:"libraryIngestTool",args:e})}),i=await a.json().catch(()=>null);(!a.ok||i?.ok===!1)&&console.warn("[memory-library-sink] ingest not accepted:",a.status,i?.error??"")}catch(a){console.warn("[memory-library-sink] ingest failed:",a?.message)}}var Vn=class{async writeJSON(t,n){await rt.promises.mkdir(n,{recursive:!0});let i=`${t.seed.toLowerCase().replace(/\W+/g,"-").slice(0,40)}-${Date.now()}.json`,s=Rt.default.join(n,i);return await rt.promises.writeFile(s,JSON.stringify(t,null,2),"utf8"),await to({title:`${t.seed} scrape`,content:JSON.stringify(t),source:`mcp-scraper:${s}`}),s}async writeCSV(t,n){await rt.promises.mkdir(n,{recursive:!0});let i=(t[0]?.seed_query??"paa").toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t.map(({sources:l,...U})=>({...U,sources_json:JSON.stringify(l)})),{header:!0}),o=`${i}-${Date.now()}.csv`,d=Rt.default.join(n,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeVideoCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t,{header:!0}),o=`${i}-videos-${Date.now()}.csv`,d=Rt.default.join(a,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeForumCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t,{header:!0}),o=`${i}-forums-${Date.now()}.csv`,d=Rt.default.join(a,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeAIOverviewCSV(t,n,a,i){await rt.promises.mkdir(i,{recursive:!0});let s=a.toLowerCase().replace(/\W+/g,"-").slice(0,40),o=t.map((S,r)=>({seed_query:a,response_text:r===0?n??"":"",citation_text:S.text,citation_href:S.href})),d=ne.default.unparse(o,{header:!0}),l=`${s}-ai-overview-${Date.now()}.csv`,U=Rt.default.join(i,l);return await rt.promises.writeFile(U,d,"utf8"),U}async writeAIModeCSV(t,n,a,i){await rt.promises.mkdir(i,{recursive:!0});let s=a.toLowerCase().replace(/\W+/g,"-").slice(0,40),o=t.map((S,r)=>({seed_query:a,response_text:r===0?n??"":"",citation_text:S.text,citation_href:S.href})),d=ne.default.unparse(o,{header:!0}),l=`${s}-ai-mode-${Date.now()}.csv`,U=Rt.default.join(i,l);return await rt.promises.writeFile(U,d,"utf8"),U}async writeWhatPeopleSayingCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=t.map(U=>({seed_query:n,...U})),o=ne.default.unparse(s,{header:!0}),d=`${i}-what-people-saying-${Date.now()}.csv`,l=Rt.default.join(a,d);return await rt.promises.writeFile(l,o,"utf8"),l}};var Yn=class{onQuestion(t){process.stdout.write(JSON.stringify({event:"question",depth:t.depth,question:t.question})+`
|
|
21896
|
+
`);for(let l of d.matchAll(/\/g\/[a-zA-Z0-9_-]{5,20}/g))n.add(l[0]);for(let l of d.matchAll(/gcid:[a-zA-Z0-9_]+/g))i.add(l[0]);for(let l of d.matchAll(/0x[0-9a-f]+:0x([0-9a-f]+)/gi))try{a.add(BigInt("0x"+l[1]).toString())}catch{}return{entities:[...s.values()],kgIds:[...n],cids:[...a],gcids:[...i]}})}mergeLocalPackIntoEntities(t,n){let a=new Set(t.cids),i=t.entities.map(s=>({...s}));for(let s of n){if(!s.cid)continue;a.add(s.cid);let o=s.name.toLowerCase().trim(),d=i.find(l=>l.name.toLowerCase().trim()===o);d?d.cid||(d.cid=s.cid):i.find(l=>l.cid===s.cid)||i.push({name:s.name,kgId:null,cid:s.cid,gcid:null})}return{...t,entities:i,cids:[...a]}}async extractAISurfaces(t,n){let a=await t.evaluate(Fs,{aio:is,aim:ss,expandWaitMs:1500}),i=typeof t.url=="function"?t.url():"https://www.google.com/",s={surface:a.surface,aiOverview:{...a.aiOverview,citations:this.normalizeAICitations(i,a.aiOverview.citations)},aiMode:{...a.aiMode,citations:this.normalizeAICitations(i,a.aiMode.citations)}};if(!s.aiOverview.detected)return this.completeness.aioShareCaptured=null,s;let o=this.aioShareUrlEarly??await this.captureAIOverviewShareUrl(t,n).catch(()=>null);return this.completeness.aioShareCaptured=o!==null,{...s,aiOverview:{...s.aiOverview,shareUrl:o}}}async captureAIOverviewShareUrl(t,n){if(n?.softDeadlineMs&&Date.now()>=n.softDeadlineMs||!await t.evaluate(()=>{let s=Array.from(document.querySelectorAll('h1,h2,h3,[role="heading"],div')).filter(o=>(o.textContent||"").trim()==="AI Overview");for(let o of s){let d=o;for(let l=0;l<8&&d;l++){let U=d.querySelector('[aria-label="Share"]');if(U)return U.scrollIntoView({block:"center"}),U.click(),!0;d=d.parentElement}}return!1}).catch(()=>!1))return null;let i=null;try{i=await(await t.waitForFunction(()=>{let o=document.createTreeWalker(document.body,NodeFilter.SHOW_TEXT);for(;o.nextNode();){let d=(o.currentNode.textContent||"").match(/https:\/\/share\.google\/aimode\/\S+/);if(d)return d[0]}return!1},void 0,{timeout:4500,polling:250})).jsonValue()}catch{i=null}return await t.keyboard.press("Escape").catch(()=>{}),i}buildTree(t,n){let a=[],i=new Map;for(let s of t){let o={questionId:s.question_id,googleLinkId:s.google_link_id||null,googleEvidenceId:s.google_evidence_id||null,question:s.question,answer:s.answer||null,sourceTitle:s.source_title||null,sourceSite:s.source_site||null,sourceCite:s.source_cite||null,sources:s.sources??[],depth:s.depth,parentQuestion:s.parent_question||null,children:[]};i.set(s.question,o)}for(let s of i.values())s.parentQuestion&&i.has(s.parentQuestion)?i.get(s.parentQuestion).children.push(s):a.push(s);return a}getBrowserDebugSnapshot(){return this.driver.getDebugSnapshot()}buildHarvestDebugSnapshot(t,n,a,i,s){if(t.debug)return{enabled:!0,request:{query:t.query,locationInput:t.location??null,canonicalLocation:n,locationResolved:s?s.matched:null,locationMatchSource:s?s.source:null,locationAmbiguousCandidates:s?s.ambiguousCandidates:null,uule:a,gl:t.gl,hl:t.hl,device:t.device,proxyMode:t.proxyMode,proxyZip:t.proxyZip??null,serpIdentity:t.serpIdentity??null,serpOnly:t.serpOnly,pages:t.pages??1},browser:this.getBrowserDebugSnapshot(),...i?{locationEvidence:i}:{}}}async captureSecondOrganicPage(t,n,a){if(this.throwIfAborted(a),!this.driver.withTemporaryPage)return{organic:[],status:"failed",failureCode:"unsupported_driver"};let i;try{let s=new URL(t.url()),o=U=>{try{let S=new URL(U,s);return s.origin==="https://www.google.com"&&S.origin===s.origin&&!S.username&&!S.password&&S.pathname==="/search"&&S.searchParams.getAll("q").length===1&&S.searchParams.get("q")===n.query&&S.searchParams.getAll("start").length===1&&S.searchParams.get("start")==="10"&&(!S.searchParams.has("num")||S.searchParams.get("num")==="10")&&["gl","hl"].every(r=>!S.searchParams.has(r)||S.searchParams.getAll(r).length===1&&S.searchParams.get(r)===n[r])&&["uule","tbs","udm","tbm","pws"].every(r=>S.searchParams.getAll(r).length<=1&&S.searchParams.get(r)===s.searchParams.get(r))}catch{return!1}},d=await t.evaluate(()=>document.querySelector('a#pnnext, a[rel="next"]')?.getAttribute("href")??null);if(!d)return{organic:[],status:"unavailable",failureCode:"missing_next"};if(!o(d))return{organic:[],status:"unavailable",failureCode:"invalid_next"};let l=await this.driver.withTemporaryPage(async U=>{if(await U.route("**/*",async S=>{let r=S.request();r.isNavigationRequest()&&r.frame()===U.mainFrame()&&!o(r.url())?(i=/^https:\/\/www\.google\.com\/sorry(?:\/|\?)/.test(r.url())?"captcha":"invalid_next",await S.abort("blockedbyclient")):await S.fallback()}),await U.goto(new URL(d,s).href,{waitUntil:"domcontentloaded",timeout:2e4}),this.throwIfAborted(a),await this.throwIfCaptcha(U,"Google SERP page 2"),!o(U.url()))throw i="invalid_next",new Error("Invalid pagination landing");return this.extractOrganicResults(U)},a);return this.throwIfAborted(a),l.length>0?{organic:l.map(U=>({...U,position:U.position+10})),status:"captured"}:{organic:[],status:"unavailable",failureCode:"empty_page"}}catch(s){if(this.throwIfAborted(a),s instanceof pt)throw s;return{organic:[],status:"failed",failureCode:i??(s instanceof it?"captcha":s instanceof Error&&(s.name==="TimeoutError"||/timed? ?out/i.test(s.message))?"timeout":"navigation_error")}}}async extract(t,n){let a=Date.now();this.completeness={paaWithoutAnswer:0,paaWithoutSource:0,paaAnswersRecovered:0,aioShareCaptured:null},this.linkDiagnostics=this.emptyLinkDiagnostics(),this.aioShareUrlEarly=null,this.collectedRows=[],this.progressSequence=0,this.checkpointMaterial=null,this.clickedQuestions=new Set,this.paaLifecycle=this.emptyPaaLifecycle(t.maxQuestions),this.partialContext={seed:t.query,location:t.location??null,startMs:a,maxQuestions:t.maxQuestions,questionsOnly:t.questionsOnly};let i=t.device==="mobile",s={headless:t.headless,profileDir:t.profileDir,proxy:t.proxy,\u006b\u0065\u0072\u006e\u0065\u006cApiKey:t.\u006b\u0065\u0072\u006e\u0065\u006cApiKey,\u006b\u0065\u0072\u006e\u0065\u006cProxyId:t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId,\u006b\u0065\u0072\u006e\u0065\u006cProfileName:t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName,\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges:t.\u006b\u0065\u0072\u006e\u0065\u006cProfileSaveChanges,\u006b\u0065\u0072\u006e\u0065\u006cStealth:t.\u006b\u0065\u0072\u006e\u0065\u006cStealth,\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution:t.\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution,proxyMode:t.proxyMode,keepDefaultProxy:t.keepDefaultProxy,requireUsEgress:t.requireUsEgress,viewport:i?{width:390,height:844}:{width:1280,height:800},locale:`${t.hl}-${t.gl.toUpperCase()}`,deviceScaleFactor:i?3:1,isMobile:i,hasTouch:i,debug:t.debug,operationDeadlineMs:t.softDeadlineMs},o=0,d=[];try{this.throwIfAborted(n);let l=Date.now();await this.driver.launch(s),this.phaseTimings.providerConnectMs=Date.now()-l;let U=this.driver.getProviderSessionMetadata();if(U?.providerSessionId&&this.onProviderSession)try{await this.onProviderSession(U)}catch(V){console.warn(JSON.stringify({event:"paa_provider_session_sink_failed",provider:U.provider,message:V instanceof Error?V.message:String(V)}))}this.throwIfAborted(n);let S=t.location?Da(t.location):null,r=t.location?S?.canonical??t.location:null,u=r?Os(r):null,c=t,h=t.includeAllSerpFeatures,w=h||t.includeLocalPack,k=h||t.includeForums,f=h||t.includeVideos,m=h||t.includeAiOverview,L=h||t.includeWhatPeopleSaying,R={surface:"web",aiOverview:{detected:!1,text:null,citations:[]},aiMode:{detected:!1,text:null,citations:[]}},D=Date.now(),{hasPaa:_}=await this.driver.navigateToSERP(c.query,u,t.gl,t.hl,{...De(t.recency)?{tbs:De(t.recency)}:{},debug:t.debug,purpose:t.serpOnly?"serp":"paa",...t.softDeadlineMs?{deadlineMs:t.softDeadlineMs}:{}});this.phaseTimings.navigationMs=Date.now()-D,this.throwIfAborted(n);let M=this.driver.getPage();if(await this.throwIfCaptcha(M,"Google SERP"),_||(this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"no_paa_observed",materialStatus:"complete",completionReason:"A readable Google SERP was observed without a People Also Ask block."}),t.questionsOnly){let V=Date.now(),et=_?await this.runBFS(M,c,n):[];this.phaseTimings.paaExpansionMs=Date.now()-V,await this.resolveMaterialLinks(M,et,[],R.aiOverview,R.aiMode);let J={seed:c.query,totalQuestions:et.length,maxDepthReached:et.reduce((Q,wt)=>Math.max(Q,wt.depth),0),durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(J),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:_?"paa_found":"no_paa",..._?{}:{noPaaObserved:!0},problem:null,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,void 0,S)}:{}},totalQuestions:et.length,surface:"web",aiOverview:{detected:!1,text:null,citations:[]},aiMode:{detected:!1,text:null,citations:[]},whatPeopleSaying:[],tree:this.buildTree(et,c.query),flat:et,videos:[],forums:[],organicResults:[],localPack:[],entityIds:{entities:[],kgIds:[],cids:[],gcids:[]},stats:J}}if(m&&(this.aioShareUrlEarly=await this.captureAIOverviewShareUrl(M,t).catch(()=>null)),t.serpOnly){let V=Date.now(),[et,J,Q]=await Promise.all([this.extractOrganicResults(M),w?this.extractLocalPack(M):Promise.resolve([]),this.extractEntityIds(M)]),wt=this.mergeLocalPackIntoEntities(Q,J),kt=m?await this.extractAISurfaces(M,t):R;this.phaseTimings.serpParseMs=Date.now()-V;let rn=t.debug?tn(r,et,J):void 0,se=et;if((t.pages??1)>=2){let Be=new URLSearchParams({q:c.query,gl:t.gl,hl:t.hl,pws:"0",start:"10"});De(t.recency)&&Be.set("tbs",De(t.recency)),u&&Be.set("uule",u),await this.driver.navigateTo("https://www.google.com/search?"+Be.toString()),await this.throwIfCaptcha(M,"Google SERP page 2");let ln=await this.extractOrganicResults(M);se=[...et,...ln.map(oe=>({...oe,position:oe.position+10}))],t.debug&&(rn=tn(r,se,J))}await this.resolveMaterialLinks(M,[],se,kt.aiOverview,kt.aiMode);let dn={seed:c.query,totalQuestions:0,maxDepthReached:0,durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(dn),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"serp_only",problem:null,completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,rn,S)}:{}},totalQuestions:0,surface:kt.surface,aiOverview:kt.aiOverview,aiMode:kt.aiMode,whatPeopleSaying:[],tree:[],flat:[],videos:[],forums:[],organicResults:se,localPack:J,entityIds:wt,stats:dn}}let[H,P,y,E,p,T]=await Promise.all([f?this.extractVideos(M):Promise.resolve([]),k?this.extractForums(M):Promise.resolve([]),L?this.extractWhatPeopleSaying(M):Promise.resolve([]),this.extractEntityIds(M),this.extractOrganicResults(M),w?this.extractLocalPack(M):Promise.resolve([])]),N=this.mergeLocalPackIntoEntities(E,T),I=t.debug?tn(r,p,T):void 0;this.reporter.onVideos(H),this.reporter.onForums(P);let W=m?await this.extractAISurfaces(M,t):R,x={requestedPages:(t.pages??1)>=2?2:1,capturedPages:1,page2Status:(t.pages??1)>=2?"not_attempted":"not_requested",page1OrganicCount:p.length,page2OrganicCount:0},O=p;if(this.checkpointMaterial={surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,videos:H,forums:P,organicResults:O,localPack:T,entityIds:N,pagination:x},await this.emitProgress("serp_captured"),x.requestedPages===2){let V=await this.captureSecondOrganicPage(M,c,n);O=[...p,...V.organic],x={...x,capturedPages:V.status==="captured"?2:1,page2Status:V.status,page2OrganicCount:V.organic.length,...V.failureCode?{failureCode:V.failureCode}:{}},this.checkpointMaterial={...this.checkpointMaterial,organicResults:O,pagination:x},await this.emitProgress("serp_captured"),await this.resolveMaterialLinks(M,[],O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,organicResults:O},await this.emitProgress("serp_captured")}let j=t.debug?tn(r,O,T):I;if(!_){await this.resolveMaterialLinks(M,[],O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,organicResults:O},await this.emitProgress("serp_captured");let V={seed:c.query,totalQuestions:0,maxDepthReached:0,durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(V),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"no_paa",noPaaObserved:!0,problem:null,pagination:x,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,j,S)}:{}},totalQuestions:0,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,tree:[],flat:[],videos:H,forums:P,organicResults:O,localPack:T,entityIds:N,stats:V}}let ct=Date.now(),st=await this.runBFS(M,c,n);this.phaseTimings.paaExpansionMs=Date.now()-ct,this.throwIfAborted(n);let q=new URLSearchParams({q:c.query,gl:t.gl,hl:t.hl,pws:"0",udm:En.udm});u&&q.set("uule",u);let ht=[];if(t.includeShortVideos!==!1)try{ht=await this.extractShortVideos(M,"https://www.google.com/search?"+q.toString())}catch(V){if(!(V instanceof it))throw V;o++,d.push({code:"short_videos_captcha_skipped",surface:"short_videos",message:V.message,retryable:!0})}this.reporter.onVideos(ht),await this.resolveMaterialLinks(M,st,O,W.aiOverview,W.aiMode),this.checkpointMaterial={...this.checkpointMaterial,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,videos:[...H,...ht],organicResults:O},await this.emitProgress("expansion_finished");let He=[...H,...ht],G=this.buildTree(st,c.query),Tt={seed:c.query,totalQuestions:st.length,maxDepthReached:st.reduce((V,et)=>Math.max(V,et.depth),0),durationMs:Date.now()-a,errorCount:o};return this.reporter.onComplete(Tt),{seed:c.query,location:t.location??null,extractedAt:new Date().toISOString(),diagnostics:{phaseTimings:this.currentPhaseTimings(a),completionStatus:"paa_found",problem:null,pagination:x,paaLifecycle:{...this.paaLifecycle},completeness:{...this.completeness},links:{...this.linkDiagnostics},...d.length>0?{warnings:d}:{},...t.debug?{debug:this.buildHarvestDebugSnapshot(c,r,u,j,S)}:{}},totalQuestions:st.length,surface:W.surface,aiOverview:W.aiOverview,aiMode:W.aiMode,whatPeopleSaying:y,tree:G,flat:st,videos:He,forums:P,organicResults:O,localPack:T,entityIds:N,stats:Tt}}catch(l){throw o++,this.paaLifecycle.discoveryStatus==="in_progress"&&(this.paaLifecycle={...this.paaLifecycle,discoveryStatus:"interrupted",completionReason:"The browser attempt ended before frontier exhaustion could be proven."}),await this.emitProgress("attempt_ending").catch(()=>{}),this.reporter.onError(l instanceof Error?l:new Error(String(l))),l}}};var rt=require("fs"),Rt=hn(require("path"),1),ne=hn(require("papaparse"),1);async function to(e){if((process.env.NODE_ENV==="test"||process.env.VITEST)&&process.env.MCP_SCRAPER_ENABLE_MEMORY_LIBRARY_SINK_IN_TESTS!=="1")return;let t=process.env.MCP_SCRAPER_API_KEY?.trim(),n=(process.env.MCP_SCRAPER_BASE_URL??"https://mcpscraper.dev").replace(/\/$/,"");if(t)try{let a=await fetch(`${n}/memory/mcp-call`,{method:"POST",headers:{"content-type":"application/json","x-api-key":t},body:JSON.stringify({toolName:"libraryIngestTool",args:e})}),i=await a.json().catch(()=>null);(!a.ok||i?.ok===!1)&&console.warn("[memory-library-sink] ingest not accepted:",a.status,i?.error??"")}catch(a){console.warn("[memory-library-sink] ingest failed:",a?.message)}}var Vn=class{async writeJSON(t,n){await rt.promises.mkdir(n,{recursive:!0});let i=`${t.seed.toLowerCase().replace(/\W+/g,"-").slice(0,40)}-${Date.now()}.json`,s=Rt.default.join(n,i);return await rt.promises.writeFile(s,JSON.stringify(t,null,2),"utf8"),await to({title:`${t.seed} scrape`,content:JSON.stringify(t),source:`mcp-scraper:${s}`}),s}async writeCSV(t,n){await rt.promises.mkdir(n,{recursive:!0});let i=(t[0]?.seed_query??"paa").toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t.map(({sources:l,...U})=>({...U,sources_json:JSON.stringify(l)})),{header:!0}),o=`${i}-${Date.now()}.csv`,d=Rt.default.join(n,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeVideoCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t,{header:!0}),o=`${i}-videos-${Date.now()}.csv`,d=Rt.default.join(a,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeForumCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=ne.default.unparse(t,{header:!0}),o=`${i}-forums-${Date.now()}.csv`,d=Rt.default.join(a,o);return await rt.promises.writeFile(d,s,"utf8"),d}async writeAIOverviewCSV(t,n,a,i){await rt.promises.mkdir(i,{recursive:!0});let s=a.toLowerCase().replace(/\W+/g,"-").slice(0,40),o=t.map((S,r)=>({seed_query:a,response_text:r===0?n??"":"",citation_text:S.text,citation_href:S.href})),d=ne.default.unparse(o,{header:!0}),l=`${s}-ai-overview-${Date.now()}.csv`,U=Rt.default.join(i,l);return await rt.promises.writeFile(U,d,"utf8"),U}async writeAIModeCSV(t,n,a,i){await rt.promises.mkdir(i,{recursive:!0});let s=a.toLowerCase().replace(/\W+/g,"-").slice(0,40),o=t.map((S,r)=>({seed_query:a,response_text:r===0?n??"":"",citation_text:S.text,citation_href:S.href})),d=ne.default.unparse(o,{header:!0}),l=`${s}-ai-mode-${Date.now()}.csv`,U=Rt.default.join(i,l);return await rt.promises.writeFile(U,d,"utf8"),U}async writeWhatPeopleSayingCSV(t,n,a){await rt.promises.mkdir(a,{recursive:!0});let i=n.toLowerCase().replace(/\W+/g,"-").slice(0,40),s=t.map(U=>({seed_query:n,...U})),o=ne.default.unparse(s,{header:!0}),d=`${i}-what-people-saying-${Date.now()}.csv`,l=Rt.default.join(a,d);return await rt.promises.writeFile(l,o,"utf8"),l}};var Yn=class{onQuestion(t){process.stdout.write(JSON.stringify({event:"question",depth:t.depth,question:t.question})+`
|
|
21897
21897
|
`)}onDepth(t){process.stdout.write(JSON.stringify({event:"depth",depth:t})+`
|
|
21898
21898
|
`)}onVideos(t){for(let n of t)process.stdout.write(JSON.stringify({event:"video",type:n.type,platform:n.platform,duration:n.duration,title:n.title,channel:n.channel,url:n.url})+`
|
|
21899
21899
|
`)}onForums(t){for(let n of t)process.stdout.write(JSON.stringify({event:"forum",title:n.title,source:n.source,url:n.url})+`
|
|
21900
21900
|
`)}onComplete(t){process.stdout.write(JSON.stringify({event:"complete",...t})+`
|
|
21901
21901
|
`)}onError(t){process.stderr.write(JSON.stringify({event:"error",type:t.constructor.name,message:t.message})+`
|
|
21902
|
-
`)}};var eo=require("crypto");var Sl="pr.oxylabs.io",Ul=7777,ul=10;function no(){return process.env.OXYLABS_USERNAME?.trim()||void 0}function ao(){return process.env.OXYLABS_PASSWORD?.trim()||void 0}function cl(){return(process.env.OXYLABS_COUNTRY?.trim()||"US").toUpperCase()}function io(){return!!(no()&&ao())}function hl(){let e="";for(let t=0;t<10;t++)e+=String((0,eo.randomInt)(0,10));return e}function gl(e={}){let t=no();if(!t)return;let n=t.startsWith("customer-")?t:`customer-${t}`,a=(e.country?.trim()||cl()).toUpperCase(),i=e.sticky?`-sessid-${hl()}-sesstime-${ul}`:"";return`${n}-cc-${a}${i}`}function Ya(e){return e.replace(/pr\.oxylabs\.io(:\d+)?/gi,"backup proxy").replace(/oxylabs/gi,"backup proxy")}function pl(e){return`mcp-backup-custom-${`${Date.now()}-${e??0}-${Math.random().toString(36).slice(2,8)}`}`}async function so(e,t={}){let n=gl({sticky:t.sticky}),a=ao();if(!n||!a)throw new Error("backup proxy pool is not configured");let i=new B({apiKey:e});try{let s=await i.proxies.create({type:"custom",name:pl(t.attemptIndex),protocol:"http",config:{host:Sl,port:Ul,username:n,password:a}});if(!s.id)throw new Error("backup proxy creation did not return a proxy id");return s.id}catch(s){let o=s instanceof Error?s.message:String(s);throw new Error(Ya(o))}}var wl={alabama:"AL",alaska:"AK",arizona:"AZ",arkansas:"AR",california:"CA",colorado:"CO",connecticut:"CT",delaware:"DE",florida:"FL",georgia:"GA",hawaii:"HI",idaho:"ID",illinois:"IL",indiana:"IN",iowa:"IA",kansas:"KS",kentucky:"KY",louisiana:"LA",maine:"ME",maryland:"MD",massachusetts:"MA",michigan:"MI",minnesota:"MN",mississippi:"MS",missouri:"MO",montana:"MT",nebraska:"NE",nevada:"NV","new hampshire":"NH","new jersey":"NJ","new mexico":"NM","new york":"NY","north carolina":"NC","north dakota":"ND",ohio:"OH",oklahoma:"OK",oregon:"OR",pennsylvania:"PA","rhode island":"RI","south carolina":"SC","south dakota":"SD",tennessee:"TN",texas:"TX",utah:"UT",vermont:"VT",virginia:"VA",washington:"WA","west virginia":"WV",wisconsin:"WI",wyoming:"WY"},ml={"atlanta|GA":"30303","austin|TX":"78701","baltimore|MD":"21201","boston|MA":"02108","boulder|CO":"80302","charlotte|NC":"28202","chicago|IL":"60601","colorado_springs|CO":"80903","columbus|OH":"43215","dallas|TX":"75201","denver|CO":"80202","detroit|MI":"48226","fort_collins|CO":"80524","fort_worth|TX":"76102","houston|TX":"77002","indianapolis|IN":"46204","jacksonville|FL":"32202","las_vegas|NV":"89101","los_angeles|CA":"90012","louisville|KY":"40202","loveland|CO":"80537","memphis|TN":"38103","miami|FL":"33131","minneapolis|MN":"55401","nashville|TN":"37203","new_york|NY":"10001","orlando|FL":"32801","philadelphia|PA":"19103","phoenix|AZ":"85004","portland|OR":"97205","raleigh|NC":"27601","richmond|VA":"23219","sacramento|CA":"95814","salt_lake_city|UT":"84101","san_antonio|TX":"78205","san_diego|CA":"92101","san_francisco|CA":"94103","san_jose|CA":"95113","seattle|WA":"98101"};function yl(e){return e?e.slice(-6):null}function dt(e,t,n,a,i,s=!1){return{kernelProxyId:n,...s&&n?{disposableProxyId:n}:{},resolution:{source:e,proxyType:e==="disabled"?"none":e==="configured_fallback"?"configured":e==="isp_created"?"isp":e==="backup_custom"?"custom":e==="location_created"||e==="location_reused"?"residential":"unknown",proxyMode:t,proxyIdPresent:!!n,proxyIdSuffix:yl(n),target:a,error:i,disposable:s}}}function Cl(e){return e.trim().toLowerCase().replace(/\s+/g," ")}function Tl(e){return e.trim().toLowerCase().replace(/\./g,"").replace(/\s+/g," ")}function kl(e){if(!e)return!0;let t=Tl(e);return t==="united states"||t==="united states of america"||t==="usa"||t==="us"}function oo(e){let t=e.trim();return/^[A-Za-z]{2}$/.test(t)?t.toUpperCase():wl[Cl(t)]??null}function fl(e){let n=e.normalize("NFKD").replace(/[^\x00-\x7F]/g,"").toLowerCase().split(/[^a-z0-9]+/).filter(Boolean),a=n.join("_"),i=n.join("");return Array.from(new Set([a,i].filter(Boolean)))}function Ht(e,t,n){return n?`mcp-serp-residential-${e.toLowerCase()}-${t.toLowerCase()}-${n}`:`mcp-serp-residential-${e.toLowerCase()}-${t.toLowerCase()}`}function Kn(e,t){let n=`${Date.now()}-${t??0}-${Math.random().toString(36).slice(2,8)}`;return`${e}-fresh-${n}`}function Ml(e){return`mcp-serp-residential-us-zip-${e}`}function Nl(e,t){if(!e||t.toLowerCase()!=="us")return null;let n=Rs(e),a=n.split(",").map(U=>U.trim()).filter(Boolean);if(a.length>1&&kl(a[a.length-1])&&(a=a.slice(0,-1)),a.length===1){let U=oo(a[0]);return U?{canonicalLocation:n,level:"state",country:"US",state:U,city:"",cityCandidates:[],proxyName:Ht("US",U),config:{country:"US",state:U}}:null}let[i="",s=""]=a;if(!i||!s)return null;let o=oo(s);if(!o)return null;let d=fl(i),l=d[0];return l?{canonicalLocation:n,level:"city",country:"US",state:o,city:l,cityCandidates:d,proxyName:Ht("US",o,l),config:{country:"US",state:o,city:l}}:null}function vl(e){return`${e.city}|${e.state}`}function ro(e,t){return t&&/^\d{5}$/.test(t)?t:ml[vl(e)]??null}function lo(e,t){return{...e,level:"zip",zip:t,proxyName:Ml(t),config:{country:e.country,state:e.state,zip:t}}}function Ka(e,t){return{...e,proxyName:t}}function qa(e,t,n){return t.level==="zip"?e?.country?.toUpperCase()===t.country&&e?.zip===t.zip:e?.country?.toUpperCase()===t.country&&e?.state?.toUpperCase()===t.state&&(n?e?.city===n:!e?.city)}function _l(e,t){return e.find(n=>n.type==="residential"&&n.status!=="unavailable"&&!!n.id&&(n.name===t.proxyName||qa(n.config,t,t.level==="city"?t.city:void 0)))??null}function bl(e,t){for(let n of t.cityCandidates){let a=Ht(t.country,t.state,n),i=e.find(s=>s.type==="residential"&&s.status!=="unavailable"&&!!s.id&&(s.name===a||qa(s.config,t,n)));if(i)return i}return null}function Jn(e){return{...e,level:"state",proxyName:Ht(e.country,e.state),config:{country:e.country,state:e.state}}}function El(e,t){let n=Ht(t.country,t.state);return e.find(a=>a.type==="residential"&&a.status!=="unavailable"&&!!a.id&&(a.name===n||qa(a.config,t)))??null}function Pl(e,t){return Jn(e)}function Wt(e){return e instanceof Error?e.message:String(e)}function Il(e,t,n){let a=[],i=ro(e,t);if(i){let o=lo(e,i);a.push(Ka(o,Kn(o.proxyName,n)))}for(let o of e.cityCandidates){let d={...e,level:"city",city:o,proxyName:Ht(e.country,e.state,o),config:{country:e.country,state:e.state,city:o}};a.push(Ka(d,Kn(d.proxyName,n)))}let s=Jn(e);return a.push(Ka(s,Kn(s.proxyName,n))),a}async function Ja(e,t,n){if(e.backupOnExhaustion&&n.length>0&&e.kernelApiKey&&io())try{let a=await so(e.kernelApiKey,{attemptIndex:e.attemptIndex});return dt("backup_custom",e.proxyMode,a,t,null,!0)}catch(a){n.push(`backup: ${Ya(Wt(a))}`)}return dt("configured_fallback",e.proxyMode,e.configuredKernelProxyId,t,n.join(" | "))}async function Al(e,t,n){let a=[];for(let i of Il(n,t.proxyZip,t.attemptIndex))try{let s=await e.proxies.create({type:"residential",name:i.proxyName,config:i.level==="zip"?{country:i.country,zip:i.zip}:i.config});if(s.id)return dt("location_created",t.proxyMode,s.id,i,null,!0);a.push(`${i.proxyName}: Kernel did not return a proxy id`)}catch(s){a.push(`${i.proxyName}: ${Wt(s)}`)}if(process.env.KERNEL_PROXY_TYPE!=="residential"){let i=Jn(n);try{let s=await e.proxies.create({type:"isp",name:Kn(`mcp-serp-isp-${i.country.toLowerCase()}-${(i.state??"").toLowerCase()}`,t.attemptIndex),config:{country:i.country,...i.state?{state:i.state}:{}}});if(s.id)return dt("isp_created",t.proxyMode,s.id,i,null,!0);a.push("isp: Kernel did not return a proxy id")}catch(s){a.push(`isp: ${Wt(s)}`)}}return Ja(t,n,a)}async function So(e,t){if(!e||!t)return;await new B({apiKey:e}).proxies.delete(t)}async function Uo(e){if(e.proxyMode==="none")return dt("disabled",e.proxyMode,void 0,null,null);if(e.proxyMode==="configured")return dt("configured_fallback",e.proxyMode,e.configuredKernelProxyId,null,null);let t=Nl(e.location,e.gl);if(!t||!e.kernelApiKey)return dt("configured_fallback",e.proxyMode,e.configuredKernelProxyId,t,t?null:"location could not be normalized to a US city/state proxy target");let n=new B({apiKey:e.kernelApiKey});try{let a=e.attemptIndex??0;if(e.fresh)return await Al(n,e,t);if(a>=1){let S=Pl(t,a),r=[];try{let u=await n.proxies.create({type:"residential",name:S.proxyName,config:S.config});if(u.id)return dt("location_created",e.proxyMode,u.id,S,null);r.push(`${S.state}: Kernel did not return a proxy id`)}catch(u){r.push(`${S.state}: ${Wt(u)}`)}return Ja(e,S,r)}let i=[];for await(let S of await n.proxies.list())i.push(S);let s=ro(t,e.proxyZip),o=[];if(s){let S=lo(t,s),r=_l(i,S);if(r?.id)return dt("location_reused",e.proxyMode,r.id,S,null);try{let u=await n.proxies.create({type:"residential",name:S.proxyName,config:{country:S.country,zip:s}});if(u.id)return dt("location_created",e.proxyMode,u.id,S,null);o.push(`${s}: Kernel did not return a proxy id`)}catch(u){o.push(`${s}: ${Wt(u)}`)}}let d=bl(i,t);if(d?.id)return dt("location_reused",e.proxyMode,d.id,t,o.join(" | ")||null);for(let S of t.cityCandidates)try{let r=await n.proxies.create({type:"residential",name:Ht(t.country,t.state,S),config:{country:t.country,state:t.state,city:S}});if(r.id)return dt("location_created",e.proxyMode,r.id,{...t,level:"city",city:S,proxyName:Ht(t.country,t.state,S),config:{country:t.country,state:t.state,city:S}},null);o.push(`${S}: Kernel did not return a proxy id`)}catch(r){o.push(`${S}: ${Wt(r)}`)}let l=Jn(t),U=El(i,l);if(U?.id)return dt("location_reused",e.proxyMode,U.id,l,o.join(" | "));try{let S=await n.proxies.create({type:"residential",name:l.proxyName,config:l.config});if(S.id)return dt("location_created",e.proxyMode,S.id,l,o.join(" | "));o.push(`${l.state}: Kernel did not return a proxy id`)}catch(S){o.push(`${l.state}: ${Wt(S)}`)}return Ja(e,t,o)}catch(a){return dt("configured_fallback",e.proxyMode,e.configuredKernelProxyId,t,Wt(a))}}var an=class extends Error{constructor(t,n){super(`SERP provider mismatch: planned ${t}, observed ${n}`),this.name="SerpProviderMismatchError"}};function uo(e){return e==="bright_data_browser_api"?"brightdata":"kernel"}function co(e){return Ll({intent:e.intent,brightDataAvailable:e.brightDataAvailable,kernelAvailable:!0,persistentKernelIdentityRequested:e.persistentKernelIdentityRequested,retryIndex:e.retryIndex,priorTerminalReason:e.priorTerminalReason,allowedFallbacks:e.kernelFallbackAvailable&&e.intent!=="kernel"?["kernel"]:[],timeoutMs:e.softDeadlineMs==null?4e5:Math.max(1,e.softDeadlineMs-Date.now())})}function ho(e){if(e.forceManagedSerp&&e.forceKernelSerp)throw new Error("forceManagedSerp and forceKernelSerp cannot both be true");return e.forceManagedSerp?"brightdata":e.forceKernelSerp?"kernel":"auto"}function qn(e,t){if(!t)throw new Error(`Requested SERP provider is unavailable: ${e}`);return e}function Ll(e){if(!Number.isInteger(e.retryIndex)||e.retryIndex<0)throw new Error("retryIndex must be a non-negative integer");if(!Number.isFinite(e.timeoutMs)||e.timeoutMs<=0)throw new Error("timeoutMs must be a positive number");let t,n;e.intent==="brightdata"?(t=qn("brightdata",e.brightDataAvailable),n="explicit_brightdata"):e.intent==="kernel"?(t=qn("kernel",e.kernelAvailable),n="explicit_kernel"):e.persistentKernelIdentityRequested?(t=qn("kernel",e.kernelAvailable),n="persistent_kernel_identity"):e.brightDataAvailable?(t="brightdata",n="managed_default"):(t=qn("kernel",e.kernelAvailable),n="kernel_default");let a=e.allowedFallbacks.find(o=>o!==t&&(o==="brightdata"?e.brightDataAvailable:e.kernelAvailable)),i=e.retryIndex>0&&a?a:t,s=e.retryIndex===0?"primary":i===t?"same_provider_retry":"provider_fallback";return Object.freeze({plannedProvider:i,attemptKind:s,reasonCode:s==="primary"?n:s==="provider_fallback"?"provider_fallback":"same_provider_retry",retryIndex:e.retryIndex,priorTerminalReason:e.priorTerminalReason??null,timeoutMs:Math.floor(e.timeoutMs),fallbackAllowed:!!a})}var ja=2,xl=2,Ol=3e3;function za(e){return e.reason instanceof DOMException&&e.reason.name==="TimeoutError"?e.reason:new pt}function Rl(e){if(!e||typeof e!="object")return;let t=e.signal;if(t instanceof AbortSignal)return t}function Wl(e){if(!e||typeof e!="object")return;let t=e.onAttemptEvent;return typeof t=="function"?t:void 0}function Hl(e){if(!e||typeof e!="object")return;let t=e.onPaaProgress;return typeof t=="function"?t:void 0}function Bl(e){if(!e||typeof e!="object")return;let t=e.onPaaDomEvidence;return typeof t=="function"?t:void 0}async function Dl(e){let t=await e.evaluate(n=>{let a=n,i=Array.from(document.querySelectorAll(a.item)),s=i.map(l=>l.querySelector(a.clickTarget)).filter(l=>l!=null),o=l=>{let U=l.getBoundingClientRect();if(U.width<=0||U.height<=0)return!1;let S=U.left+U.width/2,r=U.top+U.height/2;if(S<0||r<0||S>=window.innerWidth||r>=window.innerHeight)return!1;let u=document.elementFromPoint(S,r);return u!=null&&u!==l&&!l.contains(u)&&!u.contains(l)},d=Array.from(document.querySelectorAll("body *")).filter(l=>{let U=window.getComputedStyle(l);if(U.position!=="fixed"&&U.position!=="sticky")return!1;let S=l.getBoundingClientRect();return S.width*S.height>=window.innerWidth*window.innerHeight*.15&&U.visibility!=="hidden"&&U.display!=="none"});return{itemCount:i.length,expandedItemCount:i.filter(l=>l.classList.contains(a.expandedClass)||l.querySelector(a.clickTarget)?.getAttribute("aria-expanded")==="true").length,answeredItemCount:i.filter(l=>(l.querySelector(a.answerContainer)?.textContent?.trim().length??0)>=10).length,sourcedItemCount:i.filter(l=>l.querySelector(`${a.answerContainer} a[href]`)!=null).length,clickTargetCount:s.length,clickTargetsWithButtonRole:s.filter(l=>l.getAttribute("role")==="button"||l.tagName==="BUTTON").length,clickTargetsWithExpandedState:s.filter(l=>l.hasAttribute("aria-expanded")).length,clickTargetsOffscreen:s.filter(l=>{let U=l.getBoundingClientRect(),S=U.left+U.width/2,r=U.top+U.height/2;return S<0||r<0||S>=window.innerWidth||r>=window.innerHeight}).length,clickTargetsBlockedAtCenter:s.filter(o).length,fixedOrStickyOverlayCount:d.length}},{item:X.item,answerContainer:X.answerContainer,clickTarget:X.clickTarget,expandedClass:X.expandedClass});return{capturedAt:new Date().toISOString(),...t,selectorVersion:ds}}async function Re(e,t){if(e)try{await e(t)}catch(n){console.warn(JSON.stringify({event:"harvest_attempt_log_failed",attempt_number:t.attemptNumber,message:n instanceof Error?n.message:String(n)}))}}function sn(e){if(e instanceof an)return"error";if(e instanceof it)return"captcha";if(e instanceof $e)return"location_mismatch";if(e instanceof pt)return"request_aborted";if(e instanceof Qt)return"browser_session_interrupted";if(e instanceof DOMException&&(e.name==="TimeoutError"||e.name==="AbortError"))return"timeout";let t=e instanceof Error?e.message:String(e);return/browser (?:has been )?closed|context (?:has been )?closed|target page, context or browser has been closed|session closed|page has been closed/i.test(t)?"browser_session_interrupted":Kl(t)?"proxy_tunnel_failed":Jl(t)?"proxy_unavailable":/timeout|timed out|Timeout \d+ms exceeded|deadline/i.test(t)?"timeout":"error"}function Fl(e){return e.diagnostics.degradedResult?"degraded_result":e.diagnostics?.completionStatus??(e.totalQuestions>0?"paa_found":"no_paa")}function Gl(e){return e.flat.length>0||e.organicResults.length>0||e.localPack.length>0||e.videos.length>0||e.forums.length>0||e.whatPeopleSaying.length>0||e.aiOverview.detected||e.aiMode.detected}function go(e,t,n){let a=Gl(e),i=(e.diagnostics.warnings?.length??0)>0,s=new Set(e.flat.map(w=>w.question.toLowerCase().replace(/[^\w\s]/g,"").replace(/\s+/g," ").trim())).size,o=n?0:e.flat.filter(w=>!w.answer?.trim()).length,d=n?0:e.flat.filter(w=>!w.source_cite?.trim()).length,l=e.diagnostics.completionStatus==="no_paa"&&(e.diagnostics.noPaaObserved===!0||a),U=e.diagnostics.completionStatus==="paa_found",S=e.diagnostics.paaLifecycle?.discoveryStatus,r=S==="interrupted"||S==="recovery_exhausted",u=U&&(s<t&&S!=="frontier_exhausted"||o>0||d>0||!!e.diagnostics.interruption||r),c=l?"complete":U&&s>0?u||i?"partial":"complete":a?i?"partial":"complete":"degraded",h=c==="degraded";return e.diagnostics={...e.diagnostics,resultQuality:c,degradedResult:h,degradationReasons:h?["empty_primary_serp"]:[],retryRecommended:h||c==="partial"&&(u||e.diagnostics.warnings?.some(w=>w.retryable)===!0),completeness:{paaWithoutAnswer:o,paaWithoutSource:d,paaAnswersRecovered:e.diagnostics.completeness?.paaAnswersRecovered??0,aioShareCaptured:e.diagnostics.completeness?.aioShareCaptured??null,paaRequested:t,paaReturned:e.flat.length,paaUnique:s},...e.diagnostics.paaLifecycle?{paaLifecycle:{...e.diagnostics.paaLifecycle,questionsFound:s,targetStatus:s>=t?"met":"not_met",materialStatus:o>0||d>0?"partial":"complete"}}:{}},e}function po(e,t,n){let a=e.diagnostics.paaLifecycle;if(!a)return e;let i={...a.retryBreakdown,browserRetries:t,providerFallbacks:n};return{...e,diagnostics:{...e.diagnostics,paaLifecycle:{...a,retryBreakdown:i,automaticRetries:i.controlRetries+i.browserRetries+i.runtimeRecoveries}}}}function Vl(e){return(e.diagnostics.degradationReasons??[]).includes("empty_primary_serp")?"No usable primary SERP surface was captured; the result may be incomplete.":"The harvest result was marked degraded."}function Ct(e){return e instanceof Error?e.message:String(e)}function Yl(e){return e==="location"?xl:ja}function Kl(e){return/ERR_TUNNEL_CONNECTION_FAILED|ERR_PROXY_CONNECTION_FAILED|ERR_SOCKS_CONNECTION_FAILED|tunnel connection failed|proxy connection failed|transport error: proxy/i.test(e)}function Jl(e){return/proxy unavailable|proxy_unavailable|connection_test_failed|did not return a proxy id|configured fallback/i.test(e)}function wo(e){return e==="captcha"||e==="proxy_tunnel_failed"||e==="proxy_unavailable"}function mo(e){return e==="browser_session_interrupted"}function ql(e){let t=e.diagnostics.debug?.locationEvidence,n=t?.expected?.canonicalLocation??e.location??"requested location",a=t?.candidates.slice(0,3).map(i=>`${i.city}, ${i.regionCode}`).join("; ");return a?`Google returned results for ${a}, not ${n}`:`Google returned results for a different location than ${n}`}function Xl(e,t){return t==="location"&&e.diagnostics.debug?.locationEvidence?.status==="mismatch"}function yo(e,t){if(t||!e.diagnostics.debug)return e;let n={...e.diagnostics};return delete n.debug,{...e,diagnostics:n}}async function Co(e,t){let n=t==null?3e3:t-Date.now();if(n<=0)return e;try{return await js(e,{totalBudgetMs:Math.min(3e3,n)})}catch(a){return console.warn(JSON.stringify({event:"harvest_goto_resolution_failed",message:Ct(a)})),e}}async function Xa(e,t){if(!(!e||!t))try{await So(e,t),console.info(JSON.stringify({event:"kernel_proxy_deleted",proxy_id_suffix:t.slice(-6)}))}catch(n){console.warn(JSON.stringify({event:"kernel_proxy_delete_failed",proxy_id_suffix:t.slice(-6),message:Ct(n)}))}}async function To(e,t,n,a,i,s){let o=Ps(t),d=new Yn,l=new Gn(o,d,a,i);if(n?.aborted)return{result:null,error:za(n),cleanup:await o.close(),debug:null};let U,S=n?new Promise((w,k)=>{U=()=>k(za(n)),n.addEventListener("abort",U,{once:!0})}):null,r=null,u=null,c,h=null;try{let w=l.extract(e,n);S&&w.catch(()=>{}),r=await(S?Promise.race([w,S]):w)}catch(w){u=w}finally{if(n&&U&&n.removeEventListener("abort",U),s){let w;try{let k=Dl(o);k.catch(()=>{});let f=await Promise.race([k,new Promise((m,L)=>{w=setTimeout(()=>L(new DOMException("PAA DOM evidence timed out","TimeoutError")),2e3)})]);await s(f)}catch(k){console.warn(JSON.stringify({event:"paa_dom_evidence_failed",message:Ct(k)}))}finally{w&&clearTimeout(w)}}h=r?.diagnostics.debug??(e.debug?{enabled:!0,request:{query:e.query,locationInput:e.location??null,canonicalLocation:null,locationResolved:null,locationMatchSource:null,locationAmbiguousCandidates:null,uule:null,gl:e.gl,hl:e.hl,device:e.device,proxyMode:e.proxyMode,proxyZip:e.proxyZip??null,serpIdentity:e.serpIdentity??null,serpOnly:e.serpOnly,pages:e.pages??1},browser:o.getDebugSnapshot()}:null),c=await o.close()}if(u){let w=sn(u),k=w==="timeout"||w==="request_aborted"||w==="browser_session_interrupted"?w:null,f=null;if(k)try{f=typeof l.getPartialResult=="function"?l.getPartialResult():null}catch{f=null}return f&&k?(f.diagnostics={...f.diagnostics,interruption:{code:k,reasonSource:"client_runtime",message:Ct(u)}},{result:f,error:u,cleanup:c,debug:h,salvagedFrom:u}):{result:null,error:u,cleanup:c,debug:h}}return{result:r,error:null,cleanup:c,debug:h}}async function ko(e){let t=typeof e=="object"&&e!==null?e:{},n=Rl(e),a=Wl(e),i=Hl(e),s=Bl(e),o=t.forceManagedSerp===!0,d=t.forceKernelSerp===!0,l=ho({forceManagedSerp:o,forceKernelSerp:d}),U=t.proxyMode,S=U==="location"||U==="none"||U==="configured"?U:gn,r=typeof t.kernelApiKey=="string"?t.kernelApiKey.trim():hi(),u=typeof t.kernelProxyId=="string"?t.kernelProxyId.trim():void 0,c={kernelApiKey:r,proxyMode:S,configuredKernelProxyId:u,location:typeof t.location=="string"?t.location:void 0,proxyZip:typeof t.proxyZip=="string"?t.proxyZip:void 0,gl:typeof t.gl=="string"?t.gl:"us"},h=typeof t.debug=="boolean"?t.debug:!1,w=S==="location"&&!!c.location,k=t.maxAttempts,f=typeof k=="number"&&Number.isInteger(k)&&k>=1?Math.min(ja,k):Yl(S),m=Math.min(ja,f),L=typeof t.softDeadlineMs=="number"?t.softDeadlineMs:null,R=new Vn,D=null,_=S,M=0,H=()=>L==null||L-Date.now()>=Ol;for(let P=0;P<m;P++){let y=P+1,E=Date.now();try{if(n?.aborted)throw za(n);let p=co({intent:l,brightDataAvailable:_s(),kernelFallbackAvailable:!!r,persistentKernelIdentityRequested:!!(t.serpIdentity||t.kernelProfileName),retryIndex:P,priorTerminalReason:D==null?null:sn(D),softDeadlineMs:L}),T=ea.parse({...t,kernelApiKey:r,proxyMode:_,debug:h||w}),N=p.plannedProvider==="brightdata"?"brightdata_browser":T.serpIdentity?"kernel_persistent_identity":"kernel_browser";await Re(a,{type:"started",attemptNumber:y,maxAttempts:m,method:N,provider:N==="brightdata_browser"?"brightdata":"kernel",planReason:p.reasonCode,planTimeoutMs:p.timeoutMs,retryKind:y===1?null:p.attemptKind==="provider_fallback"?"provider_fallback":"same_method",retryReason:y===1||D==null?null:sn(D),query:T.query,location:T.location??null,maxQuestions:T.maxQuestions,startedAt:new Date(E).toISOString()});let I=p.plannedProvider==="brightdata"?null:await Uo({...c,proxyMode:_,attemptIndex:P,fresh:_==="location"});if(p.plannedProvider==="kernel"&&!I)throw new Error("Kernel proxy resolution did not produce an execution plan");let W={...t,kernelApiKey:r,...I?{kernelProxyId:I.kernelProxyId,kernelProxyResolution:I.resolution}:{},proxyMode:_,keepDefaultProxy:P>0,softDeadlineMs:L==null?void 0:E+p.timeoutMs,debug:h||w};_==="none"&&(W.kernelProxyId=void 0);let x=ea.parse(W);console.info(JSON.stringify({event:"harvest_attempt_started",attempt_number:y,max_attempts:m,query:x.query,location:x.location??null,max_questions:x.maxQuestions}));let O=Zt(),j=null,ct=async J=>{uo(J.provider)!==p.plannedProvider&&(j=new an(p.plannedProvider,J.provider)),await Re(a,{type:"provider_session_started",attemptNumber:y,maxAttempts:m,provider:J.provider,providerSessionId:J.providerSessionId,billingMode:J.billingMode,observedAt:new Date().toISOString()})},st=O?.harvestBrowserMode==="headless-test"&&process.env[cs]==="true",q=O?await gs({...O,forceHeadless:st,forceHeadful:!st},()=>To(x,p,n,i,ct,s)):await To(x,p,n,i,ct,s);if(q.error||j){let J=j??q.error,Q=sn(J);(Q==="captcha"||Q==="proxy_tunnel_failed")&&_==="location"&&(M++,M>=2&&(_="none"));let wt=!q.result&&P<m-1&&H()&&(Q==="captcha"||mo(Q)||S==="location"&&wo(Q));if(Q==="captcha"?console.warn(JSON.stringify({event:"harvest_attempt_captcha",attempt_number:y,max_attempts:m,message:Ct(J),will_retry:wt})):wt&&console.warn(JSON.stringify({event:"harvest_attempt_proxy_retry",attempt_number:y,max_attempts:m,outcome:Q,message:Ct(J),will_retry:wt})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:Q,kernelSessionId:q.cleanup.kernelSessionId,questionCount:q.result?.totalQuestions??0,durationMs:Date.now()-E,error:Ct(J),willRetry:wt,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),D=J,wt)continue;if(q.result&&!j){let kt=await Co(q.result,L);return po(go(yo(kt,h),x.maxQuestions,x.questionsOnly),P,p.attemptKind==="provider_fallback"?1:0)}break}let ht=q.result;if(!ht)throw new Error("Harvest attempt completed without a result");if(Xl(ht,S)){let J=new $e(ql(ht)),Q=P<m-1&&H();if(console.warn(JSON.stringify({event:"harvest_attempt_location_mismatch",attempt_number:y,max_attempts:m,message:J.message,will_retry:Q})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:"location_mismatch",kernelSessionId:q.cleanup.kernelSessionId,questionCount:ht.totalQuestions,durationMs:Date.now()-E,error:J.message,willRetry:Q,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),D=J,Q)continue;break}let He=await Co(ht,L),G=po(go(yo(He,h),x.maxQuestions,x.questionsOnly),P,p.attemptKind==="provider_fallback"?1:0),Tt=Fl(G),V=Tt==="degraded_result"&&P<m-1&&H(),et=Tt==="degraded_result"?Vl(G):null;if(V&&console.warn(JSON.stringify({event:"harvest_attempt_degraded_result",attempt_number:y,max_attempts:m,degradation_reasons:G.diagnostics.degradationReasons,will_retry:!0})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:Tt,kernelSessionId:q.cleanup.kernelSessionId,questionCount:G.totalQuestions,durationMs:Date.now()-E,error:et,willRetry:V,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),V)continue;return(x.format==="json"||x.format==="both")&&await R.writeJSON(G,x.outputDir),(x.format==="csv"||x.format==="both")&&await Promise.all([R.writeCSV(G.flat,x.outputDir),G.videos.length>0?R.writeVideoCSV(G.videos,G.seed,x.outputDir):Promise.resolve(""),G.forums.length>0?R.writeForumCSV(G.forums,G.seed,x.outputDir):Promise.resolve(""),G.aiOverview.detected?R.writeAIOverviewCSV(G.aiOverview.citations,G.aiOverview.text,G.seed,x.outputDir):Promise.resolve(""),G.aiMode.detected?R.writeAIModeCSV(G.aiMode.citations,G.aiMode.text,G.seed,x.outputDir):Promise.resolve(""),G.whatPeopleSaying.length>0?R.writeWhatPeopleSayingCSV(G.whatPeopleSaying,G.seed,x.outputDir):Promise.resolve("")]),G}catch(p){let T=sn(p);(T==="captcha"||T==="proxy_tunnel_failed")&&_==="location"&&(M++,M>=2&&(_="none"));let N=P<m-1&&H()&&(T==="captcha"||mo(T)||S==="location"&&wo(T));if(T==="captcha"?console.warn(JSON.stringify({event:"harvest_attempt_captcha",attempt_number:y,max_attempts:m,message:Ct(p),will_retry:N})):N&&console.warn(JSON.stringify({event:"harvest_attempt_proxy_retry",attempt_number:y,max_attempts:m,outcome:T,message:Ct(p),will_retry:N})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:T,kernelSessionId:null,questionCount:0,durationMs:Date.now()-E,error:Ct(p),willRetry:N,cleanup:{kernelSessionId:null,kernelDeleteStarted:!1,kernelDeleteSucceeded:null,kernelDeleteError:null,browserCloseSucceeded:null,browserCloseError:null},debug:null,completedAt:new Date().toISOString()}),D=p,N)continue;if(T==="captcha")break;throw p}}throw D&&!(D instanceof it)?D:(console.warn(JSON.stringify({event:"harvest_captcha_exhausted",max_attempts:m,session_kind:r?"kernel":"local"})),new it(Ss(`CAPTCHA on all ${m} fresh sessions. Try again in a few minutes.`)))}var Ao=require("child_process"),St=require("fs"),oi=require("os"),ae=require("path"),ie=require("@fal-ai/client");var jl="https://api.deepinfra.com/v1/openai/chat/completions",Mo="https://openrouter.ai/api/v1/chat/completions",$a="Qwen/Qwen3.6-35B-A3B",zl=`You are a video prompt engineer for Seedance 2.0 text-to-video AI.
|
|
21902
|
+
`)}};var eo=require("crypto");var Sl="pr.oxylabs.io",Ul=7777,ul=10;function no(){return process.env.OXYLABS_USERNAME?.trim()||void 0}function ao(){return process.env.OXYLABS_PASSWORD?.trim()||void 0}function cl(){return(process.env.OXYLABS_COUNTRY?.trim()||"US").toUpperCase()}function io(){return!!(no()&&ao())}function hl(){let e="";for(let t=0;t<10;t++)e+=String((0,eo.randomInt)(0,10));return e}function gl(e={}){let t=no();if(!t)return;let n=t.startsWith("customer-")?t:`customer-${t}`,a=(e.country?.trim()||cl()).toUpperCase(),i=e.sticky?`-sessid-${hl()}-sesstime-${ul}`:"";return`${n}-cc-${a}${i}`}function Ya(e){return e.replace(/pr\.oxylabs\.io(:\d+)?/gi,"backup proxy").replace(/oxylabs/gi,"backup proxy")}function pl(e){return`mcp-backup-custom-${`${Date.now()}-${e??0}-${Math.random().toString(36).slice(2,8)}`}`}async function so(e,t={}){let n=gl({sticky:t.sticky}),a=ao();if(!n||!a)throw new Error("backup proxy pool is not configured");let i=new B({apiKey:e});try{let s=await i.proxies.create({type:"custom",name:pl(t.attemptIndex),protocol:"http",config:{host:Sl,port:Ul,username:n,password:a}});if(!s.id)throw new Error("backup proxy creation did not return a proxy id");return s.id}catch(s){let o=s instanceof Error?s.message:String(s);throw new Error(Ya(o))}}var wl={alabama:"AL",alaska:"AK",arizona:"AZ",arkansas:"AR",california:"CA",colorado:"CO",connecticut:"CT",delaware:"DE",florida:"FL",georgia:"GA",hawaii:"HI",idaho:"ID",illinois:"IL",indiana:"IN",iowa:"IA",kansas:"KS",kentucky:"KY",louisiana:"LA",maine:"ME",maryland:"MD",massachusetts:"MA",michigan:"MI",minnesota:"MN",mississippi:"MS",missouri:"MO",montana:"MT",nebraska:"NE",nevada:"NV","new hampshire":"NH","new jersey":"NJ","new mexico":"NM","new york":"NY","north carolina":"NC","north dakota":"ND",ohio:"OH",oklahoma:"OK",oregon:"OR",pennsylvania:"PA","rhode island":"RI","south carolina":"SC","south dakota":"SD",tennessee:"TN",texas:"TX",utah:"UT",vermont:"VT",virginia:"VA",washington:"WA","west virginia":"WV",wisconsin:"WI",wyoming:"WY"},ml={"atlanta|GA":"30303","austin|TX":"78701","baltimore|MD":"21201","boston|MA":"02108","boulder|CO":"80302","charlotte|NC":"28202","chicago|IL":"60601","colorado_springs|CO":"80903","columbus|OH":"43215","dallas|TX":"75201","denver|CO":"80202","detroit|MI":"48226","fort_collins|CO":"80524","fort_worth|TX":"76102","houston|TX":"77002","indianapolis|IN":"46204","jacksonville|FL":"32202","las_vegas|NV":"89101","los_angeles|CA":"90012","louisville|KY":"40202","loveland|CO":"80537","memphis|TN":"38103","miami|FL":"33131","minneapolis|MN":"55401","nashville|TN":"37203","new_york|NY":"10001","orlando|FL":"32801","philadelphia|PA":"19103","phoenix|AZ":"85004","portland|OR":"97205","raleigh|NC":"27601","richmond|VA":"23219","sacramento|CA":"95814","salt_lake_city|UT":"84101","san_antonio|TX":"78205","san_diego|CA":"92101","san_francisco|CA":"94103","san_jose|CA":"95113","seattle|WA":"98101"};function yl(e){return e?e.slice(-6):null}function dt(e,t,n,a,i,s=!1){return{\u006b\u0065\u0072\u006e\u0065\u006cProxyId:n,...s&&n?{disposableProxyId:n}:{},resolution:{source:e,proxyType:e==="disabled"?"none":e==="configured_fallback"?"configured":e==="isp_created"?"isp":e==="backup_custom"?"custom":e==="location_created"||e==="location_reused"?"residential":"unknown",proxyMode:t,proxyIdPresent:!!n,proxyIdSuffix:yl(n),target:a,error:i,disposable:s}}}function Cl(e){return e.trim().toLowerCase().replace(/\s+/g," ")}function Tl(e){return e.trim().toLowerCase().replace(/\./g,"").replace(/\s+/g," ")}function kl(e){if(!e)return!0;let t=Tl(e);return t==="united states"||t==="united states of america"||t==="usa"||t==="us"}function oo(e){let t=e.trim();return/^[A-Za-z]{2}$/.test(t)?t.toUpperCase():wl[Cl(t)]??null}function fl(e){let n=e.normalize("NFKD").replace(/[^\x00-\x7F]/g,"").toLowerCase().split(/[^a-z0-9]+/).filter(Boolean),a=n.join("_"),i=n.join("");return Array.from(new Set([a,i].filter(Boolean)))}function Ht(e,t,n){return n?`mcp-serp-residential-${e.toLowerCase()}-${t.toLowerCase()}-${n}`:`mcp-serp-residential-${e.toLowerCase()}-${t.toLowerCase()}`}function Kn(e,t){let n=`${Date.now()}-${t??0}-${Math.random().toString(36).slice(2,8)}`;return`${e}-fresh-${n}`}function Ml(e){return`mcp-serp-residential-us-zip-${e}`}function Nl(e,t){if(!e||t.toLowerCase()!=="us")return null;let n=Rs(e),a=n.split(",").map(U=>U.trim()).filter(Boolean);if(a.length>1&&kl(a[a.length-1])&&(a=a.slice(0,-1)),a.length===1){let U=oo(a[0]);return U?{canonicalLocation:n,level:"state",country:"US",state:U,city:"",cityCandidates:[],proxyName:Ht("US",U),config:{country:"US",state:U}}:null}let[i="",s=""]=a;if(!i||!s)return null;let o=oo(s);if(!o)return null;let d=fl(i),l=d[0];return l?{canonicalLocation:n,level:"city",country:"US",state:o,city:l,cityCandidates:d,proxyName:Ht("US",o,l),config:{country:"US",state:o,city:l}}:null}function vl(e){return`${e.city}|${e.state}`}function ro(e,t){return t&&/^\d{5}$/.test(t)?t:ml[vl(e)]??null}function lo(e,t){return{...e,level:"zip",zip:t,proxyName:Ml(t),config:{country:e.country,state:e.state,zip:t}}}function Ka(e,t){return{...e,proxyName:t}}function qa(e,t,n){return t.level==="zip"?e?.country?.toUpperCase()===t.country&&e?.zip===t.zip:e?.country?.toUpperCase()===t.country&&e?.state?.toUpperCase()===t.state&&(n?e?.city===n:!e?.city)}function _l(e,t){return e.find(n=>n.type==="residential"&&n.status!=="unavailable"&&!!n.id&&(n.name===t.proxyName||qa(n.config,t,t.level==="city"?t.city:void 0)))??null}function bl(e,t){for(let n of t.cityCandidates){let a=Ht(t.country,t.state,n),i=e.find(s=>s.type==="residential"&&s.status!=="unavailable"&&!!s.id&&(s.name===a||qa(s.config,t,n)));if(i)return i}return null}function Jn(e){return{...e,level:"state",proxyName:Ht(e.country,e.state),config:{country:e.country,state:e.state}}}function El(e,t){let n=Ht(t.country,t.state);return e.find(a=>a.type==="residential"&&a.status!=="unavailable"&&!!a.id&&(a.name===n||qa(a.config,t)))??null}function Pl(e,t){return Jn(e)}function Wt(e){return e instanceof Error?e.message:String(e)}function Il(e,t,n){let a=[],i=ro(e,t);if(i){let o=lo(e,i);a.push(Ka(o,Kn(o.proxyName,n)))}for(let o of e.cityCandidates){let d={...e,level:"city",city:o,proxyName:Ht(e.country,e.state,o),config:{country:e.country,state:e.state,city:o}};a.push(Ka(d,Kn(d.proxyName,n)))}let s=Jn(e);return a.push(Ka(s,Kn(s.proxyName,n))),a}async function Ja(e,t,n){if(e.backupOnExhaustion&&n.length>0&&e.\u006b\u0065\u0072\u006e\u0065\u006cApiKey&&io())try{let a=await so(e.\u006b\u0065\u0072\u006e\u0065\u006cApiKey,{attemptIndex:e.attemptIndex});return dt("backup_custom",e.proxyMode,a,t,null,!0)}catch(a){n.push(`backup: ${Ya(Wt(a))}`)}return dt("configured_fallback",e.proxyMode,e.configured\u004b\u0065\u0072\u006e\u0065\u006cProxyId,t,n.join(" | "))}async function Al(e,t,n){let a=[];for(let i of Il(n,t.proxyZip,t.attemptIndex))try{let s=await e.proxies.create({type:"residential",name:i.proxyName,config:i.level==="zip"?{country:i.country,zip:i.zip}:i.config});if(s.id)return dt("location_created",t.proxyMode,s.id,i,null,!0);a.push(`${i.proxyName}: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id`)}catch(s){a.push(`${i.proxyName}: ${Wt(s)}`)}if(process.env.\u004b\u0045\u0052\u004e\u0045\u004c_PROXY_TYPE!=="residential"){let i=Jn(n);try{let s=await e.proxies.create({type:"isp",name:Kn(`mcp-serp-isp-${i.country.toLowerCase()}-${(i.state??"").toLowerCase()}`,t.attemptIndex),config:{country:i.country,...i.state?{state:i.state}:{}}});if(s.id)return dt("isp_created",t.proxyMode,s.id,i,null,!0);a.push("isp: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id")}catch(s){a.push(`isp: ${Wt(s)}`)}}return Ja(t,n,a)}async function So(e,t){if(!e||!t)return;await new B({apiKey:e}).proxies.delete(t)}async function Uo(e){if(e.proxyMode==="none")return dt("disabled",e.proxyMode,void 0,null,null);if(e.proxyMode==="configured")return dt("configured_fallback",e.proxyMode,e.configured\u004b\u0065\u0072\u006e\u0065\u006cProxyId,null,null);let t=Nl(e.location,e.gl);if(!t||!e.\u006b\u0065\u0072\u006e\u0065\u006cApiKey)return dt("configured_fallback",e.proxyMode,e.configured\u004b\u0065\u0072\u006e\u0065\u006cProxyId,t,t?null:"location could not be normalized to a US city/state proxy target");let n=new B({apiKey:e.\u006b\u0065\u0072\u006e\u0065\u006cApiKey});try{let a=e.attemptIndex??0;if(e.fresh)return await Al(n,e,t);if(a>=1){let S=Pl(t,a),r=[];try{let u=await n.proxies.create({type:"residential",name:S.proxyName,config:S.config});if(u.id)return dt("location_created",e.proxyMode,u.id,S,null);r.push(`${S.state}: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id`)}catch(u){r.push(`${S.state}: ${Wt(u)}`)}return Ja(e,S,r)}let i=[];for await(let S of await n.proxies.list())i.push(S);let s=ro(t,e.proxyZip),o=[];if(s){let S=lo(t,s),r=_l(i,S);if(r?.id)return dt("location_reused",e.proxyMode,r.id,S,null);try{let u=await n.proxies.create({type:"residential",name:S.proxyName,config:{country:S.country,zip:s}});if(u.id)return dt("location_created",e.proxyMode,u.id,S,null);o.push(`${s}: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id`)}catch(u){o.push(`${s}: ${Wt(u)}`)}}let d=bl(i,t);if(d?.id)return dt("location_reused",e.proxyMode,d.id,t,o.join(" | ")||null);for(let S of t.cityCandidates)try{let r=await n.proxies.create({type:"residential",name:Ht(t.country,t.state,S),config:{country:t.country,state:t.state,city:S}});if(r.id)return dt("location_created",e.proxyMode,r.id,{...t,level:"city",city:S,proxyName:Ht(t.country,t.state,S),config:{country:t.country,state:t.state,city:S}},null);o.push(`${S}: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id`)}catch(r){o.push(`${S}: ${Wt(r)}`)}let l=Jn(t),U=El(i,l);if(U?.id)return dt("location_reused",e.proxyMode,U.id,l,o.join(" | "));try{let S=await n.proxies.create({type:"residential",name:l.proxyName,config:l.config});if(S.id)return dt("location_created",e.proxyMode,S.id,l,o.join(" | "));o.push(`${l.state}: \u004b\u0065\u0072\u006e\u0065\u006c did not return a proxy id`)}catch(S){o.push(`${l.state}: ${Wt(S)}`)}return Ja(e,t,o)}catch(a){return dt("configured_fallback",e.proxyMode,e.configured\u004b\u0065\u0072\u006e\u0065\u006cProxyId,t,Wt(a))}}var an=class extends Error{constructor(t,n){super(`SERP provider mismatch: planned ${t}, observed ${n}`),this.name="SerpProviderMismatchError"}};function uo(e){return e==="\u0062\u0072\u0069\u0067\u0068\u0074_\u0064\u0061\u0074\u0061_browser_api"?"\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061":"\u006b\u0065\u0072\u006e\u0065\u006c"}function co(e){return Ll({intent:e.intent,\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available:e.\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available,\u006b\u0065\u0072\u006e\u0065\u006cAvailable:!0,persistent\u004b\u0065\u0072\u006e\u0065\u006cIdentityRequested:e.persistent\u004b\u0065\u0072\u006e\u0065\u006cIdentityRequested,retryIndex:e.retryIndex,priorTerminalReason:e.priorTerminalReason,allowedFallbacks:e.\u006b\u0065\u0072\u006e\u0065\u006cFallbackAvailable&&e.intent!=="\u006b\u0065\u0072\u006e\u0065\u006c"?["\u006b\u0065\u0072\u006e\u0065\u006c"]:[],timeoutMs:e.softDeadlineMs==null?4e5:Math.max(1,e.softDeadlineMs-Date.now())})}function ho(e){if(e.forceManagedSerp&&e.force\u004b\u0065\u0072\u006e\u0065\u006cSerp)throw new Error("forceManagedSerp and force\u004b\u0065\u0072\u006e\u0065\u006cSerp cannot both be true");return e.forceManagedSerp?"\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061":e.force\u004b\u0065\u0072\u006e\u0065\u006cSerp?"\u006b\u0065\u0072\u006e\u0065\u006c":"auto"}function qn(e,t){if(!t)throw new Error(`Requested SERP provider is unavailable: ${e}`);return e}function Ll(e){if(!Number.isInteger(e.retryIndex)||e.retryIndex<0)throw new Error("retryIndex must be a non-negative integer");if(!Number.isFinite(e.timeoutMs)||e.timeoutMs<=0)throw new Error("timeoutMs must be a positive number");let t,n;e.intent==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"?(t=qn("\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061",e.\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available),n="explicit_\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"):e.intent==="\u006b\u0065\u0072\u006e\u0065\u006c"?(t=qn("\u006b\u0065\u0072\u006e\u0065\u006c",e.\u006b\u0065\u0072\u006e\u0065\u006cAvailable),n="explicit_\u006b\u0065\u0072\u006e\u0065\u006c"):e.persistent\u004b\u0065\u0072\u006e\u0065\u006cIdentityRequested?(t=qn("\u006b\u0065\u0072\u006e\u0065\u006c",e.\u006b\u0065\u0072\u006e\u0065\u006cAvailable),n="persistent_\u006b\u0065\u0072\u006e\u0065\u006c_identity"):e.\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available?(t="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061",n="managed_default"):(t=qn("\u006b\u0065\u0072\u006e\u0065\u006c",e.\u006b\u0065\u0072\u006e\u0065\u006cAvailable),n="\u006b\u0065\u0072\u006e\u0065\u006c_default");let a=e.allowedFallbacks.find(o=>o!==t&&(o==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"?e.\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available:e.\u006b\u0065\u0072\u006e\u0065\u006cAvailable)),i=e.retryIndex>0&&a?a:t,s=e.retryIndex===0?"primary":i===t?"same_provider_retry":"provider_fallback";return Object.freeze({plannedProvider:i,attemptKind:s,reasonCode:s==="primary"?n:s==="provider_fallback"?"provider_fallback":"same_provider_retry",retryIndex:e.retryIndex,priorTerminalReason:e.priorTerminalReason??null,timeoutMs:Math.floor(e.timeoutMs),fallbackAllowed:!!a})}var ja=2,xl=2,Ol=3e3;function za(e){return e.reason instanceof DOMException&&e.reason.name==="TimeoutError"?e.reason:new pt}function Rl(e){if(!e||typeof e!="object")return;let t=e.signal;if(t instanceof AbortSignal)return t}function Wl(e){if(!e||typeof e!="object")return;let t=e.onAttemptEvent;return typeof t=="function"?t:void 0}function Hl(e){if(!e||typeof e!="object")return;let t=e.onPaaProgress;return typeof t=="function"?t:void 0}function Bl(e){if(!e||typeof e!="object")return;let t=e.onPaaDomEvidence;return typeof t=="function"?t:void 0}async function Dl(e){let t=await e.evaluate(n=>{let a=n,i=Array.from(document.querySelectorAll(a.item)),s=i.map(l=>l.querySelector(a.clickTarget)).filter(l=>l!=null),o=l=>{let U=l.getBoundingClientRect();if(U.width<=0||U.height<=0)return!1;let S=U.left+U.width/2,r=U.top+U.height/2;if(S<0||r<0||S>=window.innerWidth||r>=window.innerHeight)return!1;let u=document.elementFromPoint(S,r);return u!=null&&u!==l&&!l.contains(u)&&!u.contains(l)},d=Array.from(document.querySelectorAll("body *")).filter(l=>{let U=window.getComputedStyle(l);if(U.position!=="fixed"&&U.position!=="sticky")return!1;let S=l.getBoundingClientRect();return S.width*S.height>=window.innerWidth*window.innerHeight*.15&&U.visibility!=="hidden"&&U.display!=="none"});return{itemCount:i.length,expandedItemCount:i.filter(l=>l.classList.contains(a.expandedClass)||l.querySelector(a.clickTarget)?.getAttribute("aria-expanded")==="true").length,answeredItemCount:i.filter(l=>(l.querySelector(a.answerContainer)?.textContent?.trim().length??0)>=10).length,sourcedItemCount:i.filter(l=>l.querySelector(`${a.answerContainer} a[href]`)!=null).length,clickTargetCount:s.length,clickTargetsWithButtonRole:s.filter(l=>l.getAttribute("role")==="button"||l.tagName==="BUTTON").length,clickTargetsWithExpandedState:s.filter(l=>l.hasAttribute("aria-expanded")).length,clickTargetsOffscreen:s.filter(l=>{let U=l.getBoundingClientRect(),S=U.left+U.width/2,r=U.top+U.height/2;return S<0||r<0||S>=window.innerWidth||r>=window.innerHeight}).length,clickTargetsBlockedAtCenter:s.filter(o).length,fixedOrStickyOverlayCount:d.length}},{item:X.item,answerContainer:X.answerContainer,clickTarget:X.clickTarget,expandedClass:X.expandedClass});return{capturedAt:new Date().toISOString(),...t,selectorVersion:ds}}async function Re(e,t){if(e)try{await e(t)}catch(n){console.warn(JSON.stringify({event:"harvest_attempt_log_failed",attempt_number:t.attemptNumber,message:n instanceof Error?n.message:String(n)}))}}function sn(e){if(e instanceof an)return"error";if(e instanceof it)return"captcha";if(e instanceof $e)return"location_mismatch";if(e instanceof pt)return"request_aborted";if(e instanceof Qt)return"browser_session_interrupted";if(e instanceof DOMException&&(e.name==="TimeoutError"||e.name==="AbortError"))return"timeout";let t=e instanceof Error?e.message:String(e);return/browser (?:has been )?closed|context (?:has been )?closed|target page, context or browser has been closed|session closed|page has been closed/i.test(t)?"browser_session_interrupted":Kl(t)?"proxy_tunnel_failed":Jl(t)?"proxy_unavailable":/timeout|timed out|Timeout \d+ms exceeded|deadline/i.test(t)?"timeout":"error"}function Fl(e){return e.diagnostics.degradedResult?"degraded_result":e.diagnostics?.completionStatus??(e.totalQuestions>0?"paa_found":"no_paa")}function Gl(e){return e.flat.length>0||e.organicResults.length>0||e.localPack.length>0||e.videos.length>0||e.forums.length>0||e.whatPeopleSaying.length>0||e.aiOverview.detected||e.aiMode.detected}function go(e,t,n){let a=Gl(e),i=(e.diagnostics.warnings?.length??0)>0,s=new Set(e.flat.map(w=>w.question.toLowerCase().replace(/[^\w\s]/g,"").replace(/\s+/g," ").trim())).size,o=n?0:e.flat.filter(w=>!w.answer?.trim()).length,d=n?0:e.flat.filter(w=>!w.source_cite?.trim()).length,l=e.diagnostics.completionStatus==="no_paa"&&(e.diagnostics.noPaaObserved===!0||a),U=e.diagnostics.completionStatus==="paa_found",S=e.diagnostics.paaLifecycle?.discoveryStatus,r=S==="interrupted"||S==="recovery_exhausted",u=U&&(s<t&&S!=="frontier_exhausted"||o>0||d>0||!!e.diagnostics.interruption||r),c=l?"complete":U&&s>0?u||i?"partial":"complete":a?i?"partial":"complete":"degraded",h=c==="degraded";return e.diagnostics={...e.diagnostics,resultQuality:c,degradedResult:h,degradationReasons:h?["empty_primary_serp"]:[],retryRecommended:h||c==="partial"&&(u||e.diagnostics.warnings?.some(w=>w.retryable)===!0),completeness:{paaWithoutAnswer:o,paaWithoutSource:d,paaAnswersRecovered:e.diagnostics.completeness?.paaAnswersRecovered??0,aioShareCaptured:e.diagnostics.completeness?.aioShareCaptured??null,paaRequested:t,paaReturned:e.flat.length,paaUnique:s},...e.diagnostics.paaLifecycle?{paaLifecycle:{...e.diagnostics.paaLifecycle,questionsFound:s,targetStatus:s>=t?"met":"not_met",materialStatus:o>0||d>0?"partial":"complete"}}:{}},e}function po(e,t,n){let a=e.diagnostics.paaLifecycle;if(!a)return e;let i={...a.retryBreakdown,browserRetries:t,providerFallbacks:n};return{...e,diagnostics:{...e.diagnostics,paaLifecycle:{...a,retryBreakdown:i,automaticRetries:i.controlRetries+i.browserRetries+i.runtimeRecoveries}}}}function Vl(e){return(e.diagnostics.degradationReasons??[]).includes("empty_primary_serp")?"No usable primary SERP surface was captured; the result may be incomplete.":"The harvest result was marked degraded."}function Ct(e){return e instanceof Error?e.message:String(e)}function Yl(e){return e==="location"?xl:ja}function Kl(e){return/ERR_TUNNEL_CONNECTION_FAILED|ERR_PROXY_CONNECTION_FAILED|ERR_SOCKS_CONNECTION_FAILED|tunnel connection failed|proxy connection failed|transport error: proxy/i.test(e)}function Jl(e){return/proxy unavailable|proxy_unavailable|connection_test_failed|did not return a proxy id|configured fallback/i.test(e)}function wo(e){return e==="captcha"||e==="proxy_tunnel_failed"||e==="proxy_unavailable"}function mo(e){return e==="browser_session_interrupted"}function ql(e){let t=e.diagnostics.debug?.locationEvidence,n=t?.expected?.canonicalLocation??e.location??"requested location",a=t?.candidates.slice(0,3).map(i=>`${i.city}, ${i.regionCode}`).join("; ");return a?`Google returned results for ${a}, not ${n}`:`Google returned results for a different location than ${n}`}function Xl(e,t){return t==="location"&&e.diagnostics.debug?.locationEvidence?.status==="mismatch"}function yo(e,t){if(t||!e.diagnostics.debug)return e;let n={...e.diagnostics};return delete n.debug,{...e,diagnostics:n}}async function Co(e,t){let n=t==null?3e3:t-Date.now();if(n<=0)return e;try{return await js(e,{totalBudgetMs:Math.min(3e3,n)})}catch(a){return console.warn(JSON.stringify({event:"harvest_goto_resolution_failed",message:Ct(a)})),e}}async function Xa(e,t){if(!(!e||!t))try{await So(e,t),console.info(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_proxy_deleted",proxy_id_suffix:t.slice(-6)}))}catch(n){console.warn(JSON.stringify({event:"\u006b\u0065\u0072\u006e\u0065\u006c_proxy_delete_failed",proxy_id_suffix:t.slice(-6),message:Ct(n)}))}}async function To(e,t,n,a,i,s){let o=Ps(t),d=new Yn,l=new Gn(o,d,a,i);if(n?.aborted)return{result:null,error:za(n),cleanup:await o.close(),debug:null};let U,S=n?new Promise((w,k)=>{U=()=>k(za(n)),n.addEventListener("abort",U,{once:!0})}):null,r=null,u=null,c,h=null;try{let w=l.extract(e,n);S&&w.catch(()=>{}),r=await(S?Promise.race([w,S]):w)}catch(w){u=w}finally{if(n&&U&&n.removeEventListener("abort",U),s){let w;try{let k=Dl(o);k.catch(()=>{});let f=await Promise.race([k,new Promise((m,L)=>{w=setTimeout(()=>L(new DOMException("PAA DOM evidence timed out","TimeoutError")),2e3)})]);await s(f)}catch(k){console.warn(JSON.stringify({event:"paa_dom_evidence_failed",message:Ct(k)}))}finally{w&&clearTimeout(w)}}h=r?.diagnostics.debug??(e.debug?{enabled:!0,request:{query:e.query,locationInput:e.location??null,canonicalLocation:null,locationResolved:null,locationMatchSource:null,locationAmbiguousCandidates:null,uule:null,gl:e.gl,hl:e.hl,device:e.device,proxyMode:e.proxyMode,proxyZip:e.proxyZip??null,serpIdentity:e.serpIdentity??null,serpOnly:e.serpOnly,pages:e.pages??1},browser:o.getDebugSnapshot()}:null),c=await o.close()}if(u){let w=sn(u),k=w==="timeout"||w==="request_aborted"||w==="browser_session_interrupted"?w:null,f=null;if(k)try{f=typeof l.getPartialResult=="function"?l.getPartialResult():null}catch{f=null}return f&&k?(f.diagnostics={...f.diagnostics,interruption:{code:k,reasonSource:"client_runtime",message:Ct(u)}},{result:f,error:u,cleanup:c,debug:h,salvagedFrom:u}):{result:null,error:u,cleanup:c,debug:h}}return{result:r,error:null,cleanup:c,debug:h}}async function ko(e){let t=typeof e=="object"&&e!==null?e:{},n=Rl(e),a=Wl(e),i=Hl(e),s=Bl(e),o=t.forceManagedSerp===!0,d=t.force\u004b\u0065\u0072\u006e\u0065\u006cSerp===!0,l=ho({forceManagedSerp:o,force\u004b\u0065\u0072\u006e\u0065\u006cSerp:d}),U=t.proxyMode,S=U==="location"||U==="none"||U==="configured"?U:gn,r=typeof t.\u006b\u0065\u0072\u006e\u0065\u006cApiKey=="string"?t.\u006b\u0065\u0072\u006e\u0065\u006cApiKey.trim():hi(),u=typeof t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId=="string"?t.\u006b\u0065\u0072\u006e\u0065\u006cProxyId.trim():void 0,c={\u006b\u0065\u0072\u006e\u0065\u006cApiKey:r,proxyMode:S,configured\u004b\u0065\u0072\u006e\u0065\u006cProxyId:u,location:typeof t.location=="string"?t.location:void 0,proxyZip:typeof t.proxyZip=="string"?t.proxyZip:void 0,gl:typeof t.gl=="string"?t.gl:"us"},h=typeof t.debug=="boolean"?t.debug:!1,w=S==="location"&&!!c.location,k=t.maxAttempts,f=typeof k=="number"&&Number.isInteger(k)&&k>=1?Math.min(ja,k):Yl(S),m=Math.min(ja,f),L=typeof t.softDeadlineMs=="number"?t.softDeadlineMs:null,R=new Vn,D=null,_=S,M=0,H=()=>L==null||L-Date.now()>=Ol;for(let P=0;P<m;P++){let y=P+1,E=Date.now();try{if(n?.aborted)throw za(n);let p=co({intent:l,\u0062\u0072\u0069\u0067\u0068\u0074\u0044\u0061\u0074\u0061Available:_s(),\u006b\u0065\u0072\u006e\u0065\u006cFallbackAvailable:!!r,persistent\u004b\u0065\u0072\u006e\u0065\u006cIdentityRequested:!!(t.serpIdentity||t.\u006b\u0065\u0072\u006e\u0065\u006cProfileName),retryIndex:P,priorTerminalReason:D==null?null:sn(D),softDeadlineMs:L}),T=ea.parse({...t,\u006b\u0065\u0072\u006e\u0065\u006cApiKey:r,proxyMode:_,debug:h||w}),N=p.plannedProvider==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"?"\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061_browser":T.serpIdentity?"\u006b\u0065\u0072\u006e\u0065\u006c_persistent_identity":"\u006b\u0065\u0072\u006e\u0065\u006c_browser";await Re(a,{type:"started",attemptNumber:y,maxAttempts:m,method:N,provider:N==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061_browser"?"\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061":"\u006b\u0065\u0072\u006e\u0065\u006c",planReason:p.reasonCode,planTimeoutMs:p.timeoutMs,retryKind:y===1?null:p.attemptKind==="provider_fallback"?"provider_fallback":"same_method",retryReason:y===1||D==null?null:sn(D),query:T.query,location:T.location??null,maxQuestions:T.maxQuestions,startedAt:new Date(E).toISOString()});let I=p.plannedProvider==="\u0062\u0072\u0069\u0067\u0068\u0074\u0064\u0061\u0074\u0061"?null:await Uo({...c,proxyMode:_,attemptIndex:P,fresh:_==="location"});if(p.plannedProvider==="\u006b\u0065\u0072\u006e\u0065\u006c"&&!I)throw new Error("\u004b\u0065\u0072\u006e\u0065\u006c proxy resolution did not produce an execution plan");let W={...t,\u006b\u0065\u0072\u006e\u0065\u006cApiKey:r,...I?{\u006b\u0065\u0072\u006e\u0065\u006cProxyId:I.\u006b\u0065\u0072\u006e\u0065\u006cProxyId,\u006b\u0065\u0072\u006e\u0065\u006cProxyResolution:I.resolution}:{},proxyMode:_,keepDefaultProxy:P>0,softDeadlineMs:L==null?void 0:E+p.timeoutMs,debug:h||w};_==="none"&&(W.\u006b\u0065\u0072\u006e\u0065\u006cProxyId=void 0);let x=ea.parse(W);console.info(JSON.stringify({event:"harvest_attempt_started",attempt_number:y,max_attempts:m,query:x.query,location:x.location??null,max_questions:x.maxQuestions}));let O=Zt(),j=null,ct=async J=>{uo(J.provider)!==p.plannedProvider&&(j=new an(p.plannedProvider,J.provider)),await Re(a,{type:"provider_session_started",attemptNumber:y,maxAttempts:m,provider:J.provider,providerSessionId:J.providerSessionId,billingMode:J.billingMode,observedAt:new Date().toISOString()})},st=O?.harvestBrowserMode==="headless-test"&&process.env[cs]==="true",q=O?await gs({...O,forceHeadless:st,forceHeadful:!st},()=>To(x,p,n,i,ct,s)):await To(x,p,n,i,ct,s);if(q.error||j){let J=j??q.error,Q=sn(J);(Q==="captcha"||Q==="proxy_tunnel_failed")&&_==="location"&&(M++,M>=2&&(_="none"));let wt=!q.result&&P<m-1&&H()&&(Q==="captcha"||mo(Q)||S==="location"&&wo(Q));if(Q==="captcha"?console.warn(JSON.stringify({event:"harvest_attempt_captcha",attempt_number:y,max_attempts:m,message:Ct(J),will_retry:wt})):wt&&console.warn(JSON.stringify({event:"harvest_attempt_proxy_retry",attempt_number:y,max_attempts:m,outcome:Q,message:Ct(J),will_retry:wt})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:Q,\u006b\u0065\u0072\u006e\u0065\u006cSessionId:q.cleanup.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,questionCount:q.result?.totalQuestions??0,durationMs:Date.now()-E,error:Ct(J),willRetry:wt,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),D=J,wt)continue;if(q.result&&!j){let kt=await Co(q.result,L);return po(go(yo(kt,h),x.maxQuestions,x.questionsOnly),P,p.attemptKind==="provider_fallback"?1:0)}break}let ht=q.result;if(!ht)throw new Error("Harvest attempt completed without a result");if(Xl(ht,S)){let J=new $e(ql(ht)),Q=P<m-1&&H();if(console.warn(JSON.stringify({event:"harvest_attempt_location_mismatch",attempt_number:y,max_attempts:m,message:J.message,will_retry:Q})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:"location_mismatch",\u006b\u0065\u0072\u006e\u0065\u006cSessionId:q.cleanup.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,questionCount:ht.totalQuestions,durationMs:Date.now()-E,error:J.message,willRetry:Q,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),D=J,Q)continue;break}let He=await Co(ht,L),G=po(go(yo(He,h),x.maxQuestions,x.questionsOnly),P,p.attemptKind==="provider_fallback"?1:0),Tt=Fl(G),V=Tt==="degraded_result"&&P<m-1&&H(),et=Tt==="degraded_result"?Vl(G):null;if(V&&console.warn(JSON.stringify({event:"harvest_attempt_degraded_result",attempt_number:y,max_attempts:m,degradation_reasons:G.diagnostics.degradationReasons,will_retry:!0})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:Tt,\u006b\u0065\u0072\u006e\u0065\u006cSessionId:q.cleanup.\u006b\u0065\u0072\u006e\u0065\u006cSessionId,questionCount:G.totalQuestions,durationMs:Date.now()-E,error:et,willRetry:V,cleanup:q.cleanup,debug:q.debug,completedAt:new Date().toISOString()}),await Xa(r,I?.disposableProxyId),V)continue;return(x.format==="json"||x.format==="both")&&await R.writeJSON(G,x.outputDir),(x.format==="csv"||x.format==="both")&&await Promise.all([R.writeCSV(G.flat,x.outputDir),G.videos.length>0?R.writeVideoCSV(G.videos,G.seed,x.outputDir):Promise.resolve(""),G.forums.length>0?R.writeForumCSV(G.forums,G.seed,x.outputDir):Promise.resolve(""),G.aiOverview.detected?R.writeAIOverviewCSV(G.aiOverview.citations,G.aiOverview.text,G.seed,x.outputDir):Promise.resolve(""),G.aiMode.detected?R.writeAIModeCSV(G.aiMode.citations,G.aiMode.text,G.seed,x.outputDir):Promise.resolve(""),G.whatPeopleSaying.length>0?R.writeWhatPeopleSayingCSV(G.whatPeopleSaying,G.seed,x.outputDir):Promise.resolve("")]),G}catch(p){let T=sn(p);(T==="captcha"||T==="proxy_tunnel_failed")&&_==="location"&&(M++,M>=2&&(_="none"));let N=P<m-1&&H()&&(T==="captcha"||mo(T)||S==="location"&&wo(T));if(T==="captcha"?console.warn(JSON.stringify({event:"harvest_attempt_captcha",attempt_number:y,max_attempts:m,message:Ct(p),will_retry:N})):N&&console.warn(JSON.stringify({event:"harvest_attempt_proxy_retry",attempt_number:y,max_attempts:m,outcome:T,message:Ct(p),will_retry:N})),await Re(a,{type:"finished",attemptNumber:y,maxAttempts:m,outcome:T,\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,questionCount:0,durationMs:Date.now()-E,error:Ct(p),willRetry:N,cleanup:{\u006b\u0065\u0072\u006e\u0065\u006cSessionId:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteStarted:!1,\u006b\u0065\u0072\u006e\u0065\u006cDeleteSucceeded:null,\u006b\u0065\u0072\u006e\u0065\u006cDeleteError:null,browserCloseSucceeded:null,browserCloseError:null},debug:null,completedAt:new Date().toISOString()}),D=p,N)continue;if(T==="captcha")break;throw p}}throw D&&!(D instanceof it)?D:(console.warn(JSON.stringify({event:"harvest_captcha_exhausted",max_attempts:m,session_kind:r?"\u006b\u0065\u0072\u006e\u0065\u006c":"local"})),new it(Ss(`CAPTCHA on all ${m} fresh sessions. Try again in a few minutes.`)))}var Ao=require("child_process"),St=require("fs"),oi=require("os"),ae=require("path"),ie=require("@fal-ai/client");var jl="https://api.deepinfra.com/v1/openai/chat/completions",Mo="https://openrouter.ai/api/v1/chat/completions",$a="Qwen/Qwen3.6-35B-A3B",zl=`You are a video prompt engineer for Seedance 2.0 text-to-video AI.
|
|
21903
21903
|
|
|
21904
21904
|
IMPORTANT TECHNICAL CONTEXT: Clip 2 will be generated using image-to-video, meaning it will start from the exact last frame of Clip 1. The two clips will be visually seamless \u2014 same location, same characters, continuous motion. You must write prompts that make this feel like one uninterrupted 16-second video.
|
|
21905
21905
|
|