吾爱破解 - LCG - LSG |安卓破解|病毒分析|www.52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 4472|回复: 81
上一主题 下一主题
收起左侧

[其他原创] 2024年2月份的阿里云盘自动签到,附带 WPS 脚本说明

  [复制链接]
跳转到指定楼层
楼主
kittylang 发表于 2024-2-14 20:25 回帖奖励
本帖最后由 kittylang 于 2024-4-21 10:06 编辑

这里是官方文档 airsheet,但是官方文档对一些问题并没有直接说明

  • 只支持标准 JS(ECMAScript),setTimeout 这类浏览器实现的 Api 无法使用
  • 不支持可选链,可以通过 transform-optional-chaining 转换(babel 插件,下同)
  • 不完全支持对象属性简写(不支持对象中的方法简写),通过 transform-shorthand-properties 转换
  • 请求不支持端口,故非默认端口的任务只能放弃
  • 请求头 content-type 中不能使用 charset=UTF-8,例如 application/json;charset=UTF-8,而应该使用 application/json
  • console.log 不支持输出 Error 等对象(输出为 {}),需要通过 JSON.stringify / error.message 转为字符串。
  • 不支持 new Promise (文档未提及)
  • 不支持 new Function (EvalError:Code generation from strings disallowed for this context)
  • 不支持 Array.from 的第二个参数,不管写的什么,都是填充 {}

附上阿里云盘的成品代码,(还有移动云盘的就不贴出来了,太长了,可以在下方开源地址查看)

只支持最简单的功能,签到,设备间,每日任务。没有推送,也没有随机执行。没有多余的配置(阿里没福利了,这个相当于 49 年入某军,所以这里只是抛砖引玉)

特性

网上,甚至本站已经有那么多 wps 版的阿里云盘,为啥还发了这一篇。

  • 截至目前,唯一一个支持设备间的 wps(其他版本 github 已有新的),而目前 设备间是唯一拥有永久空间的任务
  • 截至目前,唯一一个支持每日任务的 wps(其他版本 github 已有新的)

WPS 运行方式

使用只需要把 refresh_token 放 A 列就行了(支持多账号,放多行)

源代码是 typescript 写的,就不放这了,开源地址 https://github.com/asunajs/asign

