@appaflytech/zeyrek-ai-mcp 0.0.3 → 0.0.4

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.
Files changed (35) hide show
  1. package/.env.example +21 -7
  2. package/.env.production.example +42 -0
  3. package/README.md +14 -7
  4. package/dist/config.js +113 -47
  5. package/dist/knowledge/componentCatalog.js +474 -31
  6. package/dist/knowledge/componentEvents.js +150 -12
  7. package/dist/knowledge/errorPath.js +64 -0
  8. package/dist/knowledge/normalize.js +12 -1
  9. package/dist/knowledge/outlines.js +6 -0
  10. package/dist/knowledge/rules.js +184 -3
  11. package/dist/knowledge/styleResolve.js +485 -0
  12. package/dist/observability/trace.js +4 -0
  13. package/dist/platform/http.js +3 -0
  14. package/dist/platform/responses.js +80 -4
  15. package/dist/platform/screenshot.js +106 -0
  16. package/dist/resources/examples/layout-app-shell.json +368 -0
  17. package/dist/resources/examples/microservice-table-list.json +1 -0
  18. package/dist/resources/examples/middleware-authenticate.json +243 -47
  19. package/dist/resources/examples/workflow-basic.json +24 -2
  20. package/dist/resources/guides/component.md +6 -3
  21. package/dist/resources/guides/external-component.md +129 -0
  22. package/dist/resources/guides/layout.md +147 -0
  23. package/dist/resources/guides/microservice.md +35 -0
  24. package/dist/resources/guides/middleware.md +10 -0
  25. package/dist/resources/guides/page.md +132 -14
  26. package/dist/resources/guides/workflow.md +127 -2
  27. package/dist/server.js +2 -0
  28. package/dist/tools/externalComponents.js +285 -0
  29. package/dist/tools/layouts.js +48 -6
  30. package/dist/tools/microservices.js +2 -2
  31. package/dist/tools/pages.js +98 -30
  32. package/dist/tools/platformInfo.js +2 -2
  33. package/dist/tools/screens.js +36 -0
  34. package/dist/tools/workflows.js +3 -3
  35. package/package.json +4 -1
package/.env.example CHANGED
@@ -1,17 +1,24 @@
1
+ # LOKAL PROFIL — platform/gateway kodu gelistirirken. Uzak ortam icin:
2
+ # cp zeyrek-mcp/.env.production.example .env
3
+ # Ortam rolleri: docs/ortam.md
4
+
1
5
  # Platform API adresleri (host makinesinden lokal compose icin)
2
- ORG_API_BASE_URL=http://localhost:7000
3
- TENANT_API_BASE_URL=http://localhost:5000
6
+ ORG_API_BASE_URL=http://localhost:17000
7
+ TENANT_API_BASE_URL=http://localhost:15000
4
8
 
5
9
  # Org cozumu: istekler Host: {ORGANIZATION}.{HOST_SUFFIX} header'i ile gider
6
- ORGANIZATION=zeyrek-local
10
+ ORGANIZATION=zeyrek-test
7
11
  HOST_SUFFIX=localhost
8
12
 
9
- # Varsayilanlar; tool parametresi her zaman ezer
10
- DEFAULT_ENVIRONMENT=production
13
+ # ZORUNLU. Gomulu varsayilan yok: bos birakilirsa sunucu acilmaz.
14
+ # AI yazmalari her zaman development'a gider (AGENTS.md 1).
15
+ DEFAULT_ENVIRONMENT=development
11
16
  DEFAULT_PROJECT=
12
17
 
13
18
  # local: kimlik asagidaki alanlardan, passthrough: istemcinin Authorization header'i aynen gecer
14
19
  # local modda ya TOKEN (hazir Bearer JWT) ya da USERNAME+PASSWORD verin
