|
|
@@ -1,6 +1,7 @@
|
|
|
import { TOKEN_MAP, SMART_WALLET } from './const.js'
|
|
|
|
|
|
const API_URL = 'https://app-byreal-table.trrlzk.easypanel.host/api/top-positions'
|
|
|
+const TRADE_PAIR_URL = 'https://app-byreal-table.trrlzk.easypanel.host/api/pools/list?page=1&pageSize=500'
|
|
|
const DISCORD_WEBHOOK_URL = 'https://discord.com/api/webhooks/1449354624225120378/7gOkPXzZkaoQF7XWKFZRsevVSKXcUOuim2Rhtx_gWzBd9b7wphFMQiAIqBnRT3Gmkog4'
|
|
|
const DISCORD_WEBHOOK_URL_SMART_WALLET = 'https://discord.com/api/webhooks/1450301829064954040/zNYc-mnYPDFgnAPLZxY40aicERwdL4TsvXk9VyiqWgyjRqJMXKIBzVHEvBiHbpbJrmtu'
|
|
|
const DEFAULT_POOL_ADDRESS = TOKEN_MAP['MON']
|
|
|
@@ -9,6 +10,8 @@ const MAX_AGE_MS = 10 * 60 * 1000 // 10分钟
|
|
|
|
|
|
// 存储已发送的 positionAddress
|
|
|
const sentPositions = new Set()
|
|
|
+const sentTradePair = new Set()
|
|
|
+let firstRun = true
|
|
|
|
|
|
/**
|
|
|
* 获取 top-positions 数据
|
|
|
@@ -52,6 +55,30 @@ async function fetchTopPositions() {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+/**
|
|
|
+ * 获取交易对数据
|
|
|
+ */
|
|
|
+async function fetchTradePair() {
|
|
|
+ try {
|
|
|
+ const response = await fetch(TRADE_PAIR_URL)
|
|
|
+ if (!response.ok) {
|
|
|
+ throw new Error(`HTTP error! status: ${response.status}`)
|
|
|
+ }
|
|
|
+
|
|
|
+ const result = await response.json()
|
|
|
+
|
|
|
+ if (result.retCode !== 0 || !result.result?.data?.records) {
|
|
|
+ console.error('API 返回错误:', result.retMsg || '未知错误')
|
|
|
+ return []
|
|
|
+ }
|
|
|
+
|
|
|
+ return result.result.data.records
|
|
|
+ } catch (error) {
|
|
|
+ console.error('获取交易对数据失败:', error)
|
|
|
+ return []
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
/**
|
|
|
* 发送消息到 Discord
|
|
|
*/
|
|
|
@@ -152,6 +179,45 @@ async function sendToDiscord(position, symbol) {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+/**
|
|
|
+ * 发送消息到 Discord 交易对
|
|
|
+ */
|
|
|
+async function sendToDiscordTradePair(pair) {
|
|
|
+ const embed = {
|
|
|
+ title: '🆕 新交易对发现',
|
|
|
+ color: 0x00b098, // 绿色
|
|
|
+ fields: [
|
|
|
+ {
|
|
|
+ name: '交易对',
|
|
|
+ value: `${pair.mintA.mintInfo.symbol}/${pair.mintB.mintInfo.symbol}`,
|
|
|
+ inline: true,
|
|
|
+ },
|
|
|
+ ],
|
|
|
+ timestamp: new Date().toISOString(),
|
|
|
+ url: `https://www.byreal.io/en/portfolio?userAddress=${pair.poolAddress}&tab=current&positionAddress=${pair.poolAddress}`,
|
|
|
+ }
|
|
|
+
|
|
|
+ try {
|
|
|
+ const response = await fetch(DISCORD_WEBHOOK_URL_SMART_WALLET, {
|
|
|
+ method: 'POST',
|
|
|
+ headers: {
|
|
|
+ 'content-type': 'application/json',
|
|
|
+ },
|
|
|
+ body: JSON.stringify({
|
|
|
+ embeds: [embed],
|
|
|
+ }),
|
|
|
+ })
|
|
|
+
|
|
|
+ if (!response.ok) {
|
|
|
+ throw new Error(`Discord webhook 失败: ${response.status}`)
|
|
|
+ }
|
|
|
+
|
|
|
+ console.log(`✅ 已发送到 Discord: ${pair.poolAddress}`)
|
|
|
+ } catch (error) {
|
|
|
+ console.error('发送到 Discord 交易对失败:', error)
|
|
|
+ return false
|
|
|
+ }
|
|
|
+}
|
|
|
/**
|
|
|
* 计算 APR
|
|
|
*/
|
|
|
@@ -206,6 +272,41 @@ async function processPositions() {
|
|
|
console.log(`处理完成,已发送 ${unsentPositions.length} 个新仓位`)
|
|
|
}
|
|
|
|
|
|
+/**
|
|
|
+ * 处理交易对数据
|
|
|
+ */
|
|
|
+async function processTradePair() {
|
|
|
+ console.log(`\n[${new Date().toLocaleString('zh-CN')}] 开始检查交易对...`)
|
|
|
+ const tradePair = await fetchTradePair()
|
|
|
+ if (!tradePair) {
|
|
|
+ console.log('获取交易对数据失败')
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ console.log(`找到 ${tradePair.length} 个交易对`)
|
|
|
+ // 过滤出未发送过的交易对
|
|
|
+ const unsentTradePair = tradePair.filter((pair) => {
|
|
|
+ return pair.poolAddress && !sentTradePair.has(pair.poolAddress)
|
|
|
+ })
|
|
|
+
|
|
|
+ console.log(`其中 ${unsentTradePair.length} 个未发送过`)
|
|
|
+ if (firstRun) {
|
|
|
+ firstRun = false
|
|
|
+ return
|
|
|
+ }
|
|
|
+ // 发送到 Discord
|
|
|
+ for (const pair of unsentTradePair) {
|
|
|
+ const success = await sendToDiscordTradePair(pair)
|
|
|
+ if (success) {
|
|
|
+ sentTradePair.add(pair.poolAddress)
|
|
|
+ }
|
|
|
+ // 避免发送过快,稍微延迟
|
|
|
+ await new Promise((resolve) => setTimeout(resolve, 500))
|
|
|
+ }
|
|
|
+
|
|
|
+ console.log(`处理完成,已发送 ${unsentTradePair.length} 个交易对`)
|
|
|
+}
|
|
|
+
|
|
|
// 启动定时任务
|
|
|
console.log('🚀 监控程序已启动')
|
|
|
console.log(`- 检查间隔: ${INTERVAL_MS / 1000 / 60} 分钟`)
|
|
|
@@ -218,3 +319,5 @@ processPositions()
|
|
|
|
|
|
// 每5分钟执行一次
|
|
|
setInterval(processPositions, INTERVAL_MS)
|
|
|
+
|
|
|
+setInterval(processTradePair, MAX_AGE_MS)
|