您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
根据设定的价格条件自动买入或卖出指定股票
当前为
// ==UserScript== // @name 自动挂单买卖股票 // @namespace http://tampermonkey.net/ // @version 1.7 // @description 根据设定的价格条件自动买入或卖出指定股票 // @author AGSV骄阳 // @match https://stock.agsvpt.cn/* // @grant GM_xmlhttpRequest // ==/UserScript== (async function () { 'use strict'; const API_BASE_URL = 'https://stock.agsvpt.cn/api'; const CONFIG = { STOCK_INFO_URL: `${API_BASE_URL}/stocks/info`, TOKEN_KEY: 'auth_token', }; const token = localStorage.getItem(CONFIG.TOKEN_KEY); if (!token) { console.warn('未找到认证Token,脚本无法运行。'); return; } function fetchApiData(url, options) { return new Promise((resolve, reject) => { GM_xmlhttpRequest({ method: options.method || 'GET', url, responseType: 'json', timeout: 8000, headers: options.headers || {}, data: options.body || null, onload: response => { if (response.status >= 200 && response.status < 300) { resolve(response.response); } else { reject(new Error(`HTTP Error: ${response.status} ${response.statusText}`)); } }, onerror: response => reject(new Error('请求失败: ' + response.statusText)), ontimeout: () => reject(new Error('请求超时')), }); }); } const getCurrentPrice = async function (stockCode) { const url = `${CONFIG.STOCK_INFO_URL}?code=${stockCode}`; const responseData = await fetchApiData(url, { headers: { 'Authorization': 'Bearer ' + token } }); console.log('API响应数据:', responseData); const stockInfo = responseData.find(stock => stock.code === stockCode); return stockInfo ? stockInfo.price : undefined; }; async function buyStock(stockCode, quantity) { const url = `${API_BASE_URL}/stocks/${stockCode}/buy`; const data = { quantity: quantity }; try { const response = await fetchApiData(url, { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + token }, body: JSON.stringify(data) }); console.log('买入响应:', response); } catch (error) { console.error('买入请求失败:', error); } } async function sellStock(stockCode, quantity) { const url = `${API_BASE_URL}/stocks/${stockCode}/sell`; const data = { quantity: quantity }; try { const response = await fetchApiData(url, { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + token }, body: JSON.stringify(data) }); console.log('卖出响应:', response); } catch (error) { console.error('卖出请求失败:', error); // 如果是因为T+1限制导致的错误,可以针对性输出提示 if (error.message.includes("400")) { console.error('卖出请求失败,可能是由于T+1限制,请检查是否符合卖出条件。'); } } } function createInputDialog() { return new Promise((resolve) => { const dialogHtml = ` <div id="inputDialog" style="position:fixed; top:50%; left:50%; transform:translate(-50%, -50%); background:white; padding:20px; border:1px solid #ccc; z-index:1000;"> <h2>设置股票交易参数</h2> <label for="stockCode">股票代码:</label> <select id="stockCode"> <option value="TSLA">TSLA</option> <option value="AAPL">AAPL</option> <option value="GOOGL">GOOGL</option> </select><br><br> <label for="buyPrice">买入价格:</label> <input type="number" id="buyPrice" value="1600" step="0.01"><br><br> <label for="sellPrice">卖出价格:</label> <input type="number" id="sellPrice" value="1900" step="0.01"><br><br> <label for="buyQuantity">买入数量:</label> <input type="number" id="buyQuantity" value="10" min="1"><br><br> <label for="sellQuantity">卖出数量:</label> <input type="number" id="sellQuantity" value="10" min="1"><br><br> <button id="submitBtn">确认</button> <button id="cancelBtn">取消</button> </div> <div id="overlay" style="position:fixed; top:0; left:0; width:100%; height:100%; background:rgba(0,0,0,0.5); z-index:999;"></div> `; document.body.insertAdjacentHTML('beforeend', dialogHtml); document.getElementById('submitBtn').onclick = function () { const stockCode = document.getElementById('stockCode').value; const buyPrice = parseFloat(document.getElementById('buyPrice').value); const sellPrice = parseFloat(document.getElementById('sellPrice').value); const buyQuantity = parseInt(document.getElementById('buyQuantity').value, 10); const sellQuantity = parseInt(document.getElementById('sellQuantity').value, 10); // 输入验证 if (isNaN(buyPrice) || isNaN(sellPrice) || isNaN(buyQuantity) || isNaN(sellQuantity) || buyQuantity <= 0 || sellQuantity <= 0) { alert('请输入有效的价格和数量'); return; } document.getElementById('inputDialog').remove(); document.getElementById('overlay').remove(); resolve({ stockCode, buyPrice, sellPrice, buyQuantity, sellQuantity }); }; document.getElementById('cancelBtn').onclick = function () { document.getElementById('inputDialog').remove(); document.getElementById('overlay').remove(); resolve(null); }; }); } const userInput = await createInputDialog(); if (!userInput) return; // 用户取消 let { stockCode, buyPrice, sellPrice, buyQuantity, sellQuantity } = userInput; async function main() { let lastAction = null; while (true) { try { const currentPrice = await getCurrentPrice(stockCode); console.log(`当前价格: ${currentPrice}`); if (currentPrice !== undefined) { // 买入逻辑 if (currentPrice <= buyPrice && lastAction !== 'buy') { lastAction = 'buy'; await buyStock(stockCode, buyQuantity); } // 卖出逻辑 else if (currentPrice >= sellPrice && lastAction !== 'sell') { lastAction = 'sell'; await sellStock(stockCode, sellQuantity); } // 重置操作状态 else if (currentPrice < buyPrice || currentPrice > sellPrice) { lastAction = null; } } else { console.warn(`无法获取 ${stockCode} 的当前价格`); } await new Promise(resolve => setTimeout(resolve, 10000)); // 每10秒检查一次价格 } catch (error) { console.error('发生错误:', error); await new Promise(resolve => setTimeout(resolve, 10000)); // 遇到错误时也延迟检查 } } } main(); })();
QingJ © 2025
镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址