kopia lustrzana https://github.com/transitive-bullshit/chatgpt-api
feat: minor cleanups
rodzic
fe20635e0b
commit
423179dcd0
|
@ -112,7 +112,8 @@ export class ChatGPTAPIBrowser extends AChatGPTAPI {
|
||||||
this._browser = await getBrowser({
|
this._browser = await getBrowser({
|
||||||
captchaToken: this._captchaToken,
|
captchaToken: this._captchaToken,
|
||||||
executablePath: this._executablePath,
|
executablePath: this._executablePath,
|
||||||
proxyServer: this._proxyServer
|
proxyServer: this._proxyServer,
|
||||||
|
minimize: this._minimize
|
||||||
})
|
})
|
||||||
this._page =
|
this._page =
|
||||||
(await this._browser.pages())[0] || (await this._browser.newPage())
|
(await this._browser.pages())[0] || (await this._browser.newPage())
|
||||||
|
@ -474,29 +475,35 @@ export class ChatGPTAPIBrowser extends AChatGPTAPI {
|
||||||
|
|
||||||
console.warn('chatgpt sendMessage error; retrying...', err.toString())
|
console.warn('chatgpt sendMessage error; retrying...', err.toString())
|
||||||
await delay(5000)
|
await delay(5000)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if ('error' in result) {
|
||||||
|
const error = new types.ChatGPTError(result.error.message)
|
||||||
|
error.statusCode = result.error.statusCode
|
||||||
|
error.statusText = result.error.statusText
|
||||||
|
|
||||||
|
if (error.statusCode !== 403) {
|
||||||
|
throw error
|
||||||
|
} else if (++numTries >= 2) {
|
||||||
|
await this.refreshSession()
|
||||||
|
throw error
|
||||||
|
} else {
|
||||||
|
await this.refreshSession()
|
||||||
|
await delay(1000)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (!this._markdown) {
|
||||||
|
result.response = markdownToText(result.response)
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
}
|
}
|
||||||
} while (!result)
|
} while (!result)
|
||||||
|
|
||||||
// console.log('<<< EVALUATE', result)
|
// console.log('<<< EVALUATE', result)
|
||||||
|
|
||||||
if ('error' in result) {
|
|
||||||
const error = new types.ChatGPTError(result.error.message)
|
|
||||||
error.statusCode = result.error.statusCode
|
|
||||||
error.statusText = result.error.statusText
|
|
||||||
|
|
||||||
if (error.statusCode === 403) {
|
|
||||||
await this.refreshSession()
|
|
||||||
}
|
|
||||||
|
|
||||||
throw error
|
|
||||||
} else {
|
|
||||||
if (!this._markdown) {
|
|
||||||
result.response = markdownToText(result.response)
|
|
||||||
}
|
|
||||||
|
|
||||||
return result
|
|
||||||
}
|
|
||||||
|
|
||||||
// const lastMessage = await this.getLastMessage()
|
// const lastMessage = await this.getLastMessage()
|
||||||
|
|
||||||
// await inputBox.focus()
|
// await inputBox.focus()
|
||||||
|
@ -549,7 +556,17 @@ export class ChatGPTAPIBrowser extends AChatGPTAPI {
|
||||||
}
|
}
|
||||||
|
|
||||||
override async closeSession() {
|
override async closeSession() {
|
||||||
await this._browser.close()
|
try {
|
||||||
|
if (this._page) {
|
||||||
|
this._page.off('request', this._onRequest.bind(this))
|
||||||
|
this._page.off('response', this._onResponse.bind(this))
|
||||||
|
}
|
||||||
|
} catch (_) {}
|
||||||
|
|
||||||
|
if (this._browser) {
|
||||||
|
await this._browser.close()
|
||||||
|
}
|
||||||
|
|
||||||
this._page = null
|
this._page = null
|
||||||
this._browser = null
|
this._browser = null
|
||||||
this._accessToken = null
|
this._accessToken = null
|
||||||
|
|
|
@ -5,13 +5,14 @@ import * as url from 'node:url'
|
||||||
|
|
||||||
import delay from 'delay'
|
import delay from 'delay'
|
||||||
import { TimeoutError } from 'p-timeout'
|
import { TimeoutError } from 'p-timeout'
|
||||||
import type { Browser, Page, Protocol, PuppeteerLaunchOptions } from 'puppeteer'
|
import { Browser, Page, Protocol, PuppeteerLaunchOptions } from 'puppeteer'
|
||||||
import puppeteer from 'puppeteer-extra'
|
import puppeteer from 'puppeteer-extra'
|
||||||
import RecaptchaPlugin from 'puppeteer-extra-plugin-recaptcha'
|
import RecaptchaPlugin from 'puppeteer-extra-plugin-recaptcha'
|
||||||
import StealthPlugin from 'puppeteer-extra-plugin-stealth'
|
import StealthPlugin from 'puppeteer-extra-plugin-stealth'
|
||||||
import random from 'random'
|
import random from 'random'
|
||||||
|
|
||||||
import * as types from './types'
|
import * as types from './types'
|
||||||
|
import { minimizePage } from './utils'
|
||||||
|
|
||||||
puppeteer.use(StealthPlugin())
|
puppeteer.use(StealthPlugin())
|
||||||
|
|
||||||
|
@ -57,7 +58,8 @@ export async function getOpenAIAuth({
|
||||||
captchaToken = process.env.CAPTCHA_TOKEN,
|
captchaToken = process.env.CAPTCHA_TOKEN,
|
||||||
nopechaKey = process.env.NOPECHA_KEY,
|
nopechaKey = process.env.NOPECHA_KEY,
|
||||||
executablePath,
|
executablePath,
|
||||||
proxyServer = process.env.PROXY_SERVER
|
proxyServer = process.env.PROXY_SERVER,
|
||||||
|
minimize = false
|
||||||
}: {
|
}: {
|
||||||
email?: string
|
email?: string
|
||||||
password?: string
|
password?: string
|
||||||
|
@ -66,6 +68,7 @@ export async function getOpenAIAuth({
|
||||||
timeoutMs?: number
|
timeoutMs?: number
|
||||||
isGoogleLogin?: boolean
|
isGoogleLogin?: boolean
|
||||||
isMicrosoftLogin?: boolean
|
isMicrosoftLogin?: boolean
|
||||||
|
minimize?: boolean
|
||||||
captchaToken?: string
|
captchaToken?: string
|
||||||
nopechaKey?: string
|
nopechaKey?: string
|
||||||
executablePath?: string
|
executablePath?: string
|
||||||
|
@ -88,6 +91,10 @@ export async function getOpenAIAuth({
|
||||||
if (!page) {
|
if (!page) {
|
||||||
page = (await browser.pages())[0] || (await browser.newPage())
|
page = (await browser.pages())[0] || (await browser.newPage())
|
||||||
page.setDefaultTimeout(timeoutMs)
|
page.setDefaultTimeout(timeoutMs)
|
||||||
|
|
||||||
|
if (minimize) {
|
||||||
|
await minimizePage(page)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
await page.goto('https://chat.openai.com/auth/login', {
|
await page.goto('https://chat.openai.com/auth/login', {
|
||||||
|
@ -243,6 +250,7 @@ export async function getBrowser(
|
||||||
captchaToken?: string
|
captchaToken?: string
|
||||||
nopechaKey?: string
|
nopechaKey?: string
|
||||||
proxyServer?: string
|
proxyServer?: string
|
||||||
|
minimize?: boolean
|
||||||
} = {}
|
} = {}
|
||||||
) {
|
) {
|
||||||
const {
|
const {
|
||||||
|
@ -250,6 +258,7 @@ export async function getBrowser(
|
||||||
nopechaKey = process.env.NOPECHA_KEY,
|
nopechaKey = process.env.NOPECHA_KEY,
|
||||||
executablePath = defaultChromeExecutablePath(),
|
executablePath = defaultChromeExecutablePath(),
|
||||||
proxyServer = process.env.PROXY_SERVER,
|
proxyServer = process.env.PROXY_SERVER,
|
||||||
|
minimize = false,
|
||||||
...launchOptions
|
...launchOptions
|
||||||
} = opts
|
} = opts
|
||||||
|
|
||||||
|
@ -268,6 +277,7 @@ export async function getBrowser(
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// https://peter.sh/experiments/chromium-command-line-switches/
|
||||||
const puppeteerArgs = [
|
const puppeteerArgs = [
|
||||||
'--no-sandbox',
|
'--no-sandbox',
|
||||||
'--disable-setuid-sandbox',
|
'--disable-setuid-sandbox',
|
||||||
|
@ -285,8 +295,8 @@ export async function getBrowser(
|
||||||
'--disable-default-apps',
|
'--disable-default-apps',
|
||||||
'--no-zygote',
|
'--no-zygote',
|
||||||
'--disable-accelerated-2d-canvas',
|
'--disable-accelerated-2d-canvas',
|
||||||
'--disable-web-security',
|
'--disable-web-security'
|
||||||
'--disable-gpu'
|
// '--disable-gpu'
|
||||||
// '--js-flags="--max-old-space-size=1024"'
|
// '--js-flags="--max-old-space-size=1024"'
|
||||||
]
|
]
|
||||||
|
|
||||||
|
@ -308,7 +318,6 @@ export async function getBrowser(
|
||||||
|
|
||||||
const browser = await puppeteer.launch({
|
const browser = await puppeteer.launch({
|
||||||
headless: false,
|
headless: false,
|
||||||
// https://peter.sh/experiments/chromium-command-line-switches/
|
|
||||||
args: puppeteerArgs,
|
args: puppeteerArgs,
|
||||||
ignoreDefaultArgs: [
|
ignoreDefaultArgs: [
|
||||||
'--disable-extensions',
|
'--disable-extensions',
|
||||||
|
@ -322,40 +331,74 @@ export async function getBrowser(
|
||||||
|
|
||||||
if (process.env.PROXY_VALIDATE_IP) {
|
if (process.env.PROXY_VALIDATE_IP) {
|
||||||
const page = (await browser.pages())[0] || (await browser.newPage())
|
const page = (await browser.pages())[0] || (await browser.newPage())
|
||||||
// send a fetch request to https://ifconfig.co using page.evaluate() and verify the IP matches
|
if (minimize) {
|
||||||
let ip
|
await minimizePage(page)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Send a fetch request to https://ifconfig.co using page.evaluate() and
|
||||||
|
// verify that the IP matches
|
||||||
|
let ip: string
|
||||||
try {
|
try {
|
||||||
;({ ip } = await page.evaluate(() => {
|
const res = await page.evaluate(() => {
|
||||||
return fetch('https://ifconfig.co', {
|
return fetch('https://ifconfig.co', {
|
||||||
headers: {
|
headers: {
|
||||||
Accept: 'application/json'
|
Accept: 'application/json'
|
||||||
}
|
}
|
||||||
}).then((res) => res.json())
|
}).then((res) => res.json())
|
||||||
}))
|
})
|
||||||
|
|
||||||
|
ip = res?.ip
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
throw new Error(`Proxy IP validation failed: ${err.message}`)
|
throw new Error(`Proxy IP validation failed: ${err.toString()}`)
|
||||||
}
|
}
|
||||||
if (ip !== process.env.PROXY_VALIDATE_IP) {
|
|
||||||
|
if (!ip || ip !== process.env.PROXY_VALIDATE_IP) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
`Proxy IP mismatch: ${ip} !== ${process.env.PROXY_VALIDATE_IP}`
|
`Proxy IP mismatch: ${ip} !== ${process.env.PROXY_VALIDATE_IP}`
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TOdO: this is a really hackity hack way of setting the API key...
|
await initializeNopechaExtension(browser, {
|
||||||
|
minimize,
|
||||||
|
nopechaKey
|
||||||
|
})
|
||||||
|
|
||||||
|
return browser
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function initializeNopechaExtension(
|
||||||
|
browser: Browser,
|
||||||
|
opts: {
|
||||||
|
minimize?: boolean
|
||||||
|
nopechaKey?: string
|
||||||
|
}
|
||||||
|
) {
|
||||||
|
const { minimize = false, nopechaKey } = opts
|
||||||
|
|
||||||
|
// TODO: this is a really hackity hack way of setting the API key...
|
||||||
if (hasNopechaExtension) {
|
if (hasNopechaExtension) {
|
||||||
const page = (await browser.pages())[0] || (await browser.newPage())
|
const page = (await browser.pages())[0] || (await browser.newPage())
|
||||||
|
if (minimize) {
|
||||||
|
await minimizePage(page)
|
||||||
|
}
|
||||||
|
|
||||||
await page.goto(`https://nopecha.com/setup#${nopechaKey}`)
|
await page.goto(`https://nopecha.com/setup#${nopechaKey}`)
|
||||||
await delay(1000)
|
await delay(1000)
|
||||||
try {
|
try {
|
||||||
const page3 = await browser.newPage()
|
const page3 = await browser.newPage()
|
||||||
await page.close()
|
if (minimize) {
|
||||||
|
await minimizePage(page3)
|
||||||
|
}
|
||||||
|
|
||||||
|
await page.close()
|
||||||
// find the nopecha extension ID
|
// find the nopecha extension ID
|
||||||
const targets = browser.targets()
|
const targets = browser.targets()
|
||||||
const extensionIds = (
|
const extensionIds = (
|
||||||
await Promise.all(
|
await Promise.all(
|
||||||
targets.map(async (target) => {
|
targets.map(async (target) => {
|
||||||
|
// console.log(target.type(), target.url())
|
||||||
|
|
||||||
if (target.type() !== 'service_worker') {
|
if (target.type() !== 'service_worker') {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -378,23 +421,27 @@ export async function getBrowser(
|
||||||
await editKey.click()
|
await editKey.click()
|
||||||
|
|
||||||
const settingsInput = await page3.waitForSelector('input.settings_text')
|
const settingsInput = await page3.waitForSelector('input.settings_text')
|
||||||
// console.log('value1', await settingsInput.evaluate((el) => el.value))
|
// console.log('value1', )
|
||||||
|
|
||||||
await settingsInput.evaluate((el) => {
|
const value = await settingsInput.evaluate((el) => el.value)
|
||||||
el.value = ''
|
if (value !== nopechaKey) {
|
||||||
})
|
await settingsInput.evaluate((el) => {
|
||||||
await settingsInput.type(nopechaKey)
|
el.value = ''
|
||||||
|
})
|
||||||
|
await settingsInput.type(nopechaKey)
|
||||||
|
|
||||||
// console.log('value2', await settingsInput.evaluate((el) => el.value))
|
// console.log('value2', await settingsInput.evaluate((el) => el.value))
|
||||||
await settingsInput.evaluate((el, value) => {
|
await settingsInput.evaluate((el, value) => {
|
||||||
el.value = value
|
el.value = value
|
||||||
}, nopechaKey)
|
}, nopechaKey)
|
||||||
|
|
||||||
|
// console.log('value3', await settingsInput.evaluate((el) => el.value))
|
||||||
|
await settingsInput.press('Enter')
|
||||||
|
await delay(500)
|
||||||
|
await editKey.click()
|
||||||
|
await delay(2000)
|
||||||
|
}
|
||||||
|
|
||||||
// console.log('value3', await settingsInput.evaluate((el) => el.value))
|
|
||||||
await settingsInput.press('Enter')
|
|
||||||
await delay(500)
|
|
||||||
await editKey.click()
|
|
||||||
await delay(2000)
|
|
||||||
console.log('initialized nopecha extension with key', nopechaKey)
|
console.log('initialized nopecha extension with key', nopechaKey)
|
||||||
} else {
|
} else {
|
||||||
console.error(
|
console.error(
|
||||||
|
@ -405,14 +452,14 @@ export async function getBrowser(
|
||||||
console.error('error initializing nopecha extension', err)
|
console.error('error initializing nopecha extension', err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return browser
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the default path to chrome's executable for the current platform.
|
* Gets the default path to chrome's executable for the current platform.
|
||||||
*/
|
*/
|
||||||
export const defaultChromeExecutablePath = (): string => {
|
export const defaultChromeExecutablePath = (): string => {
|
||||||
|
// return executablePath()
|
||||||
|
|
||||||
if (process.env.PUPPETEER_EXECUTABLE_PATH) {
|
if (process.env.PUPPETEER_EXECUTABLE_PATH) {
|
||||||
return process.env.PUPPETEER_EXECUTABLE_PATH
|
return process.env.PUPPETEER_EXECUTABLE_PATH
|
||||||
}
|
}
|
||||||
|
|
Ładowanie…
Reference in New Issue