tdk-api-wrapper 1.0.1 → 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/README.md +53 -6
- package/dist/chunk-2TA5PMVZ.mjs +741 -0
- package/dist/cli.js +683 -85
- package/dist/cli.mjs +222 -37
- package/dist/index.d.mts +173 -5
- package/dist/index.d.ts +173 -5
- package/dist/index.js +471 -52
- package/dist/index.mjs +9 -3
- package/package.json +1 -1
- package/src/cli.ts +227 -36
- package/src/errors.ts +38 -0
- package/src/index.ts +1 -0
- package/src/tdk.ts +449 -61
- package/src/types.ts +36 -0
- package/dist/chunk-MGSXCUAX.mjs +0 -325
package/dist/chunk-MGSXCUAX.mjs
DELETED
|
@@ -1,325 +0,0 @@
|
|
|
1
|
-
// src/tdk.ts
|
|
2
|
-
import * as fs from "fs";
|
|
3
|
-
import * as path from "path";
|
|
4
|
-
import * as os from "os";
|
|
5
|
-
var TDK = class {
|
|
6
|
-
static BASE_URL = "https://sozluk.gov.tr";
|
|
7
|
-
// Cache Mechanism
|
|
8
|
-
static isCacheEnabled = false;
|
|
9
|
-
static wordCache = /* @__PURE__ */ new Map();
|
|
10
|
-
static dailyContentCache = null;
|
|
11
|
-
static autocompleteCache = [];
|
|
12
|
-
/**
|
|
13
|
-
* Enables or disables in-memory caching for API requests.
|
|
14
|
-
*/
|
|
15
|
-
static enableCache(status = true) {
|
|
16
|
-
this.isCacheEnabled = status;
|
|
17
|
-
if (!status) {
|
|
18
|
-
this.clearCache();
|
|
19
|
-
}
|
|
20
|
-
}
|
|
21
|
-
/**
|
|
22
|
-
* Clears the internal cache.
|
|
23
|
-
*/
|
|
24
|
-
static clearCache() {
|
|
25
|
-
this.wordCache.clear();
|
|
26
|
-
this.dailyContentCache = null;
|
|
27
|
-
this.autocompleteCache = [];
|
|
28
|
-
}
|
|
29
|
-
static delay(ms) {
|
|
30
|
-
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
31
|
-
}
|
|
32
|
-
/**
|
|
33
|
-
* Fetches detailed information for a given word from the TDK Dictionary.
|
|
34
|
-
*/
|
|
35
|
-
static async getWord(word) {
|
|
36
|
-
if (!word || word.trim() === "") {
|
|
37
|
-
throw new Error("Word parameter cannot be empty.");
|
|
38
|
-
}
|
|
39
|
-
const cleanWord = word.trim().toLowerCase();
|
|
40
|
-
if (this.isCacheEnabled && this.wordCache.has(cleanWord)) {
|
|
41
|
-
return this.wordCache.get(cleanWord);
|
|
42
|
-
}
|
|
43
|
-
const url = `${this.BASE_URL}/gts?ara=${encodeURIComponent(cleanWord)}`;
|
|
44
|
-
try {
|
|
45
|
-
const response = await fetch(url, {
|
|
46
|
-
headers: { "User-Agent": "TDK-API-Nodejs-Wrapper/1.0" }
|
|
47
|
-
});
|
|
48
|
-
if (!response.ok)
|
|
49
|
-
throw new Error(`HTTP error! status: ${response.status}`);
|
|
50
|
-
const data = await response.json();
|
|
51
|
-
if (!Array.isArray(data) && data && "error" in data) {
|
|
52
|
-
if (this.isCacheEnabled)
|
|
53
|
-
this.wordCache.set(cleanWord, []);
|
|
54
|
-
return [];
|
|
55
|
-
}
|
|
56
|
-
const results = data;
|
|
57
|
-
if (this.isCacheEnabled) {
|
|
58
|
-
this.wordCache.set(cleanWord, results);
|
|
59
|
-
}
|
|
60
|
-
return results;
|
|
61
|
-
} catch (error) {
|
|
62
|
-
if (error instanceof Error)
|
|
63
|
-
throw new Error(`Failed to fetch word from TDK: ${error.message}`);
|
|
64
|
-
throw new Error("Failed to fetch word from TDK: Unknown error");
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
/**
|
|
68
|
-
* Helper method to get only the meanings (definitions) of a word as a string array.
|
|
69
|
-
*/
|
|
70
|
-
static async getMeanings(word) {
|
|
71
|
-
const results = await this.getWord(word);
|
|
72
|
-
if (results.length === 0)
|
|
73
|
-
return [];
|
|
74
|
-
const meanings = [];
|
|
75
|
-
for (const result of results) {
|
|
76
|
-
if (result.anlamlarListe) {
|
|
77
|
-
for (const anlam of result.anlamlarListe) {
|
|
78
|
-
if (anlam.anlam)
|
|
79
|
-
meanings.push(anlam.anlam);
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
}
|
|
83
|
-
return meanings;
|
|
84
|
-
}
|
|
85
|
-
/**
|
|
86
|
-
* Returns suggestions (autocomplete) for a given prefix.
|
|
87
|
-
*/
|
|
88
|
-
static async getSuggestions(prefix) {
|
|
89
|
-
if (this.autocompleteCache.length === 0) {
|
|
90
|
-
try {
|
|
91
|
-
const response = await fetch(`${this.BASE_URL}/autocomplete.json`, {
|
|
92
|
-
headers: { "User-Agent": "TDK-API-Nodejs-Wrapper/1.0" }
|
|
93
|
-
});
|
|
94
|
-
if (response.ok) {
|
|
95
|
-
const data = await response.json();
|
|
96
|
-
this.autocompleteCache = data.map((item) => item.madde);
|
|
97
|
-
}
|
|
98
|
-
} catch (e) {
|
|
99
|
-
return [];
|
|
100
|
-
}
|
|
101
|
-
}
|
|
102
|
-
const cleanPrefix = prefix.toLowerCase();
|
|
103
|
-
return this.autocompleteCache.filter((w) => w.toLowerCase().startsWith(cleanPrefix)).slice(0, 10);
|
|
104
|
-
}
|
|
105
|
-
/**
|
|
106
|
-
* Returns a list of proverbs and idioms containing the word.
|
|
107
|
-
*/
|
|
108
|
-
static async getProverbs(word) {
|
|
109
|
-
const results = await this.getWord(word);
|
|
110
|
-
if (results.length === 0)
|
|
111
|
-
return [];
|
|
112
|
-
const proverbs = [];
|
|
113
|
-
for (const result of results) {
|
|
114
|
-
if (result.atasozu) {
|
|
115
|
-
for (const atasoz of result.atasozu) {
|
|
116
|
-
if (atasoz.madde)
|
|
117
|
-
proverbs.push(atasoz.madde);
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
}
|
|
121
|
-
return proverbs;
|
|
122
|
-
}
|
|
123
|
-
/**
|
|
124
|
-
* Returns the etymological origin of the word if it's a foreign word.
|
|
125
|
-
*/
|
|
126
|
-
static async getOrigin(word) {
|
|
127
|
-
const results = await this.getWord(word);
|
|
128
|
-
if (results.length > 0 && results[0].lisan) {
|
|
129
|
-
return results[0].lisan;
|
|
130
|
-
}
|
|
131
|
-
return "T\xFCrk\xE7e";
|
|
132
|
-
}
|
|
133
|
-
/**
|
|
134
|
-
* Returns literature examples containing the word.
|
|
135
|
-
*/
|
|
136
|
-
static async getExamples(word) {
|
|
137
|
-
const results = await this.getWord(word);
|
|
138
|
-
const examples = [];
|
|
139
|
-
for (const result of results) {
|
|
140
|
-
if (result.anlamlarListe) {
|
|
141
|
-
for (const anlam of result.anlamlarListe) {
|
|
142
|
-
if (anlam.orneklerListe) {
|
|
143
|
-
for (const ornek of anlam.orneklerListe) {
|
|
144
|
-
const author = ornek.yazar && ornek.yazar.length > 0 ? ornek.yazar[0].tam_adi : null;
|
|
145
|
-
examples.push({ sentence: ornek.ornek, author });
|
|
146
|
-
}
|
|
147
|
-
}
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
}
|
|
151
|
-
return examples;
|
|
152
|
-
}
|
|
153
|
-
/**
|
|
154
|
-
* Returns the direct URL of the audio pronunciation if available.
|
|
155
|
-
* Note: TDK audio URL usually uses the exact audio id. Sometimes it requires MD5, but we provide a common pattern.
|
|
156
|
-
*/
|
|
157
|
-
static async getAudioUrl(word) {
|
|
158
|
-
const results = await this.getWord(word);
|
|
159
|
-
if (results.length > 0) {
|
|
160
|
-
return `https://sozluk.gov.tr/ses/${encodeURIComponent(word)}.wav`;
|
|
161
|
-
}
|
|
162
|
-
return null;
|
|
163
|
-
}
|
|
164
|
-
/**
|
|
165
|
-
* Downloads the audio pronunciation to the specified path.
|
|
166
|
-
*/
|
|
167
|
-
static async downloadAudio(word, destPath) {
|
|
168
|
-
const url = await this.getAudioUrl(word);
|
|
169
|
-
if (!url)
|
|
170
|
-
return null;
|
|
171
|
-
const finalPath = destPath || path.join(os.tmpdir(), `${word}.wav`);
|
|
172
|
-
try {
|
|
173
|
-
const res = await fetch(url);
|
|
174
|
-
if (!res.ok)
|
|
175
|
-
return null;
|
|
176
|
-
const buffer = await res.arrayBuffer();
|
|
177
|
-
fs.writeFileSync(finalPath, Buffer.from(buffer));
|
|
178
|
-
return finalPath;
|
|
179
|
-
} catch {
|
|
180
|
-
return null;
|
|
181
|
-
}
|
|
182
|
-
}
|
|
183
|
-
/**
|
|
184
|
-
* Checks spelling and returns suggestions if wrong.
|
|
185
|
-
*/
|
|
186
|
-
static async checkSpelling(word) {
|
|
187
|
-
const results = await this.getWord(word);
|
|
188
|
-
if (results.length > 0) {
|
|
189
|
-
return { isCorrect: true, word };
|
|
190
|
-
}
|
|
191
|
-
const daily = await this.getDailyContent();
|
|
192
|
-
if (daily) {
|
|
193
|
-
const syydMatch = daily.syyd.find((s) => s.yanliskelime.toLowerCase() === word.toLowerCase());
|
|
194
|
-
if (syydMatch) {
|
|
195
|
-
return { isCorrect: false, word, suggestion: syydMatch.dogrukelime };
|
|
196
|
-
}
|
|
197
|
-
const mixMatch = daily.karistirma.find((s) => s.yanlis.toLowerCase() === word.toLowerCase());
|
|
198
|
-
if (mixMatch) {
|
|
199
|
-
return { isCorrect: false, word, suggestion: mixMatch.dogru };
|
|
200
|
-
}
|
|
201
|
-
}
|
|
202
|
-
return { isCorrect: false, word };
|
|
203
|
-
}
|
|
204
|
-
/**
|
|
205
|
-
* Fetches daily content (word of the day, proverbs, rules, etc).
|
|
206
|
-
*/
|
|
207
|
-
static async getDailyContent() {
|
|
208
|
-
if (this.isCacheEnabled && this.dailyContentCache)
|
|
209
|
-
return this.dailyContentCache;
|
|
210
|
-
try {
|
|
211
|
-
const response = await fetch(`${this.BASE_URL}/icerik`, {
|
|
212
|
-
headers: { "User-Agent": "TDK-API-Nodejs-Wrapper/1.0" }
|
|
213
|
-
});
|
|
214
|
-
if (response.ok) {
|
|
215
|
-
const data = await response.json();
|
|
216
|
-
if (this.isCacheEnabled)
|
|
217
|
-
this.dailyContentCache = data;
|
|
218
|
-
return data;
|
|
219
|
-
}
|
|
220
|
-
} catch {
|
|
221
|
-
return null;
|
|
222
|
-
}
|
|
223
|
-
return null;
|
|
224
|
-
}
|
|
225
|
-
/**
|
|
226
|
-
* Returns compound words that contain this word.
|
|
227
|
-
*/
|
|
228
|
-
static async getCompoundWords(word) {
|
|
229
|
-
const results = await this.getWord(word);
|
|
230
|
-
if (results.length === 0)
|
|
231
|
-
return [];
|
|
232
|
-
const compound = [];
|
|
233
|
-
for (const result of results) {
|
|
234
|
-
if (result.birlesikler) {
|
|
235
|
-
const words = result.birlesikler.split(",").map((w) => w.trim());
|
|
236
|
-
compound.push(...words);
|
|
237
|
-
}
|
|
238
|
-
}
|
|
239
|
-
return [...new Set(compound)];
|
|
240
|
-
}
|
|
241
|
-
/**
|
|
242
|
-
* Returns the part of speech (isim, sıfat, zarf vb.).
|
|
243
|
-
*/
|
|
244
|
-
static async getPartOfSpeech(word) {
|
|
245
|
-
const results = await this.getWord(word);
|
|
246
|
-
const pos = /* @__PURE__ */ new Set();
|
|
247
|
-
for (const result of results) {
|
|
248
|
-
if (result.anlamlarListe) {
|
|
249
|
-
for (const anlam of result.anlamlarListe) {
|
|
250
|
-
if (anlam.ozelliklerListe) {
|
|
251
|
-
for (const ozellik of anlam.ozelliklerListe) {
|
|
252
|
-
pos.add(ozellik.tam_adi);
|
|
253
|
-
}
|
|
254
|
-
}
|
|
255
|
-
}
|
|
256
|
-
}
|
|
257
|
-
}
|
|
258
|
-
if (pos.size === 0 && results.length > 0) {
|
|
259
|
-
pos.add("isim");
|
|
260
|
-
}
|
|
261
|
-
return Array.from(pos);
|
|
262
|
-
}
|
|
263
|
-
/**
|
|
264
|
-
* Fetches multiple words concurrently with a small delay to avoid rate limiting.
|
|
265
|
-
*/
|
|
266
|
-
static async getWordsBatch(words) {
|
|
267
|
-
const results = [];
|
|
268
|
-
for (const word of words) {
|
|
269
|
-
try {
|
|
270
|
-
const res = await this.getWord(word);
|
|
271
|
-
results.push(res);
|
|
272
|
-
} catch {
|
|
273
|
-
results.push([]);
|
|
274
|
-
}
|
|
275
|
-
await this.delay(200);
|
|
276
|
-
}
|
|
277
|
-
return results;
|
|
278
|
-
}
|
|
279
|
-
/**
|
|
280
|
-
* Syllabicates a Turkish word based on general grammar rules.
|
|
281
|
-
*/
|
|
282
|
-
static syllabicate(word) {
|
|
283
|
-
const vowels = /[aeıioöuüAEIİOÖUÜ]/;
|
|
284
|
-
const result = [];
|
|
285
|
-
let currentSyllable = "";
|
|
286
|
-
for (let i = word.length - 1; i >= 0; i--) {
|
|
287
|
-
currentSyllable = word[i] + currentSyllable;
|
|
288
|
-
if (vowels.test(word[i])) {
|
|
289
|
-
if (i - 1 >= 0 && !vowels.test(word[i - 1])) {
|
|
290
|
-
if (i - 2 >= 0 && vowels.test(word[i - 2])) {
|
|
291
|
-
currentSyllable = word[i - 1] + currentSyllable;
|
|
292
|
-
i--;
|
|
293
|
-
} else if (i - 2 >= 0 && !vowels.test(word[i - 2])) {
|
|
294
|
-
currentSyllable = word[i - 1] + currentSyllable;
|
|
295
|
-
i--;
|
|
296
|
-
}
|
|
297
|
-
}
|
|
298
|
-
result.unshift(currentSyllable);
|
|
299
|
-
currentSyllable = "";
|
|
300
|
-
}
|
|
301
|
-
}
|
|
302
|
-
if (currentSyllable) {
|
|
303
|
-
if (result.length > 0) {
|
|
304
|
-
result[0] = currentSyllable + result[0];
|
|
305
|
-
} else {
|
|
306
|
-
result.push(currentSyllable);
|
|
307
|
-
}
|
|
308
|
-
}
|
|
309
|
-
return result;
|
|
310
|
-
}
|
|
311
|
-
/**
|
|
312
|
-
* Checks if a word follows Turkish Major Vowel Harmony (Büyük Ünlü Uyumu).
|
|
313
|
-
*/
|
|
314
|
-
static checkVowelHarmony(word) {
|
|
315
|
-
const backVowels = /[aıou]/i;
|
|
316
|
-
const frontVowels = /[eiöü]/i;
|
|
317
|
-
const hasBack = backVowels.test(word);
|
|
318
|
-
const hasFront = frontVowels.test(word);
|
|
319
|
-
return !(hasBack && hasFront);
|
|
320
|
-
}
|
|
321
|
-
};
|
|
322
|
-
|
|
323
|
-
export {
|
|
324
|
-
TDK
|
|
325
|
-
};
|