evimnet-mcp 1.0.0 → 1.2.0
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/DIZIN-KAYIT.md +64 -0
- package/package.json +1 -1
- package/server.js +8 -4
- package/tools/agent.js +177 -86
package/DIZIN-KAYIT.md
ADDED
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
# MCP Dizin Kayıt Bilgileri
|
|
2
|
+
|
|
3
|
+
Aşağıdaki bilgileri kopyala-yapıştır ile ilgili sitelere gir.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## 1. Smithery.ai (en kolay, anında yayınlanır)
|
|
8
|
+
|
|
9
|
+
**URL:** https://smithery.ai/new
|
|
10
|
+
|
|
11
|
+
| Alan | Değer |
|
|
12
|
+
|------|-------|
|
|
13
|
+
| Server Name | evimnet-mcp |
|
|
14
|
+
| Display Name | Evimnet — Turkey Real Estate Search |
|
|
15
|
+
| GitHub URL | https://github.com/high5emlak/evimnetglobal/tree/main/mcp-server |
|
|
16
|
+
| npm Package | evimnet-mcp |
|
|
17
|
+
| Description (EN) | Search properties for sale and rent across Turkey. Covers Istanbul, Bodrum, Antalya, Izmir and all cities. Includes currency conversion (TRY/EUR/USD), area info (schools, hospitals, transport), and market statistics. 9 tools for AI assistants. |
|
|
18
|
+
|
|
19
|
+
---
|
|
20
|
+
|
|
21
|
+
## 2. mcp.so
|
|
22
|
+
|
|
23
|
+
**URL:** https://mcp.so/ → Submit butonu
|
|
24
|
+
|
|
25
|
+
| Alan | Değer |
|
|
26
|
+
|------|-------|
|
|
27
|
+
| Name | Evimnet MCP |
|
|
28
|
+
| Description | Turkey's real estate search for AI assistants. Search sale/rent properties, get property details, area info (POIs, weather, AQI), currency rates (TRY/EUR/USD), and platform stats. Supports Turkish, German, and English. |
|
|
29
|
+
| GitHub | https://github.com/high5emlak/evimnetglobal/tree/main/mcp-server |
|
|
30
|
+
| npm | https://www.npmjs.com/package/evimnet-mcp |
|
|
31
|
+
| Install command | npx evimnet-mcp |
|
|
32
|
+
| Category | Real Estate / Property |
|
|
33
|
+
| Tools count | 9 |
|
|
34
|
+
| Tools | search_properties, get_property_details, get_locations, search_location, get_area_info, send_inquiry, get_currency_rates, get_platform_stats, convert_price |
|
|
35
|
+
|
|
36
|
+
---
|
|
37
|
+
|
|
38
|
+
## 3. Glama.ai
|
|
39
|
+
|
|
40
|
+
**URL:** https://glama.ai/mcp/servers → Add Server
|
|
41
|
+
|
|
42
|
+
| Alan | Değer |
|
|
43
|
+
|------|-------|
|
|
44
|
+
| GitHub Repository URL | https://github.com/high5emlak/evimnetglobal |
|
|
45
|
+
| Server path | mcp-server/ |
|
|
46
|
+
|
|
47
|
+
---
|
|
48
|
+
|
|
49
|
+
## Ortak bilgiler (her yerde kullanılabilir)
|
|
50
|
+
|
|
51
|
+
**Kısa açıklama (TR):**
|
|
52
|
+
Türkiye'de satılık ve kiralık emlak arama. İstanbul, Bodrum, Antalya, İzmir ve tüm şehirler. Döviz çevirimi, çevre bilgisi, piyasa istatistikleri. 9 AI aracı.
|
|
53
|
+
|
|
54
|
+
**Kısa açıklama (EN):**
|
|
55
|
+
Search properties for sale and rent across Turkey. Istanbul, Bodrum, Antalya, Izmir and all cities. Currency conversion, area info, market stats. 9 AI tools.
|
|
56
|
+
|
|
57
|
+
**Kısa açıklama (DE):**
|
|
58
|
+
Immobiliensuche in der Türkei — Kauf und Miete. Istanbul, Bodrum, Antalya, Izmir und alle Städte. Währungsumrechnung, Umgebungsinfos, Marktstatistiken. 9 KI-Tools.
|
|
59
|
+
|
|
60
|
+
**Tags:** real-estate, turkey, property, mcp, ai, bodrum, istanbul, antalya, rental, sale
|
|
61
|
+
|
|
62
|
+
**Website:** https://evimnet.com
|
|
63
|
+
**npm:** https://www.npmjs.com/package/evimnet-mcp
|
|
64
|
+
**License:** MIT
|
package/package.json
CHANGED
package/server.js
CHANGED
|
@@ -60,10 +60,14 @@ const TOOL_HANDLERS = {
|
|
|
60
60
|
convert_price: (a) => handleMarketTool('convert_price', a),
|
|
61
61
|
|
|
62
62
|
// Emlakçı araçları (API key gerekli)
|
|
63
|
-
get_my_leads:
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
63
|
+
get_my_leads: (a) => handleAgentTool('get_my_leads', a),
|
|
64
|
+
get_lead_detail: (a) => handleAgentTool('get_lead_detail', a),
|
|
65
|
+
update_lead_status: (a) => handleAgentTool('update_lead_status', a),
|
|
66
|
+
get_my_listings: (a) => handleAgentTool('get_my_listings', a),
|
|
67
|
+
get_listing_analytics: (a) => handleAgentTool('get_listing_analytics', a),
|
|
68
|
+
get_my_stats: (a) => handleAgentTool('get_my_stats', a),
|
|
69
|
+
create_listing: (a) => handleAgentTool('create_listing', a),
|
|
70
|
+
update_listing: (a) => handleAgentTool('update_listing', a),
|
|
67
71
|
};
|
|
68
72
|
|
|
69
73
|
// ─── Server oluştur ──────────────────────────────────────────────────────────
|
package/tools/agent.js
CHANGED
|
@@ -30,12 +30,23 @@ Filtreleme: durum (NEW=Yeni, CONTACTED=Arandı, MEETING=Görüşme, CLOSED=Kapan
|
|
|
30
30
|
enum: ['NEW', 'CONTACTED', 'MEETING', 'CLOSED'],
|
|
31
31
|
description: 'Durum filtresi (boş = hepsi)',
|
|
32
32
|
},
|
|
33
|
-
page: { type: 'number', description: 'Sayfa numarası (varsayılan: 1)' },
|
|
34
|
-
limit: { type: 'number', description: 'Sayfa başı kayıt (maks: 50, varsayılan: 20)' },
|
|
35
33
|
},
|
|
36
34
|
},
|
|
37
35
|
},
|
|
38
36
|
|
|
37
|
+
{
|
|
38
|
+
name: 'get_lead_detail',
|
|
39
|
+
description: `Tek bir lead'in detayını getir. İlan bilgisi, mesaj ve iletişim bilgileri dahil.
|
|
40
|
+
Örnek: "Ahmet Yılmaz'ın başvuru detayını göster"`,
|
|
41
|
+
inputSchema: {
|
|
42
|
+
type: 'object',
|
|
43
|
+
properties: {
|
|
44
|
+
id: { type: 'string', description: 'Lead ID (get_my_leads\'ten alınır)' },
|
|
45
|
+
},
|
|
46
|
+
required: ['id'],
|
|
47
|
+
},
|
|
48
|
+
},
|
|
49
|
+
|
|
39
50
|
{
|
|
40
51
|
name: 'update_lead_status',
|
|
41
52
|
description: `Lead durumunu güncelle.
|
|
@@ -43,137 +54,217 @@ Filtreleme: durum (NEW=Yeni, CONTACTED=Arandı, MEETING=Görüşme, CLOSED=Kapan
|
|
|
43
54
|
inputSchema: {
|
|
44
55
|
type: 'object',
|
|
45
56
|
properties: {
|
|
46
|
-
|
|
57
|
+
id: { type: 'string', description: 'Lead ID' },
|
|
47
58
|
status: {
|
|
48
59
|
type: 'string',
|
|
49
60
|
enum: ['NEW', 'CONTACTED', 'MEETING', 'CLOSED'],
|
|
50
61
|
description: 'Yeni durum',
|
|
51
62
|
},
|
|
52
63
|
},
|
|
53
|
-
required: ['
|
|
64
|
+
required: ['id', 'status'],
|
|
54
65
|
},
|
|
55
66
|
},
|
|
56
67
|
|
|
57
68
|
{
|
|
58
69
|
name: 'get_my_listings',
|
|
59
|
-
description: `Emlakçının ilanlarını getir.
|
|
60
|
-
Aktif, taslak, pasif ilanlar. Lead sayısı ve görüntülenme bilgisi dahil.
|
|
70
|
+
description: `Emlakçının ilanlarını getir. Görüntülenme ve favori sayıları dahil.
|
|
61
71
|
Örnek: "Aktif ilanlarımı listele", "Taslak ilanlarım var mı?"`,
|
|
62
72
|
inputSchema: {
|
|
63
73
|
type: 'object',
|
|
64
74
|
properties: {
|
|
65
75
|
status: {
|
|
66
76
|
type: 'string',
|
|
67
|
-
enum: ['DRAFT', 'PENDING', 'APPROVED', 'PASSIVE'
|
|
77
|
+
enum: ['DRAFT', 'PENDING', 'APPROVED', 'PASSIVE'],
|
|
68
78
|
description: 'Durum filtresi (boş = hepsi)',
|
|
69
79
|
},
|
|
70
|
-
page: { type: 'number', description: 'Sayfa numarası' },
|
|
71
|
-
limit: { type: 'number', description: 'Sayfa başı kayıt' },
|
|
72
80
|
},
|
|
73
81
|
},
|
|
74
82
|
},
|
|
75
83
|
|
|
84
|
+
{
|
|
85
|
+
name: 'get_listing_analytics',
|
|
86
|
+
description: `Bir ilanın performans analitiğini getir: görüntülenme, tıklama, Avrupa görüntülenme, lead sayısı, boost durumu.
|
|
87
|
+
Örnek: "Yalıkavak villamın performansı nasıl?"`,
|
|
88
|
+
inputSchema: {
|
|
89
|
+
type: 'object',
|
|
90
|
+
properties: {
|
|
91
|
+
id: { type: 'string', description: 'İlan ID (get_my_listings\'ten alınır)' },
|
|
92
|
+
},
|
|
93
|
+
required: ['id'],
|
|
94
|
+
},
|
|
95
|
+
},
|
|
96
|
+
|
|
76
97
|
{
|
|
77
98
|
name: 'get_my_stats',
|
|
78
99
|
description: `Dashboard özeti: aktif ilan sayısı, yeni lead sayısı, toplam görüntülenme.
|
|
79
|
-
Örnek: "Durumumu özetle", "
|
|
100
|
+
Örnek: "Durumumu özetle", "Genel performansım nasıl?"`,
|
|
80
101
|
inputSchema: {
|
|
81
102
|
type: 'object',
|
|
82
103
|
properties: {},
|
|
83
104
|
},
|
|
84
105
|
},
|
|
106
|
+
|
|
107
|
+
{
|
|
108
|
+
name: 'create_listing',
|
|
109
|
+
description: `Yeni ilan oluştur. Şehir ve ilçe adını Türkçe yazabilirsiniz, otomatik eşleştirilir.
|
|
110
|
+
Taslak olarak oluşturulur; panelden fotoğraf ekleyip onaya gönderebilirsiniz. status: "PENDING" ile direkt onaya da gönderilebilir.
|
|
111
|
+
Örnek: "Bodrum Yalıkavak'ta 3+1 villa ekle, 4.500.000 TL, 180m², deniz manzaralı"`,
|
|
112
|
+
inputSchema: {
|
|
113
|
+
type: 'object',
|
|
114
|
+
properties: {
|
|
115
|
+
title: { type: 'string', description: 'İlan başlığı' },
|
|
116
|
+
type: { type: 'string', enum: ['SALE', 'RENT'], description: 'SALE=Satılık, RENT=Kiralık' },
|
|
117
|
+
propertyType: { type: 'string', enum: ['APARTMENT', 'VILLA', 'LAND', 'PROJECT'], description: 'Mülk tipi' },
|
|
118
|
+
priceTRY: { type: 'number', description: 'Fiyat (TRY)' },
|
|
119
|
+
city: { type: 'string', description: 'Şehir adı (ör: Bodrum, İstanbul, Antalya)' },
|
|
120
|
+
district: { type: 'string', description: 'İlçe adı (ör: Yalıkavak, Beşiktaş)' },
|
|
121
|
+
rooms: { type: 'string', description: 'Oda sayısı (ör: 3+1, 2+1, Stüdyo)' },
|
|
122
|
+
sqmNet: { type: 'number', description: 'Net m²' },
|
|
123
|
+
sqmGross: { type: 'number', description: 'Brüt m²' },
|
|
124
|
+
bathrooms: { type: 'number', description: 'Banyo sayısı' },
|
|
125
|
+
floor: { type: 'number', description: 'Bulunduğu kat' },
|
|
126
|
+
totalFloors: { type: 'number', description: 'Toplam kat' },
|
|
127
|
+
buildingAge: { type: 'number', description: 'Bina yaşı' },
|
|
128
|
+
heating: { type: 'string', description: 'Isıtma tipi (ör: Doğalgaz, Klima, Yerden)' },
|
|
129
|
+
description: { type: 'string', description: 'İlan açıklaması (Türkçe)' },
|
|
130
|
+
descriptionDE: { type: 'string', description: 'İlan açıklaması (Almanca, opsiyonel)' },
|
|
131
|
+
viewType: { type: 'string', description: 'Manzara tipi JSON array (ör: ["SEA","NATURE"])' },
|
|
132
|
+
seaDistance: { type: 'number', description: 'Denize uzaklık (metre)' },
|
|
133
|
+
villaType: { type: 'string', enum: ['DETACHED', 'SEMI_DETACHED', 'TRIPLEX', 'DUPLEX'], description: 'Villa tipi' },
|
|
134
|
+
poolType: { type: 'string', enum: ['PRIVATE', 'SHARED', 'NONE'], description: 'Havuz tipi' },
|
|
135
|
+
gardenSqm: { type: 'number', description: 'Bahçe m²' },
|
|
136
|
+
lat: { type: 'number', description: 'Enlem' },
|
|
137
|
+
lng: { type: 'number', description: 'Boylam' },
|
|
138
|
+
features: { type: 'object', description: 'Özellikler (ör: {"barbeku": true, "klima": true})' },
|
|
139
|
+
status: { type: 'string', enum: ['DRAFT', 'PENDING'], description: 'DRAFT=Taslak, PENDING=Onaya gönder' },
|
|
140
|
+
},
|
|
141
|
+
required: ['title', 'type', 'propertyType', 'priceTRY', 'city'],
|
|
142
|
+
},
|
|
143
|
+
},
|
|
144
|
+
|
|
145
|
+
{
|
|
146
|
+
name: 'update_listing',
|
|
147
|
+
description: `Mevcut bir ilanı düzenle. Sadece değişen alanları gönderin.
|
|
148
|
+
Fiyat, açıklama, m², oda sayısı vb. güncellenebilir. İçerik değişirse ilan otomatik onaya gider.
|
|
149
|
+
Örnek: "Yalıkavak villamın fiyatını 4 milyona düşür", "İlan açıklamasını güncelle"`,
|
|
150
|
+
inputSchema: {
|
|
151
|
+
type: 'object',
|
|
152
|
+
properties: {
|
|
153
|
+
id: { type: 'string', description: 'İlan ID (get_my_listings\'ten alınır)' },
|
|
154
|
+
title: { type: 'string', description: 'Yeni başlık' },
|
|
155
|
+
priceTRY: { type: 'number', description: 'Yeni fiyat (TRY)' },
|
|
156
|
+
description: { type: 'string', description: 'Yeni açıklama' },
|
|
157
|
+
descriptionDE: { type: 'string', description: 'Almanca açıklama' },
|
|
158
|
+
rooms: { type: 'string', description: 'Oda sayısı' },
|
|
159
|
+
sqmNet: { type: 'number', description: 'Net m²' },
|
|
160
|
+
sqmGross: { type: 'number', description: 'Brüt m²' },
|
|
161
|
+
bathrooms: { type: 'number', description: 'Banyo sayısı' },
|
|
162
|
+
floor: { type: 'number', description: 'Kat' },
|
|
163
|
+
buildingAge: { type: 'number', description: 'Bina yaşı' },
|
|
164
|
+
heating: { type: 'string', description: 'Isıtma tipi' },
|
|
165
|
+
viewType: { type: 'string', description: 'Manzara tipi' },
|
|
166
|
+
seaDistance: { type: 'number', description: 'Denize uzaklık' },
|
|
167
|
+
features: { type: 'object', description: 'Özellikler' },
|
|
168
|
+
status: { type: 'string', enum: ['DRAFT', 'PENDING', 'PASSIVE'], description: 'Durum' },
|
|
169
|
+
},
|
|
170
|
+
required: ['id'],
|
|
171
|
+
},
|
|
172
|
+
},
|
|
85
173
|
];
|
|
86
174
|
|
|
87
175
|
export async function handleAgentTool(name, args) {
|
|
88
|
-
if (name === 'get_my_leads')
|
|
89
|
-
if (name === '
|
|
90
|
-
if (name === '
|
|
91
|
-
if (name === '
|
|
176
|
+
if (name === 'get_my_leads') return getMyLeads(args);
|
|
177
|
+
if (name === 'get_lead_detail') return getLeadDetail(args);
|
|
178
|
+
if (name === 'update_lead_status') return updateLeadStatus(args);
|
|
179
|
+
if (name === 'get_my_listings') return getMyListings(args);
|
|
180
|
+
if (name === 'get_listing_analytics') return getListingAnalytics(args);
|
|
181
|
+
if (name === 'get_my_stats') return getMyStats();
|
|
182
|
+
if (name === 'create_listing') return createListing(args);
|
|
183
|
+
if (name === 'update_listing') return updateListing(args);
|
|
92
184
|
}
|
|
93
185
|
|
|
94
|
-
async function
|
|
95
|
-
const
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
status: l.status,
|
|
108
|
-
message: l.message || null,
|
|
109
|
-
listing: l.listing ? { title: l.listing.title, slug: l.listing.slug, price: `${l.listing.priceTRY?.toLocaleString('tr-TR')} ₺` } : null,
|
|
110
|
-
createdAt: l.createdAt,
|
|
111
|
-
}));
|
|
186
|
+
async function mcpPost(action, body) {
|
|
187
|
+
const qs = new URLSearchParams({ action });
|
|
188
|
+
const res = await fetch(`${BASE_URL}/api/mcp/agent?${qs}`, {
|
|
189
|
+
method: 'POST',
|
|
190
|
+
headers: agentHeaders(),
|
|
191
|
+
body: JSON.stringify(body),
|
|
192
|
+
});
|
|
193
|
+
if (!res.ok) {
|
|
194
|
+
const data = await res.json().catch(() => ({}));
|
|
195
|
+
throw new Error(data.error || `API hatasi: ${res.status}`);
|
|
196
|
+
}
|
|
197
|
+
return res.json();
|
|
198
|
+
}
|
|
112
199
|
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
}
|
|
118
|
-
|
|
200
|
+
async function mcpGet(action, params = {}) {
|
|
201
|
+
const qs = new URLSearchParams({ action, ...params });
|
|
202
|
+
const res = await fetch(`${BASE_URL}/api/mcp/agent?${qs}`, { headers: agentHeaders() });
|
|
203
|
+
if (!res.ok) {
|
|
204
|
+
const body = await res.json().catch(() => ({}));
|
|
205
|
+
throw new Error(body.error || `API hatası: ${res.status}`);
|
|
206
|
+
}
|
|
207
|
+
return res.json();
|
|
119
208
|
}
|
|
120
209
|
|
|
121
|
-
async function
|
|
122
|
-
const
|
|
123
|
-
|
|
210
|
+
async function mcpPatch(action, body) {
|
|
211
|
+
const qs = new URLSearchParams({ action });
|
|
212
|
+
const res = await fetch(`${BASE_URL}/api/mcp/agent?${qs}`, {
|
|
213
|
+
method: 'PATCH',
|
|
124
214
|
headers: agentHeaders(),
|
|
125
|
-
body:
|
|
215
|
+
body: JSON.stringify(body),
|
|
126
216
|
});
|
|
127
|
-
if (!res.ok)
|
|
217
|
+
if (!res.ok) {
|
|
218
|
+
const data = await res.json().catch(() => ({}));
|
|
219
|
+
throw new Error(data.error || `API hatası: ${res.status}`);
|
|
220
|
+
}
|
|
221
|
+
return res.json();
|
|
222
|
+
}
|
|
128
223
|
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
type: 'text',
|
|
132
|
-
text: JSON.stringify({ success: true, leadId, status }, null, 2),
|
|
133
|
-
}],
|
|
134
|
-
};
|
|
224
|
+
function textResult(data) {
|
|
225
|
+
return { content: [{ type: 'text', text: JSON.stringify(data, null, 2) }] };
|
|
135
226
|
}
|
|
136
227
|
|
|
137
|
-
async function
|
|
138
|
-
const params =
|
|
139
|
-
if (status) params.
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
const data = await res.json();
|
|
144
|
-
|
|
145
|
-
const listings = data.listings.map(l => ({
|
|
146
|
-
id: l.id,
|
|
147
|
-
title: l.title,
|
|
148
|
-
slug: l.slug,
|
|
149
|
-
type: l.type,
|
|
150
|
-
status: l.status,
|
|
151
|
-
price: `${l.priceTRY?.toLocaleString('tr-TR')} ₺`,
|
|
152
|
-
sqm: l.sqmNet ? `${l.sqmNet}m²` : null,
|
|
153
|
-
rooms: l.rooms || null,
|
|
154
|
-
city: l.city?.name || null,
|
|
155
|
-
district: l.district?.name || null,
|
|
156
|
-
leads: l._count?.leads || 0,
|
|
157
|
-
url: `https://evimnet.com/ilan/${l.slug}`,
|
|
158
|
-
}));
|
|
228
|
+
async function getMyLeads({ status } = {}) {
|
|
229
|
+
const params = {};
|
|
230
|
+
if (status) params.status = status;
|
|
231
|
+
const data = await mcpGet('leads', params);
|
|
232
|
+
return textResult(data);
|
|
233
|
+
}
|
|
159
234
|
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
235
|
+
async function getLeadDetail({ id }) {
|
|
236
|
+
const data = await mcpGet('lead', { id });
|
|
237
|
+
return textResult(data);
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
async function updateLeadStatus({ id, status }) {
|
|
241
|
+
const data = await mcpPatch('lead-status', { id, status });
|
|
242
|
+
return textResult(data);
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
async function getMyListings({ status } = {}) {
|
|
246
|
+
const params = {};
|
|
247
|
+
if (status) params.status = status;
|
|
248
|
+
const data = await mcpGet('listings', params);
|
|
249
|
+
return textResult(data);
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
async function getListingAnalytics({ id }) {
|
|
253
|
+
const data = await mcpGet('analytics', { id });
|
|
254
|
+
return textResult(data);
|
|
166
255
|
}
|
|
167
256
|
|
|
168
257
|
async function getMyStats() {
|
|
169
|
-
const
|
|
170
|
-
|
|
171
|
-
|
|
258
|
+
const data = await mcpGet('stats');
|
|
259
|
+
return textResult(data);
|
|
260
|
+
}
|
|
172
261
|
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
262
|
+
async function createListing(args) {
|
|
263
|
+
const data = await mcpPost('create-listing', args);
|
|
264
|
+
return textResult(data);
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
async function updateListing(args) {
|
|
268
|
+
const data = await mcpPatch('update-listing', args);
|
|
269
|
+
return textResult(data);
|
|
179
270
|
}
|