function randomHex(length) {
    return Array.from({
        length: length
    }).map(()=>Math.floor(Math.random() * 16).toString(16)).join("");
}
function createLogger(options) {
    const wrap = (type, ...args)=>{
        if (options && options.pushData) {
            const msg = args.reduce((str, cur)=>`${str} ${cur}`, "").substring(1);
            options.pushData.push({
                msg: msg,
                type: type,
                date: new Date()
            });
        }
        console[type](...args);
    };
    return {
        info: (...args)=>wrap("info", ...args),
        error: (...args)=>wrap("error", ...args),
        debug: (...args)=>wrap("info", ...args)
    };
}
function getHostname(url) {
    return url.split("/")[2].split("?")[0];
}
function _send({ logger, http }, name = "自定义消息", options) {
    try {
        const data = http.fetch(options);
        const { errcode, code, err } = data;
        if (errcode || err || ![
            0,
            200,
            undefined
        ].some((c)=>code === c)) {
            return logger.error(`${name}发送失败`, JSON.stringify(data));
        }
        logger.info(`${name}已发送!`);
    } catch (error) {
        logger.info(`${name}发送失败: ${error.message}`);
        logger.error(error);
    }
}
function pushCustomPost({ logger, http }, apiTemplate, title, text) {
    try {
        if (!apiTemplate || !apiTemplate.url) return;
        const { data, timeout, headers } = apiTemplate;
        const method = apiTemplate.method.toUpperCase() || "POST";
        const options = {
            method: method,
            timeout: timeout,
            headers: headers,
            url: ""
        };
        options.url = apiTemplate.url.replace("{title}", encodeURIComponent(title)).replace("{text}", encodeURIComponent(text));
        // 处理data
        if (data && Object.keys(data).length) {
            const str = JSON.stringify(data).replace(/{title}/g, title).replace(/{text}/g, text).replace(/\n/g, "\\n").replace(/\r/g, "\\r");
            options.data = JSON.parse(str);
        }
        http.fetch(options);
        logger.info(`自定义消息已发送!`);
    } catch (error) {
        logger.info(`自定义消息发送失败: ${error.message}`);
        logger.error(error);
    }
}
function pushplus(apiOption, { token }, title, text) {
    return _send(apiOption, "pushplus", {
        url: `http://www.pushplus.plus/send`,
        method: "POST",
        headers: {
            "content-type": "application/json"
        },
        data: {
            token: token,
            title: title,
            content: text
        }
    });
}
function serverChan(apiOption, { token }, title, text) {
    return _send(apiOption, "Server酱", {
        url: `https://sctapi.ftqq.com/${token}.send`,
        method: "POST",
        headers: {
            "Content-Type": "application/x-www-form-urlencoded"
        },
        data: {
            text: title,
            desp: text
        }
    });
}
/**
*
* @description https://developer.work.weixin.qq.com/document/path/90665#corpid
*/ function workWeixin(apiOption, { msgtype = "text", touser = "@all", agentid, corpid, corpsecret }, title, text) {
    const { access_token } = apiOption.http.fetch({
        url: `https://qyapi.weixin.qq.com/cgi-bin/gettoken`,
        method: "POST",
        data: {
            corpid: corpid,
            corpsecret: corpsecret
        },
        headers: {
            "Content-Type": "application/json"
        }
    });
    return _send(apiOption, "企业微信推送", {
        url: `https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=${access_token}`,
        method: "POST",
        headers: {
            "Content-Type": "application/json"
        },
        data: {
            touser: touser,
            msgtype: msgtype,
            agentid: agentid,
            [msgtype]: {
                content: `${title}\n\n${text}`
            }
        }
    });
}
function getCookieJSON(cookie) {
    if (!cookie) return {};
    const matchArray = cookie.match(/([^;=]+)(?:=([^;]*))?/g);
    if (!matchArray) return {};
    return matchArray.reduce((pre, cur)=>{
        const [key, value] = cur.trim().split("=");
        pre[key] = value;
        return pre;
    }, {});
}
function getCookieString(obj) {
    const string = Object.keys(obj).reduce((pre, cur)=>pre + `${cur}=${obj[cur]}; `, "");
    return string.substring(0, string.length - 2 || 0);
}
function getSetCookieValue(setCookieArray) {
    let cookieStr = "";
    setCookieArray.filter(Boolean).forEach((setCookie)=>cookieStr += setCookie.split("; ")[0] + "; ");
    if (cookieStr.endsWith("; ")) {
        cookieStr = cookieStr.substring(0, cookieStr.length - 2 || 0);
    }
    return cookieStr;
}
function getCookie(cookie = "", setCookie) {
    if (!Array.isArray(setCookie)) setCookie = [
        setCookie
    ];
    if (!setCookie || setCookie.length === 0) return cookie;
    return getCookieString({
        ...getCookieJSON(cookie),
        ...getCookieJSON(getSetCookieValue(setCookie))
    });
}
function createCookieJar(cookie = "") {
    let _cookie;
    _cookie = cookie;
    return {
        getCookieString: function() {
            return _cookie;
        },
        setCookie: function(rawCookie) {
            return getCookie(_cookie, rawCookie);
        },
        toJSON: function() {
            return getCookieJSON(_cookie);
        }
    };
}
function createRequest({ cookieJar, getHeaders }) {
    const get = (url, options)=>{
        var _resp_;
        const resp = HTTP.get(url, {
            headers: {
                ...getHeaders(url),
                ...options && options.headers
            }
        });
        cookieJar && cookieJar.setCookie(resp.headers["set-cookie"]);
        if (!options) return resp.json();
        return options.native ? resp : (_resp_ = resp[options.responseType || "json"]) === null || _resp_ === void 0 ? void 0 : _resp_.call(resp);
    };
    const post = (url, data, options)=>{
        var _resp_;
        const resp = HTTP.post(url, JSON.stringify(data), {
            headers: {
                ...getHeaders(url),
                ...options && options.headers
            }
        });
        cookieJar && cookieJar.setCookie(resp.headers["set-cookie"]);
        if (!options) return resp.json();
        return options.native ? resp : (_resp_ = resp[options.responseType || "json"]) === null || _resp_ === void 0 ? void 0 : _resp_.call(resp);
    };
    return {
        get: get,
        post: post
    };
}
function getPushConfig() {
    const usedRange = Application.Sheets.Item("推送").UsedRange, cells = usedRange.Columns.Cells, columnEnd = Math.min(50, usedRange.ColumnEnd), rowEnd = Math.min(50, usedRange.RowEnd);
    const pushConfig = {};
    for(let option = usedRange.Column; option <= columnEnd; option++){
        const t = {}, item = cells.Item(option);
        if (!item.Text) continue;
        pushConfig[item.Text] = t;
        for(let kv = 1; kv <= rowEnd; kv++){
            const key = item.Offset(kv).Text;
            if (!key.trim()) continue;
            t[key] = valueHandle(item.Offset(kv, 1).Text.trim());
        }
    }
    const base = pushConfig.base;
    if (!base) return pushConfig;
    delete pushConfig.base;
    return {
        ...pushConfig,
        ...base
    };
    function valueHandle(value) {
        if (value === "TRUE" || value === "是") return true;
        if (value === "FALSE" || value === "否") return false;
        return value;
    }
}
function email({ logger }, email, title, text) {
    try {
        if (!email || !email.pass || !email.from || !email.host) return;
        const port = email.port || 465, toUser = email.to || email.from;
        const mailer = SMTP.login({
            host: email.host,
            port: port,
            secure: port === 465,
            username: email.from,
            password: email.pass
        });
        mailer.send({
            from: `${title} <${email.from}>`,
            to: toUser,
            subject: title,
            text: text.replace(/\n/g, "\r\n")
        });
        logger.info(`邮件消息已发送`);
    } catch (error) {
        logger.error(`邮件消息发送失败`, error.message);
    }
}
function sendNotify(op, data, title, text) {
    const cbs = {
        pushplus: pushplus,
        serverChan: serverChan,
        workWeixin: workWeixin,
        email: email
    };
    for (const [name, d] of Object.entries(data)){
        const cb = cbs[name];
        if (!cb) continue;
        cb(op, d, title, text);
    }
}
function createApi(http) {
    const memberUrl = "https://member.aliyundrive.com";
    const aliyundriveUrl = "https://api.aliyundrive.com";
    const authUrl = "https://auth.aliyundrive.com";
    const apiUrl = "https://api.alipan.com";
    function refreshToken(refreshToken) {
        return http.post(`${aliyundriveUrl}/token/refresh`, {
            refresh_token: refreshToken
        });
    }
    function getAccessToken(refreshToken) {
        return http.post(`${authUrl}/v2/account/token`, {
            refresh_token: refreshToken,
            grant_type: "refresh_token"
        });
    }
    function signInList() {
        return http.post(`${memberUrl}/v2/activity/sign_in_list?_rx-s=mobile`, {
            "_rx-s": "mobile"
        });
    }
    function signIn() {
        return http.post(`${memberUrl}/v2/activity/sign_in_info?_rx-s=mobile`, {});
    }
    function signInReward(signInDay) {
        return http.post(`${memberUrl}/v1/activity/sign_in_reward?_rx-s=mobile`, {
            signInDay: signInDay
        });
    }
    function signInTaskReward(signInDay) {
        return http.post(`${memberUrl}/v2/activity/sign_in_task_reward`, {
            signInDay: signInDay
        });
    }
    function updateDeviceExtras() {
        return http.post(`${apiUrl}/users/v1/users/update_device_extras`, {
            albumAccessAuthority: true,
            albumBackupLeftFileTotal: 0,
            albumBackupLeftFileTotalSize: 0,
            albumFile: 0,
            autoBackupStatus: true,
            // totalSize: 0,
            // useSize: 0,
            brand: "xiaomi",
            systemVersion: "Android 13"
        });
    }
    function createSession(deviceId, refreshToken, pubKey, deviceName, modelName) {
        return http.post(`https://api.alipan.com/users/v1/users/device/create_session`, {
            deviceName: deviceName,
            modelName: modelName,
            nonce: "0",
            pubKey: pubKey,
            refreshToken: refreshToken
        }, {
            headers: {
                "x-device-id": deviceId
            }
        });
    }
    function getDeviceAppletList() {
        return http.post(`${apiUrl}/adrive/v2/backup/device_applet_list_summary`, {});
    }
    function getDeviceList() {
        return http.post(`${apiUrl}/users/v2/users/device_list`, {});
    }
    function getAlbumsInfo() {
        return http.post(`${aliyundriveUrl}/adrive/v1/user/albums_info`, {});
    }
    function getDeviceRoomList() {
        return http.post(`https://user.aliyundrive.com/v1/deviceRoom/listDevice`, {});
    }
    function getDeviceRoomRewardInfoToday() {
        return http.post(`${memberUrl}/v1/deviceRoom/rewardInfoToday`, {});
    }
    function getDeviceRoomRewardEnergy(deviceId) {
        return http.post(`${memberUrl}/v1/deviceRoom/rewardEnergy`, {
            deviceId: deviceId
        });
    }
    function createFile(deviceId, driveId) {
        const size = Math.floor(Math.random() * 30000);
        return http.post(`${aliyundriveUrl}/adrive/v2/biz/albums/file/create`, {
            drive_id: driveId,
            part_info_list: [
                {
                    part_number: 1,
                    part_size: size
                }
            ],
            parent_file_id: "root",
            name: Math.floor(Math.random() * 100000000) + ".jpg",
            type: "file",
            check_name_mode: "auto_rename",
            size: size,
            create_scene: "album_autobackup",
            hidden: false,
            content_type: "image/jpeg"
        }, {
            headers: {
                "x-device-id": deviceId
            }
        });
    }
    function completeUpload(deviceId, driveId, fileId, uploadId) {
        return http.post(`${aliyundriveUrl}/v2/file/complete`, {
            drive_id: driveId,
            upload_id: uploadId,
            file_id: fileId
        }, {
            headers: {
                "x-device-id": deviceId
            }
        });
    }
    function completeAlbumsUpload(deviceId, driveId, fileId, contentHash) {
        return http.post(`${aliyundriveUrl}/adrive/v2/biz/albums/file/complete`, {
            drive_id: driveId,
            file_id: fileId,
            content_hash: contentHash,
            content_hash_name: "sha1"
        }, {
            headers: {
                "x-device-id": deviceId
            }
        });
    }
    function deleteFile(deviceId, driveId, fileId) {
        return http.post(`${apiUrl}/adrive/v4/batch`, {
            requests: [
                {
                    body: {
                        drive_id: driveId,
                        file_id: fileId
                    },
                    id: fileId,
                    method: "POST",
                    url: "/file/delete"
                }
            ],
            resource: "file"
        }, {
            headers: {
                "x-device-id": deviceId
            }
        });
    }
    function home() {
        return http.post(`${aliyundriveUrl}/apps/v2/users/home/widgets`, {});
    }
    return {
        home: home,
        signIn: signIn,
        signInList: signInList,
        createFile: createFile,
        deleteFile: deleteFile,
        refreshToken: refreshToken,
        signInReward: signInReward,
        getAlbumsInfo: getAlbumsInfo,
        createSession: createSession,
        getDeviceList: getDeviceList,
        getAccessToken: getAccessToken,
        completeUpload: completeUpload,
        signInTaskReward: signInTaskReward,
        getDeviceRoomList: getDeviceRoomList,
        updateDeviceExtras: updateDeviceExtras,
        getDeviceAppletList: getDeviceAppletList,
        completeAlbumsUpload: completeAlbumsUpload,
        getDeviceRoomRewardEnergy: getDeviceRoomRewardEnergy,
        getDeviceRoomRewardInfoToday: getDeviceRoomRewardInfoToday
    };
}
function request($, api, name, ...args) {
    try {
        const { success, message, result } = api(...args);
        if (!success) {
            $.logger.error(`${name}失败`, message);
        } else {
            return result;
        }
    } catch (error) {
        $.logger.error(`${name}异常`, error.message);
    }
    return {};
}
function refreshToken($, token) {
    try {
        const data = $.api.getAccessToken(token);
        if (!data.access_token) {
            $.logger.error("获取 access_token 失败", JSON.stringify(data));
            return;
        }
        return data;
    } catch (error) {
        $.logger.error(`获取 access_token 异常`, error.message);
    }
}
function createDeviceApi($, refreshToken, deviceId) {
    try {
        const { success } = $.api.createSession(deviceId, refreshToken, randomHex(32), "XiaoMi 14Pro", "xiaomi");
        if (!success) {
            $.logger.error(`创建虚拟设备${deviceId}失败`);
            return false;
        }
        $.logger.info(`创建虚拟设备成功`);
        return true;
    } catch (error) {
        $.logger.error(`创建虚拟设备${deviceId}异常`, error.message);
    }
    return false;
}
function getDeviceRoomListApi($) {
    try {
        const { items } = $.api.getDeviceRoomList();
        if (!items) {
            $.logger.error(`获取设备间列表失败`);
            return;
        }
        return items;
    } catch (error) {
        $.logger.error(`获取设备间列表异常`, error.message);
    }
    return;
}
function getDeviceRoomRewardInfo($) {
    return request($, $.api.getDeviceRoomRewardInfoToday, "获取设备间领取信息");
}
function getAlbumsDriveId($) {
    try {
        const { code, message, data } = $.api.getAlbumsInfo();
        if (code !== "200") {
            $.logger.error(`获取相册文件夹失败`, message);
            return;
        }
        return data.driveId;
    } catch (error) {
        $.logger.error(`获取相册文件夹异常`, error.message);
    }
}
function createDevice($) {
    const deviceRoom = getDeviceRoomListApi($);
    const needNum = 5 - deviceRoom.length;
    if (needNum <= 0) {
        return;
    }
    $.logger.info(`需要创建${needNum}个虚拟设备`);
    for(let i = 0; i < needNum; i++){
        createDeviceApi($, $.DATA.refreshToken, randomHex(64));
    }
}
function uploadFile($, deviceId, driveId) {
    try {
        const { file_id, upload_id } = $.api.createFile(deviceId, driveId);
        if (file_id) {
            $.sleep(1000);
            $.api.completeUpload(deviceId, driveId, file_id, upload_id);
            $.api.completeAlbumsUpload(deviceId, driveId, file_id, "DA39A3EE5E6B4B0D3255BFEF95601890AFD80709");
            return {
                file_id: file_id,
                upload_id: upload_id
            };
        }
        $.logger.error(`${deviceId}上传文件失败`);
    } catch (error) {
        $.logger.error(`上传文件异常`, error.message);
    }
    return {};
}
function deviceRoomListHandle(deviceRooms) {
    const nofinishDevices = new Set();
    const rewardEnergys = new Set();
    let okNum = 0;
    for (const { canCollectEnergy, id, gmtCollectEnergy } of deviceRooms){
        if (!canCollectEnergy && new Date(gmtCollectEnergy).getDate() !== new Date().getDate()) {
            nofinishDevices.add(id);
        } else if (canCollectEnergy) {
            rewardEnergys.add(id);
        } else {
            okNum++;
        }
    }
    return {
        nofinishDevices: Array.from(nofinishDevices),
        rewardEnergys: Array.from(rewardEnergys),
        okNum: okNum
    };
}
function getDeviceRoomRewardApi($, id) {
    return request($, $.api.getDeviceRoomRewardEnergy, `领取${id}设备空间`, id).size;
}
function deleteFileApi($, deviceId, driveId, fileId) {
    try {
        $.api.deleteFile(deviceId, driveId, fileId);
    } catch (error) {
        $.logger.error(`删除文件${fileId}异常`, error.message);
    }
}
function deleteFiles($, needDeleteFiles, driveId) {
    for (const [fileId, deviceId] of needDeleteFiles){
        deleteFileApi($, deviceId, driveId, fileId);
        $.sleep(1000);
    }
}
function deviceRoomTask($) {
    const { rewardCountToday, rewardTotalSize } = getDeviceRoomRewardInfo($);
    if (rewardCountToday >= 5) {
        $.logger.info(`今日已领取${rewardCountToday}次设备间空间,历史总共${rewardTotalSize}M`);
        return;
    }
    const driveId = getAlbumsDriveId($);
    if (!driveId) {
        $.logger.error(`未获取到文件夹故跳过执行`);
        return;
    }
    const needDeleteFiles = new Map();
    createDevice($);
    while(_deviceRoomTask()){
        $.sleep(2000);
    }
    deleteFiles($, needDeleteFiles, driveId);
    /**
   *
   * @returns 是否继续运行
   */ function _deviceRoomTask() {
        const items = getDeviceRoomListApi($);
        if (!items) {
            $.logger.error(`无法获取虚拟设备,跳过执行`);
            return false;
        }
        if (items.length === 0) {
            $.logger.error(`无法创建虚拟设备,跳过执行`);
            return false;
        }
        const { nofinishDevices, rewardEnergys, okNum } = deviceRoomListHandle(items);
        if (okNum >= 5) {
            return false;
        }
        let tempNum = 0;
        for (const deviceId of rewardEnergys){
            const size = getDeviceRoomRewardApi($, deviceId);
            if (size) {
                $.logger.info(`领取设备间成功,获得${size}M`);
                tempNum++;
            }
            // 防止出现有超过 5 个设备间可领取
            if (tempNum + okNum >= 5) break;
            $.sleep(1000);
        }
        for (const deviceId of nofinishDevices){
            const { file_id } = uploadFile($, deviceId, driveId) || {};
            file_id && needDeleteFiles.set(file_id, deviceId);
            $.sleep(1000);
        }
        return true;
    }
}
function signIn($) {
    const { rewards, signInDay } = request($, $.api.signIn, "签到");
    if (!rewards) {
        return;
    }
    for (const { status, type } of rewards){
        if (status !== "finished") {
            continue;
        }
        switch(type){
            case "dailySignIn":
                request($, $.api.signInReward, "领取签到奖励", signInDay);
                break;
            case "dailyTask":
                request($, $.api.signInTaskReward, "领取每日任务奖励", signInDay);
                break;
            default:
                break;
        }
    }
}
function getDeviceList($) {
    try {
        const data = $.api.getDeviceAppletList();
        if (!data.deviceItems) {
            $.logger.error("获取设备信息失败", JSON.stringify(data));
            return;
        }
        if (data.deviceItems.length === 0) {
            $.logger.error("获取到的设备列表未空");
            return;
        }
        return data.deviceItems;
    } catch (error) {
        $.logger.error(`获取设备信息异常`, error.message);
    }
}
function getDevice($) {
    const devices = getDeviceList($);
    if (!devices) return;
    const device = devices.find(({ deviceId })=>deviceId);
    return device;
}
function signInTask($) {
    const { rewards } = request($, $.api.signIn, "签到");
    if (rewards.find(({ type, status })=>type === "dailyTask" && (status === "verification" || status === "finished"))) {
        return;
    }
    const { deviceId, backupViews } = getDevice($) || {};
    if (!deviceId) {
        $.logger.error(`未获取到设备 id,跳过每日任务执行`);
        return;
    }
    $.DATA.deviceId = deviceId;
    const backupView = backupViews.find(({ view })=>view === "album");
    if (!backupView) {
        $.logger.error(`未获取到文件夹 id,跳过每日任务执行`);
        return;
    }
    request($, $.api.updateDeviceExtras, "上报备份");
    const needDeleteFiles = new Map();
    for(let i = 0; i < 10; i++){
        const { file_id } = uploadFile($, deviceId, backupView.driveId);
        file_id && needDeleteFiles.set(file_id, deviceId);
        $.sleep(2000);
    }
    $.DATA.afterTask.push(()=>deleteFiles($, needDeleteFiles, backupView.driveId));
}
function printSignInInfo($) {
    const { rewards } = request($, $.api.signIn, "签到");
    if (!rewards) {
        return;
    }
    const statusMap = {
        unfinished: "未完成",
        finished: "未领取奖励",
        verification: "已领取奖励",
        notStart: "未开始"
    };
    rewards.forEach(({ remind, name, status })=>{
        $.logger.info(`${remind}/${name}/${statusMap[status]}`);
    });
}
function run($) {
    const taskList = [
        deviceRoomTask,
        signInTask,
        signIn,
        printSignInInfo
    ];
    for (const task of taskList){
        task($);
        $.sleep(1000);
    }
    for (const task of $.DATA.afterTask){
        task();
        $.sleep(1000);
    }
}
function getXSignature() {
    return "1176d75ed29c9453de0c9848e47be166e56d5cd57dd6743f71ced1f048e73d847c2847c71f8b5235105456d34054a9b30c8e364e5fee4e4cfa644cc07a45a92a01";
}
function main(index, ASIGN_ALIPAN_TOKEN, option) {
    if (!ASIGN_ALIPAN_TOKEN) return;
    const logger = createLogger({
        pushData: option && option.pushData
    });
    const DATA = {
        deviceId: ActiveSheet.Columns("C").Rows(index).Value,
        afterTask: [],
        refreshToken: ""
    };
    let accessToken;
    function getHeaders() {
        return {
            "content-type": "application/json",
            referer: "https://alipan.com/",
            origin: "https://alipan.com/",
            "x-canary": "client=Android,app=adrive,version=v5.3.0",
            "user-agent": "AliApp(AYSD/5.3.0) com.alicloud.databox/34760760 Channel/36176727979800@rimet_android_5.3.0 language/zh-CN /Android Mobile/Mi 6X",
            "x-device-id": DATA.deviceId,
            authorization: accessToken ? `Bearer ${accessToken}` : "",
            "x-signature": getXSignature()
        };
    }
    const $ = {
        api: createApi(createRequest({
            getHeaders: getHeaders
        })),
        logger: logger,
        DATA: DATA,
        sleep: Time.sleep
    };
    const rtData = refreshToken($, ASIGN_ALIPAN_TOKEN.trim());
    if (!rtData) return;
    DATA.refreshToken = rtData.refresh_token;
    accessToken = rtData.access_token;
    DATA.deviceId = rtData.device_id;
    $.logger.info(`--------------`);
    $.logger.info(`你好${rtData.nick_name || rtData.user_name}`);
    ActiveSheet.Columns("A").Rows(index).Value = rtData.refresh_token;
    ActiveSheet.Columns("B").Rows(index).Value = rtData.nick_name || rtData.user_name;
    run($);
    ActiveSheet.Columns("C").Rows(index).Value = DATA.deviceId;
}
const columnA = ActiveSheet.Columns("A");
// 获取当前工作表的使用范围
const usedRange = ActiveSheet.UsedRange;
const len = usedRange.Row + usedRange.Rows.Count - 1;
const pushData = [];
for(let i = 1; i <= len; i++){
    const cell = columnA.Rows(i);
    if (cell.Text) {
        console.log(`执行第 ${i} 行`);
        main(i, cell.Text, {
            pushData: pushData
        });
    }
}
const pushConfig = getPushConfig();
if (pushData.length && pushConfig) {
    if (!(pushConfig.onlyError && !pushData.some((el)=>el.type === "error"))) {
        const msg = pushData.map((m)=>`[${m.type} ${m.date.toLocaleTimeString()}]${m.msg}`).join("\n");
        msg && sendNotify({
            logger: createLogger(),
            http: {
                fetch: (op)=>{
                    op.data && typeof op.data !== "string" && (op.body = JSON.stringify(op.data));
                    return HTTP.fetch(op.url, op).json();
                }
            }
        }, pushConfig, pushConfig.title || "asign 运行推送", msg);
    }
}