20
+ # NOT: USERNAME isletim sisteminde de tanimli olabilir (Windows her zaman, macOS sik sik).
21
+ # Sunucu, USER/LOGNAME ile AYNI olan USERNAME'i dusurur; asagidaki deger yine de gecerli olur.
15
22
  AUTH_MODE=local
16
23
  TOKEN=
17
24
  USERNAME=
@@ -33,13 +40,20 @@ LOG_MAX_BODY_CHARS=2000
33
40
  MAX_RESPONSE_BYTES=262144
34
41
  REQUEST_TIMEOUT_MS=100000
35
42
 
43
+ # page_screenshot icin: Studio arayuzunun kok adresi (yerel gelistirmede http://localhost:3000).
44
+ # Bos birakilirsa tool anlasilir hata doner; ilk kullanimda `npx playwright-core install chromium`
45
+ # gerekir. SCREENSHOT_BROWSER_PATH ile playwright indirmesi yerine sistemdeki Chromium kullanilir.
46
+ # Lokal Studio org'u Host'tan cozer; screenshot icin uzak host gerekebilir (docs/ortam.md).
47
+ STUDIO_BASE_URL=http://localhost:3000
48
+ SCREENSHOT_BROWSER_PATH=
49
+
36
50
  # generate-schemas icin swagger adresleri. Bos birakilirsa sirayla denenir:
37
51
  # 1) asagidaki override, 2) {API_BASE_URL}/swagger/v1/swagger.json, 3) localhost:3000 frontend proxy'si
38
52
  ORG_SWAGGER_URL=
39
53
  TENANT_SWAGGER_URL=
40
54
 
41
- # Bos = tum moduller (148 tool). Hazir kumeler: core (veri+mantik, 92), studio (sayfa
42
- # tasarimi, 45), admin (template/organizasyon/deployment, 15). Kume ve tekil modul adi
55
+ # Bos = tum moduller (149 tool). Hazir kumeler: core (veri+mantik, 92), studio (sayfa
56
+ # tasarimi, 46), admin (template/organizasyon/deployment, 15). Kume ve tekil modul adi
43
57
  # karisik yazilabilir. Ornek: core,studio | entity,row,microservice
44
58
  MODULES=
45
59
 
@@ -0,0 +1,42 @@
1
+ # UZAK PROFIL — kosular, uygulama kurulumu, gercek-ekran dogrulama, demo.
2
+ # Kurulum: cp zeyrek-mcp/.env.production.example .env (sonra PASSWORD'u doldurun)
3
+ # Ortam rolleri: docs/ortam.md
4
+ #
5
+ # "production" burada PLATFORM KURULUMUNUN adidir. AI'in yazma hedefi orada da
6
+ # development environment'idir — asagidaki DEFAULT_ENVIRONMENT bu yuzden development.
7
+
8
+ ORG_API_BASE_URL=https://new-zeyrek.glomil.com/api/org
9
+ TENANT_API_BASE_URL=https://new-zeyrek.glomil.com/api
10
+
11
+ ORGANIZATION=new-zeyrek
12
+ HOST_SUFFIX=glomil.com
13
+
14
+ # ZORUNLU. Gomulu varsayilan yok.
15
+ DEFAULT_ENVIRONMENT=development
16
+ DEFAULT_PROJECT=
17
+
18
+ AUTH_MODE=local
19
+ TOKEN=
20
+ USERNAME=admin@zeyrek.com
21
+ PASSWORD=
22
+
23
+ POLICY=strict
24
+
25
+ LOG_LEVEL=detail
26
+ LOG_DIR=zeyrek-mcp/logs
27
+ LOG_FILE=
28
+ LOG_MAX_BODY_CHARS=2000
29
+
30
+ MAX_RESPONSE_BYTES=262144
31
+ REQUEST_TIMEOUT_MS=100000
32
+
33
+ # page_screenshot icin gercek Studio host'u (localhost:3000 org'u cozemez — 27/S-22).
34
+ STUDIO_BASE_URL=https://new-zeyrek.glomil.com
35
+ SCREENSHOT_BROWSER_PATH=
36
+
37
+ ORG_SWAGGER_URL=
38
+ TENANT_SWAGGER_URL=
39
+
40
+ MODULES=
41
+
42
+ MCP_PORT=5100
package/README.md CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  NgApps platformunu MCP tool'ları olarak sunan bağımsız gateway — veri/mantık tarafı (project,
4
4
  application, datasource, entity, row, microservice, query, workflow, automation, dto, view) ve
