// ==UserScript==
// @name DuohackerMAX v3
// @namespace https://duohackermax.net
// @version 3.0
// @description Real server-based XP, streak, gems, and perfect lesson manipulation for Duolingo
// @author misbisshi & ChatGPT
// @match https://www.duolingo.com/*
// @grant none
// @downloadURL none
// ==/UserScript==
(function() {
'use strict';
// Basic UI
const panel = document.createElement('div');
panel.innerHTML = `
`;
document.body.appendChild(panel);
const getJWT = () => {
const match = document.cookie.match(/jwt_token=([^;]+)/);
return match ? match[1] : null;
};
const sendSession = (data, jwt) => {
return fetch("https://www.duolingo.com/2017-06-30/sessions", {
method: "POST",
headers: {
"Content-Type": "application/json",
"Authorization": `Bearer ${jwt}`
},
body: JSON.stringify(data)
});
};
document.getElementById("duo_claim").onclick = async function() {
const xp = parseInt(document.getElementById("xp_input").value) || 0;
const streak = parseInt(document.getElementById("streak_input").value) || 0;
const gems = parseInt(document.getElementById("gems_input").value) || 0;
const lessons = parseInt(document.getElementById("lesson_input").value) || 0;
const jwt = getJWT();
const status = document.getElementById("duo_status");
if (!jwt) {
status.innerHTML = "JWT 토큰을 찾을 수 없습니다. 로그인 상태를 확인하세요.";
return;
}
// XP 조작
if (xp > 0) {
await sendSession({
xpGain: xp,
skillId: "global",
fromLanguage: "en",
isFinalLevel: true,
type: "practice",
startTime: new Date().toISOString(),
endTime: new Date().toISOString()
}, jwt);
}
// 스트릭 조작
for (let i = 0; i < streak; i++) {
const date = new Date();
date.setDate(date.getDate() - i);
await sendSession({
xpGain: 10,
skillId: "streak",
fromLanguage: "en",
type: "practice",
startTime: date.toISOString(),
endTime: date.toISOString()
}, jwt);
}
// 퍼펙트 레슨 조작
for (let i = 0; i < lessons; i++) {
await sendSession({
xpGain: 20,
perfect: true,
lessonCompleted: true,
fromLanguage: "en",
skillId: "perfect",
type: "lesson",
startTime: new Date().toISOString(),
endTime: new Date().toISOString()
}, jwt);
}
status.innerHTML = `적용 완료! XP: ${xp}, 스트릭: ${streak}일, 퍼펙트 레슨: ${lessons}`;
};
})();