推送

在原表格的基础上新建一个推送表格(一定要叫推送)

表格如图所示,每两列为一个配置单元(每个单元之间运行空列)

单元的第首行首列放置推送名,如 email,pushplus。base 比较特殊。

除第一行外,每个单元第一列为配置名称,第二列为值,中间允许空行(如email所示)

pFazyLD.png

注意

  • 不用的配置就不要写第一行,或者直接删除。
  • 运行时点击工作表1(或者其他名字,反正是你放token配置的那个表,不是推送配置),然后再运行代码,不然一堆报错。
  • 更多推送参考本地运行填写

本地运行

(包括云函数/青龙面板也能举一反三)

使用 npm 安装包 @asunajs/alipan,然后创建一个 js 文件,内容如下:

const alipan = require('@asunajs/alipan');
const { resolve } = require('path');

(async () => {
  await alipan.run(resolve(process.cwd(), './asign.json')); // 按需修改路径
})();

在 js 的旁边创建一个 asign.json 文件,不创建就会使用环境变量 ASIGN_ALIPAN_TOKEN (多个用 token @ 分开),

推送目前支持:email 邮箱, workWeixin 企业微信(app,非 bot),serverChan 等。按需配置即可(不要的记得删除)。onlyError 这一项配置为 true 表示,仅出现 error 级别的日志时才推送