5
- Studio tasarım tarafı (page, component, flow, layout, variable, folder, file) birlikte, **152
5
+ Studio tasarım tarafı (page, component, flow, layout, variable, folder, file) birlikte, **162
6
6
  tool / 24 modül**. Durum + yol haritası:
7
7
  [`docs/00-durum-ve-yol-haritasi.md`](docs/00-durum-ve-yol-haritasi.md);
8
8
  tasarım: [`docs/`](docs/01-vizyon-ve-kapsam.md). Platform koduna
@@ -36,6 +36,8 @@ kurulum](#npm-paketi-olarak-kurulum). Asgari şunlar gerekir:
36
36
  | `ORGANIZATION` | `zeyrek-local` | Org subdomain'i; istekler `Host: {org}.{suffix}` ile gider |
37
37
  | `USERNAME` / `PASSWORD` | | `/connect/token` ile takas edilir (AuthMode=local) |
38
38
  | `DEFAULT_PROJECT` | `crm` | Opsiyonel; tool'daki `project` parametresi her zaman ezer |
39
+ | `STUDIO_BASE_URL` | `http://localhost:3000` | Opsiyonel; yalnız `page_screenshot` kullanır — Studio arayüzünün kök adresi ([`docs/26`](docs/26-sayfa-ekran-goruntusu.md)) |
40
+ | `SCREENSHOT_BROWSER_PATH` | `/usr/bin/chromium-browser` | Opsiyonel; `page_screenshot` için sistemdeki Chromium ikilisinin yolu (verilmezse playwright-core'un indirdiği tarayıcı) |
39
41
 
40
42
  ## Çalıştırma
41
43
 
@@ -69,7 +71,8 @@ okuyabilmek.
69
71
  Adım etiketleri: `politika` (lint kuralları; `politika ✕` isteği hiç göndermez), `düzeltme`
70
72
  (gateway'in gövdeye uyguladığı otomatik düzeltmeler — yanıttaki `gatewayNormalized`), `kimlik →/←`
71
73
  (`/connect/token` turu), `istek →/yanıt ←` (platform API turu, tam URL + süre + boyut),
72
- `kırpma ✂` (yanıt `MAX_RESPONSE_BYTES` sınırını aştı), `hata ✕` (yakalanan hata: sınıf,
74
+ `kırpma ✂` (yanıt `MAX_RESPONSE_BYTES` sınırını aştı), `tarayıcı →/←` (`page_screenshot`'ın
75
+ headless Chromium turu: açılan URL, viewport, PNG boyutu), `hata ✕` (yakalanan hata: sınıf,
73
76
  HTTP kodu, mesaj, ilk 3 stack satırı). Tool gövdesine hiç girmeyen çağrılar — yanlış tool adı ya da
74
77
  parametre şemasına takılan gövde — `MCP KATMANI REDDETTİ` bloğu olarak düşer; bunlar aksi hâlde
75
78
  hiçbir yerde görünmezdi.
@@ -145,9 +148,13 @@ pakette `.env` yoktur, tüm ayarlar env bloğundan gelir.
145
148
  - Boş bırakılan (`""`) alanlar **tanımsız** sayılır; varsayılana düşer ya da `.env`'den
146
149
  doldurulur. Yani `"${MODULES:-}"` yazmak alanı hiç yazmamakla aynıdır.
147
150
  - Değişken adları ön eksizdir (`USERNAME`, `PASSWORD`, `TOKEN`, `LOG_LEVEL` …), yani kabuk
148
- ortamındaki aynı adlı değişkenlerle çakışabilir — `USERNAME` Windows'ta yerleşiktir. Bu yüzden
149
- `.mcp.json`'da `${USERNAME:-…}` gibi genişletme kullanmayın; değeri düz yazın ya da `.env`'e
150
- koyun.
151
+ ortamındaki aynı adlı değişkenlerle çakışabilir — `USERNAME` Windows'ta yerleşiktir, macOS
152
+ kabukları da sık sık tanımlar. Bu yüzden `.mcp.json`'da `${USERNAME:-…}` gibi genişletme
153
+ kullanmayın; değeri düz yazın.
154
+ `USERNAME` işletim sisteminin kullanıcı adıyla (`USER`/`LOGNAME`) AYNIYSA sunucu onu düşürür ve
155
+ `.env`'deki değer geçerli olur — bu guard olmadan terminalden `npm run dev` çalıştırmak kimliği
156
+ makine kullanıcısı adıyla almaya kalkıyor ve `POST /connect/token` 404 dönüyordu. Hata metni
157
+ "kayıt bulunamadı" olduğu için kimlik ayarına değil veriye işaret ediyor, teşhisi zorlaştırıyordu.
151
158
  - `LOG_DIR` verilmezse günlükler **çalışma dizininin** altındaki `logs/` klasörüne yazılır.
152
159
  - Konfigürasyon geçersizse sunucu stderr'e tek satır sebep yazıp `exit 1` yapar — istemci artık
153
160
  sessizce sıfır tool ile bağlanmaz.
@@ -183,7 +190,7 @@ npm publish # prepack: tsc -p tsconfig.build.json + varlık kopyalama
183
190
  `component_update` kaydı önce okur, yalnız verdiğiniz alanları değiştirir; şema/olay kaybı
184
191
  olmaz. `flow_*` uçlarının istediği barındırıcı gövdesini de gateway kurar.
185
192
  - Tool seti `MODULES` ile daraltılabilir: tekil modül adı (`entity,row,microservice`)
186
- ya da hazır küme — `core` (92 tool: veri + mantık), `studio` (49 tool: sayfa tasarımı),
193
+ ya da hazır küme — `core` (92 tool: veri + mantık), `studio` (50 tool: sayfa tasarımı),
187
194
  `admin` (15 tool: template, organizasyon, deployment). Küme ve modül adları karışık
188
195
  yazılabilir: `MODULES=core,page`.
189
196
 
@@ -193,7 +200,7 @@ Tasarım: [`docs/07-bilgi-katmani.md`](docs/07-bilgi-katmani.md).
193
200
  Üç savunma hattı:
194
201
 
195
202
  - **Rehberler:** `platform_guide` tool'u (workflow, microservice, entity, page, component,
196
- html, middleware, view, expressions, getting-started, modify-existing) + `ngapps://guides/*`
203
+ html, layout, middleware, view, expressions, getting-started, modify-existing) + `ngapps://guides/*`
197
204
  resource'ları. Bir modülde ilk yazma işleminden önce ilgili rehber okunmalı; tool
198
205
  açıklamaları bunu söyler. Komponent davranış bilgisi ayrıca `component_get` çıktısında
199
206
  `knowledge` alanı olarak döner (`src/knowledge/componentCatalog.ts`).
package/dist/config.js CHANGED
@@ -1,35 +1,62 @@
1
- import { z } from 'zod';
1
+ import { z } from "zod";
2
2
  export const moduleNames = [
3
- 'platform',
4
- 'project',
5
- 'application',
6
- 'datasource',
7
- 'entity',
8
- 'row',
9
- 'microservice',
10
- 'query',
11
- 'workflow',
12
- 'automation',
13
- 'dto',
14
- 'view',
15
- 'page',
16
- 'component',
17
- 'flow',
18
- 'layout',
19
- 'variable',
20
- 'folder',
21
- 'file',
22
- 'access',
23
- 'translation',
24
- 'template',
25
- 'organization',
26
- 'dependency',
27
- 'deployment'
3
+ "platform",
4
+ "project",
5
+ "application",
6
+ "datasource",
7
+ "entity",
8
+ "row",
9
+ "microservice",
10
+ "query",
11
+ "workflow",
12
+ "automation",
13
+ "dto",
14
+ "view",
15
+ "page",
16
+ "component",
17
+ "externalComponent",
18
+ "flow",
19
+ "layout",
20
+ "variable",
21
+ "folder",
22
+ "file",
23
+ "access",
24
+ "translation",
25
+ "template",
26
+ "organization",
27
+ "dependency",
28
+ "deployment",
28
29
  ];
29
30
  export const modulePresets = {
30
- core: ['platform', 'project', 'application', 'datasource', 'entity', 'row', 'microservice', 'query', 'workflow', 'automation', 'dto', 'view', 'dependency'],
31
- studio: ['platform', 'page', 'component', 'flow', 'layout', 'variable', 'folder', 'file', 'access', 'translation'],
32
- admin: ['platform', 'template', 'organization', 'deployment']
31
+ core: [
32
+ "platform",
33
+ "project",
34
+ "application",
35
+ "datasource",
36
+ "entity",
37
+ "row",
38
+ "microservice",
39
+ "query",
40
+ "workflow",
41
+ "automation",
42
+ "dto",
43
+ "view",
44
+ "dependency",
45
+ ],
46
+ studio: [
47
+ "platform",
48
+ "page",
49
+ "component",
50
+ "externalComponent",
51
+ "flow",
52
+ "layout",
53
+ "variable",
54
+ "folder",
55
+ "file",
56
+ "access",
57
+ "translation",
58
+ ],
59
+ admin: ["platform", "template", "organization", "deployment"],
33
60
  };
34
61
  function expandModuleNames(entries) {
35
62
  const modules = [];
@@ -52,22 +79,24 @@ const environmentSchema = z.object({
52
79
  ORG_API_BASE_URL: z.string().url(),
53
80
  TENANT_API_BASE_URL: z.string().url(),
54
81
  ORGANIZATION: z.string().min(1),
55
- HOST_SUFFIX: z.string().min(1).default('localhost'),
56
- DEFAULT_ENVIRONMENT: z.string().min(1).default('production'),
82
+ HOST_SUFFIX: z.string().min(1).default("localhost"),
83
+ DEFAULT_ENVIRONMENT: z.string().min(1),
57
84
  DEFAULT_PROJECT: z.string().optional(),
58
- AUTH_MODE: z.enum(['local', 'passthrough']).default('local'),
85
+ AUTH_MODE: z.enum(["local", "passthrough"]).default("local"),
59
86
  TOKEN: z.string().optional(),
60
87
  USERNAME: z.string().optional(),
61
88
  PASSWORD: z.string().optional(),
62
- POLICY: z.enum(['strict', 'warn', 'off']).default('strict'),
89
+ POLICY: z.enum(["strict", "warn", "off"]).default("strict"),
63
90
  MAX_RESPONSE_BYTES: z.coerce.number().int().positive().default(262144),
64
91
  REQUEST_TIMEOUT_MS: z.coerce.number().int().positive().default(100000),
65
92
  MODULES: z.string().optional(),
66
- LOG_LEVEL: z.enum(['off', 'summary', 'detail']).default('detail'),
93
+ LOG_LEVEL: z.enum(["off", "summary", "detail"]).default("detail"),
67
94
  LOG_DIR: z.string().min(1).optional(),
68
95
  LOG_FILE: z.string().min(1).optional(),
69
96
  LOG_MAX_BODY_CHARS: z.coerce.number().int().positive().default(2000),
70
- MCP_PORT: z.coerce.number().int().positive().default(5100)
97
+ MCP_PORT: z.coerce.number().int().positive().default(5100),
98
+ STUDIO_BASE_URL: z.string().url().optional(),
99
+ SCREENSHOT_BROWSER_PATH: z.string().min(1).optional(),
71
100
  });
72
101
  export const environmentKeys = Object.keys(environmentSchema.shape);
73
102
  /**
@@ -76,38 +105,73 @@ export const environmentKeys = Object.keys(environmentSchema.shape);
76
105
  * kullanılamazdır: boş string (README §Ayar öncelik sırası: boş = tanımsız) ve genişletilmemiş
77
106
  * `${VAR:-…}` yer tutucusu — Claude Code bu sözdizimini açar, VS Code'un kendi MCP istemcisi
78
107
  * açmadan olduğu gibi geçirir ve düşürülmezse konfigürasyon doğrulaması yer tutucu metinle patlar.
108
+ *
109
+ * Üçüncü hâl `USERNAME`'e özeldir: bu ad işletim sistemine ait. Windows onu HER ZAMAN, macOS
110
+ * kabukları da sık sık oturum açan kullanıcının adıyla tanımlar. dotenv mevcut anahtarı ezmediği
111
+ * için `.env`'deki `USERNAME=admin@…` sessizce yok sayılır ve gateway, kimliği makine kullanıcısı
112
+ * adıyla almaya çalışıp `POST /connect/token` üzerinden 404 alır — hata mesajı da "kayıt
113
+ * bulunamadı" dediği için kimlik ayarına değil, veriye işaret eder. `USERNAME` yalnız işletim
114
+ * sisteminin kullanıcı adıyla AYNIYSA düşürülür: gerçekten o adla giren bir kurulum zaten
115
+ * `.env`/`.mcp.json`'da aynı değeri yazar ve dosyadan geri okunur.
79
116
  */
80
117
  export function dropUnusableEnvironment(env) {
81
118
  for (const key of environmentKeys) {
82
119
  const value = env[key];
83
- if (value === '' || (value !== undefined && /^\$\{[^}]*\}$/.test(value))) {
120
+ if (value === "" || (value !== undefined && /^\$\{[^}]*\}$/.test(value))) {
84
121
  delete env[key];
85
122
  }
86
123
  }
124
+ const osUser = env.USER ?? env.LOGNAME;
125
+ if (env.USERNAME !== undefined && env.USERNAME === osUser) {
126
+ delete env.USERNAME;
127
+ }
128
+ }
129
+ /**
130
+ * "Boş = tanımsız" kuralını `.env`'den gelen değerlere de uygular. `dropUnusableEnvironment`
131
+ * yalnız süreç ortamına, yani dotenv ÖNCESİNE bakar; `.env`'deki `LOG_FILE=` gibi boş bir satırı
132
+ * dotenv sonradan boş string olarak yazar ve `.min(1)` şemaları patlar. `.env.example` bu
133
+ * anahtarları boş gönderdiği için kopyalayan her kurulum açılmayan bir gateway alıyordu.
134
+ * USERNAME kuralı bilerek burada tekrarlanmaz: o, dotenv'den ÖNCE bir kez uygulanmalıdır ki
135
+ * `.env`'deki kimlik işletim sistemininkiyle aynı olduğunda düşürülmesin.
136
+ */
137
+ function withoutEmptyValues(env) {
138
+ const copy = { ...env };
139
+ for (const key of environmentKeys) {
140
+ if (copy[key] === "")
141
+ delete copy[key];
142
+ }
143
+ return copy;
87
144
  }
88
145
  export function loadConfig(env) {
89
- const parsed = environmentSchema.safeParse(env);
146
+ const parsed = environmentSchema.safeParse(withoutEmptyValues(env));
90
147
  if (!parsed.success) {
91
- const missing = parsed.error.issues.map(issue => `${issue.path.join('.')}: ${issue.message}`).join('; ');
148
+ const missing = parsed.error.issues
149
+ .map((issue) => `${issue.path.join(".")}: ${issue.message}`)
150
+ .join("; ");
92
151
  throw new Error(`Gateway konfigürasyonu geçersiz — ${missing}. Gerekli değişkenler için zeyrek-mcp/.env.example dosyasına bakın.`);
93
152
  }
94
153
  const values = parsed.data;
95
- if (values.AUTH_MODE === 'local' && !values.TOKEN && (!values.USERNAME || !values.PASSWORD)) {
96
- throw new Error('AUTH_MODE=local için TOKEN ya da USERNAME + PASSWORD zorunludur.');
154
+ if (values.AUTH_MODE === "local" &&
155
+ !values.TOKEN &&
156
+ (!values.USERNAME || !values.PASSWORD)) {
157
+ throw new Error("AUTH_MODE=local için TOKEN ya da USERNAME + PASSWORD zorunludur.");
97
158
  }
98
- if (values.AUTH_MODE === 'passthrough' && (values.TOKEN || values.USERNAME || values.PASSWORD)) {
99
- throw new Error('AUTH_MODE=passthrough iken TOKEN/USERNAME/PASSWORD tanımlanamaz — kimlik istemciden gelir.');
159
+ if (values.AUTH_MODE === "passthrough" &&
160
+ (values.TOKEN || values.USERNAME || values.PASSWORD)) {
161
+ throw new Error("AUTH_MODE=passthrough iken TOKEN/USERNAME/PASSWORD tanımlanamaz — kimlik istemciden gelir.");
100
162
  }
101
163
  const requested = values.MODULES
102
- ? values.MODULES.split(',').map(name => name.trim()).filter(name => name.length > 0)
164
+ ? values.MODULES.split(",")
165
+ .map((name) => name.trim())
166
+ .filter((name) => name.length > 0)
103
167
  : [...moduleNames];
104
168
  const { modules, unknown: unknownModules } = expandModuleNames(requested);
105
169
  if (unknownModules.length > 0) {
106
- throw new Error(`MODULES bilinmeyen modül/küme içeriyor: ${unknownModules.join(', ')}. Kümeler: ${Object.keys(modulePresets).join(', ')}. Modüller: ${moduleNames.join(', ')}.`);
170
+ throw new Error(`MODULES bilinmeyen modül/küme içeriyor: ${unknownModules.join(", ")}. Kümeler: ${Object.keys(modulePresets).join(", ")}. Modüller: ${moduleNames.join(", ")}.`);
107
171
  }
108
172
  return {
109
- orgApiBaseUrl: values.ORG_API_BASE_URL.replace(/\/+$/, ''),
110
- tenantApiBaseUrl: values.TENANT_API_BASE_URL.replace(/\/+$/, ''),
173
+ orgApiBaseUrl: values.ORG_API_BASE_URL.replace(/\/+$/, ""),
174
+ tenantApiBaseUrl: values.TENANT_API_BASE_URL.replace(/\/+$/, ""),
111
175
  organization: values.ORGANIZATION,
112
176
  hostSuffix: values.HOST_SUFFIX,
113
177
  defaultEnvironment: values.DEFAULT_ENVIRONMENT,
@@ -124,6 +188,8 @@ export function loadConfig(env) {
124
188
  logDirectory: values.LOG_DIR,
125
189
  logFile: values.LOG_FILE,
126
190
  logMaxBodyChars: values.LOG_MAX_BODY_CHARS,
127
- port: values.MCP_PORT
191
+ port: values.MCP_PORT,
192
+ studioBaseUrl: values.STUDIO_BASE_URL?.replace(/\/+$/, ""),
193
+ screenshotBrowserPath: values.SCREENSHOT_BROWSER_PATH,
128
194
  };
129
195
  }