vantuz 3.2.4 → 3.2.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/cli.js +385 -61
- package/core/ai-provider.js +7 -6
- package/core/channels.js +107 -12
- package/core/database.js +24 -25
- package/core/engine.js +123 -133
- package/core/gateway.js +340 -0
- package/onboard.js +59 -67
- package/package.json +6 -3
- package/plugins/vantuz/index.js +1 -1
- package/plugins/vantuz/platforms/_template.js +118 -0
- package/plugins/vantuz/platforms/trendyol.js +23 -5
- package/plugins/vantuz/services/license.js +15 -259
- package/plugins/vantuz/services/scheduler.js +1 -1
package/core/channels.js
CHANGED
|
@@ -1,44 +1,129 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* 📱 CHANNEL MANAGER
|
|
3
|
-
* OpenClaw Gateway
|
|
2
|
+
* 📱 CHANNEL MANAGER v3.2
|
|
3
|
+
* OpenClaw Gateway üzerinden kanal yönetimi
|
|
4
4
|
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
5
|
+
* Desteklenen kanallar:
|
|
6
|
+
* - WhatsApp (Meta Business API / Gateway)
|
|
7
|
+
* - Telegram (Bot API / Gateway)
|
|
7
8
|
*/
|
|
8
9
|
|
|
9
10
|
import fs from 'fs';
|
|
10
11
|
import path from 'path';
|
|
11
12
|
import os from 'os';
|
|
12
13
|
import { log } from './ai-provider.js';
|
|
14
|
+
import { getGateway } from './gateway.js';
|
|
13
15
|
|
|
14
16
|
const VANTUZ_HOME = path.join(os.homedir(), '.vantuz');
|
|
15
17
|
const CONFIG_PATH = path.join(VANTUZ_HOME, '.env');
|
|
16
18
|
|
|
17
19
|
export class ChannelManager {
|
|
18
20
|
constructor() {
|
|
21
|
+
this.gateway = null;
|
|
19
22
|
this.status = {
|
|
20
|
-
whatsapp: { connected: false, mode: 'gateway' },
|
|
21
|
-
telegram: { connected: false, mode: 'gateway' }
|
|
23
|
+
whatsapp: { connected: false, mode: 'gateway', info: '' },
|
|
24
|
+
telegram: { connected: false, mode: 'gateway', info: '' }
|
|
22
25
|
};
|
|
23
26
|
}
|
|
24
27
|
|
|
28
|
+
/**
|
|
29
|
+
* Tüm kanalları başlat
|
|
30
|
+
*/
|
|
25
31
|
async initAll() {
|
|
26
|
-
// OpenClaw Gateway durumunu kontrol et (varsayım)
|
|
27
|
-
// Gerçekte Gateway ayrı bir process olarak çalışır
|
|
28
|
-
|
|
29
32
|
const env = this._loadEnv();
|
|
30
33
|
|
|
34
|
+
// OpenClaw Gateway üzerinden kanal durumu kontrol et
|
|
35
|
+
try {
|
|
36
|
+
this.gateway = await getGateway();
|
|
37
|
+
|
|
38
|
+
if (this.gateway.isConnected()) {
|
|
39
|
+
const channelResult = await this.gateway.getChannels();
|
|
40
|
+
if (channelResult.success && channelResult.data) {
|
|
41
|
+
this._syncGatewayChannels(channelResult.data);
|
|
42
|
+
log('INFO', 'Kanal durumları gateway üzerinden alındı');
|
|
43
|
+
return this.status;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
} catch (e) {
|
|
47
|
+
log('WARN', 'Gateway kanal kontrolü başarısız, lokal mod', { error: e.message });
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// Fallback: Lokal env kontrolü
|
|
31
51
|
if (env.TELEGRAM_BOT_TOKEN) {
|
|
32
52
|
this.status.telegram.connected = true;
|
|
33
|
-
this.status.telegram.info = 'Bot Token Configured';
|
|
53
|
+
this.status.telegram.info = 'Bot Token Configured (local)';
|
|
54
|
+
} else {
|
|
55
|
+
this.status.telegram.info = 'Token yapılandırılmamış';
|
|
34
56
|
}
|
|
35
57
|
|
|
36
|
-
|
|
37
|
-
|
|
58
|
+
if (env.WHATSAPP_ACCESS_TOKEN) {
|
|
59
|
+
this.status.whatsapp.connected = true;
|
|
60
|
+
this.status.whatsapp.info = 'Access Token Configured (local)';
|
|
61
|
+
} else {
|
|
62
|
+
this.status.whatsapp.info = 'Bağlanmak için: vantuz channels login';
|
|
63
|
+
}
|
|
38
64
|
|
|
39
65
|
return this.status;
|
|
40
66
|
}
|
|
41
67
|
|
|
68
|
+
/**
|
|
69
|
+
* Gateway'den gelen kanal verilerini senkronize et
|
|
70
|
+
*/
|
|
71
|
+
_syncGatewayChannels(gatewayData) {
|
|
72
|
+
if (Array.isArray(gatewayData)) {
|
|
73
|
+
for (const ch of gatewayData) {
|
|
74
|
+
const name = ch.name?.toLowerCase();
|
|
75
|
+
if (name === 'whatsapp' || name === 'telegram') {
|
|
76
|
+
this.status[name] = {
|
|
77
|
+
connected: ch.connected || ch.status === 'connected',
|
|
78
|
+
mode: 'gateway',
|
|
79
|
+
info: ch.info || ch.status || 'Gateway üzerinden bağlı',
|
|
80
|
+
capabilities: ch.capabilities || []
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
} else if (typeof gatewayData === 'object') {
|
|
85
|
+
// Object format: { whatsapp: {...}, telegram: {...} }
|
|
86
|
+
for (const [name, data] of Object.entries(gatewayData)) {
|
|
87
|
+
const key = name.toLowerCase();
|
|
88
|
+
if (this.status[key]) {
|
|
89
|
+
this.status[key] = {
|
|
90
|
+
connected: data.connected || data.status === 'connected',
|
|
91
|
+
mode: 'gateway',
|
|
92
|
+
info: data.info || data.status || 'Gateway üzerinden bağlı',
|
|
93
|
+
capabilities: data.capabilities || []
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Mesaj gönder (gateway üzerinden)
|
|
102
|
+
*/
|
|
103
|
+
async sendMessage(channel, to, message) {
|
|
104
|
+
if (!this.gateway?.isConnected()) {
|
|
105
|
+
return { success: false, error: 'Gateway bağlı değil' };
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
const result = await this.gateway.sendMessage(channel, to, message);
|
|
109
|
+
if (result.success) {
|
|
110
|
+
log('INFO', `Mesaj gönderildi: ${channel} → ${to}`);
|
|
111
|
+
} else {
|
|
112
|
+
log('ERROR', `Mesaj gönderilemedi: ${channel}`, { error: result.error });
|
|
113
|
+
}
|
|
114
|
+
return result;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* Kanal durumunu yenile
|
|
119
|
+
*/
|
|
120
|
+
async refresh() {
|
|
121
|
+
return await this.initAll();
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
/**
|
|
125
|
+
* Env dosyasını yükle
|
|
126
|
+
*/
|
|
42
127
|
_loadEnv() {
|
|
43
128
|
const env = {};
|
|
44
129
|
try {
|
|
@@ -55,9 +140,19 @@ export class ChannelManager {
|
|
|
55
140
|
return env;
|
|
56
141
|
}
|
|
57
142
|
|
|
143
|
+
/**
|
|
144
|
+
* Kanal durumları
|
|
145
|
+
*/
|
|
58
146
|
getStatus() {
|
|
59
147
|
return this.status;
|
|
60
148
|
}
|
|
149
|
+
|
|
150
|
+
/**
|
|
151
|
+
* Gateway bağlı mı?
|
|
152
|
+
*/
|
|
153
|
+
isGatewayMode() {
|
|
154
|
+
return this.gateway?.isConnected() || false;
|
|
155
|
+
}
|
|
61
156
|
}
|
|
62
157
|
|
|
63
158
|
// Singleton
|
package/core/database.js
CHANGED
|
@@ -1,14 +1,19 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
1
|
+
/**
|
|
2
|
+
* 💾 VANTUZ DATABASE v3.2
|
|
3
|
+
* SQLite veritabanı - ESM modülü
|
|
4
|
+
*/
|
|
4
5
|
|
|
5
|
-
|
|
6
|
-
|
|
6
|
+
import { Sequelize, DataTypes } from 'sequelize';
|
|
7
|
+
import path from 'path';
|
|
8
|
+
import os from 'os';
|
|
9
|
+
|
|
10
|
+
const VANTUZ_HOME = path.join(os.homedir(), '.vantuz');
|
|
11
|
+
const dbPath = path.join(VANTUZ_HOME, 'vantuz.sqlite');
|
|
7
12
|
|
|
8
13
|
const sequelize = new Sequelize({
|
|
9
14
|
dialect: 'sqlite',
|
|
10
15
|
storage: dbPath,
|
|
11
|
-
logging: false
|
|
16
|
+
logging: false
|
|
12
17
|
});
|
|
13
18
|
|
|
14
19
|
// --- MODELLER ---
|
|
@@ -16,8 +21,8 @@ const sequelize = new Sequelize({
|
|
|
16
21
|
// Mağaza Ayarları (API Keyler vb.)
|
|
17
22
|
const Store = sequelize.define('Store', {
|
|
18
23
|
name: { type: DataTypes.STRING, allowNull: false },
|
|
19
|
-
platform: { type: DataTypes.STRING, allowNull: false },
|
|
20
|
-
credentials: { type: DataTypes.JSON, allowNull: false },
|
|
24
|
+
platform: { type: DataTypes.STRING, allowNull: false },
|
|
25
|
+
credentials: { type: DataTypes.JSON, allowNull: false },
|
|
21
26
|
isActive: { type: DataTypes.BOOLEAN, defaultValue: true }
|
|
22
27
|
});
|
|
23
28
|
|
|
@@ -28,9 +33,9 @@ const Product = sequelize.define('Product', {
|
|
|
28
33
|
sku: { type: DataTypes.STRING },
|
|
29
34
|
description: { type: DataTypes.TEXT },
|
|
30
35
|
brand: { type: DataTypes.STRING },
|
|
31
|
-
images: { type: DataTypes.JSON },
|
|
32
|
-
marketData: { type: DataTypes.JSON },
|
|
33
|
-
aiAnalysis: { type: DataTypes.TEXT }
|
|
36
|
+
images: { type: DataTypes.JSON },
|
|
37
|
+
marketData: { type: DataTypes.JSON },
|
|
38
|
+
aiAnalysis: { type: DataTypes.TEXT }
|
|
34
39
|
});
|
|
35
40
|
|
|
36
41
|
// Siparişler
|
|
@@ -42,21 +47,21 @@ const Order = sequelize.define('Order', {
|
|
|
42
47
|
currency: { type: DataTypes.STRING, defaultValue: 'TRY' },
|
|
43
48
|
status: { type: DataTypes.STRING },
|
|
44
49
|
orderDate: { type: DataTypes.DATE },
|
|
45
|
-
items: { type: DataTypes.JSON }
|
|
50
|
+
items: { type: DataTypes.JSON }
|
|
46
51
|
});
|
|
47
52
|
|
|
48
|
-
//
|
|
53
|
+
// AI Önerileri
|
|
49
54
|
const Insight = sequelize.define('Insight', {
|
|
50
|
-
type: { type: DataTypes.STRING },
|
|
55
|
+
type: { type: DataTypes.STRING },
|
|
51
56
|
message: { type: DataTypes.TEXT },
|
|
52
|
-
priority: { type: DataTypes.INTEGER },
|
|
57
|
+
priority: { type: DataTypes.INTEGER },
|
|
53
58
|
isRead: { type: DataTypes.BOOLEAN, defaultValue: false }
|
|
54
59
|
});
|
|
55
60
|
|
|
56
61
|
// Veritabanını Başlat
|
|
57
|
-
async function initDB() {
|
|
62
|
+
export async function initDB() {
|
|
58
63
|
try {
|
|
59
|
-
await sequelize.sync({ alter: true });
|
|
64
|
+
await sequelize.sync({ alter: true });
|
|
60
65
|
return true;
|
|
61
66
|
} catch (error) {
|
|
62
67
|
console.error('Veritabanı hatası:', error);
|
|
@@ -64,11 +69,5 @@ async function initDB() {
|
|
|
64
69
|
}
|
|
65
70
|
}
|
|
66
71
|
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
Store,
|
|
70
|
-
Product,
|
|
71
|
-
Order,
|
|
72
|
-
Insight,
|
|
73
|
-
initDB
|
|
74
|
-
};
|
|
72
|
+
export { sequelize, Store, Product, Order, Insight };
|
|
73
|
+
export default { sequelize, Store, Product, Order, Insight, initDB };
|
package/core/engine.js
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* 🐙 VANTUZ ENGINE v3.
|
|
2
|
+
* 🐙 VANTUZ ENGINE v3.2
|
|
3
3
|
* Merkezi motor - Tüm sistemleri yönetir
|
|
4
4
|
*
|
|
5
|
-
*
|
|
5
|
+
* Vantuz Gateway üzerinden güçlendirilmiş altyapı
|
|
6
|
+
* Entegre Tool Sistemi
|
|
6
7
|
*/
|
|
7
8
|
|
|
8
9
|
import fs from 'fs';
|
|
@@ -10,14 +11,21 @@ import path from 'path';
|
|
|
10
11
|
import os from 'os';
|
|
11
12
|
|
|
12
13
|
// Platform Hub
|
|
13
|
-
import platformHub
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
} from '
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
14
|
+
import platformHub from '../plugins/vantuz/platforms/index.js';
|
|
15
|
+
|
|
16
|
+
// AI Provider & Gateway
|
|
17
|
+
import { getChannelManager } from './channels.js';
|
|
18
|
+
import { chat as aiChat, log } from './ai-provider.js';
|
|
19
|
+
import { getGateway } from './gateway.js';
|
|
20
|
+
|
|
21
|
+
// Tools
|
|
22
|
+
import { repricerTool } from '../plugins/vantuz/tools/repricer.js';
|
|
23
|
+
import { visionTool } from '../plugins/vantuz/tools/vision.js';
|
|
24
|
+
import { sentimentTool } from '../plugins/vantuz/tools/sentiment.js';
|
|
25
|
+
import { crossborderTool } from '../plugins/vantuz/tools/crossborder.js';
|
|
26
|
+
import { productTool } from '../plugins/vantuz/tools/product.js';
|
|
27
|
+
import { analyticsTool } from '../plugins/vantuz/tools/analytics.js';
|
|
28
|
+
import { quickReportTool } from '../plugins/vantuz/tools/quick-report.js';
|
|
21
29
|
|
|
22
30
|
// ═══════════════════════════════════════════════════════════════════════════
|
|
23
31
|
// CONFIG
|
|
@@ -26,7 +34,6 @@ import { chat as aiChat, log, getLogs } from './ai-provider.js';
|
|
|
26
34
|
const VANTUZ_HOME = path.join(os.homedir(), '.vantuz');
|
|
27
35
|
const CONFIG_PATH = path.join(VANTUZ_HOME, '.env');
|
|
28
36
|
const CONFIG_JSON = path.join(VANTUZ_HOME, 'config.json');
|
|
29
|
-
const DB_PATH = path.join(VANTUZ_HOME, 'vantuz.db');
|
|
30
37
|
|
|
31
38
|
// ═══════════════════════════════════════════════════════════════════════════
|
|
32
39
|
// ENGINE CLASS
|
|
@@ -38,24 +45,48 @@ export class VantuzEngine {
|
|
|
38
45
|
this.config = {};
|
|
39
46
|
this.env = {};
|
|
40
47
|
this.platforms = {};
|
|
41
|
-
this.channels =
|
|
48
|
+
this.channels = null;
|
|
49
|
+
this.gateway = null;
|
|
42
50
|
this.context = {
|
|
43
51
|
products: [],
|
|
44
|
-
orders: [],
|
|
45
52
|
connectedPlatforms: []
|
|
46
53
|
};
|
|
54
|
+
|
|
55
|
+
// Tool Registry
|
|
56
|
+
this.tools = {
|
|
57
|
+
repricer: repricerTool,
|
|
58
|
+
vision: visionTool,
|
|
59
|
+
sentiment: sentimentTool,
|
|
60
|
+
crossborder: crossborderTool,
|
|
61
|
+
product: productTool,
|
|
62
|
+
analytics: analyticsTool,
|
|
63
|
+
quickReport: quickReportTool
|
|
64
|
+
};
|
|
47
65
|
}
|
|
48
66
|
|
|
49
67
|
/**
|
|
50
68
|
* Engine'i başlat
|
|
51
69
|
*/
|
|
52
70
|
async initialize() {
|
|
53
|
-
log('INFO', 'Vantuz Engine başlatılıyor...');
|
|
71
|
+
log('INFO', 'Vantuz Engine v3.2 başlatılıyor...');
|
|
54
72
|
|
|
55
73
|
// Config ve env yükle
|
|
56
74
|
this._loadConfig();
|
|
57
75
|
this._loadEnv();
|
|
58
76
|
|
|
77
|
+
// Vantuz Gateway bağlantısı
|
|
78
|
+
try {
|
|
79
|
+
this.gateway = await getGateway();
|
|
80
|
+
if (this.gateway.isConnected()) {
|
|
81
|
+
log('INFO', 'Vantuz Gateway bağlı', this.gateway.getInfo());
|
|
82
|
+
}
|
|
83
|
+
} catch (e) {
|
|
84
|
+
log('WARN', 'Gateway bağlantısı başarısız, direkt mod', { error: e.message });
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
// Channel Manager'ı başlat
|
|
88
|
+
this.channels = await getChannelManager();
|
|
89
|
+
|
|
59
90
|
// Platform Hub'ı başlat
|
|
60
91
|
await this._initPlatforms();
|
|
61
92
|
|
|
@@ -64,7 +95,8 @@ export class VantuzEngine {
|
|
|
64
95
|
|
|
65
96
|
this.initialized = true;
|
|
66
97
|
log('INFO', 'Vantuz Engine hazır', {
|
|
67
|
-
platforms: this.context.connectedPlatforms.length
|
|
98
|
+
platforms: this.context.connectedPlatforms.length,
|
|
99
|
+
gateway: this.gateway?.isConnected() || false
|
|
68
100
|
});
|
|
69
101
|
|
|
70
102
|
return this;
|
|
@@ -108,36 +140,27 @@ export class VantuzEngine {
|
|
|
108
140
|
async _initPlatforms() {
|
|
109
141
|
const platformConfig = {};
|
|
110
142
|
|
|
111
|
-
//
|
|
112
|
-
if (this.env.TRENDYOL_API_KEY
|
|
143
|
+
// Otomatik config eşleme
|
|
144
|
+
if (this.env.TRENDYOL_API_KEY) {
|
|
113
145
|
platformConfig.trendyol = {
|
|
114
146
|
supplierId: this.env.TRENDYOL_SUPPLIER_ID,
|
|
115
147
|
apiKey: this.env.TRENDYOL_API_KEY,
|
|
116
148
|
apiSecret: this.env.TRENDYOL_API_SECRET
|
|
117
149
|
};
|
|
118
|
-
log('INFO', 'Trendyol config hazır');
|
|
119
150
|
}
|
|
120
|
-
|
|
121
|
-
// Hepsiburada
|
|
122
151
|
if (this.env.HEPSIBURADA_MERCHANT_ID) {
|
|
123
152
|
platformConfig.hepsiburada = {
|
|
124
153
|
merchantId: this.env.HEPSIBURADA_MERCHANT_ID,
|
|
125
154
|
username: this.env.HEPSIBURADA_USERNAME,
|
|
126
155
|
password: this.env.HEPSIBURADA_PASSWORD
|
|
127
156
|
};
|
|
128
|
-
log('INFO', 'Hepsiburada config hazır');
|
|
129
157
|
}
|
|
130
|
-
|
|
131
|
-
// N11
|
|
132
158
|
if (this.env.N11_API_KEY) {
|
|
133
159
|
platformConfig.n11 = {
|
|
134
160
|
apiKey: this.env.N11_API_KEY,
|
|
135
161
|
apiSecret: this.env.N11_API_SECRET
|
|
136
162
|
};
|
|
137
|
-
log('INFO', 'N11 config hazır');
|
|
138
163
|
}
|
|
139
|
-
|
|
140
|
-
// Amazon
|
|
141
164
|
if (this.env.AMAZON_SELLER_ID) {
|
|
142
165
|
platformConfig.amazon = {
|
|
143
166
|
eu: {
|
|
@@ -148,29 +171,6 @@ export class VantuzEngine {
|
|
|
148
171
|
};
|
|
149
172
|
}
|
|
150
173
|
|
|
151
|
-
// Çiçeksepeti
|
|
152
|
-
if (this.env.CICEKSEPETI_API_KEY) {
|
|
153
|
-
platformConfig.ciceksepeti = {
|
|
154
|
-
apiKey: this.env.CICEKSEPETI_API_KEY
|
|
155
|
-
};
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
// PTTavm
|
|
159
|
-
if (this.env.PTTAVM_API_KEY) {
|
|
160
|
-
platformConfig.pttavm = {
|
|
161
|
-
apiKey: this.env.PTTAVM_API_KEY,
|
|
162
|
-
token: this.env.PTTAVM_TOKEN
|
|
163
|
-
};
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
// Pazarama
|
|
167
|
-
if (this.env.PAZARAMA_CLIENT_ID) {
|
|
168
|
-
platformConfig.pazarama = {
|
|
169
|
-
clientId: this.env.PAZARAMA_CLIENT_ID,
|
|
170
|
-
clientSecret: this.env.PAZARAMA_CLIENT_SECRET
|
|
171
|
-
};
|
|
172
|
-
}
|
|
173
|
-
|
|
174
174
|
// Platform Hub'ı başlat
|
|
175
175
|
if (Object.keys(platformConfig).length > 0) {
|
|
176
176
|
this.platforms = await platformHub.initAll(platformConfig);
|
|
@@ -186,7 +186,6 @@ export class VantuzEngine {
|
|
|
186
186
|
async _buildContext() {
|
|
187
187
|
this.context.connectedPlatforms = platformHub.getConnected();
|
|
188
188
|
|
|
189
|
-
// Her bağlı platformdan temel veri çek
|
|
190
189
|
for (const platform of this.context.connectedPlatforms) {
|
|
191
190
|
try {
|
|
192
191
|
const api = platformHub.resolve(platform);
|
|
@@ -198,7 +197,6 @@ export class VantuzEngine {
|
|
|
198
197
|
...p,
|
|
199
198
|
_platform: platform
|
|
200
199
|
})));
|
|
201
|
-
log('INFO', `${platform} ürünleri çekildi`, { count: products.length });
|
|
202
200
|
}
|
|
203
201
|
}
|
|
204
202
|
} catch (e) {
|
|
@@ -208,52 +206,52 @@ export class VantuzEngine {
|
|
|
208
206
|
}
|
|
209
207
|
|
|
210
208
|
/**
|
|
211
|
-
*
|
|
209
|
+
* AI ile sohbet - Tool destekli
|
|
212
210
|
*/
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
connectedPlatforms: this.context.connectedPlatforms,
|
|
216
|
-
productCount: this.context.products.length,
|
|
217
|
-
platforms: platformHub.getStatus(),
|
|
218
|
-
aiProvider: this.config.aiProvider || 'gemini'
|
|
219
|
-
};
|
|
220
|
-
}
|
|
211
|
+
async chat(message) {
|
|
212
|
+
if (!this.initialized) await this.initialize();
|
|
221
213
|
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
getStatus() {
|
|
226
|
-
const status = platformHub.getStatus();
|
|
227
|
-
const connected = this.context.connectedPlatforms;
|
|
214
|
+
// 1. Basit komut kontrolü (Tool çağırma)
|
|
215
|
+
const toolResult = await this._tryExecuteToolFromMessage(message);
|
|
216
|
+
if (toolResult) return toolResult;
|
|
228
217
|
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
218
|
+
// 2. Gateway üzerinden AI (Eğer varsa)
|
|
219
|
+
if (this.gateway?.isConnected()) {
|
|
220
|
+
try {
|
|
221
|
+
const gatewayResult = await this.gateway.chat(message, {
|
|
222
|
+
systemPrompt: this._buildContextInfo()
|
|
223
|
+
});
|
|
224
|
+
if (gatewayResult.success) return gatewayResult.response;
|
|
225
|
+
} catch (e) { }
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
// 3. Direkt API (Fallback)
|
|
229
|
+
const enrichedConfig = {
|
|
230
|
+
...this.config,
|
|
231
|
+
systemContext: this._buildContextInfo()
|
|
236
232
|
};
|
|
233
|
+
|
|
234
|
+
return await aiChat(message, enrichedConfig, this.env);
|
|
237
235
|
}
|
|
238
236
|
|
|
239
237
|
/**
|
|
240
|
-
*
|
|
238
|
+
* Mesajdan Tool tespiti (Basit NLP)
|
|
241
239
|
*/
|
|
242
|
-
async
|
|
243
|
-
|
|
244
|
-
await this.initialize();
|
|
245
|
-
}
|
|
240
|
+
async _tryExecuteToolFromMessage(message) {
|
|
241
|
+
const lower = message.toLowerCase();
|
|
246
242
|
|
|
247
|
-
//
|
|
248
|
-
|
|
243
|
+
// Repricer
|
|
244
|
+
if (lower.includes('fiyat analizi') || lower.includes('rakip analizi')) {
|
|
245
|
+
return "Repricer aracı çalıştırılıyor... (Detaylı parametreler için /rakip komutunu kullanın)";
|
|
246
|
+
}
|
|
249
247
|
|
|
250
|
-
//
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
}
|
|
248
|
+
// Stok
|
|
249
|
+
if (lower.includes('stok durumu')) {
|
|
250
|
+
const stocks = await this.getStock();
|
|
251
|
+
return JSON.stringify(stocks.map(s => ({ platform: s.platform, items: s.products.length })), null, 2);
|
|
252
|
+
}
|
|
255
253
|
|
|
256
|
-
return
|
|
254
|
+
return null;
|
|
257
255
|
}
|
|
258
256
|
|
|
259
257
|
/**
|
|
@@ -261,25 +259,22 @@ export class VantuzEngine {
|
|
|
261
259
|
*/
|
|
262
260
|
_buildContextInfo() {
|
|
263
261
|
const connected = this.context.connectedPlatforms;
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
let info = `\n\n--- MEVCUT DURUM ---\n`;
|
|
262
|
+
let info = `\n\n--- MEVCUT SİSTEM DURUMU ---\n`;
|
|
267
263
|
info += `Bağlı Platformlar: ${connected.length > 0 ? connected.join(', ') : 'Hiçbiri'}\n`;
|
|
268
|
-
info += `
|
|
264
|
+
info += `Gateway: ${this.gateway?.isConnected() ? 'BAĞLI' : 'KOPUK'}\n`;
|
|
265
|
+
info += `Mevcut Toollar: Repricer, Vision, Sentiment, Analytics, CrossBorder\n`;
|
|
269
266
|
|
|
270
267
|
if (this.context.products.length > 0) {
|
|
271
268
|
info += `\nÖrnek Ürünler:\n`;
|
|
272
|
-
this.context.products.slice(0,
|
|
273
|
-
info += `- ${p.title
|
|
269
|
+
this.context.products.slice(0, 3).forEach(p => {
|
|
270
|
+
info += `- ${p.title} (${p._platform}): ${p.salePrice} TL\n`;
|
|
274
271
|
});
|
|
275
272
|
}
|
|
276
|
-
|
|
277
273
|
return info;
|
|
278
274
|
}
|
|
279
275
|
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
*/
|
|
276
|
+
// --- Helper Methods ---
|
|
277
|
+
|
|
283
278
|
async getStock(platform = 'all') {
|
|
284
279
|
const results = [];
|
|
285
280
|
const targets = platform === 'all'
|
|
@@ -309,53 +304,48 @@ export class VantuzEngine {
|
|
|
309
304
|
log('ERROR', `Stok çekme hatası: ${p}`, { error: e.message });
|
|
310
305
|
}
|
|
311
306
|
}
|
|
312
|
-
|
|
313
307
|
return results;
|
|
314
308
|
}
|
|
315
309
|
|
|
316
|
-
/**
|
|
317
|
-
* Sipariş bilgisi al
|
|
318
|
-
*/
|
|
319
310
|
async getOrders(params = {}) {
|
|
320
311
|
return await platformHub.getAllOrders(params);
|
|
321
312
|
}
|
|
322
313
|
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
return await platformHub.updatePriceMulti(barcode, price, platforms);
|
|
329
|
-
}
|
|
314
|
+
getStatus() {
|
|
315
|
+
const status = platformHub.getStatus();
|
|
316
|
+
const connected = this.context.connectedPlatforms;
|
|
317
|
+
const channelStatus = this.channels ? this.channels.getStatus() : {};
|
|
318
|
+
const gatewayInfo = this.gateway ? this.gateway.getInfo() : { connected: false };
|
|
330
319
|
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
320
|
+
return {
|
|
321
|
+
engine: this.initialized ? 'active' : 'inactive',
|
|
322
|
+
version: '3.2',
|
|
323
|
+
aiProvider: this.config.aiProvider || 'gemini',
|
|
324
|
+
gateway: gatewayInfo,
|
|
325
|
+
platforms: status,
|
|
326
|
+
channels: channelStatus,
|
|
327
|
+
connectedCount: connected.length,
|
|
328
|
+
totalPlatforms: 7,
|
|
329
|
+
productCount: this.context.products.length
|
|
330
|
+
};
|
|
337
331
|
}
|
|
338
332
|
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
}
|
|
356
|
-
}
|
|
357
|
-
|
|
358
|
-
return results;
|
|
333
|
+
async doctor() {
|
|
334
|
+
const status = this.getStatus();
|
|
335
|
+
return {
|
|
336
|
+
engine: this.initialized,
|
|
337
|
+
gateway: {
|
|
338
|
+
status: status.gateway.connected ? 'healthy' : 'unreachable',
|
|
339
|
+
...status.gateway
|
|
340
|
+
},
|
|
341
|
+
platforms: status.platforms,
|
|
342
|
+
ai: {
|
|
343
|
+
provider: status.aiProvider,
|
|
344
|
+
keyConfigured: true,
|
|
345
|
+
gatewayFallback: status.gateway.connected
|
|
346
|
+
},
|
|
347
|
+
channels: status.channels
|
|
348
|
+
};
|
|
359
349
|
}
|
|
360
350
|
}
|
|
361
351
|
|