{
  "alipan": [
    {
      "token": "xxxxxxxxxxxxxxxxx"
    },
    {
      "token": "xxxxxxxxxxxxxxxxxxxxxxxxx"
    }
  ],
  "message": {
    "email": {
      "pass": "xxxxxxxxxxxx",
      "from": "xxxxxx@163.com",
      "host": "smtp.163.com",
      "to": "xxx@mht.com"
    },
    "workWeixin": {
      "corpid": "ww4xxxxxxxxxxxxc12",
      "corpsecret": "NBMUW4fxxxxxxxxxxxxxxxxxxxxxu2roo",
      "touser": "cxxxxxxxxxt",
      "agentid": 1008611266666,
      "msgtype": "markdown"
    },
    "serverChan": {
      "token": ""
    },
    "pushplus": {
      "token": ""
    },
    "onlyError": false
  }
}

免费评分

参与人数 14吾爱币 +27 热心值 +12 收起 理由
侃遍天下无二人 + 7 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
fzhhn + 2 + 1 用心讨论,共获提升!
生物未鉴定 + 1 + 1 我很赞同!
JinxBoy + 1 谢谢@Thanks!
abc7940 + 1 + 1 谢谢@Thanks!
文西思密达 + 3 + 1 感谢发布原创作品,吾爱破解论坛因你更精彩!
苏紫方璇 + 7 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
haiyangnanzi + 1 + 1 谢谢@Thanks!
yylmzxc + 1 热心回复!
tianya0908 + 1 + 1 能不能改成本地运行 谢谢
shengruqing + 1 &amp;lt;font style=&amp;quot;vertical-align: inherit;&amp;quot;&amp;gt;&amp;lt;font style=
ysy2001 + 1 + 1 谢谢@Thanks!
zhongyihaitun + 1 谢谢@Thanks!
勤快的懒虫 + 1 + 1 谢谢@Thanks!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

