-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcontentScript.js
More file actions
1 lines (1 loc) · 37.4 KB
/
contentScript.js
File metadata and controls
1 lines (1 loc) · 37.4 KB
1
(()=>{"use strict";var e={751:(e,t,n)=>{n.d(t,{g:()=>i});class i{constructor(e){this.maxTokens=4e3,this.apiKey=e}async extractClaimsFromChunk(e){try{if(!this.apiKey||""===this.apiKey)throw new Error("OpenAI API key not provided or empty");if(!this.apiKey.startsWith("sk-"))throw new Error("Invalid OpenAI API key format");console.log("Sending request to OpenAI API...");const t=await fetch("https://api.openai.com/v1/chat/completions",{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.apiKey}`},body:JSON.stringify({model:"gpt-4",messages:[{role:"system",content:'Extract factual claims from the text. Return a JSON array where each item has:\n - claim: The exact claim text\n - confidence: 0-1 score of how clearly it\'s a factual claim (0.9+ for very clear factual claims with specific data, 0.7-0.9 for likely factual claims, below 0.7 for statements that might be factual but lack specificity)\n \n Only include clear, verifiable claims that could be fact-checked against reliable sources.\n \n EXCLUDE the following types of statements:\n - Opinions, subjective judgments, or matters of taste\n - Speculative statements containing "might," "may," "could," "possibly," etc.\n - Value judgments containing "good," "bad," "best," "worst," etc.\n - Relative or comparative claims without specific metrics\n - Personal beliefs starting with "I think," "I believe," etc.\n - Questions or hypotheticals\n - Future predictions\n - Claims about intentions or motivations\n - General claims without specificity\n \n INCLUDE statements that:\n - Contain specific numbers, dates, statistics, or measurements\n - Reference research, studies, or specific published findings\n - Make clear cause-effect assertions based on evidence\n - Describe specific historical events, discoveries, or observations\n - Reference specific organizations, people, or places in relation to verifiable actions\n - Make definitive statements about established processes or systems\n \n Prioritize precision, specificity, and verifiability in your selection.'},{role:"user",content:e}],temperature:.1})});if(!t.ok)throw new Error(`OpenAI API error: ${t.status}`);const n=await t.json();if(!(n&&n.choices&&n.choices[0]&&n.choices[0].message&&n.choices[0].message.content))throw new Error("Invalid response format from OpenAI API");const i=n.choices[0].message.content;try{const e=JSON.parse(i);if(!Array.isArray(e))throw new Error("Expected JSON array in response");return{claims:e.map((e=>e.claim)),confidence:e.map((e=>e.confidence))}}catch(e){console.error("Failed to parse OpenAI response as JSON:",e);const t=i.match(/claim["\s:]+([^"]+)/gi),n=i.match(/confidence["\s:]+([0-9.]+)/gi);if(t){const e=t.map((e=>{const t=e.match(/claim["\s:]+(.+)/i);return t?t[1].trim():""})).filter((e=>e)),i=n?n.map((e=>{const t=e.match(/confidence["\s:]+([0-9.]+)/i);return t?parseFloat(t[1]):.5})):e.map((()=>.5));if(e.length>0)return{claims:e,confidence:i}}throw new Error("Failed to parse claims from OpenAI response")}}catch(e){return console.error("LLM extraction failed:",e),{claims:[],confidence:[]}}}chunkText(e,t=3e3){const n=e.split(/\n\s*\n/),i=[];let o="";for(const e of n)(o+e).length>t?(o&&i.push(o),o=e):o+=(o?"\n\n":"")+e;return o&&i.push(o),i}async extractClaims(e){const t=this.chunkText(e),n=await Promise.all(t.map((e=>this.extractClaimsFromChunk(e))));return{claims:n.flatMap((e=>e.claims)),confidence:n.flatMap((e=>e.confidence))}}}}},t={};function n(i){var o=t[i];if(void 0!==o)return o.exports;var s=t[i]={exports:{}};return e[i](s,s.exports,n),s.exports}n.d=(e,t)=>{for(var i in t)n.o(t,i)&&!n.o(e,i)&&Object.defineProperty(e,i,{enumerable:!0,get:t[i]})},n.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t);class i{constructor(){this.claimCounter=0}getMainContent(){console.log("Getting main content from webpage");const e=document.body.querySelectorAll("p, h1, h2, h3, h4, h5, h6, article, section, div");console.log(`Found ${e.length} potential text elements`);const t=Array.from(e).filter((e=>{const t=e.textContent||"";if(t.length<30)return!1;if("div"===e.tagName.toLowerCase()){const n=t.length>100,i=t.split(".").length>2,o=null!==e.querySelector("p");return n&&i&&!o}return!0}));console.log(`Filtered down to ${t.length} content elements`),t.forEach(((e,t)=>{e.getAttribute("data-deepcite-id")||(e.setAttribute("data-deepcite-id",`content-${t}`),e.style.border="1px dashed rgba(47, 128, 237, 0.3)")}));const n=[...t.map((e=>e.textContent)).filter((e=>e.length>30)),...Array.from(document.getElementsByTagName("p")).filter((e=>e.textContent&&e.textContent.length>50)).map((e=>e.textContent))],i=[];for(const e of n)i.includes(e)||i.push(e);return console.log(`Final content extraction: ${i.length} text blocks`),i}isLikelyClaim(e){if(e.length<20)return!1;const t=/\b(I think|I believe|in my opinion|I feel|it might be|it may be|we believe|probably|possibly|maybe|perhaps|likely|unlikely|seems to|could be|might be|may be|allegedly|supposedly|apparently)\b/i.test(e);if(t)return!1;if(e.trim().endsWith("?"))return!1;const n=/\b(beautiful|ugly|wonderful|terrible|best|worst|amazing|awful|good|bad|love|hate|favorite|great|excellent|poor|superior|inferior)\b/i.test(e);if(n)return!1;const i=/\d/.test(e),o=/\s[A-Z][a-z]+/.test(e),s=/(found|showed|discovered|reported|according to|study|research|analysis|evidence|data|results|concluded|suggests|indicates|confirms|demonstrates|proves|supported by|measured|observed|conducted|survey|experiments|calculations|statistics|percent|percentage|proportion|scientific|researchers|scientists|experts|published|journal|paper|investigate|examine|analyze|determine|established|verify|confirmed|identify|document|record|reveal|show that|demonstrate that|indicate that|prove that|establish that|verified that)/i.test(e);return!(t||n||!(e.includes("climate")||e.includes("research")||e.includes("study")||e.includes("found")||e.includes("data")||e.includes("showed")))||(i||o)&&s}splitIntoSentences(e){return e.replace(/([.?!])\s+(?=[A-Z])/g,"$1|").split("|").map((e=>e.trim())).filter((e=>e.length>0))}calculateRelevance(e){let t=.5;return/\d/.test(e)&&(t+=.15),/\d+(\.\d+)?%|\d+ percent|\d+ percentage/i.test(e)&&(t+=.1),/\s[A-Z][a-z]+/.test(e)&&(t+=.1),/(study|research|found|showed|evidence|data|results|published|journal|paper)/i.test(e)&&(t+=.15),/(according to|reported by|measured|observed|conducted|statistics|researchers|scientists)/i.test(e)&&(t+=.1),e.length>200&&(t-=.1),/\b(I|we|our|my)\b/i.test(e)&&(t-=.15),/\b(will|going to|shall|would)\b/i.test(e)&&(t-=.05),Math.min(Math.max(t,0),1)}async extractClaims(e=5){const t=this.getMainContent(),n=[];let i=0;for(let o=0;o<t.length;o++){const s=this.splitIntoSentences(t[o]);for(const t of s)if(i++,this.isLikelyClaim(t)){const s=this.calculateRelevance(t),a=t.replace(/\[\d+\]/g,"");if(n.push({id:++this.claimCounter,text:t,cleanText:a,context:{page:1,paragraph:o},relevance:s}),n.length>=e)return{claims:n,totalProcessed:i}}}return{claims:n,totalProcessed:i}}}var o=n(751);class s{constructor(e){this.pdfDoc=null,this.textItems=[],this.url=e,pdfjsLib.GlobalWorkerOptions.workerSrc=chrome.runtime.getURL("pdf.worker.min.js")}async init(){try{const e=pdfjsLib.getDocument(this.url);this.pdfDoc=await e.promise}catch(e){throw console.error("Error loading PDF:",e),e}}async getPageContent(e){const t=await this.pdfDoc.getPage(e),n=t.getViewport({scale:1}),i=await t.getTextContent();let o,s=0;return i.items.forEach((t=>{void 0!==o&&Math.abs(t.transform[5]-o)>15&&s++,o=t.transform[5],this.textItems.push({str:t.str,pageNum:e,paragraph:s})})),{text:i.items.map((e=>e.str)).join(" "),viewport:n,pageNum:e}}async getAllContent(){const e=this.pdfDoc.numPages,t=[];for(let n=1;n<=e;n++){const{text:e}=await this.getPageContent(n);t.push(e)}return t.join("\n\n")}findTextLocation(e){for(let t=0;t<this.textItems.length;t++){const n=100;if(this.textItems.slice(t,t+n).map((e=>e.str)).join(" ").includes(e))return this.textItems[t]}return null}}function a(e){return e>=.8?"var(--high-confidence)":e>=.5?"var(--medium-confidence)":"var(--low-confidence)"}function l(){const e=document.createElement("span");return e.className="deepcite-badge",e.textContent="DEEPCITE",e.title="This element contains a factual claim verified by DeepCite",e}function r(e,t){if(console.log("Starting highlight process for claim:",e.cleanText),document.querySelector(`[data-claim-id="${e.id}"]`))return console.log("This claim is already highlighted, skipping duplicate highlight"),!0;const n=document.getElementsByTagName("p");console.log("Found paragraphs:",n.length);let i=!1;for(let o=0;o<n.length;o++){const s=n[o];if((s.textContent?.replace(/\[\d+\]/g,"")||"").includes(e.cleanText)){console.log("Found matching paragraph!",s.getAttribute("data-deepcite-id")),i=!0;try{if(s.style.backgroundColor="rgba(47, 128, 237, 0.2)",s.style.borderLeft="4px solid rgba(47, 128, 237, 0.6)",s.style.padding="8px",s.style.cursor="pointer",s.style.transition="all 0.25s ease",s.style.borderRadius="3px",s.style.boxShadow="0 1px 3px rgba(0, 0, 0, 0.05)",s.setAttribute("data-claim-id",e.id.toString()),!s.querySelector(".deepcite-badge")){const t=l();if(void 0!==e.confidence){const n=Math.round(100*e.confidence);t.title=`Confidence score: ${n}%`}s.firstChild?s.insertBefore(t,s.firstChild):s.appendChild(t)}console.log("Applied enhanced styles to paragraph")}catch(e){console.error("Error highlighting paragraph:",e)}let n=null,o=null,r=0;const c=()=>{if(!n)return;let i="";if(void 0!==e.confidence&&(i+=`\n <div class="exa-claim-confidence" style="margin-bottom: 10px; padding: 6px 8px; background: rgba(47, 128, 237, 0.05); border-radius: 6px; font-size: 13px;">\n <span style="font-weight: bold;">Certainty:</span> \n <span style="display: inline-block; height: 8px; border-radius: 4px; margin: 0 6px; width: ${Math.round(100*e.confidence)}px; background-color: ${a(e.confidence)};">\n </span>\n <span style="font-weight: 500; margin-left: 4px; color: ${a(e.confidence)}">\n ${Math.round(100*e.confidence)}%\n </span>\n </div>\n `),i+=`<div style="font-weight: 600; margin-bottom: 10px; color: #333;">\n Sources (${t.length})\n </div>`,t.length<=2)i+=t.map(((e,n)=>`\n <div style="margin-bottom: 10px; padding: 6px;">\n <div style="display: flex; align-items: center; margin-bottom: 6px;">\n <img src="https://www.google.com/s2/favicons?domain=${new URL(e.url).hostname}" alt="Source icon" style="width: 16px; height: 16px; margin-right: 8px; border-radius: 2px;">\n <strong>${e.title}</strong>\n <span style="display: inline-block; padding: 2px 6px; background: rgba(47, 128, 237, 0.05); border-radius: 4px; font-size: 12px; margin-left: 8px; color: #666;">\n ${Math.round(100*e.score)}%\n </span>\n </div>\n <a href="${e.url}" target="_blank" style="color: #007AFF; text-decoration: none;">View source</a>\n ${n<t.length-1?'<hr style="margin: 10px 0; border: 0; border-top: 1px solid #eee;">':""}\n </div>\n `)).join("");else{const e=t[r];i+=`\n <div style="margin-bottom: 10px; padding: 6px;">\n <div style="display: flex; align-items: center; margin-bottom: 6px;">\n <img src="https://www.google.com/s2/favicons?domain=${new URL(e.url).hostname}" alt="Source icon" style="width: 16px; height: 16px; margin-right: 8px; border-radius: 2px;">\n <strong>${e.title}</strong>\n <span style="display: inline-block; padding: 2px 6px; background: rgba(47, 128, 237, 0.05); border-radius: 4px; font-size: 12px; margin-left: 8px; color: #666;">\n ${Math.round(100*e.score)}%\n </span>\n </div>\n <a href="${e.url}" target="_blank" style="color: #007AFF; text-decoration: none;">View source</a>\n </div>\n <div style="display: flex; align-items: center; justify-content: space-between; margin-top: 10px; padding-top: 8px; border-top: 1px solid #eee;">\n <button id="prev-btn" ${0===r?"disabled":""} style="background: #f8f9fa; border: 1px solid #eee; color: #333; cursor: pointer; padding: 4px 10px; border-radius: 6px;">\n ← Previous\n </button>\n <span>${r+1}/${t.length}</span>\n <button id="next-btn" ${r===t.length-1?"disabled":""} style="background: #f8f9fa; border: 1px solid #eee; color: #333; cursor: pointer; padding: 4px 10px; border-radius: 6px;">\n Next →\n </button>\n </div>\n `}if(n.innerHTML=i,t.length>2){const e=n.querySelector("#prev-btn"),i=n.querySelector("#next-btn");e&&e.addEventListener("click",(()=>{r>0&&(r--,c())})),i&&i.addEventListener("click",(()=>{r<t.length-1&&(r++,c())}))}},d=()=>{o&&(clearTimeout(o),o=null)},p=()=>{d(),o=window.setTimeout((()=>{n&&(n.remove(),n=null)}),300)};s.addEventListener("mouseenter",(()=>{d();const e=document.querySelector(".exa-tooltip");e&&e.remove();const t=document.createElement("div");t.className="exa-tooltip",t.style.position="fixed",t.style.background="white",t.style.border="1px solid #e0e0e0",t.style.boxShadow="0 8px 24px rgba(0,0,0,0.1)",t.style.padding="14px 18px",t.style.borderRadius="8px",t.style.fontSize="14px",t.style.maxWidth="320px",t.style.zIndex="999999",t.style.color="#333",t.style.backdropFilter="blur(10px)",t.style.opacity="0",t.style.transform="translateY(8px)",t.style.transition="opacity 0.25s, transform 0.25s",t.style.fontFamily='-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif',t.style.lineHeight="1.5";const i=s.getBoundingClientRect();t.style.top=`${i.bottom+5}px`,t.style.left=`${i.left}px`,document.body.appendChild(t),n=t,setTimeout((()=>{t.style.opacity="1",t.style.transform="translateY(0)"}),10),c(),t.addEventListener("mouseenter",d),t.addEventListener("mouseleave",p)})),s.addEventListener("mouseleave",p);break}}return i}async function c(e=!1){console.log("Creating claims overlay, isPDF:",e),d();let t=document.querySelector(".deepcite-claims-overlay");if(console.log("Existing overlay found:",!!t),t){console.log("Using existing overlay");const e=t.querySelector(".deepcite-claims-header small");return e&&(e.textContent="Processing..."),t}console.log("Creating new overlay"),t=document.createElement("div"),t.className="deepcite-claims-overlay";const n=document.createElement("button");n.className="deepcite-overlay-close",n.textContent="×",n.title="Toggle sidebar",n.addEventListener("click",(e=>{e.stopPropagation(),t.classList.contains("minimized")?(t.classList.remove("minimized"),n.title="Toggle sidebar"):(t.classList.add("minimized"),n.title="Expand sidebar")})),n.addEventListener("dblclick",(e=>{e.stopPropagation(),t.classList.add("closed"),setTimeout((()=>{t.classList.contains("closed")&&(t.style.display="none",d())}),300)})),t.appendChild(n);const i=document.createElement("div");i.className="deepcite-claims-header",i.innerHTML="\n <h3>Detected Claims</h3>\n <small>Processing...</small>\n ",t.appendChild(i),function(e,t){let n=0,i=0,o=0,s=0;const a=t=>{t.preventDefault();const o=n-t.clientX,s=i-t.clientY;n=t.clientX,i=t.clientY;const a=e.offsetTop-s,l=e.offsetLeft-o;a>=20&&a+e.offsetHeight<=window.innerHeight-20&&(e.style.top=`${a}px`),l>=20&&l+e.offsetWidth<=window.innerWidth-20&&(e.style.left=`${l}px`)},l=()=>{document.removeEventListener("mousemove",a),document.removeEventListener("mouseup",l),e.classList.remove("dragging")};t.addEventListener("mousedown",(t=>{t.preventDefault(),o=e.offsetLeft,s=e.offsetTop,n=t.clientX,i=t.clientY,document.addEventListener("mousemove",a),document.addEventListener("mouseup",l),e.classList.add("dragging")})),t.style.cursor="move",e.style.position="fixed"}(t,i);const o=document.createElement("button");return o.className="deepcite-close-panel-button",o.textContent="Close Panel",o.addEventListener("click",(()=>{t.classList.add("closed"),setTimeout((()=>{t.classList.contains("closed")&&(t.style.display="none",d())}),300)})),t.appendChild(o),document.body.appendChild(t),t.style.display="none",t.classList.add("closed"),t}function d(){document.querySelectorAll(".exa-tooltip").forEach((e=>e.remove())),document.querySelectorAll("[data-temporary-indicator]").forEach((e=>e.remove()))}function p(e,t,n=[]){const i=document.createElement("div");i.className="deepcite-claim-item",i.setAttribute("data-claim-id",t.id.toString());let o=`\n ${t.pdfLocation?`\n <div class="pdf-claim-location">\n Page ${t.pdfLocation.pageNum}, Paragraph ${t.pdfLocation.paragraph+1}\n </div>\n `:""}\n <div class="deepcite-claim-text">${t.text}</div>\n <div class="deepcite-claim-confidence" style="${void 0===t.confidence?"display: none;":""}">\n <span style="font-weight: bold;">Certainty:</span>\n <span class="confidence-meter" style="\n width: ${void 0!==t.confidence?Math.round(100*t.confidence):0}px;\n background-color: ${void 0!==t.confidence?a(t.confidence):"transparent"};\n "></span>\n <span class="confidence-text" style="color: ${void 0!==t.confidence?a(t.confidence):"inherit"}; font-weight: 500;">\n ${void 0!==t.confidence?Math.round(100*t.confidence)+"%":""}\n </span>\n </div>\n `;0===n.length?o+=`\n <button class="verify-claim-btn" data-claim-id="${t.id}">\n Verify\n </button>\n <div class="deepcite-claim-sources" style="margin-top: 8px; display: none;">\n \x3c!-- Sources will go here after user verifies --\x3e\n </div>\n `:(o+=`\n <div class="deepcite-claim-sources" style="margin-top: 8px;">\n <div class="deepcite-claim-sources-header">Sources (${n.length}):</div>\n `,0===n.length?o+='\n <div class="deepcite-claim-source-item">\n <div class="deepcite-source-title">\n <span style="color: #666; font-style: italic;">No relevant sources found</span>\n </div>\n </div>\n ':n.forEach(((e,t)=>{"No relevant sources found"===e.title||"#"===e.url?o+='\n <div class="deepcite-claim-source-item">\n <div class="deepcite-source-title">\n <span style="color: #666; font-style: italic;">No relevant sources found</span>\n </div>\n </div>\n ':o+=`\n <div class="deepcite-claim-source-item">\n <div class="deepcite-source-title">\n <a href="${e.url}" target="_blank">${e.title}</a>\n <span class="deepcite-source-confidence">(${Math.round(100*e.score)}% confidence)</span>\n </div>\n ${e.highlights&&e.highlights.length>0?`<div class="deepcite-source-highlight">"${e.highlights[0]}"</div>`:""}\n ${t<n.length-1?'<hr class="deepcite-source-divider">':""}\n </div>\n `})),o+="</div>"),i.innerHTML=o,i.addEventListener("click",(e=>{if(e.target.classList.contains("verify-claim-btn"))return;const n=document.querySelectorAll(".exa-claim-highlight");for(let e=0;e<n.length;e++){const i=n[e];if(i.textContent?.includes(t.cleanText)){i.scrollIntoView({behavior:"smooth",block:"center"}),i.classList.add("exa-claim-highlight-flash"),setTimeout((()=>{i.classList.remove("exa-claim-highlight-flash")}),1500);break}}})),e.appendChild(i)}function m(e,t){e.addEventListener("click",(e=>{const n=e.target;if(n.classList.contains("verify-claim-btn")){e.stopPropagation();const i=n.getAttribute("data-claim-id");if(!i)return;n.innerHTML='<span class="exa-loading" style="margin-right: 8px;"></span>Verifying...',n.setAttribute("disabled","true"),n.style.opacity="0.8",n.style.cursor="wait";const o=t.find((e=>e.id.toString()===i));if(!o)return void(n.textContent="Error");chrome.runtime.sendMessage({type:"VERIFY_CLAIM",claim:o},(e=>{if(e&&e.success&&e.results){const o=n.closest(".deepcite-claim-item"),s=o?.querySelector(".deepcite-claim-sources");s&&(function(e,t,n,i){if(!t.length)return void(n.innerHTML='<div class="deepcite-claim-sources-header">Sources:</div><em>No sources found</em>');const o=i.find((t=>t.id.toString()===e));if(o){const e=Math.max(...t.map((e=>e.score||0)));if(e>0){o.confidence=e;const t=n.closest(".deepcite-claim-item"),i=t?.querySelector(".deepcite-claim-confidence"),s=t?.querySelector(".confidence-meter"),l=t?.querySelector(".confidence-text");i&&s&&l&&(i.style.display="block",s.style.width="0px",s.style.transition="none",s.offsetWidth,void 0!==o.confidence&&(l.textContent=Math.round(100*o.confidence)+"%",l.style.color=a(o.confidence)),setTimeout((()=>{void 0!==o.confidence&&(s.style.transition="width 1s ease-out",s.style.backgroundColor=a(o.confidence),s.style.width=Math.round(100*o.confidence)+"px")}),50))}}let s=`<div class="deepcite-claim-sources-header">Sources (${t.length}):</div>`;t.forEach(((e,n)=>{"No relevant sources found"===e.title||"#"===e.url?s+='\n <div class="deepcite-claim-source-item">\n <div class="deepcite-source-title">\n <span style="color: #666; font-style: italic;">No relevant sources found</span>\n </div>\n </div>\n ':s+=`\n <div class="deepcite-claim-source-item">\n <div class="deepcite-source-title">\n <a href="${e.url}" target="_blank">${e.title}</a>\n <span class="deepcite-source-confidence">(${Math.round(100*e.score)}% confidence)</span>\n </div>\n ${e.highlights&&e.highlights.length>0?`<div class="deepcite-source-highlight">"${e.highlights[0]}"</div>`:""}\n ${n<t.length-1?'<hr class="deepcite-source-divider">':""}\n </div>\n `})),n.innerHTML=s}(i,e.results,s,t),s.style.display="block"),n.remove()}else if(e&&"DAILY_LIMIT_REACHED"===e.error){const t=n.closest(".deepcite-claim-item"),i=t?.querySelector(".deepcite-claim-sources");i&&(i.style.display="block",i.innerHTML=`\n <div style="color: #dc3545; padding: 10px; background: rgba(220, 53, 69, 0.1); border-radius: 6px; margin-top: 10px;">\n <strong>⚠️ ${e.message}</strong>\n <div style="margin-top: 5px; font-size: 14px;">\n You can adjust limits in the extension options.\n </div>\n </div>\n `),n.textContent="Options",n.removeAttribute("disabled"),n.style.opacity="1",n.style.cursor="pointer",n.addEventListener("click",(e=>{e.stopPropagation(),chrome.runtime.openOptionsPage()}),{once:!0})}else{n.textContent="Retry",n.removeAttribute("disabled"),n.style.opacity="1",n.style.cursor="pointer";const e=n.closest(".deepcite-claim-item"),t=e?.querySelector(".deepcite-claim-sources");t&&(t.style.display="block",t.innerHTML='\n <div style="color: #666; font-style: italic; padding: 10px;">\n No sources could be found. Please try again later.\n </div>\n ')}}))}}))}let u=[];async function y(e,t,n){u=[];const i=[...e].sort(((e,t)=>{const n=void 0!==e.confidence?e.confidence:0;return(void 0!==t.confidence?t.confidence:0)-n}));for(const e of i){if(void 0!==e.confidence&&e.confidence<.65){console.log(`Skipping low confidence claim (${e.confidence}): ${e.text.substring(0,50)}...`);continue}if(/\b(I think|I believe|in my opinion|we feel|might be|may be|probably|possibly|maybe|perhaps|could be|allegedly)\b/i.test(e.text)){console.log(`Skipping subjective claim: ${e.text.substring(0,50)}...`);continue}const i=t.findTextLocation(e.cleanText),o={...e,pdfLocation:i};u.push(o),p(n,o);const s=n.querySelector(`.deepcite-claim-item[data-claim-id="${o.id}"]`);s&&i&&s.addEventListener("click",(e=>{e.target.classList.contains("verify-claim-btn")||(window.location.hash=`#page=${i.pageNum}`)}))}m(n,u),n.classList.remove("closed","minimized"),n.style.display="block"}!function(){if(console.log("Adding stylesheet to document head"),document.querySelectorAll('link[href*="pdf-overlay.css"]').length>0)return void console.log("Stylesheet already exists, not adding again");const e=document.createElement("link");e.rel="stylesheet",e.href=chrome.runtime.getURL("styles/pdf-overlay.css"),document.head.appendChild(e),console.log("Stylesheet added:",e.href)}(),chrome.storage.local.get(["openaiKey","exaKey","highlightsEnabled","useLLMExtraction"],(async e=>{console.log("OpenAI key available:",!!e.openaiKey&&""!==e.openaiKey),console.log("Exa key available:",!!e.exaKey&&""!==e.exaKey),console.log("Highlights enabled:",!1!==e.highlightsEnabled),console.log("Using LLM extraction:",!0===e.useLLMExtraction&&!!e.openaiKey);const t=await async function(){return"application/pdf"===document.contentType||window.location.pathname.toLowerCase().endsWith(".pdf")}();await c(t);const n=function(){const e=document.createElement("button");return e.className="deepcite-sidebar-toggle",e.textContent="»",e.style.position="fixed",e.style.right="0",e.style.top="50%",e.style.transform="translateY(-50%)",e.style.width="32px",e.style.height="48px",e.style.backgroundColor="var(--primary-color, #2F80ED)",e.style.color="#fff",e.style.border="none",e.style.borderRadius="8px 0 0 8px",e.style.cursor="pointer",e.style.zIndex="99999",e.style.boxShadow="0 2px 8px rgba(0,0,0,0.2)",e.style.fontSize="16px",e.style.fontWeight="bold",e.style.transition="all 0.3s ease",e.addEventListener("mouseenter",(()=>{e.style.width="36px",e.style.backgroundColor="var(--primary-color-hover, #1c68d3)"})),e.addEventListener("mouseleave",(()=>{e.style.width="32px",e.style.backgroundColor="var(--primary-color, #2F80ED)"})),document.body.appendChild(e),e}();if(n.addEventListener("click",(()=>{const e="true"===n.getAttribute("data-analysis-run"),t=document.querySelector(".deepcite-claims-overlay");e||(n.setAttribute("data-analysis-run","true"),n.textContent="⟳",n.style.opacity="0.8","application/pdf"===document.contentType||window.location.pathname.toLowerCase().endsWith(".pdf")?chrome.storage.local.get(["openaiKey","useLLMExtraction"],(e=>{!async function(e,t=!0){const n=await c(!0),{exaKey:a}=await new Promise((e=>{chrome.storage.local.get(["exaKey"],(t=>e(t)))}));if(!a||""===a){console.error("Exa API key is missing");const e=n.querySelector(".deepcite-claims-header small");e&&(e.textContent="API key missing. Please set in options.");const t=document.createElement("div");t.className="deepcite-claim-item",t.innerHTML='\n <div class="deepcite-claim-text" style="color: #dc3545; text-align: center; padding: 15px;">\n Exa API key is missing. Please set it in the extension options.\n </div>\n <button id="open-options-btn" style="margin: 10px auto; display: block; padding: 8px 16px; background: #f8f9fa; border: 1px solid #eee; color: #333; cursor: pointer; border-radius: 6px;">\n Open Options\n </button>\n ',n.appendChild(t);const i=t.querySelector("#open-options-btn");return void(i&&i.addEventListener("click",(()=>{chrome.runtime.openOptionsPage()})))}const l=document.createElement("div");l.setAttribute("data-temporary-indicator","true"),l.style.position="fixed",l.style.top="20px",l.style.right="20px",l.style.padding="12px 16px",l.style.backgroundColor="var(--primary-color)",l.style.color="white",l.style.zIndex="99999",l.style.borderRadius="var(--border-radius-md)",l.style.fontWeight="bold",l.style.boxShadow="0 4px 12px rgba(0,0,0,0.15)",l.style.transition="all 0.5s cubic-bezier(0.16, 1, 0.3, 1)",l.style.fontFamily="var(--font-family)",l.style.fontSize="14px",l.style.display="flex",l.style.alignItems="center",l.style.opacity="0",l.style.transform="translateY(-10px)",l.innerHTML='<span style="margin-right: 8px; font-size: 16px;">📄</span> Analyzing PDF...',document.body.appendChild(l),setTimeout((()=>{l.style.opacity="1",l.style.transform="translateY(0)"}),10);try{const a=new s(window.location.href);await a.init();const r=await a.getAllContent();let c=!1;if(e&&""!==e&&t)try{console.log("Testing LLM extraction for PDF...");const t=new o.g(e),i=await t.extractClaimsFromChunk("This is a test claim.");if(i&&i.claims.length>0){console.log("LLM extraction successful, will use it for PDF content"),c=!0;const e=document.createElement("div");e.setAttribute("data-temporary-indicator","true"),e.style.position="fixed",e.style.bottom="20px",e.style.right="20px",e.style.padding="8px 12px",e.style.backgroundColor="rgba(47, 128, 237, 0.8)",e.style.color="white",e.style.zIndex="99998",e.style.borderRadius="var(--border-radius-md)",e.style.fontWeight="500",e.style.fontSize="13px",e.style.boxShadow="0 2px 8px rgba(0,0,0,0.15)",e.style.fontFamily="var(--font-family)",e.innerHTML="🧠 Using AI Extraction",document.body.appendChild(e),setTimeout((()=>e.remove()),5e3);const i=await t.extractClaims(r);if(i&&i.claims.length>0){const e=i.claims.map(((e,t)=>({id:t+1,text:e,cleanText:e.replace(/\[\d+\]/g,""),context:{page:1,paragraph:0},relevance:.8,confidence:void 0}))),t=n.querySelector(".deepcite-claims-header small");t&&(t.textContent=`${e.length} claims found (AI-based)`),y(e,a,n)}else console.log("LLM extraction returned no claims, falling back to rule-based"),c=!1}else console.log("LLM test failed, falling back to rule-based extraction")}catch(e){console.error("LLM extraction failed, using rule-based approach:",e),c=!1}else!t||e&&""!==e?console.log("Using rule-based extraction (LLM extraction disabled in settings)"):console.log("LLM extraction enabled but OpenAI key missing, using rule-based extraction");if(!c){console.log("Using rule-based extraction for PDF");const e=document.createElement("div");e.setAttribute("data-temporary-indicator","true"),e.style.position="fixed",e.style.bottom="20px",e.style.right="20px",e.style.padding="8px 12px",e.style.backgroundColor="rgba(100, 100, 100, 0.8)",e.style.color="white",e.style.zIndex="99998",e.style.borderRadius="var(--border-radius-md)",e.style.fontWeight="500",e.style.fontSize="13px",e.style.boxShadow="0 2px 8px rgba(0,0,0,0.15)",e.style.fontFamily="var(--font-family)",e.innerHTML="📊 Using Rule-Based Extraction",document.body.appendChild(e),setTimeout((()=>e.remove()),5e3);const t=new i,o=await t.extractClaims(10);for(const e of o.claims)e.confidence=void 0;const s=n.querySelector(".deepcite-claims-header small");s&&(s.textContent=`${o.claims.length} claims found (rule-based)`),y(o.claims,a,n)}l.innerHTML='<span style="margin-right: 8px; font-size: 16px;">✓</span> PDF Analysis Complete'}catch(e){console.error("PDF analysis failed:",e),l.style.backgroundColor="#dc3545",l.innerHTML='<span style="margin-right: 8px; font-size: 16px;">❌</span> PDF Analysis Failed'}setTimeout((()=>{l.style.opacity="0",l.style.transform="translateY(-10px)",setTimeout((()=>l.remove()),500)}),5e3)}(e.openaiKey,e.useLLMExtraction),n.textContent="»",n.style.opacity="1"})):chrome.storage.local.get(["openaiKey","useLLMExtraction"],(async e=>{const t=new i;await async function(e,t="",n=!1){console.log("Running extraction, LLM enabled:",n&&!!t);const i=n&&t?{text:"🧠 Using AI Extraction",color:"rgba(47, 128, 237, 0.8)"}:{text:"📊 Using Rule-Based Extraction",color:"rgba(100, 100, 100, 0.8)"},s=document.createElement("div");s.setAttribute("data-temporary-indicator","true"),s.style.position="fixed",s.style.bottom="20px",s.style.right="20px",s.style.padding="8px 12px",s.style.backgroundColor=i.color,s.style.color="white",s.style.zIndex="99998",s.style.borderRadius="var(--border-radius-md)",s.style.fontWeight="500",s.style.fontSize="13px",s.style.boxShadow="0 2px 8px rgba(0,0,0,0.15)",s.style.fontFamily="var(--font-family)",s.innerHTML=i.text,document.body.appendChild(s),setTimeout((()=>s.remove()),5e3);const a=document.createElement("div");a.setAttribute("data-temporary-indicator","true"),a.style.position="fixed",a.style.top="20px",a.style.right="20px",a.style.padding="12px 16px",a.style.backgroundColor="var(--primary-color)",a.style.color="white",a.style.zIndex="99999",a.style.borderRadius="var(--border-radius-md)",a.style.fontWeight="bold",a.style.boxShadow="0 4px 12px rgba(0,0,0,0.15)",a.style.transition="all 0.5s cubic-bezier(0.16, 1, 0.3, 1)",a.style.fontFamily="var(--font-family)",a.style.fontSize="14px",a.style.display="flex",a.style.alignItems="center",a.style.opacity="0",a.style.transform="translateY(-10px)",a.innerHTML='<span style="margin-right: 8px; font-size: 16px;">🔍</span> DeepCite Analysis Active',document.body.appendChild(a),setTimeout((()=>{a.style.opacity="1",a.style.transform="translateY(0)"}),10),setTimeout((()=>{a.style.opacity="0",a.style.transform="translateY(-10px)",setTimeout((()=>a.remove()),500)}),5e3);const d=document.querySelectorAll("p"),y=[];for(let e=0;e<d.length;e++){const t=d[e];if(t.textContent&&t.textContent.length>80){const e=t.textContent.toLowerCase(),n=/(I think|I believe|in my opinion|we feel|might be|may be|probably|possibly|maybe|perhaps|could be|allegedly)/i.test(e),i=/(beautiful|ugly|wonderful|terrible|best|worst|amazing|awful|good|bad|love|hate|favorite)/i.test(e);if(n&&i)continue;const o=/\d/.test(e),s=/\s[A-Z][a-z]+/.test(t.textContent),a=/(study|research|found|showed|according to|evidence|data|results|published|journal|measure|observe|statistic|percent|survey|experiment)/i.test(e);(o||s&&!n)&&a&&y.push(t)}}const g=y.slice(0,Math.min(2,y.length));let h;if(g.forEach((e=>{if(e.querySelector(".deepcite-badge")||e.getAttribute("data-claim-id"))return void console.log("Paragraph already has a DEEPCITE badge, skipping");const t=document.createElement("div");t.style.position="relative",t.style.backgroundColor="rgba(47, 128, 237, 0.15)",t.style.borderLeft="3px solid rgba(47, 128, 237, 0.5)",t.style.padding="8px",t.style.borderRadius="3px",t.style.marginBottom="10px",t.style.transition="all 0.3s ease";const n=document.createElement("button");n.style.position="absolute",n.style.top="5px",n.style.right="5px",n.style.backgroundColor="rgba(255, 255, 255, 0.8)",n.style.color="#666",n.style.border="none",n.style.borderRadius="50%",n.style.width="20px",n.style.height="20px",n.style.fontSize="12px",n.style.cursor="pointer",n.style.display="flex",n.style.alignItems="center",n.style.justifyContent="center",n.textContent="×",n.title="Remove highlight";const i=l();i.style.marginBottom="8px",i.style.marginLeft="0";const o=e.cloneNode(!0);n.addEventListener("click",(e=>{e.stopPropagation(),t.style.opacity="0",setTimeout((()=>t.remove()),300)})),t.appendChild(n),t.appendChild(i),t.appendChild(o),e.style.display="none",e.parentNode?.insertBefore(t,e.nextSibling),setTimeout((()=>{document.body.contains(t)&&(t.style.opacity="0",setTimeout((()=>{document.body.contains(t)&&(t.remove(),e.style.display="")}),300))}),3e4)})),0===g.length&&console.log("No factual paragraphs detected for demonstration"),n&&t&&""!==t)try{console.log("Attempting LLM-based claim extraction for web page");const n=new o.g(t),i=e.getMainContent(),s=i.join("\n\n"),a=await n.extractClaims(s);a&&a.claims.length>0?(console.log("LLM extraction successful, found claims:",a.claims.length),h={claims:a.claims.map(((e,t)=>({id:t+1,text:e,cleanText:e.replace(/\[\d+\]/g,""),context:{page:1,paragraph:0},relevance:.8,confidence:void 0}))),totalProcessed:i.length}):(console.log("LLM extraction returned no claims, falling back to rule-based"),h=await e.extractClaims(10))}catch(t){console.error("LLM extraction failed, using rule-based approach:",t),h=await e.extractClaims(10)}else console.log("Using rule-based claim extraction for web page"),h=await e.extractClaims(10);u=h.claims,console.log("Extraction found claims:",h.claims.length);const f=await c(!1);if(f.style.display="block",h.claims.length>0){const e=f.querySelector(".deepcite-claims-header small");if(e){const i=n&&t&&""!==t?"AI-based":"rule-based";e.textContent=`${h.claims.length} claims found (${i})`}for(const e of h.claims)e.confidence=void 0,r(e,[]),p(f,e);m(f,u),f.classList.remove("closed","minimized"),f.style.display="block"}else{const e=f.querySelector(".deepcite-claims-header small");e&&(e.textContent="No claims found on this page");const t=document.createElement("div");t.className="deepcite-claim-item",t.innerHTML='\n <div class="deepcite-claim-text" style="text-align: center; padding: 15px;">\n No factual claims were detected on this page.\n </div>\n ',f.appendChild(t),f.classList.remove("closed","minimized"),f.style.display="block"}}(t,e.openaiKey,e.useLLMExtraction),n.textContent="»",n.style.opacity="1"}))),t&&(t.classList.contains("closed")||"none"===t.style.display?(t.style.display="block",t.offsetHeight,setTimeout((()=>{t.classList.remove("closed","minimized"),n.textContent="«"}),10)):t.classList.contains("minimized")?(t.classList.remove("minimized"),n.textContent="«"):(t.classList.add("minimized"),n.textContent="»"))})),!e.exaKey||""===e.exaKey){console.warn("Exa API key is missing"),n.title="DeepCite (API key missing)",n.style.backgroundColor="#dc3545";const e=document.querySelector(".deepcite-claims-overlay");if(e){const t=document.createElement("div");t.className="deepcite-claim-item",t.innerHTML='\n <div style="color: #dc3545; padding: 15px; background: rgba(220, 53, 69, 0.1); border-radius: 6px; text-align: center;">\n <span style="font-size: 24px; display: block; margin-bottom: 10px;">⚠️</span>\n <strong>Exa API Key Missing</strong>\n <p style="margin: 10px 0; font-size: 14px;">\n DeepCite requires an Exa API key to verify claims. Please add your key in the options page.\n </p>\n <button id="open-options-btn" style="margin: 10px auto; display: block; padding: 8px 16px; background: #f8f9fa; border: 1px solid #eee; color: #333; cursor: pointer; border-radius: 6px;">\n Open Options\n </button>\n </div>\n ',e.insertBefore(t,e.querySelector(".deepcite-claim-item"));const n=t.querySelector("#open-options-btn");n&&n.addEventListener("click",(()=>{chrome.runtime.openOptionsPage()}))}}}))})();