### Summary of Changes ### New Endpoints The following new endpoints were added in `src/routes/token.js`: 1. **GET /dev_ip_info**: - **Purpose**: Retrieves IP-related information for a token's developer/creator. - **Query Parameters**: `mintAddr` (required). - **Response**: Includes token details, developer IP information (address, VPN status, score, country), creator details, and bundled status. 2. **GET /get_bundled_tokens**: - **Purpose**: Retrieves a list of tokens identified as bundled based on a timeframe. - **Query Parameters**: `timeframe` (default: 60 seconds), `limit` (default: 50), `offset` (default: 0). - **Response**: List of bundled tokens with details like name, ticker, creator info, trade details, and market cap. 3. **GET /check_bundled_status**: - **Purpose**: Checks the bundled status of a specific token and triggers retroactive analysis if pending. - **Query Parameters**: `mintAddr` (required). - **Response**: Token details, bundled status, trade information, and creator details. 4. **GET /bundled_stats**: - **Purpose**: Provides statistics on bundled tokens in the system. - **Query Parameters**: None. - **Response**: Detailed bundled token statistics (total, bundled, non-bundled, average time delta). 5. **GET /check_ip**: - **Purpose**: Tests IP address checking for VPN status. - **Query Parameters**: `ip` (required). - **Response**: IP check results including VPN status, score, country, and cache status. 6. **GET /test_ip_capture**: - **Purpose**: Tests IP capture from the client request. - **Query Parameters**: None. - **Response**: Client IP, VPN status, score, country, user agent, and timestamp. 7. **GET /analyze_token**: - **Purpose**: Provides comprehensive analysis of a token. - **Query Parameters**: `mintAddr` (required). - **Response**: Detailed token analysis including creator info, holder distribution, bundled status, and risk factors. 8. **GET /top_holders**: - **Purpose**: Retrieves the top token holders for a given mint address. - **Query Parameters**: `mintAddr` (required), `limit` (default: 25). - **Response**: List of top holders with wallet address, hold percentage, SOL amount, and wallet age. 9. **GET /creator_analysis**: - **Purpose**: Analyzes the creator of a token. - **Query Parameters**: `mintAddr` (required). - **Response**: Creator details including wallet address, username, wallet age, IP information, and VPN status. ### New Fields Added to Existing Endpoints 1. **GET /get_token_info** (`src/engine/token.js`): - **New Fields in Response**: - `devIpAddress`: Developer's IP address. - `devIsVPN`: Boolean indicating if the developer's IP is a VPN. - `devVPNScore`: VPN probability score (0-1). - `devCountry`: Developer's country based on IP. - `devIpUpdateTime`: Timestamp of last IP update. - `creatorLoginCountry`: Creator's login country. - `creatorFirstIP`: Creator's first login IP. - `creatorWalletAge`: Object containing wallet age details (`ageInDays`, `createdAt`, `walletAgeFormatted`). - `isBundled`: Boolean indicating if the token is bundled. - `bundledStatus`: Status of bundled detection (`pending`, `bundled`, `not_bundled`). - `firstTradeTime`: Timestamp of the first trade. - `firstTradeIsBuy`: Boolean indicating if the first trade was a buy. - `bundledTimeDelta`: Time difference (ms) between token creation and first trade. - `firstTradeAmount`: Amount of the first trade. - `creatorFirstBuyAmount`: Creator's first buy amount. - `bundledDetectionTime`: Timestamp of bundled detection. - `creatorWalletAgeInDays`: Creator's wallet age in days. - `creatorWalletAgeFormatted`: Formatted creator wallet age. - `totalHolders`: Total number of token holders. - `bundledTokenPercentage`: Percentage of tokens in the system that are bundled. ### Changelog 1. **Database Models**: - Added a new `IPCache` model (`src/db/model.ip.check.js`) to store IP address check results, including VPN detection, country, ASN, and error tracking. - Enhanced `Token` model (`src/db/model.token.js`) with fields for developer IP tracking and bundled token detection. - Enhanced `User` model (`src/db/model.user.js`) with fields for IP tracking (first login IP, last login IP, login country, and total logins). - Updated `src/db/index.js` to include the new `IPCache` model in exports. 2. **Authentication Enhancements**: - Modified `src/engine/auth.js` to capture client IP addresses during login and store IP-related information (IP address, country) in the `User` model. 3. **Token Management Enhancements**: - Updated `src/engine/token.js` to: - Log client IP during token updates. - Include IP tracking and bundled token detection data in `getTokenInfo` responses. - Optimize user ID parsing with `cleanObjectId`. - Fix query parameter in `getFeedData` from `tokenId` to `mintAddr`. - Enhance `getThreadData` to handle `cleanedUserId` safely. 4. **New IP Service**: - Added `src/services/ipService.js`, implementing an `IPService` class to: - Extract client IP from requests. - Check IP addresses for VPN usage via GetIPIntel API with rate limiting and caching. - Cache IP check results in the `IPCache` model. - Provide statistics on IP checks. 5. **Token Analysis**: - Added `src/engine/tokenAnalysis.js` to provide comprehensive token analysis, including: - Bundled token statistics. - Holder pattern analysis (e.g., high concentration, new wallets, low SOL amounts). - Comprehensive token analysis combining token, creator, and holder data. 6. **Solana Engine Enhancements**: - Updated `src/solana/engine.js` to: - Add `limit` parameter to `getTokenHolderDistribution` for flexible holder queries. - Implement `getWalletAge` with caching to calculate wallet age efficiently. - Enhance holder distribution with additional fields like wallet age and user avatar. 7. **Solana Web3 Enhancements**: - Updated `src/solana/solana_web3.js` to: - Handle `bs58` import issues and provide fallback for invalid `ADMIN_PRIVKEY`. - Add bundled trade detection logic in `onTradeEvent`, identifying tokens with trades within 60 seconds of creation. 7. **New Routes**: - Added multiple new endpoints in `src/routes/token.js` for IP tracking, bundled token detection, and token analysis. ### Additional Notes - **IP Tracking**: The addition of IP tracking (via `ipService.js`) enhances security by monitoring user and developer IP addresses for VPN usage and geographic information, cached in the `IPCache` model to reduce API calls. - **Bundled Token Detection**: New logic in `src/solana/solana_web3.js` and `src/engine/tokenAnalysis.js` identifies tokens with trades within 60 seconds of creation as potentially bundled, improving fraud detection. - **Performance Optimizations**: Caching (e.g., wallet age, IP checks) and batch processing (e.g., in `getTokenHolderDistribution`) improve efficiency. - **Error Handling**: Enhanced error handling in new endpoints and services ensures robust responses to invalid inputs or API failures. ### Example responses of API endpoints #### /api/token/get_token_info?mintAddr=DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame { "id": "6867cf8e6645c852166e57d8", "name": "Test3", "ticker": "TES", "mintAddr": "DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame", "desc": "sdf", "logo": "https://arweave.net/sAMQRBJoBL80Ax0dSqmEb2OOHDHXRgK6Wy49rxfek7k", "banner": null, "twitter": null, "telegram": null, "website": null, "cdate": "2025-07-04T12:56:48.186Z", "marketCap": 35, "price": { "_id": "6867cf8e6645c852166e57da", "baseReserve": 800000000000000, "quoteReserve": 28000000000, "price": 3.5e-8 }, "virtLiq": 56000000000, "walletAddr": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "username": "21g6VK", "avatar": null, "tokenBalance": 0, "solBalance": 0, "replies": 0, "bondingCurveProgress": 0, "kingOfTheHillProgress": 0, "crownDate": null, "tokensAvailableForSale": 640000000, "realQuoteReserve": 0, "tokenHolderDistribution": [ { "walletAddr": "CUZZmeuB8HLD3cuukCnHfLaKd5kGs3SX1FmBmnBazRMr", "username": "CUZZme", "bio": null, "holdPercent": 79.5686413621852, "solAmount": 0.00189312, "createdAt": 1751633804, "walletAgeInDays": 51, "walletAgeFormatted": "51 days", "isDev": false, "isKnownUser": false, "userAvatar": null }, { "walletAddr": "4tp3Rgd9HwrZxY4oxeGV1FPG3JSeWtNRu1a217r698Fx", "username": "4tp3Rg", "bio": null, "holdPercent": 20, "solAmount": 0, "createdAt": 1755278973, "walletAgeInDays": 8, "walletAgeFormatted": "8 days", "isDev": false, "isKnownUser": false, "userAvatar": null }, { "walletAddr": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "username": "21g6VK", "bio": "dev", "holdPercent": 0.4313586378148, "solAmount": 42.20951092, "createdAt": 1751633804, "walletAgeInDays": 51, "walletAgeFormatted": "51 days", "isDev": true, "isKnownUser": true, "userAvatar": null } ], "isFavorited": false, "isWatchListed": false, "devIpAddress": null, "devIsVPN": null, "devVPNScore": null, "devCountry": null, "devIpUpdateTime": null, "creatorLoginCountry": null, "creatorFirstIP": null, "creatorWalletAge": { "ageInDays": 51, "createdAt": 1751633804, "walletAgeFormatted": "51 days" }, "isBundled": false, "bundledStatus": "not_bundled", "firstTradeTime": null, "firstTradeIsBuy": null, "bundledTimeDelta": null, "firstTradeAmount": 0, "creatorFirstBuyAmount": 0, "bundledDetectionTime": null, "creatorWalletAgeInDays": 51, "creatorWalletAgeFormatted": "51 days", "totalHolders": 3, "bundledTokenPercentage": 0 } #### /api/token/dev_ip_info?mintAddr=DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame { "success": true, "data": { "mintAddr": "DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame", "tokenName": "Test3", "ticker": "TES", "devIpAddress": null, "devIsVPN": null, "devVPNScore": null, "devCountry": null, "devIpUpdateTime": null, "creatorWallet": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "creatorUsername": "21g6VK", "creatorFirstIP": null, "creatorLastLoginIP": null, "creatorLoginCountry": null, "creatorTotalLogins": 0, "isBundled": false, "bundledStatus": "not_bundled", "firstTradeTime": null, "bundledTimeDelta": null } } #### /api/token/check_bundled_status?mintAddr=DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame { "mintAddr": "DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame", "name": "Test3", "isBundled": false, "bundledStatus": "not_bundled", "bundledTimeDelta": null, "firstTradeIsBuy": null, "firstTradeTime": null, "firstTradeAmount": 0, "creationTime": "2025-07-04T12:56:48.186Z", "creatorWallet": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "creatorUsername": "21g6VK", "firstTrader": null } > /api/token/check_ip?ip=1.1.1.1 { "success": true, "data": { "ip": "1.1.1.1", "isVPN": true, "vpnScore": 1, "country": null, "fromCache": true, "checkTime": "2025-08-24T13:41:55.172Z" } } #### /api/token/test_ip_capture { "success": true, "data": { "ip": "::1", "isVPN": false, "vpnScore": 0, "country": "localhost", "userAgent": "curl/8.12.1", "timestamp": "2025-08-24T13:43:06.247Z" } } #### /api/token/top_holders?mintAddr=DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame&limit=25 { "success": true, "data": { "mintAddr": "DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame", "holders": [ { "walletAddr": "CUZZmeuB8HLD3cuukCnHfLaKd5kGs3SX1FmBmnBazRMr", "username": "CUZZme", "bio": null, "holdPercent": 79.5686413621852, "solAmount": 0.00189312, "createdAt": 1751633804, "walletAgeInDays": 51, "walletAgeFormatted": "51 days", "isDev": false, "isKnownUser": false, "userAvatar": null }, { "walletAddr": "4tp3Rgd9HwrZxY4oxeGV1FPG3JSeWtNRu1a217r698Fx", "username": "4tp3Rg", "bio": null, "holdPercent": 20, "solAmount": 0, "createdAt": 1755278973, "walletAgeInDays": 8, "walletAgeFormatted": "8 days", "isDev": false, "isKnownUser": false, "userAvatar": null }, { "walletAddr": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "username": "21g6VK", "bio": "dev", "holdPercent": 0.4313586378148, "solAmount": 42.20951092, "createdAt": 1751633804, "walletAgeInDays": 51, "walletAgeFormatted": "51 days", "isDev": true, "isKnownUser": true, "userAvatar": null } ], "count": 3 } } #### /api/token/creator_analysis?mintAddr=DYnYitMA5KVS43F9U5ku3SZ7bnfgZTfJcf6f6GriFame { "success": true, "data": { "creatorWallet": "21g6VKka2r4qbmqnHskyLLuEt4YrBbdMnx94ZojSaoBL", "creatorUsername": "21g6VK", "creatorWalletAge": { "ageInDays": 51, "createdAt": 1751633804, "walletAgeFormatted": "51 days" }, "creatorFirstIP": null, "creatorLoginCountry": null, "creatorIsVPN": null, "creatorVPNScore": null, "creationTime": "2025-07-04T12:56:48.186Z" } } #### /api/token/get_bundled_tokens { "count": 0, "tokens": [], "timeframe": "60s", "timestamp": "2025-08-24T13:39:42.624Z" } #### /api/token/bundled_stats { "success": true, "data": { "totalTokens": 3, "bundledTokens": 0, "bundledPercentage": 0, "nonBundledTokens": 3, "averageTimeDelta": 0 } }