推荐
YuanFang0w0 发表于 2024-2-15 17:31
阿里云现在已经是有限速了,还不给空间 没卵用,还不如用回百度云,百度云有时下载还能跑满速,阿里云虽然限的不狠但是一直两三兆每秒很难受
推荐
 楼主| kittylang 发表于 2024-2-23 21:22 |楼主
abc7940 发表于 2024-2-21 14:56
大佬牛逼,阿里云盘、移动云盘的wps功能都用上了
热切期待
随机时间登录

随机时间其实个人感觉没有用,所有暂时没有计划,后面有空再加吧(wps的ip很容易被针对,判断时间对阿里来说多此一举)

node的推送已经支持,wps 暂时没头绪,但是已经再计划内了。

移动云盘的自动获取更新这个应该是无法实现的,官方并没有这个功能。而密码登录可能会有短信验证码。

免费评分

参与人数 1吾爱币 +1 热心值 +1 收起 理由
abc7940 + 1 + 1 谢谢@Thanks!

查看全部评分

推荐
sxp3468 发表于 2024-2-15 07:55
开始限制   已删除以前会员的空间,现在签到已经没有动力了
3#
zjtzjt 发表于 2024-2-15 00:19
感谢分享,现在不给延期卡了,永久容量不够啊
4#
亲亲宝贝A静 发表于 2024-2-15 00:24
感谢分享,现在签到已经没有动力了
5#
zhangxiaoxiao 发表于 2024-2-15 05:47
学习了,谢谢
6#
福森108 发表于 2024-2-15 07:48
新年快乐,谢谢大佬分享
7#
yinuo2012 发表于 2024-2-15 08:45
这个功能真的太赞了
8#
gcfdhhh 发表于 2024-2-15 08:49
感谢分享,这个功能真的很不错
9#
maya123 发表于 2024-2-15 09:05
现在好像对阿里云盘签到没有按时打卡的激情了
10#
zhangyw40 发表于 2024-2-15 09:09
感谢分析,新年快乐
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则 警告:本版块禁止灌水或回复与主题无关内容,违者重罚!

快速回复 收藏帖子 返回列表 搜索

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-5-3 14:01

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表