This commit is contained in:
Andrey Kondratev
2025-08-27 18:57:09 +05:00
parent 98787a382e
commit 57f0519a32
13 changed files with 829 additions and 550 deletions

View File

@@ -1,70 +0,0 @@
# YouTube Authentication Setup
Чтобы обойти блокировку YouTube "Sign in to confirm you're not a bot", нужно использовать cookies из вашего авторизованного браузера.
## Шаг 1: Получение cookies
1. Откройте Chrome/Firefox и зайдите на [youtube.com](https://youtube.com)
2. Убедитесь что вы авторизованы в своем аккаунте
3. Нажмите F12 чтобы открыть Developer Tools
4. Перейдите на вкладку **Application** (Chrome) или **Storage** (Firefox)
5. В левом меню найдите **Cookies****https://www.youtube.com**
6. Найдите и скопируйте значения следующих cookies:
### Обязательные cookies:
- `__Secure-1PSID`
- `__Secure-3PSID`
- `__Secure-1PAPISID`
- `__Secure-3PAPISID`
### Дополнительные (рекомендуемые):
- `VISITOR_INFO1_LIVE`
- `YSC`
## Шаг 2: Настройка файла
1. Откройте файл `youtube-cookies.json` в корне проекта
2. Замените `your_*_value_here` на реальные значения из браузера:
```json
{
"comment": "Replace these values with your actual YouTube cookies from browser",
"__Secure-1PSID": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ",
"__Secure-3PSID": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ",
"__Secure-1PAPISID": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ",
"__Secure-3PAPISID": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ",
"VISITOR_INFO1_LIVE": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ",
"YSC": "СКОПИРОВАННОЕ_ЗНАЧЕНИЕ_ЗДЕСЬ"
}
```
## Шаг 3: Перезапуск сервера
После настройки cookies перезапустите сервер:
```bash
yarn start
```
В логах вы должны увидеть:
```
YouTube cookies loaded successfully
```
## Примечания
- Cookies периодически истекают, и их нужно обновлять
- Файл `youtube-cookies.json` добавлен в `.gitignore` для безопасности
- Если cookies не работают, попробуйте обновить их из браузера
- В случае проблем сервер автоматически переключится на анонимный доступ
## Альтернативный способ
Если cookies не помогают, можно установить системный `yt-dlp`:
```bash
# macOS
brew install yt-dlp
# Затем использовать через exec в Node.js
```

View File

@@ -2,13 +2,17 @@
"name": "quixotic", "name": "quixotic",
"version": "1.0.0", "version": "1.0.0",
"description": "Telegram miniapp for YouTube music search and MP3 conversion", "description": "Telegram miniapp for YouTube music search and MP3 conversion",
"main": "src/server.js", "main": "dist/server.js",
"scripts": { "scripts": {
"start": "node src/server.js", "build": "tsc && tsc -p tsconfig.frontend.json",
"dev": "nodemon src/server.js", "build:backend": "tsc",
"lint": "eslint src/ public/", "build:frontend": "tsc -p tsconfig.frontend.json",
"lint:fix": "eslint src/ public/ --fix", "start": "node dist/server.js",
"validate": "npm run lint && node -c src/server.js && echo '✅ All checks passed!'", "dev": "ts-node src/server.ts",
"dev:watch": "nodemon --exec ts-node src/server.ts",
"lint": "eslint src/ public/ --ext .ts,.js",
"lint:fix": "eslint src/ public/ --ext .ts,.js --fix",
"validate": "npm run lint && npm run build && echo '✅ All checks passed!'",
"pretest": "npm run validate" "pretest": "npm run validate"
}, },
"packageManager": "yarn@1.22.19", "packageManager": "yarn@1.22.19",
@@ -22,8 +26,14 @@
"sqlite3": "^5.1.6" "sqlite3": "^5.1.6"
}, },
"devDependencies": { "devDependencies": {
"@types/express": "^5.0.3",
"@types/fluent-ffmpeg": "^2.1.27",
"@types/node": "^24.3.0",
"@types/node-telegram-bot-api": "^0.64.10",
"eslint": "^9.34.0", "eslint": "^9.34.0",
"nodemon": "^3.0.2" "nodemon": "^3.0.2",
"ts-node": "^10.9.2",
"typescript": "^5.9.2"
}, },
"engines": { "engines": {
"node": ">=16.0.0" "node": ">=16.0.0"

View File

@@ -35,6 +35,6 @@
</div> </div>
</div> </div>
<script src="script.js"></script> <script src="dist/script.js"></script>
</body> </body>
</html> </html>

View File

@@ -1,34 +1,79 @@
interface TelegramWebApp {
ready(): void;
expand(): void;
sendData(data: string): void;
MainButton: {
show(): void;
hide(): void;
};
initDataUnsafe?: {
user?: {
id: number;
};
};
}
interface Window {
Telegram?: {
WebApp: TelegramWebApp;
};
}
interface VideoResult {
id: string;
title: string;
channel: string;
thumbnail: string;
duration: number;
}
interface SearchResponse {
videos: VideoResult[];
}
interface ConvertResponse {
audioUrl?: string;
title: string;
}
class QuixoticApp { class QuixoticApp {
private tg?: TelegramWebApp;
private searchInput!: HTMLInputElement;
private searchBtn!: HTMLButtonElement;
private loading!: HTMLElement;
private results!: HTMLElement;
private noResults!: HTMLElement;
constructor() { constructor() {
this.tg = window.Telegram?.WebApp; this.tg = window.Telegram?.WebApp;
this.init(); this.init();
this.bindEvents(); this.bindEvents();
} }
init() { private init(): void {
if (this.tg) { if (this.tg) {
this.tg.ready(); this.tg.ready();
this.tg.expand(); this.tg.expand();
this.tg.MainButton.hide(); this.tg.MainButton.hide();
} }
this.searchInput = document.getElementById('searchInput'); this.searchInput = document.getElementById('searchInput') as HTMLInputElement;
this.searchBtn = document.getElementById('searchBtn'); this.searchBtn = document.getElementById('searchBtn') as HTMLButtonElement;
this.loading = document.getElementById('loading'); this.loading = document.getElementById('loading') as HTMLElement;
this.results = document.getElementById('results'); this.results = document.getElementById('results') as HTMLElement;
this.noResults = document.getElementById('noResults'); this.noResults = document.getElementById('noResults') as HTMLElement;
} }
bindEvents() { private bindEvents(): void {
this.searchBtn.addEventListener('click', () => this.search()); this.searchBtn.addEventListener('click', () => this.search());
this.searchInput.addEventListener('keypress', (e) => { this.searchInput.addEventListener('keypress', (e: KeyboardEvent) => {
if (e.key === 'Enter') { if (e.key === 'Enter') {
this.search(); this.search();
} }
}); });
} }
async search() { private async search(): Promise<void> {
const query = this.searchInput.value.trim(); const query = this.searchInput.value.trim();
if (!query) return; if (!query) return;
@@ -50,7 +95,7 @@ class QuixoticApp {
throw new Error('Search failed'); throw new Error('Search failed');
} }
const data = await response.json(); const data: SearchResponse = await response.json();
this.displayResults(data.videos); this.displayResults(data.videos);
} catch (error) { } catch (error) {
console.error('Search error:', error); console.error('Search error:', error);
@@ -58,19 +103,19 @@ class QuixoticApp {
} }
} }
showLoading() { private showLoading(): void {
this.loading.classList.remove('hidden'); this.loading.classList.remove('hidden');
this.results.classList.add('hidden'); this.results.classList.add('hidden');
this.noResults.classList.add('hidden'); this.noResults.classList.add('hidden');
this.searchBtn.disabled = true; this.searchBtn.disabled = true;
} }
hideLoading() { private hideLoading(): void {
this.loading.classList.add('hidden'); this.loading.classList.add('hidden');
this.searchBtn.disabled = false; this.searchBtn.disabled = false;
} }
displayResults(videos) { private displayResults(videos: VideoResult[]): void {
this.hideLoading(); this.hideLoading();
if (!videos || videos.length === 0) { if (!videos || videos.length === 0) {
@@ -93,16 +138,18 @@ class QuixoticApp {
this.noResults.classList.add('hidden'); this.noResults.classList.add('hidden');
} }
showNoResults() { private showNoResults(): void {
this.hideLoading(); this.hideLoading();
this.results.classList.add('hidden'); this.results.classList.add('hidden');
this.noResults.classList.remove('hidden'); this.noResults.classList.remove('hidden');
} }
async convertVideo(videoId, title) { public async convertVideo(videoId: string, title: string): Promise<void> {
console.log('Convert video called:', { videoId, title }); console.log('Convert video called:', { videoId, title });
const videoElement = event.currentTarget; const videoElement = (event as any)?.currentTarget as HTMLElement;
videoElement.classList.add('converting'); if (videoElement) {
videoElement.classList.add('converting');
}
try { try {
console.log('Sending convert request...'); console.log('Sending convert request...');
@@ -123,7 +170,7 @@ class QuixoticApp {
throw new Error(`Conversion failed with status: ${response.status}`); throw new Error(`Conversion failed with status: ${response.status}`);
} }
const data = await response.json(); const data: ConvertResponse = await response.json();
console.log('Response data:', data); console.log('Response data:', data);
if (data.audioUrl) { if (data.audioUrl) {
@@ -152,7 +199,7 @@ class QuixoticApp {
// Should not happen since we removed fallbacks // Should not happen since we removed fallbacks
throw new Error('No audio URL received'); throw new Error('No audio URL received');
} }
} catch (error) { } catch (error: any) {
console.error('Conversion error:', error); console.error('Conversion error:', error);
// Show specific error message // Show specific error message
@@ -168,18 +215,20 @@ class QuixoticApp {
this.showMessage(`${errorMsg}`, 'warning'); this.showMessage(`${errorMsg}`, 'warning');
} finally { } finally {
videoElement.classList.remove('converting'); if (videoElement) {
videoElement.classList.remove('converting');
}
} }
} }
formatDuration(seconds) { private formatDuration(seconds: number): string {
if (!seconds) return ''; if (!seconds) return '';
const mins = Math.floor(seconds / 60); const mins = Math.floor(seconds / 60);
const secs = seconds % 60; const secs = seconds % 60;
return `${mins}:${secs.toString().padStart(2, '0')}`; return `${mins}:${secs.toString().padStart(2, '0')}`;
} }
showMessage(message, type = 'info') { private showMessage(message: string, type: string = 'info'): void {
// Remove existing message if any // Remove existing message if any
const existingMessage = document.querySelector('.status-message'); const existingMessage = document.querySelector('.status-message');
if (existingMessage) { if (existingMessage) {
@@ -193,7 +242,9 @@ class QuixoticApp {
// Add to page // Add to page
const container = document.querySelector('.container'); const container = document.querySelector('.container');
container.insertBefore(messageEl, container.firstChild); if (container) {
container.insertBefore(messageEl, container.firstChild);
}
// Auto-remove after 5 seconds // Auto-remove after 5 seconds
setTimeout(() => { setTimeout(() => {
@@ -203,7 +254,7 @@ class QuixoticApp {
}, 5000); }, 5000);
} }
escapeHtml(text) { private escapeHtml(text: string): string {
const div = document.createElement('div'); const div = document.createElement('div');
div.textContent = text; div.textContent = text;
return div.innerHTML; return div.innerHTML;
@@ -211,3 +262,4 @@ class QuixoticApp {
} }
const app = new QuixoticApp(); const app = new QuixoticApp();
(window as any).app = app;

View File

@@ -1,223 +0,0 @@
const TelegramBot = require('node-telegram-bot-api');
const Database = require('./database');
class QuixoticBot {
constructor(token, webAppUrl) {
this.bot = new TelegramBot(token, { polling: true });
this.webAppUrl = webAppUrl;
this.db = new Database();
this.init();
}
init() {
console.log('> Telegram bot initialized');
this.setupCommands();
this.setupHandlers();
}
setupCommands() {
// Set bot commands
this.bot.setMyCommands([
{ command: 'start', description: '0?CAB8BL ?@8;>65=85' },
{ command: 'help', description: '><>IL' },
{ command: 'history', description: 'AB>@8O ?>8A:0' }
]);
}
setupHandlers() {
// Start command
this.bot.onText(/\/start/, async (msg) => {
const chatId = msg.chat.id;
const user = msg.from;
try {
// Add user to database
await this.db.addUser(user);
const keyboard = {
inline_keyboard: [[
{
text: '<µ B:@KBL Quixotic',
web_app: { url: this.webAppUrl }
}
]]
};
await this.bot.sendMessage(chatId,
'<µ >1@> ?>60;>20BL 2 Quixotic!\n\n' +
'0948 ;N1CN ?5A=N =0 YouTube 8 ?>;CG8 MP3 D09; ?@O<> 2 G0B.\n\n' +
'06<8 :=>?:C =865, GB>1K =0G0BL ?>8A::',
{ reply_markup: keyboard }
);
} catch (error) {
console.error('Start command error:', error);
await this.bot.sendMessage(chatId, '@>87>H;0 >H81:0. >?@>1C9B5 ?>765.');
}
});
// Help command
this.bot.onText(/\/help/, async (msg) => {
const chatId = msg.chat.id;
const helpText = `<µ *Quixotic - YouTube to MP3*
*0: ?>;L7>20BLAO:*
1ã 06<8 :=>?:C "B:@KBL Quixotic"
2ã 2548 =0720=85 ?5A=8 2 ?>8A:>2CN AB@>:C
3ã K15@8 =C6=K9 B@5: 87 A?8A:0
4ã >;CG8 MP3 D09; 2 G0B!
*><0=4K:*
/start - 0?CAB8BL ?@8;>65=85
/help - -B0 A?@02:0
/history - AB>@8O ?>8A:0
*>7<>6=>AB8:*
" >8A: ?> YouTube
" KA>:>5 :0G5AB2> MP3 (128kbps)
" KAB@0O :>=25@B0F8O
" AB>@8O ?>8A:0`;
await this.bot.sendMessage(chatId, helpText, { parse_mode: 'Markdown' });
});
// History command
this.bot.onText(/\/history/, async (msg) => {
const chatId = msg.chat.id;
const userId = msg.from.id;
try {
const user = await this.db.getUserByTelegramId(userId);
if (!user) {
await this.bot.sendMessage(chatId, 'AB>@8O ?>8A:0 ?CAB0.');
return;
}
// Get recent search history
const history = await this.db.db.all(
`SELECT query, created_at FROM search_history
WHERE user_id = ?
ORDER BY created_at DESC
LIMIT 10`,
[user.id]
);
if (history.length === 0) {
await this.bot.sendMessage(chatId, 'AB>@8O ?>8A:0 ?CAB0.');
return;
}
let historyText = '=È *>A;54=85 ?>8A:>2K5 70?@>AK:*\n\n';
history.forEach((item, index) => {
const date = new Date(item.created_at).toLocaleDateString('ru-RU');
historyText += `${index + 1}. ${item.query} _(${date})_\n`;
});
await this.bot.sendMessage(chatId, historyText, { parse_mode: 'Markdown' });
} catch (error) {
console.error('History command error:', error);
await this.bot.sendMessage(chatId, 'H81:0 ?>;CG5=8O 8AB>@88.');
}
});
// Handle web app data
this.bot.on('web_app_data', async (msg) => {
const chatId = msg.chat.id;
const data = JSON.parse(msg.web_app.data);
try {
if (data.action === 'send_audio') {
await this.sendAudioFile(chatId, data.audioUrl, data.title);
}
} catch (error) {
console.error('Web app data error:', error);
await this.bot.sendMessage(chatId, 'H81:0 >1@01>B:8 40==KE.');
}
});
// Handle inline queries for search
this.bot.on('inline_query', async (query) => {
const queryId = query.id;
const searchQuery = query.query;
if (!searchQuery || searchQuery.length < 3) {
await this.bot.answerInlineQuery(queryId, []);
return;
}
try {
const YouTubeService = require('./youtube');
const youtube = new YouTubeService();
const videos = await youtube.searchVideos(searchQuery, 5);
const results = videos.map((video, index) => ({
type: 'article',
id: `${index}`,
title: video.title,
description: `${video.channel} " ${this.formatDuration(video.duration)}`,
thumb_url: video.thumbnail,
input_message_content: {
message_text: `${video.title}\n${video.url}`
}
}));
await this.bot.answerInlineQuery(queryId, results, {
cache_time: 300,
is_personal: true
});
} catch (error) {
console.error('Inline query error:', error);
await this.bot.answerInlineQuery(queryId, []);
}
});
// Error handler
this.bot.on('error', (error) => {
console.error('Telegram bot error:', error);
});
console.log(' Bot handlers setup complete');
}
async sendAudioFile(chatId, audioUrl, title) {
try {
await this.bot.sendMessage(chatId, >43>B02;820N MP3 D09;...');
// Send audio file
await this.bot.sendAudio(chatId, audioUrl, {
title: title,
performer: 'Quixotic',
caption: `${title}`
});
} catch (error) {
console.error('Send audio error:', error);
await this.bot.sendMessage(chatId,
'L 5 C40;>AL >B?@028BL 0C48>D09;. >?@>1C9B5 5I5 @07.\n\n' +
`@O<0O AAK;:0: ${audioUrl}`
);
}
}
formatDuration(seconds) {
if (!seconds) return '';
const mins = Math.floor(seconds / 60);
const secs = seconds % 60;
return `${mins}:${secs.toString().padStart(2, '0')}`;
}
}
// Initialize bot if this file is run directly
if (require.main === module) {
const token = process.env.TELEGRAM_BOT_TOKEN;
const webAppUrl = process.env.WEB_APP_URL || 'https://your-domain.com';
if (!token) {
console.error('L TELEGRAM_BOT_TOKEN environment variable is required');
process.exit(1);
}
new QuixoticBot(token, webAppUrl);
}
module.exports = QuixoticBot;

275
src/bot.ts Normal file
View File

@@ -0,0 +1,275 @@
import TelegramBot from 'node-telegram-bot-api';
import { Database } from './database';
interface TelegramUser {
id: number;
first_name: string;
last_name?: string;
username?: string;
}
interface Message {
chat: {
id: number;
};
from?: TelegramUser;
web_app?: {
data: string;
};
}
interface InlineQuery {
id: string;
query: string;
}
interface WebAppData {
action: string;
audioUrl: string;
title: string;
}
interface SearchResult {
query: string;
created_at: string;
}
export class QuixoticBot {
private bot: TelegramBot;
private webAppUrl: string;
private db: Database;
constructor(token: string, webAppUrl: string) {
this.bot = new TelegramBot(token, { polling: true });
this.webAppUrl = webAppUrl;
this.db = new Database();
this.init();
}
private init(): void {
console.log('🤖 Telegram bot initialized');
this.setupCommands();
this.setupHandlers();
}
private setupCommands(): void {
// Set bot commands
this.bot.setMyCommands([
{ command: 'start', description: 'Запустить приложение' },
{ command: 'help', description: 'Помощь' },
{ command: 'history', description: 'История поиска' }
]);
}
private setupHandlers(): void {
// Start command
this.bot.onText(/\/start/, async (msg: Message) => {
const chatId = msg.chat.id;
const user = msg.from;
try {
// Add user to database
if (user) {
await this.db.addUser(user);
}
const keyboard = {
inline_keyboard: [[
{
text: '🎵 Открыть Quixotic',
web_app: { url: this.webAppUrl }
}
]]
};
await this.bot.sendMessage(chatId,
'🎵 Добро пожаловать в Quixotic!\n\n' +
'Найди любую песню на YouTube и получи MP3 файл прямо в чат.\n\n' +
'Нажми кнопку ниже, чтобы начать поиск:',
{ reply_markup: keyboard }
);
} catch (error) {
console.error('Start command error:', error);
await this.bot.sendMessage(chatId, '❌ Произошла ошибка. Попробуйте позже.');
}
});
// Help command
this.bot.onText(/\/help/, async (msg: Message) => {
const chatId = msg.chat.id;
const helpText = `🎵 *Quixotic - YouTube to MP3*
*Как пользоваться:*
1⃣ Нажми кнопку "Открыть Quixotic"
2⃣ Введи название песни в поисковую строку
3⃣ Выбери нужный трек из списка
4⃣ Получи MP3 файл в чат!
*Команды:*
/start - Запустить приложение
/help - Эта справка
/history - История поиска
*Возможности:*
✅ Поиск по YouTube
✅ Высокое качество MP3 (128kbps)
✅ Быстрая конвертация
✅ История поиска`;
await this.bot.sendMessage(chatId, helpText, { parse_mode: 'Markdown' });
});
// History command
this.bot.onText(/\/history/, async (msg: Message) => {
const chatId = msg.chat.id;
const userId = msg.from?.id;
if (!userId) return;
try {
const user = await this.db.getUserByTelegramId(userId);
if (!user) {
await this.bot.sendMessage(chatId, 'История поиска пуста.');
return;
}
// Get recent search history
const history = await this.getSearchHistory(user.id);
if (history.length === 0) {
await this.bot.sendMessage(chatId, 'История поиска пуста.');
return;
}
let historyText = '📋 *Последние поисковые запросы:*\n\n';
history.forEach((item, index) => {
const date = new Date(item.created_at).toLocaleDateString('ru-RU');
historyText += `${index + 1}. ${item.query} _(${date})_\n`;
});
await this.bot.sendMessage(chatId, historyText, { parse_mode: 'Markdown' });
} catch (error) {
console.error('History command error:', error);
await this.bot.sendMessage(chatId, '❌ Ошибка получения истории.');
}
});
// Handle web app data
this.bot.on('web_app_data', async (msg: Message) => {
const chatId = msg.chat.id;
if (!msg.web_app?.data) return;
const data: WebAppData = JSON.parse(msg.web_app.data);
try {
if (data.action === 'send_audio') {
await this.sendAudioFile(chatId, data.audioUrl, data.title);
}
} catch (error) {
console.error('Web app data error:', error);
await this.bot.sendMessage(chatId, '❌ Ошибка обработки данных.');
}
});
// Handle inline queries for search
this.bot.on('inline_query', async (query: InlineQuery) => {
const queryId = query.id;
const searchQuery = query.query;
if (!searchQuery || searchQuery.length < 3) {
await this.bot.answerInlineQuery(queryId, []);
return;
}
try {
const { SoundCloudService } = require('./soundcloud');
const soundcloud = new SoundCloudService();
const videos = await soundcloud.searchTracks(searchQuery, 5);
const results = videos.map((video: any, index: number) => ({
type: 'article',
id: `${index}`,
title: video.title,
description: `${video.channel}${this.formatDuration(video.duration)}`,
thumb_url: video.thumbnail,
input_message_content: {
message_text: `🎵 ${video.title}\n🔗 ${video.url}`
}
}));
await this.bot.answerInlineQuery(queryId, results, {
cache_time: 300,
is_personal: true
});
} catch (error) {
console.error('Inline query error:', error);
await this.bot.answerInlineQuery(queryId, []);
}
});
// Error handler
this.bot.on('error', (error: Error) => {
console.error('Telegram bot error:', error);
});
console.log('✅ Bot handlers setup complete');
}
private async getSearchHistory(userId: number): Promise<SearchResult[]> {
return new Promise((resolve, reject) => {
this.db['db'].all(
`SELECT query, created_at FROM search_history
WHERE user_id = ?
ORDER BY created_at DESC
LIMIT 10`,
[userId],
(err: Error | null, rows: SearchResult[]) => {
if (err) reject(err);
else resolve(rows || []);
}
);
});
}
private async sendAudioFile(chatId: number, audioUrl: string, title: string): Promise<void> {
try {
await this.bot.sendMessage(chatId, '⏳ Подготавливаю MP3 файл...');
// Send audio file
await this.bot.sendAudio(chatId, audioUrl, {
title: title,
performer: 'Quixotic',
caption: `🎵 ${title}`
});
} catch (error) {
console.error('Send audio error:', error);
await this.bot.sendMessage(chatId,
'❌ Не удалось отправить аудиофайл. Попробуйте еще раз.\n\n' +
`Прямая ссылка: ${audioUrl}`
);
}
}
private formatDuration(seconds: number): string {
if (!seconds) return '';
const mins = Math.floor(seconds / 60);
const secs = seconds % 60;
return `${mins}:${secs.toString().padStart(2, '0')}`;
}
}
// Initialize bot if this file is run directly
if (require.main === module) {
const token = process.env.TELEGRAM_BOT_TOKEN;
const webAppUrl = process.env.WEB_APP_URL || 'https://your-domain.com';
if (!token) {
console.error('❌ TELEGRAM_BOT_TOKEN environment variable is required');
process.exit(1);
}
new QuixoticBot(token, webAppUrl);
}

View File

@@ -1,14 +1,33 @@
const sqlite3 = require('sqlite3').verbose(); import sqlite3 from 'sqlite3';
const path = require('path'); import path from 'path';
interface TelegramUser {
id: number;
username?: string;
first_name?: string;
last_name?: string;
}
interface User {
id: number;
telegram_id: number;
username?: string;
first_name?: string;
last_name?: string;
created_at: string;
}
export class Database {
private dbPath: string;
private db: sqlite3.Database;
class Database {
constructor() { constructor() {
this.dbPath = path.join(__dirname, '../database/quixotic.db'); this.dbPath = path.join(__dirname, '../database/quixotic.db');
this.db = new sqlite3.Database(this.dbPath); this.db = new sqlite3.Database(this.dbPath);
this.init(); this.init();
} }
init() { private init(): void {
this.db.serialize(() => { this.db.serialize(() => {
// Users table // Users table
this.db.run(`CREATE TABLE IF NOT EXISTS users ( this.db.run(`CREATE TABLE IF NOT EXISTS users (
@@ -42,14 +61,14 @@ class Database {
}); });
} }
addUser(telegramUser) { addUser(telegramUser: TelegramUser): Promise<number> {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
const { id, username, first_name, last_name } = telegramUser; const { id, username, first_name, last_name } = telegramUser;
this.db.run( this.db.run(
`INSERT OR REPLACE INTO users (telegram_id, username, first_name, last_name) `INSERT OR REPLACE INTO users (telegram_id, username, first_name, last_name)
VALUES (?, ?, ?, ?)`, VALUES (?, ?, ?, ?)`,
[id, username, first_name, last_name], [id, username, first_name, last_name],
function(err) { function(err: Error | null) {
if (err) reject(err); if (err) reject(err);
else resolve(this.lastID); else resolve(this.lastID);
} }
@@ -57,12 +76,12 @@ class Database {
}); });
} }
addSearchHistory(userId, query) { addSearchHistory(userId: number, query: string): Promise<number> {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.db.run( this.db.run(
'INSERT INTO search_history (user_id, query) VALUES (?, ?)', 'INSERT INTO search_history (user_id, query) VALUES (?, ?)',
[userId, query], [userId, query],
function(err) { function(err: Error | null) {
if (err) reject(err); if (err) reject(err);
else resolve(this.lastID); else resolve(this.lastID);
} }
@@ -70,12 +89,12 @@ class Database {
}); });
} }
addDownload(userId, youtubeId, title, filePath) { addDownload(userId: number, youtubeId: string, title: string, filePath: string): Promise<number> {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.db.run( this.db.run(
'INSERT INTO downloads (user_id, youtube_id, title, file_path) VALUES (?, ?, ?, ?)', 'INSERT INTO downloads (user_id, youtube_id, title, file_path) VALUES (?, ?, ?, ?)',
[userId, youtubeId, title, filePath], [userId, youtubeId, title, filePath],
function(err) { function(err: Error | null) {
if (err) reject(err); if (err) reject(err);
else resolve(this.lastID); else resolve(this.lastID);
} }
@@ -83,12 +102,12 @@ class Database {
}); });
} }
getUserByTelegramId(telegramId) { getUserByTelegramId(telegramId: string | number): Promise<User | undefined> {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.db.get( this.db.get(
'SELECT * FROM users WHERE telegram_id = ?', 'SELECT * FROM users WHERE telegram_id = ?',
[telegramId], [telegramId],
(err, row) => { (err: Error | null, row: User) => {
if (err) reject(err); if (err) reject(err);
else resolve(row); else resolve(row);
} }
@@ -96,9 +115,7 @@ class Database {
}); });
} }
close() { close(): void {
this.db.close(); this.db.close();
} }
} }
module.exports = Database;

View File

@@ -1,9 +1,9 @@
const express = require('express'); import express, { Request, Response, NextFunction } from 'express';
const path = require('path'); import path from 'path';
const fs = require('fs'); import fs from 'fs';
const ffmpeg = require('fluent-ffmpeg'); import ffmpeg from 'fluent-ffmpeg';
const Database = require('./database'); import { Database } from './database';
const SoundCloudService = require('./soundcloud'); import { SoundCloudService } from './soundcloud';
const app = express(); const app = express();
const port = process.env.PORT || 3000; const port = process.env.PORT || 3000;
@@ -23,14 +23,14 @@ if (!fs.existsSync(downloadsDir)) {
} }
// Routes // Routes
app.get('/', (req, res) => { app.get('/', (req: Request, res: Response) => {
res.sendFile(path.join(__dirname, '../public/index.html')); res.sendFile(path.join(__dirname, '../public/index.html'));
}); });
// Search videos // Search videos
app.post('/api/search', async (req, res) => { app.post('/api/search', async (req: Request, res: Response) => {
try { try {
const { query, userId } = req.body; const { query, userId }: { query?: string; userId?: string } = req.body;
if (!query || query.trim().length === 0) { if (!query || query.trim().length === 0) {
return res.status(400).json({ error: 'Query is required' }); return res.status(400).json({ error: 'Query is required' });
@@ -58,9 +58,9 @@ app.post('/api/search', async (req, res) => {
}); });
// Convert video to MP3 // Convert video to MP3
app.post('/api/convert', async (req, res) => { app.post('/api/convert', async (req: Request, res: Response) => {
try { try {
const { videoId, title, userId } = req.body; const { videoId, title, userId }: { videoId?: string; title?: string; userId?: string } = req.body;
console.log('Convert request received:', { videoId, title, userId }); console.log('Convert request received:', { videoId, title, userId });
if (!videoId) { if (!videoId) {
@@ -68,7 +68,7 @@ app.post('/api/convert', async (req, res) => {
} }
// Generate safe filename // Generate safe filename
const safeTitle = title.replace(/[^\w\s-]/g, '').replace(/\s+/g, '_').substring(0, 50); const safeTitle = (title || '').replace(/[^\w\s-]/g, '').replace(/\s+/g, '_').substring(0, 50);
const filename = `${videoId}_${safeTitle}.mp3`; const filename = `${videoId}_${safeTitle}.mp3`;
const outputPath = path.join(downloadsDir, filename); const outputPath = path.join(downloadsDir, filename);
@@ -88,7 +88,7 @@ app.post('/api/convert', async (req, res) => {
console.log('Audio stream obtained, starting FFmpeg conversion...'); console.log('Audio stream obtained, starting FFmpeg conversion...');
// Convert to MP3 using ffmpeg // Convert to MP3 using ffmpeg
await new Promise((resolve, reject) => { await new Promise<void>((resolve, reject) => {
const conversion = ffmpeg(audioStream) const conversion = ffmpeg(audioStream)
.audioCodec('libmp3lame') .audioCodec('libmp3lame')
.audioBitrate('192k') .audioBitrate('192k')
@@ -96,10 +96,10 @@ app.post('/api/convert', async (req, res) => {
.audioFrequency(44100) .audioFrequency(44100)
.format('mp3') .format('mp3')
.output(outputPath) .output(outputPath)
.on('start', (command) => { .on('start', (command: string) => {
console.log('FFmpeg started:', command); console.log('FFmpeg started:', command);
}) })
.on('progress', (progress) => { .on('progress', (progress: any) => {
if (progress.percent) { if (progress.percent) {
console.log(`Conversion progress: ${Math.round(progress.percent)}%`); console.log(`Conversion progress: ${Math.round(progress.percent)}%`);
} }
@@ -108,7 +108,7 @@ app.post('/api/convert', async (req, res) => {
console.log('MP3 conversion completed successfully'); console.log('MP3 conversion completed successfully');
resolve(); resolve();
}) })
.on('error', (err) => { .on('error', (err: Error) => {
console.error('FFmpeg error:', err.message); console.error('FFmpeg error:', err.message);
reject(err); reject(err);
}); });
@@ -121,7 +121,7 @@ app.post('/api/convert', async (req, res) => {
try { try {
const user = await db.getUserByTelegramId(userId); const user = await db.getUserByTelegramId(userId);
if (user) { if (user) {
await db.addDownload(user.id, videoId, title, outputPath); await db.addDownload(user.id, videoId, title || '', outputPath);
} }
} catch (dbError) { } catch (dbError) {
console.error('Database error:', dbError); console.error('Database error:', dbError);
@@ -132,7 +132,7 @@ app.post('/api/convert', async (req, res) => {
console.log('Conversion successful, file available at:', audioUrl); console.log('Conversion successful, file available at:', audioUrl);
res.json({ audioUrl, title }); res.json({ audioUrl, title });
} catch (conversionError) { } catch (conversionError: any) {
console.error('Conversion failed for video:', videoId); console.error('Conversion failed for video:', videoId);
console.error('Error details:', conversionError.message); console.error('Error details:', conversionError.message);
console.error('Full error:', conversionError); console.error('Full error:', conversionError);
@@ -155,12 +155,12 @@ app.post('/api/convert', async (req, res) => {
app.use('/downloads', express.static(downloadsDir)); app.use('/downloads', express.static(downloadsDir));
// Health check // Health check
app.get('/health', (req, res) => { app.get('/health', (req: Request, res: Response) => {
res.json({ status: 'ok', timestamp: new Date().toISOString() }); res.json({ status: 'ok', timestamp: new Date().toISOString() });
}); });
// Error handler // Error handler
app.use((err, req, res, next) => { app.use((err: Error, req: Request, res: Response, next: NextFunction) => {
console.error(err.stack); console.error(err.stack);
res.status(500).json({ error: 'Something went wrong!' }); res.status(500).json({ error: 'Something went wrong!' });
}); });
@@ -196,4 +196,4 @@ app.listen(port, () => {
console.log(`Open in browser: http://localhost:${port}`); console.log(`Open in browser: http://localhost:${port}`);
}); });
module.exports = app; export default app;

View File

@@ -1,12 +1,44 @@
const scdl = require('soundcloud-downloader').default; import scdl from 'soundcloud-downloader';
import { Readable } from 'stream';
interface SearchTrack {
id: number;
title: string;
user?: {
username: string;
avatar_url?: string;
};
artwork_url?: string;
duration: number;
permalink_url: string;
streamable: boolean;
downloadable: boolean;
}
class SoundCloudService { interface TrackResult {
id: number;
title: string;
channel: string;
thumbnail: string;
duration: number;
url: string;
streamable: boolean;
downloadable: boolean;
}
interface TrackInfo {
title: string;
author: string;
length: number;
available: boolean;
}
export class SoundCloudService {
constructor() { constructor() {
console.log('SoundCloud service initialized'); console.log('SoundCloud service initialized');
} }
async searchTracks(query, maxResults = 10) { async searchTracks(query: string, maxResults: number = 10): Promise<TrackResult[]> {
try { try {
console.log(`Searching SoundCloud for: ${query}`); console.log(`Searching SoundCloud for: ${query}`);
@@ -15,14 +47,14 @@ class SoundCloudService {
query: query, query: query,
limit: maxResults, limit: maxResults,
resourceType: 'tracks' resourceType: 'tracks'
}); }) as any;
if (!tracks || tracks.length === 0) { if (!tracks || tracks.length === 0) {
console.log('No tracks found'); console.log('No tracks found');
return []; return [];
} }
const trackResults = tracks.map(track => ({ const trackResults: TrackResult[] = tracks.map(track => ({
id: track.id, id: track.id,
title: track.title, title: track.title,
channel: track.user?.username || 'Unknown Artist', channel: track.user?.username || 'Unknown Artist',
@@ -36,15 +68,15 @@ class SoundCloudService {
console.log(`Found ${trackResults.length} tracks on SoundCloud`); console.log(`Found ${trackResults.length} tracks on SoundCloud`);
return trackResults; return trackResults;
} catch (error) { } catch (error: any) {
console.error('SoundCloud search error:', error.message); console.error('SoundCloud search error:', error.message);
return []; return [];
} }
} }
async getTrackInfo(trackId) { async getTrackInfo(trackId: string | number): Promise<TrackInfo> {
try { try {
const track = await scdl.getInfo(trackId); const track = await scdl.getInfo(String(trackId)) as SearchTrack;
return { return {
title: track.title, title: track.title,
author: track.user?.username || 'Unknown', author: track.user?.username || 'Unknown',
@@ -57,12 +89,12 @@ class SoundCloudService {
} }
} }
async getAudioStream(trackId) { async getAudioStream(trackId: string | number): Promise<Readable> {
try { try {
console.log(`Getting audio stream for track: ${trackId}`); console.log(`Getting audio stream for track: ${trackId}`);
// Get track info first // Get track info first
const trackInfo = await scdl.getInfo(trackId); const trackInfo = await scdl.getInfo(String(trackId)) as SearchTrack;
if (!trackInfo.streamable) { if (!trackInfo.streamable) {
throw new Error('Track is not streamable'); throw new Error('Track is not streamable');
@@ -73,12 +105,12 @@ class SoundCloudService {
console.log(`Duration: ${Math.floor(trackInfo.duration / 1000)}s`); console.log(`Duration: ${Math.floor(trackInfo.duration / 1000)}s`);
// Get audio stream // Get audio stream
const stream = await scdl.download(trackId); const stream = await scdl.download(String(trackId));
console.log('Audio stream obtained successfully from SoundCloud'); console.log('Audio stream obtained successfully from SoundCloud');
return stream; return stream;
} catch (error) { } catch (error: any) {
console.error('SoundCloud download failed:', error.message); console.error('SoundCloud download failed:', error.message);
// Try alternative approach // Try alternative approach
@@ -90,12 +122,10 @@ class SoundCloudService {
console.log('Audio stream obtained with alternative method'); console.log('Audio stream obtained with alternative method');
return stream; return stream;
} catch (fallbackError) { } catch (fallbackError: any) {
console.error('Alternative method also failed:', fallbackError.message); console.error('Alternative method also failed:', fallbackError.message);
throw new Error(`SoundCloud download failed: ${error.message}`); throw new Error(`SoundCloud download failed: ${error.message}`);
} }
} }
} }
} }
module.exports = SoundCloudService;

25
tsconfig.frontend.json Normal file
View File

@@ -0,0 +1,25 @@
{
"compilerOptions": {
"target": "ES2020",
"module": "ES2020",
"moduleResolution": "node",
"lib": ["ES2020", "DOM"],
"outDir": "./public/dist",
"strict": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
"resolveJsonModule": true,
"declaration": false,
"sourceMap": true,
"allowJs": true
},
"include": [
"public/script.ts"
],
"exclude": [
"node_modules",
"src",
"public/dist"
]
}

29
tsconfig.json Normal file
View File

@@ -0,0 +1,29 @@
{
"compilerOptions": {
"target": "ES2020",
"module": "commonjs",
"lib": ["ES2020"],
"outDir": "./dist",
"rootDir": "./src",
"strict": false,
"noImplicitAny": false,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
"resolveJsonModule": true,
"declaration": true,
"sourceMap": true,
"experimentalDecorators": true,
"emitDecoratorMetadata": true,
"moduleResolution": "node",
"allowSyntheticDefaultImports": true
},
"include": [
"src/**/*"
],
"exclude": [
"node_modules",
"dist",
"public"
]
}

476
yarn.lock
View File

@@ -7,6 +7,13 @@
resolved "https://registry.npmjs.org/@babel/runtime/-/runtime-7.28.3.tgz" resolved "https://registry.npmjs.org/@babel/runtime/-/runtime-7.28.3.tgz"
integrity sha512-9uIQ10o0WGdpP6GDhXcdOJPJuDgFtIDtN/9+ArJQ2NAfAmiuhTQdzkaTGR33v43GYS2UrSA0eX2pPPHoFVvpxA== integrity sha512-9uIQ10o0WGdpP6GDhXcdOJPJuDgFtIDtN/9+ArJQ2NAfAmiuhTQdzkaTGR33v43GYS2UrSA0eX2pPPHoFVvpxA==
"@cspotcode/source-map-support@^0.8.0":
version "0.8.1"
resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz#00629c35a688e05a88b1cda684fb9d5e73f000a1"
integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==
dependencies:
"@jridgewell/trace-mapping" "0.3.9"
"@cypress/request-promise@^5.0.0": "@cypress/request-promise@^5.0.0":
version "5.0.0" version "5.0.0"
resolved "https://registry.npmjs.org/@cypress/request-promise/-/request-promise-5.0.0.tgz" resolved "https://registry.npmjs.org/@cypress/request-promise/-/request-promise-5.0.0.tgz"
@@ -17,7 +24,7 @@
stealthy-require "^1.1.1" stealthy-require "^1.1.1"
tough-cookie "^4.1.3" tough-cookie "^4.1.3"
"@cypress/request@^3.0.0", "@cypress/request@^3.0.1": "@cypress/request@^3.0.1":
version "3.0.9" version "3.0.9"
resolved "https://registry.npmjs.org/@cypress/request/-/request-3.0.9.tgz" resolved "https://registry.npmjs.org/@cypress/request/-/request-3.0.9.tgz"
integrity sha512-I3l7FdGRXluAS44/0NguwWlO83J18p0vlr2FYHrJkWdNYhgVoiYo61IXPqaOsL+vNxU1ZqMACzItGK3/KKDsdw== integrity sha512-I3l7FdGRXluAS44/0NguwWlO83J18p0vlr2FYHrJkWdNYhgVoiYo61IXPqaOsL+vNxU1ZqMACzItGK3/KKDsdw==
@@ -140,6 +147,24 @@
resolved "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.4.3.tgz" resolved "https://registry.npmjs.org/@humanwhocodes/retry/-/retry-0.4.3.tgz"
integrity sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ== integrity sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==
"@jridgewell/resolve-uri@^3.0.3":
version "3.1.2"
resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz#7a0ee601f60f99a20c7c7c5ff0c80388c1189bd6"
integrity sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==
"@jridgewell/sourcemap-codec@^1.4.10":
version "1.5.5"
resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz#6912b00d2c631c0d15ce1a7ab57cd657f2a8f8ba"
integrity sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==
"@jridgewell/trace-mapping@0.3.9":
version "0.3.9"
resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9"
integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==
dependencies:
"@jridgewell/resolve-uri" "^3.0.3"
"@jridgewell/sourcemap-codec" "^1.4.10"
"@npmcli/fs@^1.0.0": "@npmcli/fs@^1.0.0":
version "1.1.1" version "1.1.1"
resolved "https://registry.npmjs.org/@npmcli/fs/-/fs-1.1.1.tgz" resolved "https://registry.npmjs.org/@npmcli/fs/-/fs-1.1.1.tgz"
@@ -161,16 +186,149 @@
resolved "https://registry.npmjs.org/@tootallnate/once/-/once-1.1.2.tgz" resolved "https://registry.npmjs.org/@tootallnate/once/-/once-1.1.2.tgz"
integrity sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw== integrity sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw==
"@tsconfig/node10@^1.0.7":
version "1.0.11"
resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.11.tgz#6ee46400685f130e278128c7b38b7e031ff5b2f2"
integrity sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==
"@tsconfig/node12@^1.0.7":
version "1.0.11"
resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d"
integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==
"@tsconfig/node14@^1.0.0":
version "1.0.3"
resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1"
integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==
"@tsconfig/node16@^1.0.2":
version "1.0.4"
resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.4.tgz#0b92dcc0cc1c81f6f306a381f28e31b1a56536e9"
integrity sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==
"@types/body-parser@*":
version "1.19.6"
resolved "https://registry.yarnpkg.com/@types/body-parser/-/body-parser-1.19.6.tgz#1859bebb8fd7dac9918a45d54c1971ab8b5af474"
integrity sha512-HLFeCYgz89uk22N5Qg3dvGvsv46B8GLvKKo1zKG4NybA8U2DiEO3w9lqGg29t/tfLRJpJ6iQxnVw4OnB7MoM9g==
dependencies:
"@types/connect" "*"
"@types/node" "*"
"@types/caseless@*":
version "0.12.5"
resolved "https://registry.yarnpkg.com/@types/caseless/-/caseless-0.12.5.tgz#db9468cb1b1b5a925b8f34822f1669df0c5472f5"
integrity sha512-hWtVTC2q7hc7xZ/RLbxapMvDMgUnDvKvMOpKal4DrMyfGBUfB1oKaZlIRr6mJL+If3bAP6sV/QneGzF6tJjZDg==
"@types/connect@*":
version "3.4.38"
resolved "https://registry.yarnpkg.com/@types/connect/-/connect-3.4.38.tgz#5ba7f3bc4fbbdeaff8dded952e5ff2cc53f8d858"
integrity sha512-K6uROf1LD88uDQqJCktA4yzL1YYAK6NgfsI0v/mTgyPKWsX1CnJ0XPSDhViejru1GcRkLWb8RlzFYJRqGUbaug==
dependencies:
"@types/node" "*"
"@types/estree@^1.0.6": "@types/estree@^1.0.6":
version "1.0.8" version "1.0.8"
resolved "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz" resolved "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz"
integrity sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w== integrity sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==
"@types/express-serve-static-core@^5.0.0":
version "5.0.7"
resolved "https://registry.yarnpkg.com/@types/express-serve-static-core/-/express-serve-static-core-5.0.7.tgz#2fa94879c9d46b11a5df4c74ac75befd6b283de6"
integrity sha512-R+33OsgWw7rOhD1emjU7dzCDHucJrgJXMA5PYCzJxVil0dsyx5iBEPHqpPfiKNJQb7lZ1vxwoLR4Z87bBUpeGQ==
dependencies:
"@types/node" "*"
"@types/qs" "*"
"@types/range-parser" "*"
"@types/send" "*"
"@types/express@^5.0.3":
version "5.0.3"
resolved "https://registry.yarnpkg.com/@types/express/-/express-5.0.3.tgz#6c4bc6acddc2e2a587142e1d8be0bce20757e956"
integrity sha512-wGA0NX93b19/dZC1J18tKWVIYWyyF2ZjT9vin/NRu0qzzvfVzWjs04iq2rQ3H65vCTQYlRqs3YHfY7zjdV+9Kw==
dependencies:
"@types/body-parser" "*"
"@types/express-serve-static-core" "^5.0.0"
"@types/serve-static" "*"
"@types/fluent-ffmpeg@^2.1.27":
version "2.1.27"
resolved "https://registry.yarnpkg.com/@types/fluent-ffmpeg/-/fluent-ffmpeg-2.1.27.tgz#c4eac6fbda30bb6316d2220c8faf54f48db0812d"
integrity sha512-QiDWjihpUhriISNoBi2hJBRUUmoj/BMTYcfz+F+ZM9hHWBYABFAE6hjP/TbCZC0GWwlpa3FzvHH9RzFeRusZ7A==
dependencies:
"@types/node" "*"
"@types/http-errors@*":
version "2.0.5"
resolved "https://registry.yarnpkg.com/@types/http-errors/-/http-errors-2.0.5.tgz#5b749ab2b16ba113423feb1a64a95dcd30398472"
integrity sha512-r8Tayk8HJnX0FztbZN7oVqGccWgw98T/0neJphO91KkmOzug1KkofZURD4UaD5uH8AqcFLfdPErnBod0u71/qg==
"@types/json-schema@^7.0.15": "@types/json-schema@^7.0.15":
version "7.0.15" version "7.0.15"
resolved "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz" resolved "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz"
integrity sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA== integrity sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==
"@types/mime@^1":
version "1.3.5"
resolved "https://registry.yarnpkg.com/@types/mime/-/mime-1.3.5.tgz#1ef302e01cf7d2b5a0fa526790c9123bf1d06690"
integrity sha512-/pyBZWSLD2n0dcHE3hq8s8ZvcETHtEuF+3E7XVt0Ig2nvsVQXdghHVcEkIWjy9A0wKfTn97a/PSDYohKIlnP/w==
"@types/node-telegram-bot-api@^0.64.10":
version "0.64.10"
resolved "https://registry.yarnpkg.com/@types/node-telegram-bot-api/-/node-telegram-bot-api-0.64.10.tgz#c93a2b4a7664071babde171bbda5b2e61af8d5d6"
integrity sha512-hiwjeze0TGVB7f5Es6WnLqEsd3g3TRbR2SLeT7iAtO2rrkisCjc4N65wFXzkp+viIReV7xun2/j/PHTf+Hcaqg==
dependencies:
"@types/node" "*"
"@types/request" "*"
"@types/node@*", "@types/node@^24.3.0":
version "24.3.0"
resolved "https://registry.yarnpkg.com/@types/node/-/node-24.3.0.tgz#89b09f45cb9a8ee69466f18ee5864e4c3eb84dec"
integrity sha512-aPTXCrfwnDLj4VvXrm+UUCQjNEvJgNA8s5F1cvwQU+3KNltTOkBm1j30uNLyqqPNe7gE3KFzImYoZEfLhp4Yow==
dependencies:
undici-types "~7.10.0"
"@types/qs@*":
version "6.14.0"
resolved "https://registry.yarnpkg.com/@types/qs/-/qs-6.14.0.tgz#d8b60cecf62f2db0fb68e5e006077b9178b85de5"
integrity sha512-eOunJqu0K1923aExK6y8p6fsihYEn/BYuQ4g0CxAAgFc4b/ZLN4CrsRZ55srTdqoiLzU2B2evC+apEIxprEzkQ==
"@types/range-parser@*":
version "1.2.7"
resolved "https://registry.yarnpkg.com/@types/range-parser/-/range-parser-1.2.7.tgz#50ae4353eaaddc04044279812f52c8c65857dbcb"
integrity sha512-hKormJbkJqzQGhziax5PItDUTMAM9uE2XXQmM37dyd4hVM+5aVl7oVxMVUiVQn2oCQFN/LKCZdvSM0pFRqbSmQ==
"@types/request@*":
version "2.48.13"
resolved "https://registry.yarnpkg.com/@types/request/-/request-2.48.13.tgz#abdf4256524e801ea8fdda54320f083edb5a6b80"
integrity sha512-FGJ6udDNUCjd19pp0Q3iTiDkwhYup7J8hpMW9c4k53NrccQFFWKRho6hvtPPEhnXWKvukfwAlB6DbDz4yhH5Gg==
dependencies:
"@types/caseless" "*"
"@types/node" "*"
"@types/tough-cookie" "*"
form-data "^2.5.5"
"@types/send@*":
version "0.17.5"
resolved "https://registry.yarnpkg.com/@types/send/-/send-0.17.5.tgz#d991d4f2b16f2b1ef497131f00a9114290791e74"
integrity sha512-z6F2D3cOStZvuk2SaP6YrwkNO65iTZcwA2ZkSABegdkAh/lf+Aa/YQndZVfmEXT5vgAp6zv06VQ3ejSVjAny4w==
dependencies:
"@types/mime" "^1"
"@types/node" "*"
"@types/serve-static@*":
version "1.15.8"
resolved "https://registry.yarnpkg.com/@types/serve-static/-/serve-static-1.15.8.tgz#8180c3fbe4a70e8f00b9f70b9ba7f08f35987877"
integrity sha512-roei0UY3LhpOJvjbIP6ZZFngyLKl5dskOtDhxY5THRSpO+ZI+nzJ+m5yUMzGrp89YRa7lvknKkMYjqQFGwA7Sg==
dependencies:
"@types/http-errors" "*"
"@types/node" "*"
"@types/send" "*"
"@types/tough-cookie@*":
version "4.0.5"
resolved "https://registry.yarnpkg.com/@types/tough-cookie/-/tough-cookie-4.0.5.tgz#cb6e2a691b70cb177c6e3ae9c1d2e8b2ea8cd304"
integrity sha512-/Ad8+nIOV7Rl++6f1BdKxFSMgmoqEoYbHRpPcx3JEfv8VRsQe9Z4mCXeJBzxs7mbHY/XOZZuXlRNfhpVPbs6ZA==
abbrev@1: abbrev@1:
version "1.1.1" version "1.1.1"
resolved "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz" resolved "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz"
@@ -189,12 +347,19 @@ acorn-jsx@^5.3.2:
resolved "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz" resolved "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz"
integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==
"acorn@^6.0.0 || ^7.0.0 || ^8.0.0", acorn@^8.15.0: acorn-walk@^8.1.1:
version "8.3.4"
resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.3.4.tgz#794dd169c3977edf4ba4ea47583587c5866236b7"
integrity sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==
dependencies:
acorn "^8.11.0"
acorn@^8.11.0, acorn@^8.15.0, acorn@^8.4.1:
version "8.15.0" version "8.15.0"
resolved "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz" resolved "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz"
integrity sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg== integrity sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==
agent-base@^6.0.2, agent-base@6: agent-base@6, agent-base@^6.0.2:
version "6.0.2" version "6.0.2"
resolved "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz" resolved "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz"
integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==
@@ -216,7 +381,7 @@ aggregate-error@^3.0.0:
clean-stack "^2.0.0" clean-stack "^2.0.0"
indent-string "^4.0.0" indent-string "^4.0.0"
ajv@^6.12.3, ajv@^6.12.4: ajv@^6.12.4:
version "6.12.6" version "6.12.6"
resolved "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz" resolved "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz"
integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==
@@ -259,6 +424,11 @@ are-we-there-yet@^3.0.0:
delegates "^1.0.0" delegates "^1.0.0"
readable-stream "^3.6.0" readable-stream "^3.6.0"
arg@^4.1.0:
version "4.1.3"
resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089"
integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==
argparse@^2.0.1: argparse@^2.0.1:
version "2.0.1" version "2.0.1"
resolved "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz" resolved "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz"
@@ -309,7 +479,7 @@ asn1@~0.2.3:
dependencies: dependencies:
safer-buffer "~2.1.0" safer-buffer "~2.1.0"
assert-plus@^1.0.0, assert-plus@1.0.0: assert-plus@1.0.0, assert-plus@^1.0.0:
version "1.0.0" version "1.0.0"
resolved "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz" resolved "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz"
integrity sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw== integrity sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw==
@@ -574,7 +744,7 @@ color-support@^1.1.3:
resolved "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz" resolved "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz"
integrity sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg== integrity sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==
combined-stream@^1.0.6, combined-stream@^1.0.8, combined-stream@~1.0.6: combined-stream@^1.0.8, combined-stream@~1.0.6:
version "1.0.8" version "1.0.8"
resolved "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz" resolved "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz"
integrity sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg== integrity sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==
@@ -613,15 +783,20 @@ cookie@0.7.1:
resolved "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz" resolved "https://registry.npmjs.org/cookie/-/cookie-0.7.1.tgz"
integrity sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w== integrity sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==
core-util-is@1.0.2:
version "1.0.2"
resolved "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz"
integrity sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==
core-util-is@~1.0.0: core-util-is@~1.0.0:
version "1.0.3" version "1.0.3"
resolved "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz" resolved "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz"
integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ== integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==
core-util-is@1.0.2: create-require@^1.1.0:
version "1.0.2" version "1.1.1"
resolved "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz" resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333"
integrity sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ== integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==
cross-spawn@^7.0.6: cross-spawn@^7.0.6:
version "7.0.6" version "7.0.6"
@@ -671,20 +846,6 @@ data-view-byte-offset@^1.0.1:
es-errors "^1.3.0" es-errors "^1.3.0"
is-data-view "^1.0.1" is-data-view "^1.0.1"
debug@^3.2.7:
version "3.2.7"
resolved "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz"
integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==
dependencies:
ms "^2.1.1"
debug@^4, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3, debug@4:
version "4.4.1"
resolved "https://registry.npmjs.org/debug/-/debug-4.4.1.tgz"
integrity sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==
dependencies:
ms "^2.1.3"
debug@2.6.9: debug@2.6.9:
version "2.6.9" version "2.6.9"
resolved "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz" resolved "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz"
@@ -692,6 +853,20 @@ debug@2.6.9:
dependencies: dependencies:
ms "2.0.0" ms "2.0.0"
debug@4, debug@^4, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3:
version "4.4.1"
resolved "https://registry.npmjs.org/debug/-/debug-4.4.1.tgz"
integrity sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ==
dependencies:
ms "^2.1.3"
debug@^3.2.7:
version "3.2.7"
resolved "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz"
integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==
dependencies:
ms "^2.1.1"
decompress-response@^6.0.0: decompress-response@^6.0.0:
version "6.0.0" version "6.0.0"
resolved "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz" resolved "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz"
@@ -752,6 +927,11 @@ detect-libc@^2.0.0:
resolved "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.4.tgz" resolved "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.4.tgz"
integrity sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA== integrity sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==
diff@^4.0.1:
version "4.0.2"
resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d"
integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==
dotenv@^8.2.0: dotenv@^8.2.0:
version "8.6.0" version "8.6.0"
resolved "https://registry.npmjs.org/dotenv/-/dotenv-8.6.0.tgz" resolved "https://registry.npmjs.org/dotenv/-/dotenv-8.6.0.tgz"
@@ -949,7 +1129,7 @@ eslint-visitor-keys@^4.2.1:
resolved "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz" resolved "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-4.2.1.tgz"
integrity sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ== integrity sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==
"eslint@^6.0.0 || ^7.0.0 || >=8.0.0", eslint@^9.34.0: eslint@^9.34.0:
version "9.34.0" version "9.34.0"
resolved "https://registry.npmjs.org/eslint/-/eslint-9.34.0.tgz" resolved "https://registry.npmjs.org/eslint/-/eslint-9.34.0.tgz"
integrity sha512-RNCHRX5EwdrESy3Jc9o8ie8Bog+PeYvvSR8sDGoZxNFTvZ4dlxUB3WzQ3bQMztFrSRODGrLLj8g6OFuGY/aiQg== integrity sha512-RNCHRX5EwdrESy3Jc9o8ie8Bog+PeYvvSR8sDGoZxNFTvZ4dlxUB3WzQ3bQMztFrSRODGrLLj8g6OFuGY/aiQg==
@@ -1080,16 +1260,16 @@ extend@~3.0.2:
resolved "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz" resolved "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz"
integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g== integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==
extsprintf@^1.2.0:
version "1.4.1"
resolved "https://registry.npmjs.org/extsprintf/-/extsprintf-1.4.1.tgz"
integrity sha512-Wrk35e8ydCKDj/ArClo1VrPVmN8zph5V4AtHwIuHhvMXsKf73UT3BOD+azBIW+3wOJ4FhEH7zyaJCFvChjYvMA==
extsprintf@1.3.0: extsprintf@1.3.0:
version "1.3.0" version "1.3.0"
resolved "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz" resolved "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz"
integrity sha512-11Ndz7Nv+mvAC1j0ktTa7fAb0vLyGGX+rMHNBYQviQDGU0Hw7lhctJANqbPhu9nV9/izT/IntTgZ7Im/9LJs9g== integrity sha512-11Ndz7Nv+mvAC1j0ktTa7fAb0vLyGGX+rMHNBYQviQDGU0Hw7lhctJANqbPhu9nV9/izT/IntTgZ7Im/9LJs9g==
extsprintf@^1.2.0:
version "1.4.1"
resolved "https://registry.npmjs.org/extsprintf/-/extsprintf-1.4.1.tgz"
integrity sha512-Wrk35e8ydCKDj/ArClo1VrPVmN8zph5V4AtHwIuHhvMXsKf73UT3BOD+azBIW+3wOJ4FhEH7zyaJCFvChjYvMA==
fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3: fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3:
version "3.1.3" version "3.1.3"
resolved "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz" resolved "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz"
@@ -1196,6 +1376,18 @@ forever-agent@~0.6.1:
resolved "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz" resolved "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz"
integrity sha512-j0KLYPhm6zeac4lz3oJ3o65qvgQCcPubiyotZrXqEaG4hNagNYO8qdlUrX5vwqv9ohqeT/Z3j6+yW067yWWdUw== integrity sha512-j0KLYPhm6zeac4lz3oJ3o65qvgQCcPubiyotZrXqEaG4hNagNYO8qdlUrX5vwqv9ohqeT/Z3j6+yW067yWWdUw==
form-data@^2.5.5:
version "2.5.5"
resolved "https://registry.yarnpkg.com/form-data/-/form-data-2.5.5.tgz#a5f6364ad7e4e67e95b4a07e2d8c6f711c74f624"
integrity sha512-jqdObeR2rxZZbPSGL+3VckHMYtu+f9//KXBsVny6JSX/pa38Fy+bGjuG8eW/H6USNQWhLi8Num++cU2yOCNz4A==
dependencies:
asynckit "^0.4.0"
combined-stream "^1.0.8"
es-set-tostringtag "^2.1.0"
hasown "^2.0.2"
mime-types "^2.1.35"
safe-buffer "^5.2.1"
form-data@^4.0.4, form-data@~4.0.4: form-data@^4.0.4, form-data@~4.0.4:
version "4.0.4" version "4.0.4"
resolved "https://registry.npmjs.org/form-data/-/form-data-4.0.4.tgz" resolved "https://registry.npmjs.org/form-data/-/form-data-4.0.4.tgz"
@@ -1207,15 +1399,6 @@ form-data@^4.0.4, form-data@~4.0.4:
hasown "^2.0.2" hasown "^2.0.2"
mime-types "^2.1.12" mime-types "^2.1.12"
form-data@~2.3.2:
version "2.3.3"
resolved "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz"
integrity sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==
dependencies:
asynckit "^0.4.0"
combined-stream "^1.0.6"
mime-types "^2.1.12"
formdata-polyfill@^4.0.10: formdata-polyfill@^4.0.10:
version "4.0.10" version "4.0.10"
resolved "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz" resolved "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz"
@@ -1385,19 +1568,6 @@ graceful-fs@^4.2.6:
resolved "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz" resolved "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz"
integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==
har-schema@^2.0.0:
version "2.0.0"
resolved "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz"
integrity sha512-Oqluz6zhGX8cyRaTQlFMPw80bSJVG2x/cFb8ZPhUILGgHka9SsokCCOQgpveePerqidZOrT14ipqfJb7ILcW5Q==
har-validator@~5.1.3:
version "5.1.5"
resolved "https://registry.npmjs.org/har-validator/-/har-validator-5.1.5.tgz"
integrity sha512-nmT2T0lljbxdQZfspsno9hgrG3Uir6Ks5afism62poxqBM6sDnMEuPmzTq8XN0OEwqKLLdh1jQI3qyE66Nzb3w==
dependencies:
ajv "^6.12.3"
har-schema "^2.0.0"
has-bigints@^1.0.2: has-bigints@^1.0.2:
version "1.1.0" version "1.1.0"
resolved "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz" resolved "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz"
@@ -1476,15 +1646,6 @@ http-proxy-agent@^4.0.1:
agent-base "6" agent-base "6"
debug "4" debug "4"
http-signature@~1.2.0:
version "1.2.0"
resolved "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz"
integrity sha512-CAbnr6Rz4CYQkLYUtSNXxQPUH2gK8f3iWexVlsnMeD+GjlsQ0Xsy1cOX+mN3dtxYomRy21CiOzU8Uhw6OwncEQ==
dependencies:
assert-plus "^1.0.0"
jsprim "^1.2.2"
sshpk "^1.7.0"
http-signature@~1.4.0: http-signature@~1.4.0:
version "1.4.0" version "1.4.0"
resolved "https://registry.npmjs.org/http-signature/-/http-signature-1.4.0.tgz" resolved "https://registry.npmjs.org/http-signature/-/http-signature-1.4.0.tgz"
@@ -1509,13 +1670,6 @@ humanize-ms@^1.2.1:
dependencies: dependencies:
ms "^2.0.0" ms "^2.0.0"
iconv-lite@^0.6.2:
version "0.6.3"
resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz"
integrity sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==
dependencies:
safer-buffer ">= 2.1.2 < 3.0.0"
iconv-lite@0.4.24: iconv-lite@0.4.24:
version "0.4.24" version "0.4.24"
resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz" resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz"
@@ -1523,6 +1677,13 @@ iconv-lite@0.4.24:
dependencies: dependencies:
safer-buffer ">= 2.1.2 < 3" safer-buffer ">= 2.1.2 < 3"
iconv-lite@^0.6.2:
version "0.6.3"
resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz"
integrity sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==
dependencies:
safer-buffer ">= 2.1.2 < 3.0.0"
ieee754@^1.1.13: ieee754@^1.1.13:
version "1.2.1" version "1.2.1"
resolved "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz" resolved "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz"
@@ -1569,7 +1730,7 @@ inflight@^1.0.4:
once "^1.3.0" once "^1.3.0"
wrappy "1" wrappy "1"
inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.3, inherits@2, inherits@2.0.4: inherits@2, inherits@2.0.4, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.3:
version "2.0.4" version "2.0.4"
resolved "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz" resolved "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz"
integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==
@@ -1852,16 +2013,6 @@ json-stringify-safe@~5.0.1:
resolved "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz" resolved "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz"
integrity sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA== integrity sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==
jsprim@^1.2.2:
version "1.4.2"
resolved "https://registry.npmjs.org/jsprim/-/jsprim-1.4.2.tgz"
integrity sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==
dependencies:
assert-plus "1.0.0"
extsprintf "1.3.0"
json-schema "0.4.0"
verror "1.10.0"
jsprim@^2.0.2: jsprim@^2.0.2:
version "2.0.2" version "2.0.2"
resolved "https://registry.npmjs.org/jsprim/-/jsprim-2.0.2.tgz" resolved "https://registry.npmjs.org/jsprim/-/jsprim-2.0.2.tgz"
@@ -1919,6 +2070,11 @@ m3u8stream@^0.8.0:
miniget "^4.2.2" miniget "^4.2.2"
sax "^1.2.4" sax "^1.2.4"
make-error@^1.1.1:
version "1.3.6"
resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2"
integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==
make-fetch-happen@^9.1.0: make-fetch-happen@^9.1.0:
version "9.1.0" version "9.1.0"
resolved "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz" resolved "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz"
@@ -1966,14 +2122,14 @@ mime-db@1.52.0:
resolved "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz" resolved "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz"
integrity sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg== integrity sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==
mime-types@^2.1.12, mime-types@~2.1.19, mime-types@~2.1.24, mime-types@~2.1.34: mime-types@^2.1.12, mime-types@^2.1.35, mime-types@~2.1.19, mime-types@~2.1.24, mime-types@~2.1.34:
version "2.1.35" version "2.1.35"
resolved "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz" resolved "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz"
integrity sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw== integrity sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==
dependencies: dependencies:
mime-db "1.52.0" mime-db "1.52.0"
mime@^1.6.0, mime@1.6.0: mime@1.6.0, mime@^1.6.0:
version "1.6.0" version "1.6.0"
resolved "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz" resolved "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz"
integrity sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg== integrity sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==
@@ -2069,16 +2225,16 @@ mkdirp@^1.0.3, mkdirp@^1.0.4:
resolved "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz" resolved "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz"
integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==
ms@^2.0.0, ms@^2.1.1, ms@^2.1.3, ms@2.1.3:
version "2.1.3"
resolved "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz"
integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==
ms@2.0.0: ms@2.0.0:
version "2.0.0" version "2.0.0"
resolved "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz" resolved "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz"
integrity sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A== integrity sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==
ms@2.1.3, ms@^2.0.0, ms@^2.1.1, ms@^2.1.3:
version "2.1.3"
resolved "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz"
integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==
napi-build-utils@^2.0.0: napi-build-utils@^2.0.0:
version "2.0.0" version "2.0.0"
resolved "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-2.0.0.tgz" resolved "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-2.0.0.tgz"
@@ -2089,16 +2245,16 @@ natural-compare@^1.4.0:
resolved "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz" resolved "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz"
integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==
negotiator@^0.6.2:
version "0.6.4"
resolved "https://registry.npmjs.org/negotiator/-/negotiator-0.6.4.tgz"
integrity sha512-myRT3DiWPHqho5PrJaIRyaMv2kgYf0mUVgBNOYMuCH5Ki1yEiQaf/ZJuQ62nvpc44wL5WDbTX7yGJi1Neevw8w==
negotiator@0.6.3: negotiator@0.6.3:
version "0.6.3" version "0.6.3"
resolved "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz" resolved "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz"
integrity sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg== integrity sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==
negotiator@^0.6.2:
version "0.6.4"
resolved "https://registry.npmjs.org/negotiator/-/negotiator-0.6.4.tgz"
integrity sha512-myRT3DiWPHqho5PrJaIRyaMv2kgYf0mUVgBNOYMuCH5Ki1yEiQaf/ZJuQ62nvpc44wL5WDbTX7yGJi1Neevw8w==
node-abi@^3.3.0: node-abi@^3.3.0:
version "3.75.0" version "3.75.0"
resolved "https://registry.npmjs.org/node-abi/-/node-abi-3.75.0.tgz" resolved "https://registry.npmjs.org/node-abi/-/node-abi-3.75.0.tgz"
@@ -2194,11 +2350,6 @@ npmlog@^6.0.0:
gauge "^4.0.3" gauge "^4.0.3"
set-blocking "^2.0.0" set-blocking "^2.0.0"
oauth-sign@~0.9.0:
version "0.9.0"
resolved "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz"
integrity sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==
object-inspect@^1.13.3, object-inspect@^1.13.4: object-inspect@^1.13.3, object-inspect@^1.13.4:
version "1.13.4" version "1.13.4"
resolved "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz" resolved "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz"
@@ -2378,7 +2529,7 @@ proxy-from-env@^1.1.0:
resolved "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz" resolved "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz"
integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==
psl@^1.1.28, psl@^1.1.33: psl@^1.1.33:
version "1.15.0" version "1.15.0"
resolved "https://registry.npmjs.org/psl/-/psl-1.15.0.tgz" resolved "https://registry.npmjs.org/psl/-/psl-1.15.0.tgz"
integrity sha512-JZd3gMVBAVQkSs6HdNZo9Sdo0LNcQeMNP3CozBJb3JYC/QUYZTnKxP+f8oWRX4rHP5EurWxqAHTSwUCjlNKa1w== integrity sha512-JZd3gMVBAVQkSs6HdNZo9Sdo0LNcQeMNP3CozBJb3JYC/QUYZTnKxP+f8oWRX4rHP5EurWxqAHTSwUCjlNKa1w==
@@ -2411,11 +2562,6 @@ punycode@^2.1.0, punycode@^2.1.1, punycode@^2.3.1:
resolved "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz" resolved "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz"
integrity sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg== integrity sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==
qs@~6.5.2:
version "6.5.3"
resolved "https://registry.npmjs.org/qs/-/qs-6.5.3.tgz"
integrity sha512-qxXIEh4pCGfHICj1mAJQ2/2XVZkjCDTcEgfoSQxc/fYivUZxTkk7L3bDBJSoNrEzXI17oUO5Dp07ktqE5KzczA==
qs@6.13.0: qs@6.13.0:
version "6.13.0" version "6.13.0"
resolved "https://registry.npmjs.org/qs/-/qs-6.13.0.tgz" resolved "https://registry.npmjs.org/qs/-/qs-6.13.0.tgz"
@@ -2522,32 +2668,6 @@ request-promise-core@1.1.3:
dependencies: dependencies:
lodash "^4.17.15" lodash "^4.17.15"
request@^2.34:
version "2.88.2"
resolved "https://registry.npmjs.org/request/-/request-2.88.2.tgz"
integrity sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==
dependencies:
aws-sign2 "~0.7.0"
aws4 "^1.8.0"
caseless "~0.12.0"
combined-stream "~1.0.6"
extend "~3.0.2"
forever-agent "~0.6.1"
form-data "~2.3.2"
har-validator "~5.1.3"
http-signature "~1.2.0"
is-typedarray "~1.0.0"
isstream "~0.1.2"
json-stringify-safe "~5.0.1"
mime-types "~2.1.19"
oauth-sign "~0.9.0"
performance-now "^2.1.0"
qs "~6.5.2"
safe-buffer "^5.1.2"
tough-cookie "~2.5.0"
tunnel-agent "^0.6.0"
uuid "^3.3.2"
requires-port@^1.0.0: requires-port@^1.0.0:
version "1.0.0" version "1.0.0"
resolved "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz" resolved "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz"
@@ -2581,17 +2701,12 @@ safe-array-concat@^1.1.3:
has-symbols "^1.1.0" has-symbols "^1.1.0"
isarray "^2.0.5" isarray "^2.0.5"
safe-buffer@^5.0.1, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@~5.2.0, safe-buffer@5.2.1: safe-buffer@5.2.1, safe-buffer@^5.0.1, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.1, safe-buffer@~5.2.0:
version "5.2.1" version "5.2.1"
resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz" resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz"
integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==
safe-buffer@~5.1.0: safe-buffer@~5.1.0, safe-buffer@~5.1.1:
version "5.1.2"
resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz"
integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==
safe-buffer@~5.1.1:
version "5.1.2" version "5.1.2"
resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz" resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz"
integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g== integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==
@@ -2613,7 +2728,7 @@ safe-regex-test@^1.1.0:
es-errors "^1.3.0" es-errors "^1.3.0"
is-regex "^1.2.1" is-regex "^1.2.1"
safer-buffer@^2.0.2, safer-buffer@^2.1.0, "safer-buffer@>= 2.1.2 < 3", "safer-buffer@>= 2.1.2 < 3.0.0", safer-buffer@~2.1.0: "safer-buffer@>= 2.1.2 < 3", "safer-buffer@>= 2.1.2 < 3.0.0", safer-buffer@^2.0.2, safer-buffer@^2.1.0, safer-buffer@~2.1.0:
version "2.1.2" version "2.1.2"
resolved "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz" resolved "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz"
integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==
@@ -2826,7 +2941,7 @@ sqlite3@^5.1.6:
optionalDependencies: optionalDependencies:
node-gyp "8.x" node-gyp "8.x"
sshpk@^1.18.0, sshpk@^1.7.0: sshpk@^1.18.0:
version "1.18.0" version "1.18.0"
resolved "https://registry.npmjs.org/sshpk/-/sshpk-1.18.0.tgz" resolved "https://registry.npmjs.org/sshpk/-/sshpk-1.18.0.tgz"
integrity sha512-2p2KJZTSqQ/I3+HX42EpYOa2l3f8Erv8MWKsy2I9uf4wA7yFIkXRffYdsx86y6z4vHtV8u7g+pPlr8/4ouAxsQ== integrity sha512-2p2KJZTSqQ/I3+HX42EpYOa2l3f8Erv8MWKsy2I9uf4wA7yFIkXRffYdsx86y6z4vHtV8u7g+pPlr8/4ouAxsQ==
@@ -2866,20 +2981,6 @@ stop-iteration-iterator@^1.1.0:
es-errors "^1.3.0" es-errors "^1.3.0"
internal-slot "^1.1.0" internal-slot "^1.1.0"
string_decoder@^1.1.1:
version "1.3.0"
resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz"
integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==
dependencies:
safe-buffer "~5.2.0"
string_decoder@~1.1.1:
version "1.1.1"
resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz"
integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==
dependencies:
safe-buffer "~5.1.0"
"string-width@^1.0.2 || 2 || 3 || 4", string-width@^4.2.3: "string-width@^1.0.2 || 2 || 3 || 4", string-width@^4.2.3:
version "4.2.3" version "4.2.3"
resolved "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz" resolved "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz"
@@ -2921,6 +3022,20 @@ string.prototype.trimstart@^1.0.8:
define-properties "^1.2.1" define-properties "^1.2.1"
es-object-atoms "^1.0.0" es-object-atoms "^1.0.0"
string_decoder@^1.1.1:
version "1.3.0"
resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz"
integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==
dependencies:
safe-buffer "~5.2.0"
string_decoder@~1.1.1:
version "1.1.1"
resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz"
integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==
dependencies:
safe-buffer "~5.1.0"
strip-ansi@^6.0.1: strip-ansi@^6.0.1:
version "6.0.1" version "6.0.1"
resolved "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz" resolved "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz"
@@ -3031,13 +3146,24 @@ tough-cookie@^5.0.0:
dependencies: dependencies:
tldts "^6.1.32" tldts "^6.1.32"
tough-cookie@~2.5.0: ts-node@^10.9.2:
version "2.5.0" version "10.9.2"
resolved "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz" resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.2.tgz#70f021c9e185bccdca820e26dc413805c101c71f"
integrity sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g== integrity sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==
dependencies: dependencies:
psl "^1.1.28" "@cspotcode/source-map-support" "^0.8.0"
punycode "^2.1.1" "@tsconfig/node10" "^1.0.7"
"@tsconfig/node12" "^1.0.7"
"@tsconfig/node14" "^1.0.0"
"@tsconfig/node16" "^1.0.2"
acorn "^8.4.1"
acorn-walk "^8.1.1"
arg "^4.1.0"
create-require "^1.1.0"
diff "^4.0.1"
make-error "^1.1.1"
v8-compile-cache-lib "^3.0.1"
yn "3.1.1"
tunnel-agent@^0.6.0: tunnel-agent@^0.6.0:
version "0.6.0" version "0.6.0"
@@ -3111,6 +3237,11 @@ typed-array-length@^1.0.7:
possible-typed-array-names "^1.0.0" possible-typed-array-names "^1.0.0"
reflect.getprototypeof "^1.0.6" reflect.getprototypeof "^1.0.6"
typescript@^5.9.2:
version "5.9.2"
resolved "https://registry.yarnpkg.com/typescript/-/typescript-5.9.2.tgz#d93450cddec5154a2d5cabe3b8102b83316fb2a6"
integrity sha512-CWBzXQrc/qOkhidw1OzBTQuYRbfyxDXJMVJ1XNwUHGROVmuaeiEm3OslpZ1RV96d7SKKjZKrSJu3+t/xlw3R9A==
unbox-primitive@^1.1.0: unbox-primitive@^1.1.0:
version "1.1.0" version "1.1.0"
resolved "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz" resolved "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.1.0.tgz"
@@ -3126,6 +3257,11 @@ undefsafe@^2.0.5:
resolved "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz" resolved "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz"
integrity sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA== integrity sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA==
undici-types@~7.10.0:
version "7.10.0"
resolved "https://registry.yarnpkg.com/undici-types/-/undici-types-7.10.0.tgz#4ac2e058ce56b462b056e629cc6a02393d3ff350"
integrity sha512-t5Fy/nfn+14LuOc2KNYg75vZqClpAiqscVvMygNnlsHBFpSXdJaYtXMcdNLpl/Qvc3P2cB3s6lOV51nqsFq4ag==
unique-filename@^1.1.1: unique-filename@^1.1.1:
version "1.1.1" version "1.1.1"
resolved "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz" resolved "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz"
@@ -3145,7 +3281,7 @@ universalify@^0.2.0:
resolved "https://registry.npmjs.org/universalify/-/universalify-0.2.0.tgz" resolved "https://registry.npmjs.org/universalify/-/universalify-0.2.0.tgz"
integrity sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg== integrity sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg==
unpipe@~1.0.0, unpipe@1.0.0: unpipe@1.0.0, unpipe@~1.0.0:
version "1.0.0" version "1.0.0"
resolved "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz" resolved "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz"
integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ== integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==
@@ -3175,16 +3311,16 @@ utils-merge@1.0.1:
resolved "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz" resolved "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz"
integrity sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA== integrity sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==
uuid@^3.3.2:
version "3.4.0"
resolved "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz"
integrity sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==
uuid@^8.3.2: uuid@^8.3.2:
version "8.3.2" version "8.3.2"
resolved "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz" resolved "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz"
integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg== integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==
v8-compile-cache-lib@^3.0.1:
version "3.0.1"
resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf"
integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==
vary@~1.1.2: vary@~1.1.2:
version "1.1.2" version "1.1.2"
resolved "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz" resolved "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz"
@@ -3264,14 +3400,7 @@ which@^1.1.1:
dependencies: dependencies:
isexe "^2.0.0" isexe "^2.0.0"
which@^2.0.1: which@^2.0.1, which@^2.0.2:
version "2.0.2"
resolved "https://registry.npmjs.org/which/-/which-2.0.2.tgz"
integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==
dependencies:
isexe "^2.0.0"
which@^2.0.2:
version "2.0.2" version "2.0.2"
resolved "https://registry.npmjs.org/which/-/which-2.0.2.tgz" resolved "https://registry.npmjs.org/which/-/which-2.0.2.tgz"
integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==
@@ -3300,6 +3429,11 @@ yallist@^4.0.0:
resolved "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz" resolved "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz"
integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==
yn@3.1.1:
version "3.1.1"
resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50"
integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==
yocto-queue@^0.1.0: yocto-queue@^0.1.0:
version "0.1.0" version "0.1.0"
resolved "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz" resolved "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz"