Skip to content

Commit 77a14e2

Browse files
committed
upgrade chatgpt web (proofToken) (#677, #678, #681, #682)
1 parent 1fe4bef commit 77a14e2

File tree

3 files changed

+71
-8
lines changed

3 files changed

+71
-8
lines changed

package-lock.json

Lines changed: 18 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
"gpt-3-encoder": "^1.1.4",
3333
"graphql": "^16.6.0",
3434
"i18next": "^22.4.15",
35+
"js-sha3": "^0.9.3",
3536
"jsonwebtoken": "8.5.1",
3637
"katex": "^0.16.6",
3738
"lodash-es": "^4.17.21",
@@ -40,6 +41,7 @@
4041
"preact": "^10.13.2",
4142
"process": "^0.11.10",
4243
"prop-types": "^15.8.1",
44+
"random-int": "^3.0.0",
4345
"react": "npm:@preact/compat@^17.1.2",
4446
"react-bootstrap-icons": "^1.10.3",
4547
"react-dom": "npm:@preact/compat@^17.1.2",

src/services/apis/chatgpt-web.mjs

Lines changed: 51 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import { pushRecord, setAbortController } from './shared.mjs'
77
import Browser from 'webextension-polyfill'
88
import { v4 as uuidv4 } from 'uuid'
99
import { t } from 'i18next'
10+
import { sha3_512 } from 'js-sha3'
11+
import randomInt from 'random-int'
1012

1113
async function request(token, method, path, data) {
1214
const apiUrl = (await getUserConfig()).customChatGptWebApiUrl
@@ -49,12 +51,12 @@ export async function getModels(token) {
4951
if (response.models) return response.models.map((m) => m.slug)
5052
}
5153

52-
export async function getRequirementsToken(accessToken) {
54+
export async function getRequirements(accessToken) {
5355
const response = JSON.parse(
5456
(await request(accessToken, 'POST', '/sentinel/chat-requirements')).responseText,
5557
)
56-
if (response.token) {
57-
return response.token
58+
if (response) {
59+
return response
5860
}
5961
}
6062

@@ -91,6 +93,38 @@ export async function getArkoseToken(config) {
9193
return arkoseToken
9294
}
9395

96+
// https://github.com/tctien342/chatgpt-proxy/blob/9147a4345b34eece20681f257fd475a8a2c81171/src/openai.ts#L103
97+
function generateProofToken(seed, diff, userAgent) {
98+
const cores = [8, 12, 16, 24]
99+
const screens = [3000, 4000, 6000]
100+
101+
const core = cores[randomInt(0, cores.length)]
102+
const screen = screens[randomInt(0, screens.length)]
103+
104+
const parseTime = new Date().toString()
105+
106+
const config = [core + screen, parseTime, 4294705152, 0, userAgent]
107+
108+
const diffLen = diff.length / 2
109+
110+
for (let i = 0; i < 100000; i++) {
111+
config[3] = i
112+
const jsonData = JSON.stringify(config)
113+
// eslint-disable-next-line no-undef
114+
const base = Buffer.from(jsonData).toString('base64')
115+
const hashValue = sha3_512.create().update(seed + base)
116+
117+
if (hashValue.hex().substring(0, diffLen) <= diff) {
118+
const result = 'gAAAAAB' + base
119+
return result
120+
}
121+
}
122+
123+
// eslint-disable-next-line no-undef
124+
const fallbackBase = Buffer.from(`"${seed}"`).toString('base64')
125+
return 'gAAAAABwQ8Lk5FbGpA2NcR9dShT6gYjU7VxZ4D' + fallbackBase
126+
}
127+
94128
export async function isNeedWebsocket(accessToken) {
95129
return (await request(accessToken, 'GET', '/accounts/check/v4-2023-04-27')).responseText.includes(
96130
'shared_websocket',
@@ -167,9 +201,9 @@ export async function generateAnswersWithChatgptWebApi(port, question, session,
167201

168202
const config = await getUserConfig()
169203
let arkoseError
170-
const [models, requirementsToken, arkoseToken, useWebsocket] = await Promise.all([
204+
const [models, requirements, arkoseToken, useWebsocket] = await Promise.all([
171205
getModels(accessToken).catch(() => undefined),
172-
getRequirementsToken(accessToken).catch(() => undefined),
206+
getRequirements(accessToken).catch(() => undefined),
173207
getArkoseToken(config).catch((e) => {
174208
arkoseError = e
175209
}),
@@ -180,9 +214,17 @@ export async function generateAnswersWithChatgptWebApi(port, question, session,
180214
const usedModel =
181215
models && models.includes(selectedModel) ? selectedModel : Models[chatgptWebModelKeys[0]].value
182216
console.debug('usedModel', usedModel)
183-
const needArkoseToken = !usedModel.includes(Models[chatgptWebModelKeys[0]].value)
217+
const needArkoseToken = requirements && requirements.arkose?.required
184218
if (arkoseError && needArkoseToken) throw arkoseError
185219

220+
let proofToken
221+
if (requirements?.proofofwork?.required) {
222+
proofToken = generateProofToken(
223+
requirements.proofofwork.seed,
224+
requirements.proofofwork.difficulty,
225+
)
226+
}
227+
186228
let cookie
187229
let oaiDeviceId
188230
if (Browser.cookies && Browser.cookies.getAll) {
@@ -213,8 +255,9 @@ export async function generateAnswersWithChatgptWebApi(port, question, session,
213255
'Content-Type': 'application/json',
214256
Authorization: `Bearer ${accessToken}`,
215257
...(cookie && { Cookie: cookie }),
216-
'Openai-Sentinel-Arkose-Token': arkoseToken || '',
217-
'Openai-Sentinel-Chat-Requirements-Token': requirementsToken || '',
258+
...(needArkoseToken && { 'Openai-Sentinel-Arkose-Token': arkoseToken }),
259+
...(requirements && { 'Openai-Sentinel-Chat-Requirements-Token': requirements.token }),
260+
...(proofToken && { 'Openai-Sentinel-Proof-Token': proofToken }),
218261
'Oai-Device-Id': oaiDeviceId,
219262
'Oai-Language': 'en-US',
220263
},

0 commit comments

Comments
 (0)