@thanh01.pmt/interactive-quiz-kit 1.0.89 → 1.1.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/dist/index.mjs CHANGED
@@ -1,3 +1,4 @@
1
+ import i18n from 'i18next';
1
2
  import { initReactI18next } from 'react-i18next';
2
3
  import LanguageDetector from 'i18next-browser-languagedetector';
3
4
  import { GoogleGenerativeAI } from '@google/generative-ai';
@@ -182,10 +183,10 @@ var require_util = __commonJS({
182
183
  return typeof arg === "number";
183
184
  }
184
185
  exports$1.isNumber = isNumber2;
185
- function isString2(arg) {
186
+ function isString(arg) {
186
187
  return typeof arg === "string";
187
188
  }
188
- exports$1.isString = isString2;
189
+ exports$1.isString = isString;
189
190
  function isSymbol(arg) {
190
191
  return typeof arg === "symbol";
191
192
  }
@@ -275,8 +276,8 @@ var require_inherits = __commonJS({
275
276
  // ../../node_modules/.pnpm/readable-stream@2.3.8/node_modules/readable-stream/lib/internal/streams/BufferList.js
276
277
  var require_BufferList = __commonJS({
277
278
  "../../node_modules/.pnpm/readable-stream@2.3.8/node_modules/readable-stream/lib/internal/streams/BufferList.js"(exports$1, module) {
278
- function _classCallCheck(instance2, Constructor) {
279
- if (!(instance2 instanceof Constructor)) {
279
+ function _classCallCheck(instance, Constructor) {
280
+ if (!(instance instanceof Constructor)) {
280
281
  throw new TypeError("Cannot call a class as a function");
281
282
  }
282
283
  }
@@ -3745,18 +3746,18 @@ var require_crc32 = __commonJS({
3745
3746
  }
3746
3747
  var crcTable = makeTable();
3747
3748
  function crc32(crc, buf, len, pos) {
3748
- var t2 = crcTable, end = pos + len;
3749
+ var t = crcTable, end = pos + len;
3749
3750
  crc = crc ^ -1;
3750
3751
  for (var i = pos; i < end; i++) {
3751
- crc = crc >>> 8 ^ t2[(crc ^ buf[i]) & 255];
3752
+ crc = crc >>> 8 ^ t[(crc ^ buf[i]) & 255];
3752
3753
  }
3753
3754
  return crc ^ -1;
3754
3755
  }
3755
3756
  function crc32str(crc, str, len, pos) {
3756
- var t2 = crcTable, end = pos + len;
3757
+ var t = crcTable, end = pos + len;
3757
3758
  crc = crc ^ -1;
3758
3759
  for (var i = pos; i < end; i++) {
3759
- crc = crc >>> 8 ^ t2[(crc ^ str.charCodeAt(i)) & 255];
3760
+ crc = crc >>> 8 ^ t[(crc ^ str.charCodeAt(i)) & 255];
3760
3761
  }
3761
3762
  return crc ^ -1;
3762
3763
  }
@@ -4743,10 +4744,10 @@ var require_crc322 = __commonJS({
4743
4744
  }
4744
4745
  var crcTable = makeTable();
4745
4746
  function crc32(crc, buf, len, pos) {
4746
- var t2 = crcTable, end = pos + len;
4747
+ var t = crcTable, end = pos + len;
4747
4748
  crc ^= -1;
4748
4749
  for (var i = pos; i < end; i++) {
4749
- crc = crc >>> 8 ^ t2[(crc ^ buf[i]) & 255];
4750
+ crc = crc >>> 8 ^ t[(crc ^ buf[i]) & 255];
4750
4751
  }
4751
4752
  return crc ^ -1;
4752
4753
  }
@@ -6904,7 +6905,7 @@ var require_inflate = __commonJS({
6904
6905
  state.distcode = distfix;
6905
6906
  state.distbits = 5;
6906
6907
  }
6907
- function updatewindow(strm, src, end, copy2) {
6908
+ function updatewindow(strm, src, end, copy) {
6908
6909
  var dist;
6909
6910
  var state = strm.state;
6910
6911
  if (state.window === null) {
@@ -6913,20 +6914,20 @@ var require_inflate = __commonJS({
6913
6914
  state.whave = 0;
6914
6915
  state.window = new utils.Buf8(state.wsize);
6915
6916
  }
6916
- if (copy2 >= state.wsize) {
6917
+ if (copy >= state.wsize) {
6917
6918
  utils.arraySet(state.window, src, end - state.wsize, state.wsize, 0);
6918
6919
  state.wnext = 0;
6919
6920
  state.whave = state.wsize;
6920
6921
  } else {
6921
6922
  dist = state.wsize - state.wnext;
6922
- if (dist > copy2) {
6923
- dist = copy2;
6924
- }
6925
- utils.arraySet(state.window, src, end - copy2, dist, state.wnext);
6926
- copy2 -= dist;
6927
- if (copy2) {
6928
- utils.arraySet(state.window, src, end - copy2, copy2, 0);
6929
- state.wnext = copy2;
6923
+ if (dist > copy) {
6924
+ dist = copy;
6925
+ }
6926
+ utils.arraySet(state.window, src, end - copy, dist, state.wnext);
6927
+ copy -= dist;
6928
+ if (copy) {
6929
+ utils.arraySet(state.window, src, end - copy, copy, 0);
6930
+ state.wnext = copy;
6930
6931
  state.whave = state.wsize;
6931
6932
  } else {
6932
6933
  state.wnext += dist;
@@ -6949,7 +6950,7 @@ var require_inflate = __commonJS({
6949
6950
  var hold;
6950
6951
  var bits;
6951
6952
  var _in, _out;
6952
- var copy2;
6953
+ var copy;
6953
6954
  var from;
6954
6955
  var from_source;
6955
6956
  var here = 0;
@@ -7144,11 +7145,11 @@ var require_inflate = __commonJS({
7144
7145
  /* falls through */
7145
7146
  case EXTRA:
7146
7147
  if (state.flags & 1024) {
7147
- copy2 = state.length;
7148
- if (copy2 > have) {
7149
- copy2 = have;
7148
+ copy = state.length;
7149
+ if (copy > have) {
7150
+ copy = have;
7150
7151
  }
7151
- if (copy2) {
7152
+ if (copy) {
7152
7153
  if (state.head) {
7153
7154
  len = state.head.extra_len - state.length;
7154
7155
  if (!state.head.extra) {
@@ -7160,17 +7161,17 @@ var require_inflate = __commonJS({
7160
7161
  next,
7161
7162
  // extra field is limited to 65536 bytes
7162
7163
  // - no need for additional size check
7163
- copy2,
7164
+ copy,
7164
7165
  /*len + copy > state.head.extra_max - len ? state.head.extra_max : copy,*/
7165
7166
  len
7166
7167
  );
7167
7168
  }
7168
7169
  if (state.flags & 512) {
7169
- state.check = crc32(state.check, input, copy2, next);
7170
+ state.check = crc32(state.check, input, copy, next);
7170
7171
  }
7171
- have -= copy2;
7172
- next += copy2;
7173
- state.length -= copy2;
7172
+ have -= copy;
7173
+ next += copy;
7174
+ state.length -= copy;
7174
7175
  }
7175
7176
  if (state.length) {
7176
7177
  break inf_leave;
@@ -7184,18 +7185,18 @@ var require_inflate = __commonJS({
7184
7185
  if (have === 0) {
7185
7186
  break inf_leave;
7186
7187
  }
7187
- copy2 = 0;
7188
+ copy = 0;
7188
7189
  do {
7189
- len = input[next + copy2++];
7190
+ len = input[next + copy++];
7190
7191
  if (state.head && len && state.length < 65536) {
7191
7192
  state.head.name += String.fromCharCode(len);
7192
7193
  }
7193
- } while (len && copy2 < have);
7194
+ } while (len && copy < have);
7194
7195
  if (state.flags & 512) {
7195
- state.check = crc32(state.check, input, copy2, next);
7196
+ state.check = crc32(state.check, input, copy, next);
7196
7197
  }
7197
- have -= copy2;
7198
- next += copy2;
7198
+ have -= copy;
7199
+ next += copy;
7199
7200
  if (len) {
7200
7201
  break inf_leave;
7201
7202
  }
@@ -7210,18 +7211,18 @@ var require_inflate = __commonJS({
7210
7211
  if (have === 0) {
7211
7212
  break inf_leave;
7212
7213
  }
7213
- copy2 = 0;
7214
+ copy = 0;
7214
7215
  do {
7215
- len = input[next + copy2++];
7216
+ len = input[next + copy++];
7216
7217
  if (state.head && len && state.length < 65536) {
7217
7218
  state.head.comment += String.fromCharCode(len);
7218
7219
  }
7219
- } while (len && copy2 < have);
7220
+ } while (len && copy < have);
7220
7221
  if (state.flags & 512) {
7221
- state.check = crc32(state.check, input, copy2, next);
7222
+ state.check = crc32(state.check, input, copy, next);
7222
7223
  }
7223
- have -= copy2;
7224
- next += copy2;
7224
+ have -= copy;
7225
+ next += copy;
7225
7226
  if (len) {
7226
7227
  break inf_leave;
7227
7228
  }
@@ -7356,23 +7357,23 @@ var require_inflate = __commonJS({
7356
7357
  state.mode = COPY;
7357
7358
  /* falls through */
7358
7359
  case COPY:
7359
- copy2 = state.length;
7360
- if (copy2) {
7361
- if (copy2 > have) {
7362
- copy2 = have;
7360
+ copy = state.length;
7361
+ if (copy) {
7362
+ if (copy > have) {
7363
+ copy = have;
7363
7364
  }
7364
- if (copy2 > left) {
7365
- copy2 = left;
7365
+ if (copy > left) {
7366
+ copy = left;
7366
7367
  }
7367
- if (copy2 === 0) {
7368
+ if (copy === 0) {
7368
7369
  break inf_leave;
7369
7370
  }
7370
- utils.arraySet(output, input, next, copy2, put);
7371
- have -= copy2;
7372
- next += copy2;
7373
- left -= copy2;
7374
- put += copy2;
7375
- state.length -= copy2;
7371
+ utils.arraySet(output, input, next, copy, put);
7372
+ have -= copy;
7373
+ next += copy;
7374
+ left -= copy;
7375
+ put += copy;
7376
+ state.length -= copy;
7376
7377
  break;
7377
7378
  }
7378
7379
  state.mode = TYPE;
@@ -7473,7 +7474,7 @@ var require_inflate = __commonJS({
7473
7474
  break;
7474
7475
  }
7475
7476
  len = state.lens[state.have - 1];
7476
- copy2 = 3 + (hold & 3);
7477
+ copy = 3 + (hold & 3);
7477
7478
  hold >>>= 2;
7478
7479
  bits -= 2;
7479
7480
  } else if (here_val === 17) {
@@ -7489,7 +7490,7 @@ var require_inflate = __commonJS({
7489
7490
  hold >>>= here_bits;
7490
7491
  bits -= here_bits;
7491
7492
  len = 0;
7492
- copy2 = 3 + (hold & 7);
7493
+ copy = 3 + (hold & 7);
7493
7494
  hold >>>= 3;
7494
7495
  bits -= 3;
7495
7496
  } else {
@@ -7505,16 +7506,16 @@ var require_inflate = __commonJS({
7505
7506
  hold >>>= here_bits;
7506
7507
  bits -= here_bits;
7507
7508
  len = 0;
7508
- copy2 = 11 + (hold & 127);
7509
+ copy = 11 + (hold & 127);
7509
7510
  hold >>>= 7;
7510
7511
  bits -= 7;
7511
7512
  }
7512
- if (state.have + copy2 > state.nlen + state.ndist) {
7513
+ if (state.have + copy > state.nlen + state.ndist) {
7513
7514
  strm.msg = "invalid bit length repeat";
7514
7515
  state.mode = BAD;
7515
7516
  break;
7516
7517
  }
7517
- while (copy2--) {
7518
+ while (copy--) {
7518
7519
  state.lens[state.have++] = len;
7519
7520
  }
7520
7521
  }
@@ -7733,39 +7734,39 @@ var require_inflate = __commonJS({
7733
7734
  if (left === 0) {
7734
7735
  break inf_leave;
7735
7736
  }
7736
- copy2 = _out - left;
7737
- if (state.offset > copy2) {
7738
- copy2 = state.offset - copy2;
7739
- if (copy2 > state.whave) {
7737
+ copy = _out - left;
7738
+ if (state.offset > copy) {
7739
+ copy = state.offset - copy;
7740
+ if (copy > state.whave) {
7740
7741
  if (state.sane) {
7741
7742
  strm.msg = "invalid distance too far back";
7742
7743
  state.mode = BAD;
7743
7744
  break;
7744
7745
  }
7745
7746
  }
7746
- if (copy2 > state.wnext) {
7747
- copy2 -= state.wnext;
7748
- from = state.wsize - copy2;
7747
+ if (copy > state.wnext) {
7748
+ copy -= state.wnext;
7749
+ from = state.wsize - copy;
7749
7750
  } else {
7750
- from = state.wnext - copy2;
7751
+ from = state.wnext - copy;
7751
7752
  }
7752
- if (copy2 > state.length) {
7753
- copy2 = state.length;
7753
+ if (copy > state.length) {
7754
+ copy = state.length;
7754
7755
  }
7755
7756
  from_source = state.window;
7756
7757
  } else {
7757
7758
  from_source = output;
7758
7759
  from = put - state.offset;
7759
- copy2 = state.length;
7760
+ copy = state.length;
7760
7761
  }
7761
- if (copy2 > left) {
7762
- copy2 = left;
7762
+ if (copy > left) {
7763
+ copy = left;
7763
7764
  }
7764
- left -= copy2;
7765
- state.length -= copy2;
7765
+ left -= copy;
7766
+ state.length -= copy;
7766
7767
  do {
7767
7768
  output[put++] = from_source[from++];
7768
- } while (--copy2);
7769
+ } while (--copy);
7769
7770
  if (state.length === 0) {
7770
7771
  state.mode = LEN;
7771
7772
  }
@@ -8293,7 +8294,7 @@ var require_ZipFileWorker = __commonJS({
8293
8294
  return (dosPermissions || 0) & 63;
8294
8295
  };
8295
8296
  var generateZipParts = function(streamInfo, streamedContent, streamingEnded, offset, platform, encodeFileName) {
8296
- var file = streamInfo["file"], compression = streamInfo["compression"], useCustomEncoding = encodeFileName !== utf8.utf8encode, encodedFileName = utils.transformTo("string", encodeFileName(file.name)), utfEncodedFileName = utils.transformTo("string", utf8.utf8encode(file.name)), comment = file.comment, encodedComment = utils.transformTo("string", encodeFileName(comment)), utfEncodedComment = utils.transformTo("string", utf8.utf8encode(comment)), useUTF8ForFileName = utfEncodedFileName.length !== file.name.length, useUTF8ForComment = utfEncodedComment.length !== comment.length, dosTime, dosDate, extraFields = "", unicodePathExtraField = "", unicodeCommentExtraField = "", dir2 = file.dir, date = file.date;
8297
+ var file = streamInfo["file"], compression = streamInfo["compression"], useCustomEncoding = encodeFileName !== utf8.utf8encode, encodedFileName = utils.transformTo("string", encodeFileName(file.name)), utfEncodedFileName = utils.transformTo("string", utf8.utf8encode(file.name)), comment = file.comment, encodedComment = utils.transformTo("string", encodeFileName(comment)), utfEncodedComment = utils.transformTo("string", utf8.utf8encode(comment)), useUTF8ForFileName = utfEncodedFileName.length !== file.name.length, useUTF8ForComment = utfEncodedComment.length !== comment.length, dosTime, dosDate, extraFields = "", unicodePathExtraField = "", unicodeCommentExtraField = "", dir = file.dir, date = file.date;
8297
8298
  var dataInfo = {
8298
8299
  crc32: 0,
8299
8300
  compressedSize: 0,
@@ -8313,12 +8314,12 @@ var require_ZipFileWorker = __commonJS({
8313
8314
  }
8314
8315
  var extFileAttr = 0;
8315
8316
  var versionMadeBy = 0;
8316
- if (dir2) {
8317
+ if (dir) {
8317
8318
  extFileAttr |= 16;
8318
8319
  }
8319
8320
  if (platform === "UNIX") {
8320
8321
  versionMadeBy = 798;
8321
- extFileAttr |= generateUnixExternalFileAttr(file.unixPermissions, dir2);
8322
+ extFileAttr |= generateUnixExternalFileAttr(file.unixPermissions, dir);
8322
8323
  } else {
8323
8324
  versionMadeBy = 20;
8324
8325
  extFileAttr |= generateDosExternalFileAttr(file.dosPermissions);
@@ -8570,10 +8571,10 @@ var require_generate = __commonJS({
8570
8571
  entriesCount++;
8571
8572
  var compression = getCompression(file.options.compression, options.compression);
8572
8573
  var compressionOptions = file.options.compressionOptions || options.compressionOptions || {};
8573
- var dir2 = file.dir, date = file.date;
8574
+ var dir = file.dir, date = file.date;
8574
8575
  file._compressWorker(compression, compressionOptions).withStreamInfo("file", {
8575
8576
  name: relativePath,
8576
- dir: dir2,
8577
+ dir,
8577
8578
  date,
8578
8579
  comment: file.comment || "",
8579
8580
  unixPermissions: file.unixPermissions,
@@ -9908,8 +9909,8 @@ var ZodParsedType = util.arrayToEnum([
9908
9909
  "set"
9909
9910
  ]);
9910
9911
  var getParsedType = (data) => {
9911
- const t2 = typeof data;
9912
- switch (t2) {
9912
+ const t = typeof data;
9913
+ switch (t) {
9913
9914
  case "undefined":
9914
9915
  return ZodParsedType.undefined;
9915
9916
  case "string":
@@ -14239,2379 +14240,6 @@ var TrueFalseQuestionSchema2 = external_exports.object({
14239
14240
  topic: external_exports.string().optional().describe("Specific topic within the category.")
14240
14241
  });
14241
14242
 
14242
- // ../../node_modules/.pnpm/i18next@23.16.8/node_modules/i18next/dist/esm/i18next.js
14243
- var isString = (obj) => typeof obj === "string";
14244
- var defer = () => {
14245
- let res;
14246
- let rej;
14247
- const promise = new Promise((resolve, reject) => {
14248
- res = resolve;
14249
- rej = reject;
14250
- });
14251
- promise.resolve = res;
14252
- promise.reject = rej;
14253
- return promise;
14254
- };
14255
- var makeString = (object) => {
14256
- if (object == null) return "";
14257
- return "" + object;
14258
- };
14259
- var copy = (a, s, t2) => {
14260
- a.forEach((m) => {
14261
- if (s[m]) t2[m] = s[m];
14262
- });
14263
- };
14264
- var lastOfPathSeparatorRegExp = /###/g;
14265
- var cleanKey = (key) => key && key.indexOf("###") > -1 ? key.replace(lastOfPathSeparatorRegExp, ".") : key;
14266
- var canNotTraverseDeeper = (object) => !object || isString(object);
14267
- var getLastOfPath = (object, path, Empty) => {
14268
- const stack = !isString(path) ? path : path.split(".");
14269
- let stackIndex = 0;
14270
- while (stackIndex < stack.length - 1) {
14271
- if (canNotTraverseDeeper(object)) return {};
14272
- const key = cleanKey(stack[stackIndex]);
14273
- if (!object[key] && Empty) object[key] = new Empty();
14274
- if (Object.prototype.hasOwnProperty.call(object, key)) {
14275
- object = object[key];
14276
- } else {
14277
- object = {};
14278
- }
14279
- ++stackIndex;
14280
- }
14281
- if (canNotTraverseDeeper(object)) return {};
14282
- return {
14283
- obj: object,
14284
- k: cleanKey(stack[stackIndex])
14285
- };
14286
- };
14287
- var setPath = (object, path, newValue) => {
14288
- const {
14289
- obj,
14290
- k
14291
- } = getLastOfPath(object, path, Object);
14292
- if (obj !== void 0 || path.length === 1) {
14293
- obj[k] = newValue;
14294
- return;
14295
- }
14296
- let e = path[path.length - 1];
14297
- let p = path.slice(0, path.length - 1);
14298
- let last = getLastOfPath(object, p, Object);
14299
- while (last.obj === void 0 && p.length) {
14300
- e = `${p[p.length - 1]}.${e}`;
14301
- p = p.slice(0, p.length - 1);
14302
- last = getLastOfPath(object, p, Object);
14303
- if (last && last.obj && typeof last.obj[`${last.k}.${e}`] !== "undefined") {
14304
- last.obj = void 0;
14305
- }
14306
- }
14307
- last.obj[`${last.k}.${e}`] = newValue;
14308
- };
14309
- var pushPath = (object, path, newValue, concat) => {
14310
- const {
14311
- obj,
14312
- k
14313
- } = getLastOfPath(object, path, Object);
14314
- obj[k] = obj[k] || [];
14315
- obj[k].push(newValue);
14316
- };
14317
- var getPath = (object, path) => {
14318
- const {
14319
- obj,
14320
- k
14321
- } = getLastOfPath(object, path);
14322
- if (!obj) return void 0;
14323
- return obj[k];
14324
- };
14325
- var getPathWithDefaults = (data, defaultData, key) => {
14326
- const value = getPath(data, key);
14327
- if (value !== void 0) {
14328
- return value;
14329
- }
14330
- return getPath(defaultData, key);
14331
- };
14332
- var deepExtend = (target, source, overwrite) => {
14333
- for (const prop in source) {
14334
- if (prop !== "__proto__" && prop !== "constructor") {
14335
- if (prop in target) {
14336
- if (isString(target[prop]) || target[prop] instanceof String || isString(source[prop]) || source[prop] instanceof String) {
14337
- if (overwrite) target[prop] = source[prop];
14338
- } else {
14339
- deepExtend(target[prop], source[prop], overwrite);
14340
- }
14341
- } else {
14342
- target[prop] = source[prop];
14343
- }
14344
- }
14345
- }
14346
- return target;
14347
- };
14348
- var regexEscape = (str) => str.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
14349
- var _entityMap = {
14350
- "&": "&amp;",
14351
- "<": "&lt;",
14352
- ">": "&gt;",
14353
- '"': "&quot;",
14354
- "'": "&#39;",
14355
- "/": "&#x2F;"
14356
- };
14357
- var escape = (data) => {
14358
- if (isString(data)) {
14359
- return data.replace(/[&<>"'\/]/g, (s) => _entityMap[s]);
14360
- }
14361
- return data;
14362
- };
14363
- var RegExpCache = class {
14364
- constructor(capacity) {
14365
- this.capacity = capacity;
14366
- this.regExpMap = /* @__PURE__ */ new Map();
14367
- this.regExpQueue = [];
14368
- }
14369
- getRegExp(pattern) {
14370
- const regExpFromCache = this.regExpMap.get(pattern);
14371
- if (regExpFromCache !== void 0) {
14372
- return regExpFromCache;
14373
- }
14374
- const regExpNew = new RegExp(pattern);
14375
- if (this.regExpQueue.length === this.capacity) {
14376
- this.regExpMap.delete(this.regExpQueue.shift());
14377
- }
14378
- this.regExpMap.set(pattern, regExpNew);
14379
- this.regExpQueue.push(pattern);
14380
- return regExpNew;
14381
- }
14382
- };
14383
- var chars = [" ", ",", "?", "!", ";"];
14384
- var looksLikeObjectPathRegExpCache = new RegExpCache(20);
14385
- var looksLikeObjectPath = (key, nsSeparator, keySeparator) => {
14386
- nsSeparator = nsSeparator || "";
14387
- keySeparator = keySeparator || "";
14388
- const possibleChars = chars.filter((c) => nsSeparator.indexOf(c) < 0 && keySeparator.indexOf(c) < 0);
14389
- if (possibleChars.length === 0) return true;
14390
- const r2 = looksLikeObjectPathRegExpCache.getRegExp(`(${possibleChars.map((c) => c === "?" ? "\\?" : c).join("|")})`);
14391
- let matched = !r2.test(key);
14392
- if (!matched) {
14393
- const ki = key.indexOf(keySeparator);
14394
- if (ki > 0 && !r2.test(key.substring(0, ki))) {
14395
- matched = true;
14396
- }
14397
- }
14398
- return matched;
14399
- };
14400
- var deepFind = function(obj, path) {
14401
- let keySeparator = arguments.length > 2 && arguments[2] !== void 0 ? arguments[2] : ".";
14402
- if (!obj) return void 0;
14403
- if (obj[path]) return obj[path];
14404
- const tokens = path.split(keySeparator);
14405
- let current = obj;
14406
- for (let i = 0; i < tokens.length; ) {
14407
- if (!current || typeof current !== "object") {
14408
- return void 0;
14409
- }
14410
- let next;
14411
- let nextPath = "";
14412
- for (let j = i; j < tokens.length; ++j) {
14413
- if (j !== i) {
14414
- nextPath += keySeparator;
14415
- }
14416
- nextPath += tokens[j];
14417
- next = current[nextPath];
14418
- if (next !== void 0) {
14419
- if (["string", "number", "boolean"].indexOf(typeof next) > -1 && j < tokens.length - 1) {
14420
- continue;
14421
- }
14422
- i += j - i + 1;
14423
- break;
14424
- }
14425
- }
14426
- current = next;
14427
- }
14428
- return current;
14429
- };
14430
- var getCleanedCode = (code) => code && code.replace("_", "-");
14431
- var consoleLogger = {
14432
- type: "logger",
14433
- log(args) {
14434
- this.output("log", args);
14435
- },
14436
- warn(args) {
14437
- this.output("warn", args);
14438
- },
14439
- error(args) {
14440
- this.output("error", args);
14441
- },
14442
- output(type, args) {
14443
- if (console && console[type]) console[type].apply(console, args);
14444
- }
14445
- };
14446
- var Logger = class _Logger {
14447
- constructor(concreteLogger) {
14448
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
14449
- this.init(concreteLogger, options);
14450
- }
14451
- init(concreteLogger) {
14452
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
14453
- this.prefix = options.prefix || "i18next:";
14454
- this.logger = concreteLogger || consoleLogger;
14455
- this.options = options;
14456
- this.debug = options.debug;
14457
- }
14458
- log() {
14459
- for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
14460
- args[_key] = arguments[_key];
14461
- }
14462
- return this.forward(args, "log", "", true);
14463
- }
14464
- warn() {
14465
- for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
14466
- args[_key2] = arguments[_key2];
14467
- }
14468
- return this.forward(args, "warn", "", true);
14469
- }
14470
- error() {
14471
- for (var _len3 = arguments.length, args = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
14472
- args[_key3] = arguments[_key3];
14473
- }
14474
- return this.forward(args, "error", "");
14475
- }
14476
- deprecate() {
14477
- for (var _len4 = arguments.length, args = new Array(_len4), _key4 = 0; _key4 < _len4; _key4++) {
14478
- args[_key4] = arguments[_key4];
14479
- }
14480
- return this.forward(args, "warn", "WARNING DEPRECATED: ", true);
14481
- }
14482
- forward(args, lvl, prefix, debugOnly) {
14483
- if (debugOnly && !this.debug) return null;
14484
- if (isString(args[0])) args[0] = `${prefix}${this.prefix} ${args[0]}`;
14485
- return this.logger[lvl](args);
14486
- }
14487
- create(moduleName) {
14488
- return new _Logger(this.logger, {
14489
- ...{
14490
- prefix: `${this.prefix}:${moduleName}:`
14491
- },
14492
- ...this.options
14493
- });
14494
- }
14495
- clone(options) {
14496
- options = options || this.options;
14497
- options.prefix = options.prefix || this.prefix;
14498
- return new _Logger(this.logger, options);
14499
- }
14500
- };
14501
- var baseLogger = new Logger();
14502
- var EventEmitter = class {
14503
- constructor() {
14504
- this.observers = {};
14505
- }
14506
- on(events, listener) {
14507
- events.split(" ").forEach((event) => {
14508
- if (!this.observers[event]) this.observers[event] = /* @__PURE__ */ new Map();
14509
- const numListeners = this.observers[event].get(listener) || 0;
14510
- this.observers[event].set(listener, numListeners + 1);
14511
- });
14512
- return this;
14513
- }
14514
- off(event, listener) {
14515
- if (!this.observers[event]) return;
14516
- if (!listener) {
14517
- delete this.observers[event];
14518
- return;
14519
- }
14520
- this.observers[event].delete(listener);
14521
- }
14522
- emit(event) {
14523
- for (var _len = arguments.length, args = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
14524
- args[_key - 1] = arguments[_key];
14525
- }
14526
- if (this.observers[event]) {
14527
- const cloned = Array.from(this.observers[event].entries());
14528
- cloned.forEach((_ref) => {
14529
- let [observer, numTimesAdded] = _ref;
14530
- for (let i = 0; i < numTimesAdded; i++) {
14531
- observer(...args);
14532
- }
14533
- });
14534
- }
14535
- if (this.observers["*"]) {
14536
- const cloned = Array.from(this.observers["*"].entries());
14537
- cloned.forEach((_ref2) => {
14538
- let [observer, numTimesAdded] = _ref2;
14539
- for (let i = 0; i < numTimesAdded; i++) {
14540
- observer.apply(observer, [event, ...args]);
14541
- }
14542
- });
14543
- }
14544
- }
14545
- };
14546
- var ResourceStore = class extends EventEmitter {
14547
- constructor(data) {
14548
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {
14549
- ns: ["translation"],
14550
- defaultNS: "translation"
14551
- };
14552
- super();
14553
- this.data = data || {};
14554
- this.options = options;
14555
- if (this.options.keySeparator === void 0) {
14556
- this.options.keySeparator = ".";
14557
- }
14558
- if (this.options.ignoreJSONStructure === void 0) {
14559
- this.options.ignoreJSONStructure = true;
14560
- }
14561
- }
14562
- addNamespaces(ns) {
14563
- if (this.options.ns.indexOf(ns) < 0) {
14564
- this.options.ns.push(ns);
14565
- }
14566
- }
14567
- removeNamespaces(ns) {
14568
- const index = this.options.ns.indexOf(ns);
14569
- if (index > -1) {
14570
- this.options.ns.splice(index, 1);
14571
- }
14572
- }
14573
- getResource(lng, ns, key) {
14574
- let options = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {};
14575
- const keySeparator = options.keySeparator !== void 0 ? options.keySeparator : this.options.keySeparator;
14576
- const ignoreJSONStructure = options.ignoreJSONStructure !== void 0 ? options.ignoreJSONStructure : this.options.ignoreJSONStructure;
14577
- let path;
14578
- if (lng.indexOf(".") > -1) {
14579
- path = lng.split(".");
14580
- } else {
14581
- path = [lng, ns];
14582
- if (key) {
14583
- if (Array.isArray(key)) {
14584
- path.push(...key);
14585
- } else if (isString(key) && keySeparator) {
14586
- path.push(...key.split(keySeparator));
14587
- } else {
14588
- path.push(key);
14589
- }
14590
- }
14591
- }
14592
- const result = getPath(this.data, path);
14593
- if (!result && !ns && !key && lng.indexOf(".") > -1) {
14594
- lng = path[0];
14595
- ns = path[1];
14596
- key = path.slice(2).join(".");
14597
- }
14598
- if (result || !ignoreJSONStructure || !isString(key)) return result;
14599
- return deepFind(this.data && this.data[lng] && this.data[lng][ns], key, keySeparator);
14600
- }
14601
- addResource(lng, ns, key, value) {
14602
- let options = arguments.length > 4 && arguments[4] !== void 0 ? arguments[4] : {
14603
- silent: false
14604
- };
14605
- const keySeparator = options.keySeparator !== void 0 ? options.keySeparator : this.options.keySeparator;
14606
- let path = [lng, ns];
14607
- if (key) path = path.concat(keySeparator ? key.split(keySeparator) : key);
14608
- if (lng.indexOf(".") > -1) {
14609
- path = lng.split(".");
14610
- value = ns;
14611
- ns = path[1];
14612
- }
14613
- this.addNamespaces(ns);
14614
- setPath(this.data, path, value);
14615
- if (!options.silent) this.emit("added", lng, ns, key, value);
14616
- }
14617
- addResources(lng, ns, resources2) {
14618
- let options = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {
14619
- silent: false
14620
- };
14621
- for (const m in resources2) {
14622
- if (isString(resources2[m]) || Array.isArray(resources2[m])) this.addResource(lng, ns, m, resources2[m], {
14623
- silent: true
14624
- });
14625
- }
14626
- if (!options.silent) this.emit("added", lng, ns, resources2);
14627
- }
14628
- addResourceBundle(lng, ns, resources2, deep, overwrite) {
14629
- let options = arguments.length > 5 && arguments[5] !== void 0 ? arguments[5] : {
14630
- silent: false,
14631
- skipCopy: false
14632
- };
14633
- let path = [lng, ns];
14634
- if (lng.indexOf(".") > -1) {
14635
- path = lng.split(".");
14636
- deep = resources2;
14637
- resources2 = ns;
14638
- ns = path[1];
14639
- }
14640
- this.addNamespaces(ns);
14641
- let pack = getPath(this.data, path) || {};
14642
- if (!options.skipCopy) resources2 = JSON.parse(JSON.stringify(resources2));
14643
- if (deep) {
14644
- deepExtend(pack, resources2, overwrite);
14645
- } else {
14646
- pack = {
14647
- ...pack,
14648
- ...resources2
14649
- };
14650
- }
14651
- setPath(this.data, path, pack);
14652
- if (!options.silent) this.emit("added", lng, ns, resources2);
14653
- }
14654
- removeResourceBundle(lng, ns) {
14655
- if (this.hasResourceBundle(lng, ns)) {
14656
- delete this.data[lng][ns];
14657
- }
14658
- this.removeNamespaces(ns);
14659
- this.emit("removed", lng, ns);
14660
- }
14661
- hasResourceBundle(lng, ns) {
14662
- return this.getResource(lng, ns) !== void 0;
14663
- }
14664
- getResourceBundle(lng, ns) {
14665
- if (!ns) ns = this.options.defaultNS;
14666
- if (this.options.compatibilityAPI === "v1") return {
14667
- ...{},
14668
- ...this.getResource(lng, ns)
14669
- };
14670
- return this.getResource(lng, ns);
14671
- }
14672
- getDataByLanguage(lng) {
14673
- return this.data[lng];
14674
- }
14675
- hasLanguageSomeTranslations(lng) {
14676
- const data = this.getDataByLanguage(lng);
14677
- const n = data && Object.keys(data) || [];
14678
- return !!n.find((v) => data[v] && Object.keys(data[v]).length > 0);
14679
- }
14680
- toJSON() {
14681
- return this.data;
14682
- }
14683
- };
14684
- var postProcessor = {
14685
- processors: {},
14686
- addPostProcessor(module) {
14687
- this.processors[module.name] = module;
14688
- },
14689
- handle(processors, value, key, options, translator) {
14690
- processors.forEach((processor) => {
14691
- if (this.processors[processor]) value = this.processors[processor].process(value, key, options, translator);
14692
- });
14693
- return value;
14694
- }
14695
- };
14696
- var checkedLoadedFor = {};
14697
- var Translator = class _Translator extends EventEmitter {
14698
- constructor(services) {
14699
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
14700
- super();
14701
- copy(["resourceStore", "languageUtils", "pluralResolver", "interpolator", "backendConnector", "i18nFormat", "utils"], services, this);
14702
- this.options = options;
14703
- if (this.options.keySeparator === void 0) {
14704
- this.options.keySeparator = ".";
14705
- }
14706
- this.logger = baseLogger.create("translator");
14707
- }
14708
- changeLanguage(lng) {
14709
- if (lng) this.language = lng;
14710
- }
14711
- exists(key) {
14712
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {
14713
- interpolation: {}
14714
- };
14715
- if (key === void 0 || key === null) {
14716
- return false;
14717
- }
14718
- const resolved = this.resolve(key, options);
14719
- return resolved && resolved.res !== void 0;
14720
- }
14721
- extractFromKey(key, options) {
14722
- let nsSeparator = options.nsSeparator !== void 0 ? options.nsSeparator : this.options.nsSeparator;
14723
- if (nsSeparator === void 0) nsSeparator = ":";
14724
- const keySeparator = options.keySeparator !== void 0 ? options.keySeparator : this.options.keySeparator;
14725
- let namespaces = options.ns || this.options.defaultNS || [];
14726
- const wouldCheckForNsInKey = nsSeparator && key.indexOf(nsSeparator) > -1;
14727
- const seemsNaturalLanguage = !this.options.userDefinedKeySeparator && !options.keySeparator && !this.options.userDefinedNsSeparator && !options.nsSeparator && !looksLikeObjectPath(key, nsSeparator, keySeparator);
14728
- if (wouldCheckForNsInKey && !seemsNaturalLanguage) {
14729
- const m = key.match(this.interpolator.nestingRegexp);
14730
- if (m && m.length > 0) {
14731
- return {
14732
- key,
14733
- namespaces: isString(namespaces) ? [namespaces] : namespaces
14734
- };
14735
- }
14736
- const parts = key.split(nsSeparator);
14737
- if (nsSeparator !== keySeparator || nsSeparator === keySeparator && this.options.ns.indexOf(parts[0]) > -1) namespaces = parts.shift();
14738
- key = parts.join(keySeparator);
14739
- }
14740
- return {
14741
- key,
14742
- namespaces: isString(namespaces) ? [namespaces] : namespaces
14743
- };
14744
- }
14745
- translate(keys, options, lastKey) {
14746
- if (typeof options !== "object" && this.options.overloadTranslationOptionHandler) {
14747
- options = this.options.overloadTranslationOptionHandler(arguments);
14748
- }
14749
- if (typeof options === "object") options = {
14750
- ...options
14751
- };
14752
- if (!options) options = {};
14753
- if (keys === void 0 || keys === null) return "";
14754
- if (!Array.isArray(keys)) keys = [String(keys)];
14755
- const returnDetails = options.returnDetails !== void 0 ? options.returnDetails : this.options.returnDetails;
14756
- const keySeparator = options.keySeparator !== void 0 ? options.keySeparator : this.options.keySeparator;
14757
- const {
14758
- key,
14759
- namespaces
14760
- } = this.extractFromKey(keys[keys.length - 1], options);
14761
- const namespace = namespaces[namespaces.length - 1];
14762
- const lng = options.lng || this.language;
14763
- const appendNamespaceToCIMode = options.appendNamespaceToCIMode || this.options.appendNamespaceToCIMode;
14764
- if (lng && lng.toLowerCase() === "cimode") {
14765
- if (appendNamespaceToCIMode) {
14766
- const nsSeparator = options.nsSeparator || this.options.nsSeparator;
14767
- if (returnDetails) {
14768
- return {
14769
- res: `${namespace}${nsSeparator}${key}`,
14770
- usedKey: key,
14771
- exactUsedKey: key,
14772
- usedLng: lng,
14773
- usedNS: namespace,
14774
- usedParams: this.getUsedParamsDetails(options)
14775
- };
14776
- }
14777
- return `${namespace}${nsSeparator}${key}`;
14778
- }
14779
- if (returnDetails) {
14780
- return {
14781
- res: key,
14782
- usedKey: key,
14783
- exactUsedKey: key,
14784
- usedLng: lng,
14785
- usedNS: namespace,
14786
- usedParams: this.getUsedParamsDetails(options)
14787
- };
14788
- }
14789
- return key;
14790
- }
14791
- const resolved = this.resolve(keys, options);
14792
- let res = resolved && resolved.res;
14793
- const resUsedKey = resolved && resolved.usedKey || key;
14794
- const resExactUsedKey = resolved && resolved.exactUsedKey || key;
14795
- const resType = Object.prototype.toString.apply(res);
14796
- const noObject = ["[object Number]", "[object Function]", "[object RegExp]"];
14797
- const joinArrays = options.joinArrays !== void 0 ? options.joinArrays : this.options.joinArrays;
14798
- const handleAsObjectInI18nFormat = !this.i18nFormat || this.i18nFormat.handleAsObject;
14799
- const handleAsObject = !isString(res) && typeof res !== "boolean" && typeof res !== "number";
14800
- if (handleAsObjectInI18nFormat && res && handleAsObject && noObject.indexOf(resType) < 0 && !(isString(joinArrays) && Array.isArray(res))) {
14801
- if (!options.returnObjects && !this.options.returnObjects) {
14802
- if (!this.options.returnedObjectHandler) {
14803
- this.logger.warn("accessing an object - but returnObjects options is not enabled!");
14804
- }
14805
- const r2 = this.options.returnedObjectHandler ? this.options.returnedObjectHandler(resUsedKey, res, {
14806
- ...options,
14807
- ns: namespaces
14808
- }) : `key '${key} (${this.language})' returned an object instead of string.`;
14809
- if (returnDetails) {
14810
- resolved.res = r2;
14811
- resolved.usedParams = this.getUsedParamsDetails(options);
14812
- return resolved;
14813
- }
14814
- return r2;
14815
- }
14816
- if (keySeparator) {
14817
- const resTypeIsArray = Array.isArray(res);
14818
- const copy2 = resTypeIsArray ? [] : {};
14819
- const newKeyToUse = resTypeIsArray ? resExactUsedKey : resUsedKey;
14820
- for (const m in res) {
14821
- if (Object.prototype.hasOwnProperty.call(res, m)) {
14822
- const deepKey = `${newKeyToUse}${keySeparator}${m}`;
14823
- copy2[m] = this.translate(deepKey, {
14824
- ...options,
14825
- ...{
14826
- joinArrays: false,
14827
- ns: namespaces
14828
- }
14829
- });
14830
- if (copy2[m] === deepKey) copy2[m] = res[m];
14831
- }
14832
- }
14833
- res = copy2;
14834
- }
14835
- } else if (handleAsObjectInI18nFormat && isString(joinArrays) && Array.isArray(res)) {
14836
- res = res.join(joinArrays);
14837
- if (res) res = this.extendTranslation(res, keys, options, lastKey);
14838
- } else {
14839
- let usedDefault = false;
14840
- let usedKey = false;
14841
- const needsPluralHandling = options.count !== void 0 && !isString(options.count);
14842
- const hasDefaultValue = _Translator.hasDefaultValue(options);
14843
- const defaultValueSuffix = needsPluralHandling ? this.pluralResolver.getSuffix(lng, options.count, options) : "";
14844
- const defaultValueSuffixOrdinalFallback = options.ordinal && needsPluralHandling ? this.pluralResolver.getSuffix(lng, options.count, {
14845
- ordinal: false
14846
- }) : "";
14847
- const needsZeroSuffixLookup = needsPluralHandling && !options.ordinal && options.count === 0 && this.pluralResolver.shouldUseIntlApi();
14848
- const defaultValue = needsZeroSuffixLookup && options[`defaultValue${this.options.pluralSeparator}zero`] || options[`defaultValue${defaultValueSuffix}`] || options[`defaultValue${defaultValueSuffixOrdinalFallback}`] || options.defaultValue;
14849
- if (!this.isValidLookup(res) && hasDefaultValue) {
14850
- usedDefault = true;
14851
- res = defaultValue;
14852
- }
14853
- if (!this.isValidLookup(res)) {
14854
- usedKey = true;
14855
- res = key;
14856
- }
14857
- const missingKeyNoValueFallbackToKey = options.missingKeyNoValueFallbackToKey || this.options.missingKeyNoValueFallbackToKey;
14858
- const resForMissing = missingKeyNoValueFallbackToKey && usedKey ? void 0 : res;
14859
- const updateMissing = hasDefaultValue && defaultValue !== res && this.options.updateMissing;
14860
- if (usedKey || usedDefault || updateMissing) {
14861
- this.logger.log(updateMissing ? "updateKey" : "missingKey", lng, namespace, key, updateMissing ? defaultValue : res);
14862
- if (keySeparator) {
14863
- const fk = this.resolve(key, {
14864
- ...options,
14865
- keySeparator: false
14866
- });
14867
- if (fk && fk.res) this.logger.warn("Seems the loaded translations were in flat JSON format instead of nested. Either set keySeparator: false on init or make sure your translations are published in nested format.");
14868
- }
14869
- let lngs = [];
14870
- const fallbackLngs = this.languageUtils.getFallbackCodes(this.options.fallbackLng, options.lng || this.language);
14871
- if (this.options.saveMissingTo === "fallback" && fallbackLngs && fallbackLngs[0]) {
14872
- for (let i = 0; i < fallbackLngs.length; i++) {
14873
- lngs.push(fallbackLngs[i]);
14874
- }
14875
- } else if (this.options.saveMissingTo === "all") {
14876
- lngs = this.languageUtils.toResolveHierarchy(options.lng || this.language);
14877
- } else {
14878
- lngs.push(options.lng || this.language);
14879
- }
14880
- const send = (l, k, specificDefaultValue) => {
14881
- const defaultForMissing = hasDefaultValue && specificDefaultValue !== res ? specificDefaultValue : resForMissing;
14882
- if (this.options.missingKeyHandler) {
14883
- this.options.missingKeyHandler(l, namespace, k, defaultForMissing, updateMissing, options);
14884
- } else if (this.backendConnector && this.backendConnector.saveMissing) {
14885
- this.backendConnector.saveMissing(l, namespace, k, defaultForMissing, updateMissing, options);
14886
- }
14887
- this.emit("missingKey", l, namespace, k, res);
14888
- };
14889
- if (this.options.saveMissing) {
14890
- if (this.options.saveMissingPlurals && needsPluralHandling) {
14891
- lngs.forEach((language) => {
14892
- const suffixes = this.pluralResolver.getSuffixes(language, options);
14893
- if (needsZeroSuffixLookup && options[`defaultValue${this.options.pluralSeparator}zero`] && suffixes.indexOf(`${this.options.pluralSeparator}zero`) < 0) {
14894
- suffixes.push(`${this.options.pluralSeparator}zero`);
14895
- }
14896
- suffixes.forEach((suffix) => {
14897
- send([language], key + suffix, options[`defaultValue${suffix}`] || defaultValue);
14898
- });
14899
- });
14900
- } else {
14901
- send(lngs, key, defaultValue);
14902
- }
14903
- }
14904
- }
14905
- res = this.extendTranslation(res, keys, options, resolved, lastKey);
14906
- if (usedKey && res === key && this.options.appendNamespaceToMissingKey) res = `${namespace}:${key}`;
14907
- if ((usedKey || usedDefault) && this.options.parseMissingKeyHandler) {
14908
- if (this.options.compatibilityAPI !== "v1") {
14909
- res = this.options.parseMissingKeyHandler(this.options.appendNamespaceToMissingKey ? `${namespace}:${key}` : key, usedDefault ? res : void 0);
14910
- } else {
14911
- res = this.options.parseMissingKeyHandler(res);
14912
- }
14913
- }
14914
- }
14915
- if (returnDetails) {
14916
- resolved.res = res;
14917
- resolved.usedParams = this.getUsedParamsDetails(options);
14918
- return resolved;
14919
- }
14920
- return res;
14921
- }
14922
- extendTranslation(res, key, options, resolved, lastKey) {
14923
- var _this = this;
14924
- if (this.i18nFormat && this.i18nFormat.parse) {
14925
- res = this.i18nFormat.parse(res, {
14926
- ...this.options.interpolation.defaultVariables,
14927
- ...options
14928
- }, options.lng || this.language || resolved.usedLng, resolved.usedNS, resolved.usedKey, {
14929
- resolved
14930
- });
14931
- } else if (!options.skipInterpolation) {
14932
- if (options.interpolation) this.interpolator.init({
14933
- ...options,
14934
- ...{
14935
- interpolation: {
14936
- ...this.options.interpolation,
14937
- ...options.interpolation
14938
- }
14939
- }
14940
- });
14941
- const skipOnVariables = isString(res) && (options && options.interpolation && options.interpolation.skipOnVariables !== void 0 ? options.interpolation.skipOnVariables : this.options.interpolation.skipOnVariables);
14942
- let nestBef;
14943
- if (skipOnVariables) {
14944
- const nb = res.match(this.interpolator.nestingRegexp);
14945
- nestBef = nb && nb.length;
14946
- }
14947
- let data = options.replace && !isString(options.replace) ? options.replace : options;
14948
- if (this.options.interpolation.defaultVariables) data = {
14949
- ...this.options.interpolation.defaultVariables,
14950
- ...data
14951
- };
14952
- res = this.interpolator.interpolate(res, data, options.lng || this.language || resolved.usedLng, options);
14953
- if (skipOnVariables) {
14954
- const na = res.match(this.interpolator.nestingRegexp);
14955
- const nestAft = na && na.length;
14956
- if (nestBef < nestAft) options.nest = false;
14957
- }
14958
- if (!options.lng && this.options.compatibilityAPI !== "v1" && resolved && resolved.res) options.lng = this.language || resolved.usedLng;
14959
- if (options.nest !== false) res = this.interpolator.nest(res, function() {
14960
- for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
14961
- args[_key] = arguments[_key];
14962
- }
14963
- if (lastKey && lastKey[0] === args[0] && !options.context) {
14964
- _this.logger.warn(`It seems you are nesting recursively key: ${args[0]} in key: ${key[0]}`);
14965
- return null;
14966
- }
14967
- return _this.translate(...args, key);
14968
- }, options);
14969
- if (options.interpolation) this.interpolator.reset();
14970
- }
14971
- const postProcess = options.postProcess || this.options.postProcess;
14972
- const postProcessorNames = isString(postProcess) ? [postProcess] : postProcess;
14973
- if (res !== void 0 && res !== null && postProcessorNames && postProcessorNames.length && options.applyPostProcessor !== false) {
14974
- res = postProcessor.handle(postProcessorNames, res, key, this.options && this.options.postProcessPassResolved ? {
14975
- i18nResolved: {
14976
- ...resolved,
14977
- usedParams: this.getUsedParamsDetails(options)
14978
- },
14979
- ...options
14980
- } : options, this);
14981
- }
14982
- return res;
14983
- }
14984
- resolve(keys) {
14985
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
14986
- let found;
14987
- let usedKey;
14988
- let exactUsedKey;
14989
- let usedLng;
14990
- let usedNS;
14991
- if (isString(keys)) keys = [keys];
14992
- keys.forEach((k) => {
14993
- if (this.isValidLookup(found)) return;
14994
- const extracted = this.extractFromKey(k, options);
14995
- const key = extracted.key;
14996
- usedKey = key;
14997
- let namespaces = extracted.namespaces;
14998
- if (this.options.fallbackNS) namespaces = namespaces.concat(this.options.fallbackNS);
14999
- const needsPluralHandling = options.count !== void 0 && !isString(options.count);
15000
- const needsZeroSuffixLookup = needsPluralHandling && !options.ordinal && options.count === 0 && this.pluralResolver.shouldUseIntlApi();
15001
- const needsContextHandling = options.context !== void 0 && (isString(options.context) || typeof options.context === "number") && options.context !== "";
15002
- const codes = options.lngs ? options.lngs : this.languageUtils.toResolveHierarchy(options.lng || this.language, options.fallbackLng);
15003
- namespaces.forEach((ns) => {
15004
- if (this.isValidLookup(found)) return;
15005
- usedNS = ns;
15006
- if (!checkedLoadedFor[`${codes[0]}-${ns}`] && this.utils && this.utils.hasLoadedNamespace && !this.utils.hasLoadedNamespace(usedNS)) {
15007
- checkedLoadedFor[`${codes[0]}-${ns}`] = true;
15008
- this.logger.warn(`key "${usedKey}" for languages "${codes.join(", ")}" won't get resolved as namespace "${usedNS}" was not yet loaded`, "This means something IS WRONG in your setup. You access the t function before i18next.init / i18next.loadNamespace / i18next.changeLanguage was done. Wait for the callback or Promise to resolve before accessing it!!!");
15009
- }
15010
- codes.forEach((code) => {
15011
- if (this.isValidLookup(found)) return;
15012
- usedLng = code;
15013
- const finalKeys = [key];
15014
- if (this.i18nFormat && this.i18nFormat.addLookupKeys) {
15015
- this.i18nFormat.addLookupKeys(finalKeys, key, code, ns, options);
15016
- } else {
15017
- let pluralSuffix;
15018
- if (needsPluralHandling) pluralSuffix = this.pluralResolver.getSuffix(code, options.count, options);
15019
- const zeroSuffix = `${this.options.pluralSeparator}zero`;
15020
- const ordinalPrefix = `${this.options.pluralSeparator}ordinal${this.options.pluralSeparator}`;
15021
- if (needsPluralHandling) {
15022
- finalKeys.push(key + pluralSuffix);
15023
- if (options.ordinal && pluralSuffix.indexOf(ordinalPrefix) === 0) {
15024
- finalKeys.push(key + pluralSuffix.replace(ordinalPrefix, this.options.pluralSeparator));
15025
- }
15026
- if (needsZeroSuffixLookup) {
15027
- finalKeys.push(key + zeroSuffix);
15028
- }
15029
- }
15030
- if (needsContextHandling) {
15031
- const contextKey = `${key}${this.options.contextSeparator}${options.context}`;
15032
- finalKeys.push(contextKey);
15033
- if (needsPluralHandling) {
15034
- finalKeys.push(contextKey + pluralSuffix);
15035
- if (options.ordinal && pluralSuffix.indexOf(ordinalPrefix) === 0) {
15036
- finalKeys.push(contextKey + pluralSuffix.replace(ordinalPrefix, this.options.pluralSeparator));
15037
- }
15038
- if (needsZeroSuffixLookup) {
15039
- finalKeys.push(contextKey + zeroSuffix);
15040
- }
15041
- }
15042
- }
15043
- }
15044
- let possibleKey;
15045
- while (possibleKey = finalKeys.pop()) {
15046
- if (!this.isValidLookup(found)) {
15047
- exactUsedKey = possibleKey;
15048
- found = this.getResource(code, ns, possibleKey, options);
15049
- }
15050
- }
15051
- });
15052
- });
15053
- });
15054
- return {
15055
- res: found,
15056
- usedKey,
15057
- exactUsedKey,
15058
- usedLng,
15059
- usedNS
15060
- };
15061
- }
15062
- isValidLookup(res) {
15063
- return res !== void 0 && !(!this.options.returnNull && res === null) && !(!this.options.returnEmptyString && res === "");
15064
- }
15065
- getResource(code, ns, key) {
15066
- let options = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {};
15067
- if (this.i18nFormat && this.i18nFormat.getResource) return this.i18nFormat.getResource(code, ns, key, options);
15068
- return this.resourceStore.getResource(code, ns, key, options);
15069
- }
15070
- getUsedParamsDetails() {
15071
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
15072
- const optionsKeys = ["defaultValue", "ordinal", "context", "replace", "lng", "lngs", "fallbackLng", "ns", "keySeparator", "nsSeparator", "returnObjects", "returnDetails", "joinArrays", "postProcess", "interpolation"];
15073
- const useOptionsReplaceForData = options.replace && !isString(options.replace);
15074
- let data = useOptionsReplaceForData ? options.replace : options;
15075
- if (useOptionsReplaceForData && typeof options.count !== "undefined") {
15076
- data.count = options.count;
15077
- }
15078
- if (this.options.interpolation.defaultVariables) {
15079
- data = {
15080
- ...this.options.interpolation.defaultVariables,
15081
- ...data
15082
- };
15083
- }
15084
- if (!useOptionsReplaceForData) {
15085
- data = {
15086
- ...data
15087
- };
15088
- for (const key of optionsKeys) {
15089
- delete data[key];
15090
- }
15091
- }
15092
- return data;
15093
- }
15094
- static hasDefaultValue(options) {
15095
- const prefix = "defaultValue";
15096
- for (const option in options) {
15097
- if (Object.prototype.hasOwnProperty.call(options, option) && prefix === option.substring(0, prefix.length) && void 0 !== options[option]) {
15098
- return true;
15099
- }
15100
- }
15101
- return false;
15102
- }
15103
- };
15104
- var capitalize = (string) => string.charAt(0).toUpperCase() + string.slice(1);
15105
- var LanguageUtil = class {
15106
- constructor(options) {
15107
- this.options = options;
15108
- this.supportedLngs = this.options.supportedLngs || false;
15109
- this.logger = baseLogger.create("languageUtils");
15110
- }
15111
- getScriptPartFromCode(code) {
15112
- code = getCleanedCode(code);
15113
- if (!code || code.indexOf("-") < 0) return null;
15114
- const p = code.split("-");
15115
- if (p.length === 2) return null;
15116
- p.pop();
15117
- if (p[p.length - 1].toLowerCase() === "x") return null;
15118
- return this.formatLanguageCode(p.join("-"));
15119
- }
15120
- getLanguagePartFromCode(code) {
15121
- code = getCleanedCode(code);
15122
- if (!code || code.indexOf("-") < 0) return code;
15123
- const p = code.split("-");
15124
- return this.formatLanguageCode(p[0]);
15125
- }
15126
- formatLanguageCode(code) {
15127
- if (isString(code) && code.indexOf("-") > -1) {
15128
- if (typeof Intl !== "undefined" && typeof Intl.getCanonicalLocales !== "undefined") {
15129
- try {
15130
- let formattedCode = Intl.getCanonicalLocales(code)[0];
15131
- if (formattedCode && this.options.lowerCaseLng) {
15132
- formattedCode = formattedCode.toLowerCase();
15133
- }
15134
- if (formattedCode) return formattedCode;
15135
- } catch (e) {
15136
- }
15137
- }
15138
- const specialCases = ["hans", "hant", "latn", "cyrl", "cans", "mong", "arab"];
15139
- let p = code.split("-");
15140
- if (this.options.lowerCaseLng) {
15141
- p = p.map((part) => part.toLowerCase());
15142
- } else if (p.length === 2) {
15143
- p[0] = p[0].toLowerCase();
15144
- p[1] = p[1].toUpperCase();
15145
- if (specialCases.indexOf(p[1].toLowerCase()) > -1) p[1] = capitalize(p[1].toLowerCase());
15146
- } else if (p.length === 3) {
15147
- p[0] = p[0].toLowerCase();
15148
- if (p[1].length === 2) p[1] = p[1].toUpperCase();
15149
- if (p[0] !== "sgn" && p[2].length === 2) p[2] = p[2].toUpperCase();
15150
- if (specialCases.indexOf(p[1].toLowerCase()) > -1) p[1] = capitalize(p[1].toLowerCase());
15151
- if (specialCases.indexOf(p[2].toLowerCase()) > -1) p[2] = capitalize(p[2].toLowerCase());
15152
- }
15153
- return p.join("-");
15154
- }
15155
- return this.options.cleanCode || this.options.lowerCaseLng ? code.toLowerCase() : code;
15156
- }
15157
- isSupportedCode(code) {
15158
- if (this.options.load === "languageOnly" || this.options.nonExplicitSupportedLngs) {
15159
- code = this.getLanguagePartFromCode(code);
15160
- }
15161
- return !this.supportedLngs || !this.supportedLngs.length || this.supportedLngs.indexOf(code) > -1;
15162
- }
15163
- getBestMatchFromCodes(codes) {
15164
- if (!codes) return null;
15165
- let found;
15166
- codes.forEach((code) => {
15167
- if (found) return;
15168
- const cleanedLng = this.formatLanguageCode(code);
15169
- if (!this.options.supportedLngs || this.isSupportedCode(cleanedLng)) found = cleanedLng;
15170
- });
15171
- if (!found && this.options.supportedLngs) {
15172
- codes.forEach((code) => {
15173
- if (found) return;
15174
- const lngOnly = this.getLanguagePartFromCode(code);
15175
- if (this.isSupportedCode(lngOnly)) return found = lngOnly;
15176
- found = this.options.supportedLngs.find((supportedLng) => {
15177
- if (supportedLng === lngOnly) return supportedLng;
15178
- if (supportedLng.indexOf("-") < 0 && lngOnly.indexOf("-") < 0) return;
15179
- if (supportedLng.indexOf("-") > 0 && lngOnly.indexOf("-") < 0 && supportedLng.substring(0, supportedLng.indexOf("-")) === lngOnly) return supportedLng;
15180
- if (supportedLng.indexOf(lngOnly) === 0 && lngOnly.length > 1) return supportedLng;
15181
- });
15182
- });
15183
- }
15184
- if (!found) found = this.getFallbackCodes(this.options.fallbackLng)[0];
15185
- return found;
15186
- }
15187
- getFallbackCodes(fallbacks, code) {
15188
- if (!fallbacks) return [];
15189
- if (typeof fallbacks === "function") fallbacks = fallbacks(code);
15190
- if (isString(fallbacks)) fallbacks = [fallbacks];
15191
- if (Array.isArray(fallbacks)) return fallbacks;
15192
- if (!code) return fallbacks.default || [];
15193
- let found = fallbacks[code];
15194
- if (!found) found = fallbacks[this.getScriptPartFromCode(code)];
15195
- if (!found) found = fallbacks[this.formatLanguageCode(code)];
15196
- if (!found) found = fallbacks[this.getLanguagePartFromCode(code)];
15197
- if (!found) found = fallbacks.default;
15198
- return found || [];
15199
- }
15200
- toResolveHierarchy(code, fallbackCode) {
15201
- const fallbackCodes = this.getFallbackCodes(fallbackCode || this.options.fallbackLng || [], code);
15202
- const codes = [];
15203
- const addCode = (c) => {
15204
- if (!c) return;
15205
- if (this.isSupportedCode(c)) {
15206
- codes.push(c);
15207
- } else {
15208
- this.logger.warn(`rejecting language code not found in supportedLngs: ${c}`);
15209
- }
15210
- };
15211
- if (isString(code) && (code.indexOf("-") > -1 || code.indexOf("_") > -1)) {
15212
- if (this.options.load !== "languageOnly") addCode(this.formatLanguageCode(code));
15213
- if (this.options.load !== "languageOnly" && this.options.load !== "currentOnly") addCode(this.getScriptPartFromCode(code));
15214
- if (this.options.load !== "currentOnly") addCode(this.getLanguagePartFromCode(code));
15215
- } else if (isString(code)) {
15216
- addCode(this.formatLanguageCode(code));
15217
- }
15218
- fallbackCodes.forEach((fc) => {
15219
- if (codes.indexOf(fc) < 0) addCode(this.formatLanguageCode(fc));
15220
- });
15221
- return codes;
15222
- }
15223
- };
15224
- var sets = [{
15225
- lngs: ["ach", "ak", "am", "arn", "br", "fil", "gun", "ln", "mfe", "mg", "mi", "oc", "pt", "pt-BR", "tg", "tl", "ti", "tr", "uz", "wa"],
15226
- nr: [1, 2],
15227
- fc: 1
15228
- }, {
15229
- lngs: ["af", "an", "ast", "az", "bg", "bn", "ca", "da", "de", "dev", "el", "en", "eo", "es", "et", "eu", "fi", "fo", "fur", "fy", "gl", "gu", "ha", "hi", "hu", "hy", "ia", "it", "kk", "kn", "ku", "lb", "mai", "ml", "mn", "mr", "nah", "nap", "nb", "ne", "nl", "nn", "no", "nso", "pa", "pap", "pms", "ps", "pt-PT", "rm", "sco", "se", "si", "so", "son", "sq", "sv", "sw", "ta", "te", "tk", "ur", "yo"],
15230
- nr: [1, 2],
15231
- fc: 2
15232
- }, {
15233
- lngs: ["ay", "bo", "cgg", "fa", "ht", "id", "ja", "jbo", "ka", "km", "ko", "ky", "lo", "ms", "sah", "su", "th", "tt", "ug", "vi", "wo", "zh"],
15234
- nr: [1],
15235
- fc: 3
15236
- }, {
15237
- lngs: ["be", "bs", "cnr", "dz", "hr", "ru", "sr", "uk"],
15238
- nr: [1, 2, 5],
15239
- fc: 4
15240
- }, {
15241
- lngs: ["ar"],
15242
- nr: [0, 1, 2, 3, 11, 100],
15243
- fc: 5
15244
- }, {
15245
- lngs: ["cs", "sk"],
15246
- nr: [1, 2, 5],
15247
- fc: 6
15248
- }, {
15249
- lngs: ["csb", "pl"],
15250
- nr: [1, 2, 5],
15251
- fc: 7
15252
- }, {
15253
- lngs: ["cy"],
15254
- nr: [1, 2, 3, 8],
15255
- fc: 8
15256
- }, {
15257
- lngs: ["fr"],
15258
- nr: [1, 2],
15259
- fc: 9
15260
- }, {
15261
- lngs: ["ga"],
15262
- nr: [1, 2, 3, 7, 11],
15263
- fc: 10
15264
- }, {
15265
- lngs: ["gd"],
15266
- nr: [1, 2, 3, 20],
15267
- fc: 11
15268
- }, {
15269
- lngs: ["is"],
15270
- nr: [1, 2],
15271
- fc: 12
15272
- }, {
15273
- lngs: ["jv"],
15274
- nr: [0, 1],
15275
- fc: 13
15276
- }, {
15277
- lngs: ["kw"],
15278
- nr: [1, 2, 3, 4],
15279
- fc: 14
15280
- }, {
15281
- lngs: ["lt"],
15282
- nr: [1, 2, 10],
15283
- fc: 15
15284
- }, {
15285
- lngs: ["lv"],
15286
- nr: [1, 2, 0],
15287
- fc: 16
15288
- }, {
15289
- lngs: ["mk"],
15290
- nr: [1, 2],
15291
- fc: 17
15292
- }, {
15293
- lngs: ["mnk"],
15294
- nr: [0, 1, 2],
15295
- fc: 18
15296
- }, {
15297
- lngs: ["mt"],
15298
- nr: [1, 2, 11, 20],
15299
- fc: 19
15300
- }, {
15301
- lngs: ["or"],
15302
- nr: [2, 1],
15303
- fc: 2
15304
- }, {
15305
- lngs: ["ro"],
15306
- nr: [1, 2, 20],
15307
- fc: 20
15308
- }, {
15309
- lngs: ["sl"],
15310
- nr: [5, 1, 2, 3],
15311
- fc: 21
15312
- }, {
15313
- lngs: ["he", "iw"],
15314
- nr: [1, 2, 20, 21],
15315
- fc: 22
15316
- }];
15317
- var _rulesPluralsTypes = {
15318
- 1: (n) => Number(n > 1),
15319
- 2: (n) => Number(n != 1),
15320
- 3: (n) => 0,
15321
- 4: (n) => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n % 10 >= 2 && n % 10 <= 4 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
15322
- 5: (n) => Number(n == 0 ? 0 : n == 1 ? 1 : n == 2 ? 2 : n % 100 >= 3 && n % 100 <= 10 ? 3 : n % 100 >= 11 ? 4 : 5),
15323
- 6: (n) => Number(n == 1 ? 0 : n >= 2 && n <= 4 ? 1 : 2),
15324
- 7: (n) => Number(n == 1 ? 0 : n % 10 >= 2 && n % 10 <= 4 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
15325
- 8: (n) => Number(n == 1 ? 0 : n == 2 ? 1 : n != 8 && n != 11 ? 2 : 3),
15326
- 9: (n) => Number(n >= 2),
15327
- 10: (n) => Number(n == 1 ? 0 : n == 2 ? 1 : n < 7 ? 2 : n < 11 ? 3 : 4),
15328
- 11: (n) => Number(n == 1 || n == 11 ? 0 : n == 2 || n == 12 ? 1 : n > 2 && n < 20 ? 2 : 3),
15329
- 12: (n) => Number(n % 10 != 1 || n % 100 == 11),
15330
- 13: (n) => Number(n !== 0),
15331
- 14: (n) => Number(n == 1 ? 0 : n == 2 ? 1 : n == 3 ? 2 : 3),
15332
- 15: (n) => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n % 10 >= 2 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
15333
- 16: (n) => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n !== 0 ? 1 : 2),
15334
- 17: (n) => Number(n == 1 || n % 10 == 1 && n % 100 != 11 ? 0 : 1),
15335
- 18: (n) => Number(n == 0 ? 0 : n == 1 ? 1 : 2),
15336
- 19: (n) => Number(n == 1 ? 0 : n == 0 || n % 100 > 1 && n % 100 < 11 ? 1 : n % 100 > 10 && n % 100 < 20 ? 2 : 3),
15337
- 20: (n) => Number(n == 1 ? 0 : n == 0 || n % 100 > 0 && n % 100 < 20 ? 1 : 2),
15338
- 21: (n) => Number(n % 100 == 1 ? 1 : n % 100 == 2 ? 2 : n % 100 == 3 || n % 100 == 4 ? 3 : 0),
15339
- 22: (n) => Number(n == 1 ? 0 : n == 2 ? 1 : (n < 0 || n > 10) && n % 10 == 0 ? 2 : 3)
15340
- };
15341
- var nonIntlVersions = ["v1", "v2", "v3"];
15342
- var intlVersions = ["v4"];
15343
- var suffixesOrder = {
15344
- zero: 0,
15345
- one: 1,
15346
- two: 2,
15347
- few: 3,
15348
- many: 4,
15349
- other: 5
15350
- };
15351
- var createRules = () => {
15352
- const rules = {};
15353
- sets.forEach((set) => {
15354
- set.lngs.forEach((l) => {
15355
- rules[l] = {
15356
- numbers: set.nr,
15357
- plurals: _rulesPluralsTypes[set.fc]
15358
- };
15359
- });
15360
- });
15361
- return rules;
15362
- };
15363
- var PluralResolver = class {
15364
- constructor(languageUtils) {
15365
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
15366
- this.languageUtils = languageUtils;
15367
- this.options = options;
15368
- this.logger = baseLogger.create("pluralResolver");
15369
- if ((!this.options.compatibilityJSON || intlVersions.includes(this.options.compatibilityJSON)) && (typeof Intl === "undefined" || !Intl.PluralRules)) {
15370
- this.options.compatibilityJSON = "v3";
15371
- this.logger.error("Your environment seems not to be Intl API compatible, use an Intl.PluralRules polyfill. Will fallback to the compatibilityJSON v3 format handling.");
15372
- }
15373
- this.rules = createRules();
15374
- this.pluralRulesCache = {};
15375
- }
15376
- addRule(lng, obj) {
15377
- this.rules[lng] = obj;
15378
- }
15379
- clearCache() {
15380
- this.pluralRulesCache = {};
15381
- }
15382
- getRule(code) {
15383
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
15384
- if (this.shouldUseIntlApi()) {
15385
- const cleanedCode = getCleanedCode(code === "dev" ? "en" : code);
15386
- const type = options.ordinal ? "ordinal" : "cardinal";
15387
- const cacheKey = JSON.stringify({
15388
- cleanedCode,
15389
- type
15390
- });
15391
- if (cacheKey in this.pluralRulesCache) {
15392
- return this.pluralRulesCache[cacheKey];
15393
- }
15394
- let rule;
15395
- try {
15396
- rule = new Intl.PluralRules(cleanedCode, {
15397
- type
15398
- });
15399
- } catch (err) {
15400
- if (!code.match(/-|_/)) return;
15401
- const lngPart = this.languageUtils.getLanguagePartFromCode(code);
15402
- rule = this.getRule(lngPart, options);
15403
- }
15404
- this.pluralRulesCache[cacheKey] = rule;
15405
- return rule;
15406
- }
15407
- return this.rules[code] || this.rules[this.languageUtils.getLanguagePartFromCode(code)];
15408
- }
15409
- needsPlural(code) {
15410
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
15411
- const rule = this.getRule(code, options);
15412
- if (this.shouldUseIntlApi()) {
15413
- return rule && rule.resolvedOptions().pluralCategories.length > 1;
15414
- }
15415
- return rule && rule.numbers.length > 1;
15416
- }
15417
- getPluralFormsOfKey(code, key) {
15418
- let options = arguments.length > 2 && arguments[2] !== void 0 ? arguments[2] : {};
15419
- return this.getSuffixes(code, options).map((suffix) => `${key}${suffix}`);
15420
- }
15421
- getSuffixes(code) {
15422
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
15423
- const rule = this.getRule(code, options);
15424
- if (!rule) {
15425
- return [];
15426
- }
15427
- if (this.shouldUseIntlApi()) {
15428
- return rule.resolvedOptions().pluralCategories.sort((pluralCategory1, pluralCategory2) => suffixesOrder[pluralCategory1] - suffixesOrder[pluralCategory2]).map((pluralCategory) => `${this.options.prepend}${options.ordinal ? `ordinal${this.options.prepend}` : ""}${pluralCategory}`);
15429
- }
15430
- return rule.numbers.map((number) => this.getSuffix(code, number, options));
15431
- }
15432
- getSuffix(code, count) {
15433
- let options = arguments.length > 2 && arguments[2] !== void 0 ? arguments[2] : {};
15434
- const rule = this.getRule(code, options);
15435
- if (rule) {
15436
- if (this.shouldUseIntlApi()) {
15437
- return `${this.options.prepend}${options.ordinal ? `ordinal${this.options.prepend}` : ""}${rule.select(count)}`;
15438
- }
15439
- return this.getSuffixRetroCompatible(rule, count);
15440
- }
15441
- this.logger.warn(`no plural rule found for: ${code}`);
15442
- return "";
15443
- }
15444
- getSuffixRetroCompatible(rule, count) {
15445
- const idx = rule.noAbs ? rule.plurals(count) : rule.plurals(Math.abs(count));
15446
- let suffix = rule.numbers[idx];
15447
- if (this.options.simplifyPluralSuffix && rule.numbers.length === 2 && rule.numbers[0] === 1) {
15448
- if (suffix === 2) {
15449
- suffix = "plural";
15450
- } else if (suffix === 1) {
15451
- suffix = "";
15452
- }
15453
- }
15454
- const returnSuffix = () => this.options.prepend && suffix.toString() ? this.options.prepend + suffix.toString() : suffix.toString();
15455
- if (this.options.compatibilityJSON === "v1") {
15456
- if (suffix === 1) return "";
15457
- if (typeof suffix === "number") return `_plural_${suffix.toString()}`;
15458
- return returnSuffix();
15459
- } else if (this.options.compatibilityJSON === "v2") {
15460
- return returnSuffix();
15461
- } else if (this.options.simplifyPluralSuffix && rule.numbers.length === 2 && rule.numbers[0] === 1) {
15462
- return returnSuffix();
15463
- }
15464
- return this.options.prepend && idx.toString() ? this.options.prepend + idx.toString() : idx.toString();
15465
- }
15466
- shouldUseIntlApi() {
15467
- return !nonIntlVersions.includes(this.options.compatibilityJSON);
15468
- }
15469
- };
15470
- var deepFindWithDefaults = function(data, defaultData, key) {
15471
- let keySeparator = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : ".";
15472
- let ignoreJSONStructure = arguments.length > 4 && arguments[4] !== void 0 ? arguments[4] : true;
15473
- let path = getPathWithDefaults(data, defaultData, key);
15474
- if (!path && ignoreJSONStructure && isString(key)) {
15475
- path = deepFind(data, key, keySeparator);
15476
- if (path === void 0) path = deepFind(defaultData, key, keySeparator);
15477
- }
15478
- return path;
15479
- };
15480
- var regexSafe = (val) => val.replace(/\$/g, "$$$$");
15481
- var Interpolator = class {
15482
- constructor() {
15483
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
15484
- this.logger = baseLogger.create("interpolator");
15485
- this.options = options;
15486
- this.format = options.interpolation && options.interpolation.format || ((value) => value);
15487
- this.init(options);
15488
- }
15489
- init() {
15490
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
15491
- if (!options.interpolation) options.interpolation = {
15492
- escapeValue: true
15493
- };
15494
- const {
15495
- escape: escape$1,
15496
- escapeValue,
15497
- useRawValueToEscape,
15498
- prefix,
15499
- prefixEscaped,
15500
- suffix,
15501
- suffixEscaped,
15502
- formatSeparator,
15503
- unescapeSuffix,
15504
- unescapePrefix,
15505
- nestingPrefix,
15506
- nestingPrefixEscaped,
15507
- nestingSuffix,
15508
- nestingSuffixEscaped,
15509
- nestingOptionsSeparator,
15510
- maxReplaces,
15511
- alwaysFormat
15512
- } = options.interpolation;
15513
- this.escape = escape$1 !== void 0 ? escape$1 : escape;
15514
- this.escapeValue = escapeValue !== void 0 ? escapeValue : true;
15515
- this.useRawValueToEscape = useRawValueToEscape !== void 0 ? useRawValueToEscape : false;
15516
- this.prefix = prefix ? regexEscape(prefix) : prefixEscaped || "{{";
15517
- this.suffix = suffix ? regexEscape(suffix) : suffixEscaped || "}}";
15518
- this.formatSeparator = formatSeparator || ",";
15519
- this.unescapePrefix = unescapeSuffix ? "" : unescapePrefix || "-";
15520
- this.unescapeSuffix = this.unescapePrefix ? "" : unescapeSuffix || "";
15521
- this.nestingPrefix = nestingPrefix ? regexEscape(nestingPrefix) : nestingPrefixEscaped || regexEscape("$t(");
15522
- this.nestingSuffix = nestingSuffix ? regexEscape(nestingSuffix) : nestingSuffixEscaped || regexEscape(")");
15523
- this.nestingOptionsSeparator = nestingOptionsSeparator || ",";
15524
- this.maxReplaces = maxReplaces || 1e3;
15525
- this.alwaysFormat = alwaysFormat !== void 0 ? alwaysFormat : false;
15526
- this.resetRegExp();
15527
- }
15528
- reset() {
15529
- if (this.options) this.init(this.options);
15530
- }
15531
- resetRegExp() {
15532
- const getOrResetRegExp = (existingRegExp, pattern) => {
15533
- if (existingRegExp && existingRegExp.source === pattern) {
15534
- existingRegExp.lastIndex = 0;
15535
- return existingRegExp;
15536
- }
15537
- return new RegExp(pattern, "g");
15538
- };
15539
- this.regexp = getOrResetRegExp(this.regexp, `${this.prefix}(.+?)${this.suffix}`);
15540
- this.regexpUnescape = getOrResetRegExp(this.regexpUnescape, `${this.prefix}${this.unescapePrefix}(.+?)${this.unescapeSuffix}${this.suffix}`);
15541
- this.nestingRegexp = getOrResetRegExp(this.nestingRegexp, `${this.nestingPrefix}(.+?)${this.nestingSuffix}`);
15542
- }
15543
- interpolate(str, data, lng, options) {
15544
- let match;
15545
- let value;
15546
- let replaces;
15547
- const defaultData = this.options && this.options.interpolation && this.options.interpolation.defaultVariables || {};
15548
- const handleFormat = (key) => {
15549
- if (key.indexOf(this.formatSeparator) < 0) {
15550
- const path = deepFindWithDefaults(data, defaultData, key, this.options.keySeparator, this.options.ignoreJSONStructure);
15551
- return this.alwaysFormat ? this.format(path, void 0, lng, {
15552
- ...options,
15553
- ...data,
15554
- interpolationkey: key
15555
- }) : path;
15556
- }
15557
- const p = key.split(this.formatSeparator);
15558
- const k = p.shift().trim();
15559
- const f = p.join(this.formatSeparator).trim();
15560
- return this.format(deepFindWithDefaults(data, defaultData, k, this.options.keySeparator, this.options.ignoreJSONStructure), f, lng, {
15561
- ...options,
15562
- ...data,
15563
- interpolationkey: k
15564
- });
15565
- };
15566
- this.resetRegExp();
15567
- const missingInterpolationHandler = options && options.missingInterpolationHandler || this.options.missingInterpolationHandler;
15568
- const skipOnVariables = options && options.interpolation && options.interpolation.skipOnVariables !== void 0 ? options.interpolation.skipOnVariables : this.options.interpolation.skipOnVariables;
15569
- const todos = [{
15570
- regex: this.regexpUnescape,
15571
- safeValue: (val) => regexSafe(val)
15572
- }, {
15573
- regex: this.regexp,
15574
- safeValue: (val) => this.escapeValue ? regexSafe(this.escape(val)) : regexSafe(val)
15575
- }];
15576
- todos.forEach((todo) => {
15577
- replaces = 0;
15578
- while (match = todo.regex.exec(str)) {
15579
- const matchedVar = match[1].trim();
15580
- value = handleFormat(matchedVar);
15581
- if (value === void 0) {
15582
- if (typeof missingInterpolationHandler === "function") {
15583
- const temp = missingInterpolationHandler(str, match, options);
15584
- value = isString(temp) ? temp : "";
15585
- } else if (options && Object.prototype.hasOwnProperty.call(options, matchedVar)) {
15586
- value = "";
15587
- } else if (skipOnVariables) {
15588
- value = match[0];
15589
- continue;
15590
- } else {
15591
- this.logger.warn(`missed to pass in variable ${matchedVar} for interpolating ${str}`);
15592
- value = "";
15593
- }
15594
- } else if (!isString(value) && !this.useRawValueToEscape) {
15595
- value = makeString(value);
15596
- }
15597
- const safeValue = todo.safeValue(value);
15598
- str = str.replace(match[0], safeValue);
15599
- if (skipOnVariables) {
15600
- todo.regex.lastIndex += value.length;
15601
- todo.regex.lastIndex -= match[0].length;
15602
- } else {
15603
- todo.regex.lastIndex = 0;
15604
- }
15605
- replaces++;
15606
- if (replaces >= this.maxReplaces) {
15607
- break;
15608
- }
15609
- }
15610
- });
15611
- return str;
15612
- }
15613
- nest(str, fc) {
15614
- let options = arguments.length > 2 && arguments[2] !== void 0 ? arguments[2] : {};
15615
- let match;
15616
- let value;
15617
- let clonedOptions;
15618
- const handleHasOptions = (key, inheritedOptions) => {
15619
- const sep = this.nestingOptionsSeparator;
15620
- if (key.indexOf(sep) < 0) return key;
15621
- const c = key.split(new RegExp(`${sep}[ ]*{`));
15622
- let optionsString = `{${c[1]}`;
15623
- key = c[0];
15624
- optionsString = this.interpolate(optionsString, clonedOptions);
15625
- const matchedSingleQuotes = optionsString.match(/'/g);
15626
- const matchedDoubleQuotes = optionsString.match(/"/g);
15627
- if (matchedSingleQuotes && matchedSingleQuotes.length % 2 === 0 && !matchedDoubleQuotes || matchedDoubleQuotes.length % 2 !== 0) {
15628
- optionsString = optionsString.replace(/'/g, '"');
15629
- }
15630
- try {
15631
- clonedOptions = JSON.parse(optionsString);
15632
- if (inheritedOptions) clonedOptions = {
15633
- ...inheritedOptions,
15634
- ...clonedOptions
15635
- };
15636
- } catch (e) {
15637
- this.logger.warn(`failed parsing options string in nesting for key ${key}`, e);
15638
- return `${key}${sep}${optionsString}`;
15639
- }
15640
- if (clonedOptions.defaultValue && clonedOptions.defaultValue.indexOf(this.prefix) > -1) delete clonedOptions.defaultValue;
15641
- return key;
15642
- };
15643
- while (match = this.nestingRegexp.exec(str)) {
15644
- let formatters = [];
15645
- clonedOptions = {
15646
- ...options
15647
- };
15648
- clonedOptions = clonedOptions.replace && !isString(clonedOptions.replace) ? clonedOptions.replace : clonedOptions;
15649
- clonedOptions.applyPostProcessor = false;
15650
- delete clonedOptions.defaultValue;
15651
- let doReduce = false;
15652
- if (match[0].indexOf(this.formatSeparator) !== -1 && !/{.*}/.test(match[1])) {
15653
- const r2 = match[1].split(this.formatSeparator).map((elem) => elem.trim());
15654
- match[1] = r2.shift();
15655
- formatters = r2;
15656
- doReduce = true;
15657
- }
15658
- value = fc(handleHasOptions.call(this, match[1].trim(), clonedOptions), clonedOptions);
15659
- if (value && match[0] === str && !isString(value)) return value;
15660
- if (!isString(value)) value = makeString(value);
15661
- if (!value) {
15662
- this.logger.warn(`missed to resolve ${match[1]} for nesting ${str}`);
15663
- value = "";
15664
- }
15665
- if (doReduce) {
15666
- value = formatters.reduce((v, f) => this.format(v, f, options.lng, {
15667
- ...options,
15668
- interpolationkey: match[1].trim()
15669
- }), value.trim());
15670
- }
15671
- str = str.replace(match[0], value);
15672
- this.regexp.lastIndex = 0;
15673
- }
15674
- return str;
15675
- }
15676
- };
15677
- var parseFormatStr = (formatStr) => {
15678
- let formatName = formatStr.toLowerCase().trim();
15679
- const formatOptions = {};
15680
- if (formatStr.indexOf("(") > -1) {
15681
- const p = formatStr.split("(");
15682
- formatName = p[0].toLowerCase().trim();
15683
- const optStr = p[1].substring(0, p[1].length - 1);
15684
- if (formatName === "currency" && optStr.indexOf(":") < 0) {
15685
- if (!formatOptions.currency) formatOptions.currency = optStr.trim();
15686
- } else if (formatName === "relativetime" && optStr.indexOf(":") < 0) {
15687
- if (!formatOptions.range) formatOptions.range = optStr.trim();
15688
- } else {
15689
- const opts = optStr.split(";");
15690
- opts.forEach((opt) => {
15691
- if (opt) {
15692
- const [key, ...rest] = opt.split(":");
15693
- const val = rest.join(":").trim().replace(/^'+|'+$/g, "");
15694
- const trimmedKey = key.trim();
15695
- if (!formatOptions[trimmedKey]) formatOptions[trimmedKey] = val;
15696
- if (val === "false") formatOptions[trimmedKey] = false;
15697
- if (val === "true") formatOptions[trimmedKey] = true;
15698
- if (!isNaN(val)) formatOptions[trimmedKey] = parseInt(val, 10);
15699
- }
15700
- });
15701
- }
15702
- }
15703
- return {
15704
- formatName,
15705
- formatOptions
15706
- };
15707
- };
15708
- var createCachedFormatter = (fn) => {
15709
- const cache = {};
15710
- return (val, lng, options) => {
15711
- let optForCache = options;
15712
- if (options && options.interpolationkey && options.formatParams && options.formatParams[options.interpolationkey] && options[options.interpolationkey]) {
15713
- optForCache = {
15714
- ...optForCache,
15715
- [options.interpolationkey]: void 0
15716
- };
15717
- }
15718
- const key = lng + JSON.stringify(optForCache);
15719
- let formatter = cache[key];
15720
- if (!formatter) {
15721
- formatter = fn(getCleanedCode(lng), options);
15722
- cache[key] = formatter;
15723
- }
15724
- return formatter(val);
15725
- };
15726
- };
15727
- var Formatter = class {
15728
- constructor() {
15729
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
15730
- this.logger = baseLogger.create("formatter");
15731
- this.options = options;
15732
- this.formats = {
15733
- number: createCachedFormatter((lng, opt) => {
15734
- const formatter = new Intl.NumberFormat(lng, {
15735
- ...opt
15736
- });
15737
- return (val) => formatter.format(val);
15738
- }),
15739
- currency: createCachedFormatter((lng, opt) => {
15740
- const formatter = new Intl.NumberFormat(lng, {
15741
- ...opt,
15742
- style: "currency"
15743
- });
15744
- return (val) => formatter.format(val);
15745
- }),
15746
- datetime: createCachedFormatter((lng, opt) => {
15747
- const formatter = new Intl.DateTimeFormat(lng, {
15748
- ...opt
15749
- });
15750
- return (val) => formatter.format(val);
15751
- }),
15752
- relativetime: createCachedFormatter((lng, opt) => {
15753
- const formatter = new Intl.RelativeTimeFormat(lng, {
15754
- ...opt
15755
- });
15756
- return (val) => formatter.format(val, opt.range || "day");
15757
- }),
15758
- list: createCachedFormatter((lng, opt) => {
15759
- const formatter = new Intl.ListFormat(lng, {
15760
- ...opt
15761
- });
15762
- return (val) => formatter.format(val);
15763
- })
15764
- };
15765
- this.init(options);
15766
- }
15767
- init(services) {
15768
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {
15769
- interpolation: {}
15770
- };
15771
- this.formatSeparator = options.interpolation.formatSeparator || ",";
15772
- }
15773
- add(name, fc) {
15774
- this.formats[name.toLowerCase().trim()] = fc;
15775
- }
15776
- addCached(name, fc) {
15777
- this.formats[name.toLowerCase().trim()] = createCachedFormatter(fc);
15778
- }
15779
- format(value, format, lng) {
15780
- let options = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {};
15781
- const formats = format.split(this.formatSeparator);
15782
- if (formats.length > 1 && formats[0].indexOf("(") > 1 && formats[0].indexOf(")") < 0 && formats.find((f) => f.indexOf(")") > -1)) {
15783
- const lastIndex = formats.findIndex((f) => f.indexOf(")") > -1);
15784
- formats[0] = [formats[0], ...formats.splice(1, lastIndex)].join(this.formatSeparator);
15785
- }
15786
- const result = formats.reduce((mem, f) => {
15787
- const {
15788
- formatName,
15789
- formatOptions
15790
- } = parseFormatStr(f);
15791
- if (this.formats[formatName]) {
15792
- let formatted = mem;
15793
- try {
15794
- const valOptions = options && options.formatParams && options.formatParams[options.interpolationkey] || {};
15795
- const l = valOptions.locale || valOptions.lng || options.locale || options.lng || lng;
15796
- formatted = this.formats[formatName](mem, l, {
15797
- ...formatOptions,
15798
- ...options,
15799
- ...valOptions
15800
- });
15801
- } catch (error) {
15802
- this.logger.warn(error);
15803
- }
15804
- return formatted;
15805
- } else {
15806
- this.logger.warn(`there was no format function for ${formatName}`);
15807
- }
15808
- return mem;
15809
- }, value);
15810
- return result;
15811
- }
15812
- };
15813
- var removePending = (q, name) => {
15814
- if (q.pending[name] !== void 0) {
15815
- delete q.pending[name];
15816
- q.pendingCount--;
15817
- }
15818
- };
15819
- var Connector = class extends EventEmitter {
15820
- constructor(backend, store, services) {
15821
- let options = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {};
15822
- super();
15823
- this.backend = backend;
15824
- this.store = store;
15825
- this.services = services;
15826
- this.languageUtils = services.languageUtils;
15827
- this.options = options;
15828
- this.logger = baseLogger.create("backendConnector");
15829
- this.waitingReads = [];
15830
- this.maxParallelReads = options.maxParallelReads || 10;
15831
- this.readingCalls = 0;
15832
- this.maxRetries = options.maxRetries >= 0 ? options.maxRetries : 5;
15833
- this.retryTimeout = options.retryTimeout >= 1 ? options.retryTimeout : 350;
15834
- this.state = {};
15835
- this.queue = [];
15836
- if (this.backend && this.backend.init) {
15837
- this.backend.init(services, options.backend, options);
15838
- }
15839
- }
15840
- queueLoad(languages, namespaces, options, callback) {
15841
- const toLoad = {};
15842
- const pending = {};
15843
- const toLoadLanguages = {};
15844
- const toLoadNamespaces = {};
15845
- languages.forEach((lng) => {
15846
- let hasAllNamespaces = true;
15847
- namespaces.forEach((ns) => {
15848
- const name = `${lng}|${ns}`;
15849
- if (!options.reload && this.store.hasResourceBundle(lng, ns)) {
15850
- this.state[name] = 2;
15851
- } else if (this.state[name] < 0) ;
15852
- else if (this.state[name] === 1) {
15853
- if (pending[name] === void 0) pending[name] = true;
15854
- } else {
15855
- this.state[name] = 1;
15856
- hasAllNamespaces = false;
15857
- if (pending[name] === void 0) pending[name] = true;
15858
- if (toLoad[name] === void 0) toLoad[name] = true;
15859
- if (toLoadNamespaces[ns] === void 0) toLoadNamespaces[ns] = true;
15860
- }
15861
- });
15862
- if (!hasAllNamespaces) toLoadLanguages[lng] = true;
15863
- });
15864
- if (Object.keys(toLoad).length || Object.keys(pending).length) {
15865
- this.queue.push({
15866
- pending,
15867
- pendingCount: Object.keys(pending).length,
15868
- loaded: {},
15869
- errors: [],
15870
- callback
15871
- });
15872
- }
15873
- return {
15874
- toLoad: Object.keys(toLoad),
15875
- pending: Object.keys(pending),
15876
- toLoadLanguages: Object.keys(toLoadLanguages),
15877
- toLoadNamespaces: Object.keys(toLoadNamespaces)
15878
- };
15879
- }
15880
- loaded(name, err, data) {
15881
- const s = name.split("|");
15882
- const lng = s[0];
15883
- const ns = s[1];
15884
- if (err) this.emit("failedLoading", lng, ns, err);
15885
- if (!err && data) {
15886
- this.store.addResourceBundle(lng, ns, data, void 0, void 0, {
15887
- skipCopy: true
15888
- });
15889
- }
15890
- this.state[name] = err ? -1 : 2;
15891
- if (err && data) this.state[name] = 0;
15892
- const loaded = {};
15893
- this.queue.forEach((q) => {
15894
- pushPath(q.loaded, [lng], ns);
15895
- removePending(q, name);
15896
- if (err) q.errors.push(err);
15897
- if (q.pendingCount === 0 && !q.done) {
15898
- Object.keys(q.loaded).forEach((l) => {
15899
- if (!loaded[l]) loaded[l] = {};
15900
- const loadedKeys = q.loaded[l];
15901
- if (loadedKeys.length) {
15902
- loadedKeys.forEach((n) => {
15903
- if (loaded[l][n] === void 0) loaded[l][n] = true;
15904
- });
15905
- }
15906
- });
15907
- q.done = true;
15908
- if (q.errors.length) {
15909
- q.callback(q.errors);
15910
- } else {
15911
- q.callback();
15912
- }
15913
- }
15914
- });
15915
- this.emit("loaded", loaded);
15916
- this.queue = this.queue.filter((q) => !q.done);
15917
- }
15918
- read(lng, ns, fcName) {
15919
- let tried = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : 0;
15920
- let wait = arguments.length > 4 && arguments[4] !== void 0 ? arguments[4] : this.retryTimeout;
15921
- let callback = arguments.length > 5 ? arguments[5] : void 0;
15922
- if (!lng.length) return callback(null, {});
15923
- if (this.readingCalls >= this.maxParallelReads) {
15924
- this.waitingReads.push({
15925
- lng,
15926
- ns,
15927
- fcName,
15928
- tried,
15929
- wait,
15930
- callback
15931
- });
15932
- return;
15933
- }
15934
- this.readingCalls++;
15935
- const resolver = (err, data) => {
15936
- this.readingCalls--;
15937
- if (this.waitingReads.length > 0) {
15938
- const next = this.waitingReads.shift();
15939
- this.read(next.lng, next.ns, next.fcName, next.tried, next.wait, next.callback);
15940
- }
15941
- if (err && data && tried < this.maxRetries) {
15942
- setTimeout(() => {
15943
- this.read.call(this, lng, ns, fcName, tried + 1, wait * 2, callback);
15944
- }, wait);
15945
- return;
15946
- }
15947
- callback(err, data);
15948
- };
15949
- const fc = this.backend[fcName].bind(this.backend);
15950
- if (fc.length === 2) {
15951
- try {
15952
- const r2 = fc(lng, ns);
15953
- if (r2 && typeof r2.then === "function") {
15954
- r2.then((data) => resolver(null, data)).catch(resolver);
15955
- } else {
15956
- resolver(null, r2);
15957
- }
15958
- } catch (err) {
15959
- resolver(err);
15960
- }
15961
- return;
15962
- }
15963
- return fc(lng, ns, resolver);
15964
- }
15965
- prepareLoading(languages, namespaces) {
15966
- let options = arguments.length > 2 && arguments[2] !== void 0 ? arguments[2] : {};
15967
- let callback = arguments.length > 3 ? arguments[3] : void 0;
15968
- if (!this.backend) {
15969
- this.logger.warn("No backend was added via i18next.use. Will not load resources.");
15970
- return callback && callback();
15971
- }
15972
- if (isString(languages)) languages = this.languageUtils.toResolveHierarchy(languages);
15973
- if (isString(namespaces)) namespaces = [namespaces];
15974
- const toLoad = this.queueLoad(languages, namespaces, options, callback);
15975
- if (!toLoad.toLoad.length) {
15976
- if (!toLoad.pending.length) callback();
15977
- return null;
15978
- }
15979
- toLoad.toLoad.forEach((name) => {
15980
- this.loadOne(name);
15981
- });
15982
- }
15983
- load(languages, namespaces, callback) {
15984
- this.prepareLoading(languages, namespaces, {}, callback);
15985
- }
15986
- reload(languages, namespaces, callback) {
15987
- this.prepareLoading(languages, namespaces, {
15988
- reload: true
15989
- }, callback);
15990
- }
15991
- loadOne(name) {
15992
- let prefix = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : "";
15993
- const s = name.split("|");
15994
- const lng = s[0];
15995
- const ns = s[1];
15996
- this.read(lng, ns, "read", void 0, void 0, (err, data) => {
15997
- if (err) this.logger.warn(`${prefix}loading namespace ${ns} for language ${lng} failed`, err);
15998
- if (!err && data) this.logger.log(`${prefix}loaded namespace ${ns} for language ${lng}`, data);
15999
- this.loaded(name, err, data);
16000
- });
16001
- }
16002
- saveMissing(languages, namespace, key, fallbackValue, isUpdate) {
16003
- let options = arguments.length > 5 && arguments[5] !== void 0 ? arguments[5] : {};
16004
- let clb = arguments.length > 6 && arguments[6] !== void 0 ? arguments[6] : () => {
16005
- };
16006
- if (this.services.utils && this.services.utils.hasLoadedNamespace && !this.services.utils.hasLoadedNamespace(namespace)) {
16007
- this.logger.warn(`did not save key "${key}" as the namespace "${namespace}" was not yet loaded`, "This means something IS WRONG in your setup. You access the t function before i18next.init / i18next.loadNamespace / i18next.changeLanguage was done. Wait for the callback or Promise to resolve before accessing it!!!");
16008
- return;
16009
- }
16010
- if (key === void 0 || key === null || key === "") return;
16011
- if (this.backend && this.backend.create) {
16012
- const opts = {
16013
- ...options,
16014
- isUpdate
16015
- };
16016
- const fc = this.backend.create.bind(this.backend);
16017
- if (fc.length < 6) {
16018
- try {
16019
- let r2;
16020
- if (fc.length === 5) {
16021
- r2 = fc(languages, namespace, key, fallbackValue, opts);
16022
- } else {
16023
- r2 = fc(languages, namespace, key, fallbackValue);
16024
- }
16025
- if (r2 && typeof r2.then === "function") {
16026
- r2.then((data) => clb(null, data)).catch(clb);
16027
- } else {
16028
- clb(null, r2);
16029
- }
16030
- } catch (err) {
16031
- clb(err);
16032
- }
16033
- } else {
16034
- fc(languages, namespace, key, fallbackValue, clb, opts);
16035
- }
16036
- }
16037
- if (!languages || !languages[0]) return;
16038
- this.store.addResource(languages[0], namespace, key, fallbackValue);
16039
- }
16040
- };
16041
- var get = () => ({
16042
- debug: false,
16043
- initImmediate: true,
16044
- ns: ["translation"],
16045
- defaultNS: ["translation"],
16046
- fallbackLng: ["dev"],
16047
- fallbackNS: false,
16048
- supportedLngs: false,
16049
- nonExplicitSupportedLngs: false,
16050
- load: "all",
16051
- preload: false,
16052
- simplifyPluralSuffix: true,
16053
- keySeparator: ".",
16054
- nsSeparator: ":",
16055
- pluralSeparator: "_",
16056
- contextSeparator: "_",
16057
- partialBundledLanguages: false,
16058
- saveMissing: false,
16059
- updateMissing: false,
16060
- saveMissingTo: "fallback",
16061
- saveMissingPlurals: true,
16062
- missingKeyHandler: false,
16063
- missingInterpolationHandler: false,
16064
- postProcess: false,
16065
- postProcessPassResolved: false,
16066
- returnNull: false,
16067
- returnEmptyString: true,
16068
- returnObjects: false,
16069
- joinArrays: false,
16070
- returnedObjectHandler: false,
16071
- parseMissingKeyHandler: false,
16072
- appendNamespaceToMissingKey: false,
16073
- appendNamespaceToCIMode: false,
16074
- overloadTranslationOptionHandler: (args) => {
16075
- let ret = {};
16076
- if (typeof args[1] === "object") ret = args[1];
16077
- if (isString(args[1])) ret.defaultValue = args[1];
16078
- if (isString(args[2])) ret.tDescription = args[2];
16079
- if (typeof args[2] === "object" || typeof args[3] === "object") {
16080
- const options = args[3] || args[2];
16081
- Object.keys(options).forEach((key) => {
16082
- ret[key] = options[key];
16083
- });
16084
- }
16085
- return ret;
16086
- },
16087
- interpolation: {
16088
- escapeValue: true,
16089
- format: (value) => value,
16090
- prefix: "{{",
16091
- suffix: "}}",
16092
- formatSeparator: ",",
16093
- unescapePrefix: "-",
16094
- nestingPrefix: "$t(",
16095
- nestingSuffix: ")",
16096
- nestingOptionsSeparator: ",",
16097
- maxReplaces: 1e3,
16098
- skipOnVariables: true
16099
- }
16100
- });
16101
- var transformOptions = (options) => {
16102
- if (isString(options.ns)) options.ns = [options.ns];
16103
- if (isString(options.fallbackLng)) options.fallbackLng = [options.fallbackLng];
16104
- if (isString(options.fallbackNS)) options.fallbackNS = [options.fallbackNS];
16105
- if (options.supportedLngs && options.supportedLngs.indexOf("cimode") < 0) {
16106
- options.supportedLngs = options.supportedLngs.concat(["cimode"]);
16107
- }
16108
- return options;
16109
- };
16110
- var noop = () => {
16111
- };
16112
- var bindMemberFunctions = (inst) => {
16113
- const mems = Object.getOwnPropertyNames(Object.getPrototypeOf(inst));
16114
- mems.forEach((mem) => {
16115
- if (typeof inst[mem] === "function") {
16116
- inst[mem] = inst[mem].bind(inst);
16117
- }
16118
- });
16119
- };
16120
- var I18n = class _I18n extends EventEmitter {
16121
- constructor() {
16122
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
16123
- let callback = arguments.length > 1 ? arguments[1] : void 0;
16124
- super();
16125
- this.options = transformOptions(options);
16126
- this.services = {};
16127
- this.logger = baseLogger;
16128
- this.modules = {
16129
- external: []
16130
- };
16131
- bindMemberFunctions(this);
16132
- if (callback && !this.isInitialized && !options.isClone) {
16133
- if (!this.options.initImmediate) {
16134
- this.init(options, callback);
16135
- return this;
16136
- }
16137
- setTimeout(() => {
16138
- this.init(options, callback);
16139
- }, 0);
16140
- }
16141
- }
16142
- init() {
16143
- var _this = this;
16144
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
16145
- let callback = arguments.length > 1 ? arguments[1] : void 0;
16146
- this.isInitializing = true;
16147
- if (typeof options === "function") {
16148
- callback = options;
16149
- options = {};
16150
- }
16151
- if (!options.defaultNS && options.defaultNS !== false && options.ns) {
16152
- if (isString(options.ns)) {
16153
- options.defaultNS = options.ns;
16154
- } else if (options.ns.indexOf("translation") < 0) {
16155
- options.defaultNS = options.ns[0];
16156
- }
16157
- }
16158
- const defOpts = get();
16159
- this.options = {
16160
- ...defOpts,
16161
- ...this.options,
16162
- ...transformOptions(options)
16163
- };
16164
- if (this.options.compatibilityAPI !== "v1") {
16165
- this.options.interpolation = {
16166
- ...defOpts.interpolation,
16167
- ...this.options.interpolation
16168
- };
16169
- }
16170
- if (options.keySeparator !== void 0) {
16171
- this.options.userDefinedKeySeparator = options.keySeparator;
16172
- }
16173
- if (options.nsSeparator !== void 0) {
16174
- this.options.userDefinedNsSeparator = options.nsSeparator;
16175
- }
16176
- const createClassOnDemand = (ClassOrObject) => {
16177
- if (!ClassOrObject) return null;
16178
- if (typeof ClassOrObject === "function") return new ClassOrObject();
16179
- return ClassOrObject;
16180
- };
16181
- if (!this.options.isClone) {
16182
- if (this.modules.logger) {
16183
- baseLogger.init(createClassOnDemand(this.modules.logger), this.options);
16184
- } else {
16185
- baseLogger.init(null, this.options);
16186
- }
16187
- let formatter;
16188
- if (this.modules.formatter) {
16189
- formatter = this.modules.formatter;
16190
- } else if (typeof Intl !== "undefined") {
16191
- formatter = Formatter;
16192
- }
16193
- const lu = new LanguageUtil(this.options);
16194
- this.store = new ResourceStore(this.options.resources, this.options);
16195
- const s = this.services;
16196
- s.logger = baseLogger;
16197
- s.resourceStore = this.store;
16198
- s.languageUtils = lu;
16199
- s.pluralResolver = new PluralResolver(lu, {
16200
- prepend: this.options.pluralSeparator,
16201
- compatibilityJSON: this.options.compatibilityJSON,
16202
- simplifyPluralSuffix: this.options.simplifyPluralSuffix
16203
- });
16204
- if (formatter && (!this.options.interpolation.format || this.options.interpolation.format === defOpts.interpolation.format)) {
16205
- s.formatter = createClassOnDemand(formatter);
16206
- s.formatter.init(s, this.options);
16207
- this.options.interpolation.format = s.formatter.format.bind(s.formatter);
16208
- }
16209
- s.interpolator = new Interpolator(this.options);
16210
- s.utils = {
16211
- hasLoadedNamespace: this.hasLoadedNamespace.bind(this)
16212
- };
16213
- s.backendConnector = new Connector(createClassOnDemand(this.modules.backend), s.resourceStore, s, this.options);
16214
- s.backendConnector.on("*", function(event) {
16215
- for (var _len = arguments.length, args = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
16216
- args[_key - 1] = arguments[_key];
16217
- }
16218
- _this.emit(event, ...args);
16219
- });
16220
- if (this.modules.languageDetector) {
16221
- s.languageDetector = createClassOnDemand(this.modules.languageDetector);
16222
- if (s.languageDetector.init) s.languageDetector.init(s, this.options.detection, this.options);
16223
- }
16224
- if (this.modules.i18nFormat) {
16225
- s.i18nFormat = createClassOnDemand(this.modules.i18nFormat);
16226
- if (s.i18nFormat.init) s.i18nFormat.init(this);
16227
- }
16228
- this.translator = new Translator(this.services, this.options);
16229
- this.translator.on("*", function(event) {
16230
- for (var _len2 = arguments.length, args = new Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {
16231
- args[_key2 - 1] = arguments[_key2];
16232
- }
16233
- _this.emit(event, ...args);
16234
- });
16235
- this.modules.external.forEach((m) => {
16236
- if (m.init) m.init(this);
16237
- });
16238
- }
16239
- this.format = this.options.interpolation.format;
16240
- if (!callback) callback = noop;
16241
- if (this.options.fallbackLng && !this.services.languageDetector && !this.options.lng) {
16242
- const codes = this.services.languageUtils.getFallbackCodes(this.options.fallbackLng);
16243
- if (codes.length > 0 && codes[0] !== "dev") this.options.lng = codes[0];
16244
- }
16245
- if (!this.services.languageDetector && !this.options.lng) {
16246
- this.logger.warn("init: no languageDetector is used and no lng is defined");
16247
- }
16248
- const storeApi = ["getResource", "hasResourceBundle", "getResourceBundle", "getDataByLanguage"];
16249
- storeApi.forEach((fcName) => {
16250
- this[fcName] = function() {
16251
- return _this.store[fcName](...arguments);
16252
- };
16253
- });
16254
- const storeApiChained = ["addResource", "addResources", "addResourceBundle", "removeResourceBundle"];
16255
- storeApiChained.forEach((fcName) => {
16256
- this[fcName] = function() {
16257
- _this.store[fcName](...arguments);
16258
- return _this;
16259
- };
16260
- });
16261
- const deferred = defer();
16262
- const load = () => {
16263
- const finish = (err, t2) => {
16264
- this.isInitializing = false;
16265
- if (this.isInitialized && !this.initializedStoreOnce) this.logger.warn("init: i18next is already initialized. You should call init just once!");
16266
- this.isInitialized = true;
16267
- if (!this.options.isClone) this.logger.log("initialized", this.options);
16268
- this.emit("initialized", this.options);
16269
- deferred.resolve(t2);
16270
- callback(err, t2);
16271
- };
16272
- if (this.languages && this.options.compatibilityAPI !== "v1" && !this.isInitialized) return finish(null, this.t.bind(this));
16273
- this.changeLanguage(this.options.lng, finish);
16274
- };
16275
- if (this.options.resources || !this.options.initImmediate) {
16276
- load();
16277
- } else {
16278
- setTimeout(load, 0);
16279
- }
16280
- return deferred;
16281
- }
16282
- loadResources(language) {
16283
- let callback = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : noop;
16284
- let usedCallback = callback;
16285
- const usedLng = isString(language) ? language : this.language;
16286
- if (typeof language === "function") usedCallback = language;
16287
- if (!this.options.resources || this.options.partialBundledLanguages) {
16288
- if (usedLng && usedLng.toLowerCase() === "cimode" && (!this.options.preload || this.options.preload.length === 0)) return usedCallback();
16289
- const toLoad = [];
16290
- const append = (lng) => {
16291
- if (!lng) return;
16292
- if (lng === "cimode") return;
16293
- const lngs = this.services.languageUtils.toResolveHierarchy(lng);
16294
- lngs.forEach((l) => {
16295
- if (l === "cimode") return;
16296
- if (toLoad.indexOf(l) < 0) toLoad.push(l);
16297
- });
16298
- };
16299
- if (!usedLng) {
16300
- const fallbacks = this.services.languageUtils.getFallbackCodes(this.options.fallbackLng);
16301
- fallbacks.forEach((l) => append(l));
16302
- } else {
16303
- append(usedLng);
16304
- }
16305
- if (this.options.preload) {
16306
- this.options.preload.forEach((l) => append(l));
16307
- }
16308
- this.services.backendConnector.load(toLoad, this.options.ns, (e) => {
16309
- if (!e && !this.resolvedLanguage && this.language) this.setResolvedLanguage(this.language);
16310
- usedCallback(e);
16311
- });
16312
- } else {
16313
- usedCallback(null);
16314
- }
16315
- }
16316
- reloadResources(lngs, ns, callback) {
16317
- const deferred = defer();
16318
- if (typeof lngs === "function") {
16319
- callback = lngs;
16320
- lngs = void 0;
16321
- }
16322
- if (typeof ns === "function") {
16323
- callback = ns;
16324
- ns = void 0;
16325
- }
16326
- if (!lngs) lngs = this.languages;
16327
- if (!ns) ns = this.options.ns;
16328
- if (!callback) callback = noop;
16329
- this.services.backendConnector.reload(lngs, ns, (err) => {
16330
- deferred.resolve();
16331
- callback(err);
16332
- });
16333
- return deferred;
16334
- }
16335
- use(module) {
16336
- if (!module) throw new Error("You are passing an undefined module! Please check the object you are passing to i18next.use()");
16337
- if (!module.type) throw new Error("You are passing a wrong module! Please check the object you are passing to i18next.use()");
16338
- if (module.type === "backend") {
16339
- this.modules.backend = module;
16340
- }
16341
- if (module.type === "logger" || module.log && module.warn && module.error) {
16342
- this.modules.logger = module;
16343
- }
16344
- if (module.type === "languageDetector") {
16345
- this.modules.languageDetector = module;
16346
- }
16347
- if (module.type === "i18nFormat") {
16348
- this.modules.i18nFormat = module;
16349
- }
16350
- if (module.type === "postProcessor") {
16351
- postProcessor.addPostProcessor(module);
16352
- }
16353
- if (module.type === "formatter") {
16354
- this.modules.formatter = module;
16355
- }
16356
- if (module.type === "3rdParty") {
16357
- this.modules.external.push(module);
16358
- }
16359
- return this;
16360
- }
16361
- setResolvedLanguage(l) {
16362
- if (!l || !this.languages) return;
16363
- if (["cimode", "dev"].indexOf(l) > -1) return;
16364
- for (let li = 0; li < this.languages.length; li++) {
16365
- const lngInLngs = this.languages[li];
16366
- if (["cimode", "dev"].indexOf(lngInLngs) > -1) continue;
16367
- if (this.store.hasLanguageSomeTranslations(lngInLngs)) {
16368
- this.resolvedLanguage = lngInLngs;
16369
- break;
16370
- }
16371
- }
16372
- }
16373
- changeLanguage(lng, callback) {
16374
- var _this2 = this;
16375
- this.isLanguageChangingTo = lng;
16376
- const deferred = defer();
16377
- this.emit("languageChanging", lng);
16378
- const setLngProps = (l) => {
16379
- this.language = l;
16380
- this.languages = this.services.languageUtils.toResolveHierarchy(l);
16381
- this.resolvedLanguage = void 0;
16382
- this.setResolvedLanguage(l);
16383
- };
16384
- const done = (err, l) => {
16385
- if (l) {
16386
- setLngProps(l);
16387
- this.translator.changeLanguage(l);
16388
- this.isLanguageChangingTo = void 0;
16389
- this.emit("languageChanged", l);
16390
- this.logger.log("languageChanged", l);
16391
- } else {
16392
- this.isLanguageChangingTo = void 0;
16393
- }
16394
- deferred.resolve(function() {
16395
- return _this2.t(...arguments);
16396
- });
16397
- if (callback) callback(err, function() {
16398
- return _this2.t(...arguments);
16399
- });
16400
- };
16401
- const setLng = (lngs) => {
16402
- if (!lng && !lngs && this.services.languageDetector) lngs = [];
16403
- const l = isString(lngs) ? lngs : this.services.languageUtils.getBestMatchFromCodes(lngs);
16404
- if (l) {
16405
- if (!this.language) {
16406
- setLngProps(l);
16407
- }
16408
- if (!this.translator.language) this.translator.changeLanguage(l);
16409
- if (this.services.languageDetector && this.services.languageDetector.cacheUserLanguage) this.services.languageDetector.cacheUserLanguage(l);
16410
- }
16411
- this.loadResources(l, (err) => {
16412
- done(err, l);
16413
- });
16414
- };
16415
- if (!lng && this.services.languageDetector && !this.services.languageDetector.async) {
16416
- setLng(this.services.languageDetector.detect());
16417
- } else if (!lng && this.services.languageDetector && this.services.languageDetector.async) {
16418
- if (this.services.languageDetector.detect.length === 0) {
16419
- this.services.languageDetector.detect().then(setLng);
16420
- } else {
16421
- this.services.languageDetector.detect(setLng);
16422
- }
16423
- } else {
16424
- setLng(lng);
16425
- }
16426
- return deferred;
16427
- }
16428
- getFixedT(lng, ns, keyPrefix) {
16429
- var _this3 = this;
16430
- const fixedT = function(key, opts) {
16431
- let options;
16432
- if (typeof opts !== "object") {
16433
- for (var _len3 = arguments.length, rest = new Array(_len3 > 2 ? _len3 - 2 : 0), _key3 = 2; _key3 < _len3; _key3++) {
16434
- rest[_key3 - 2] = arguments[_key3];
16435
- }
16436
- options = _this3.options.overloadTranslationOptionHandler([key, opts].concat(rest));
16437
- } else {
16438
- options = {
16439
- ...opts
16440
- };
16441
- }
16442
- options.lng = options.lng || fixedT.lng;
16443
- options.lngs = options.lngs || fixedT.lngs;
16444
- options.ns = options.ns || fixedT.ns;
16445
- if (options.keyPrefix !== "") options.keyPrefix = options.keyPrefix || keyPrefix || fixedT.keyPrefix;
16446
- const keySeparator = _this3.options.keySeparator || ".";
16447
- let resultKey;
16448
- if (options.keyPrefix && Array.isArray(key)) {
16449
- resultKey = key.map((k) => `${options.keyPrefix}${keySeparator}${k}`);
16450
- } else {
16451
- resultKey = options.keyPrefix ? `${options.keyPrefix}${keySeparator}${key}` : key;
16452
- }
16453
- return _this3.t(resultKey, options);
16454
- };
16455
- if (isString(lng)) {
16456
- fixedT.lng = lng;
16457
- } else {
16458
- fixedT.lngs = lng;
16459
- }
16460
- fixedT.ns = ns;
16461
- fixedT.keyPrefix = keyPrefix;
16462
- return fixedT;
16463
- }
16464
- t() {
16465
- return this.translator && this.translator.translate(...arguments);
16466
- }
16467
- exists() {
16468
- return this.translator && this.translator.exists(...arguments);
16469
- }
16470
- setDefaultNamespace(ns) {
16471
- this.options.defaultNS = ns;
16472
- }
16473
- hasLoadedNamespace(ns) {
16474
- let options = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : {};
16475
- if (!this.isInitialized) {
16476
- this.logger.warn("hasLoadedNamespace: i18next was not initialized", this.languages);
16477
- return false;
16478
- }
16479
- if (!this.languages || !this.languages.length) {
16480
- this.logger.warn("hasLoadedNamespace: i18n.languages were undefined or empty", this.languages);
16481
- return false;
16482
- }
16483
- const lng = options.lng || this.resolvedLanguage || this.languages[0];
16484
- const fallbackLng = this.options ? this.options.fallbackLng : false;
16485
- const lastLng = this.languages[this.languages.length - 1];
16486
- if (lng.toLowerCase() === "cimode") return true;
16487
- const loadNotPending = (l, n) => {
16488
- const loadState = this.services.backendConnector.state[`${l}|${n}`];
16489
- return loadState === -1 || loadState === 0 || loadState === 2;
16490
- };
16491
- if (options.precheck) {
16492
- const preResult = options.precheck(this, loadNotPending);
16493
- if (preResult !== void 0) return preResult;
16494
- }
16495
- if (this.hasResourceBundle(lng, ns)) return true;
16496
- if (!this.services.backendConnector.backend || this.options.resources && !this.options.partialBundledLanguages) return true;
16497
- if (loadNotPending(lng, ns) && (!fallbackLng || loadNotPending(lastLng, ns))) return true;
16498
- return false;
16499
- }
16500
- loadNamespaces(ns, callback) {
16501
- const deferred = defer();
16502
- if (!this.options.ns) {
16503
- if (callback) callback();
16504
- return Promise.resolve();
16505
- }
16506
- if (isString(ns)) ns = [ns];
16507
- ns.forEach((n) => {
16508
- if (this.options.ns.indexOf(n) < 0) this.options.ns.push(n);
16509
- });
16510
- this.loadResources((err) => {
16511
- deferred.resolve();
16512
- if (callback) callback(err);
16513
- });
16514
- return deferred;
16515
- }
16516
- loadLanguages(lngs, callback) {
16517
- const deferred = defer();
16518
- if (isString(lngs)) lngs = [lngs];
16519
- const preloaded = this.options.preload || [];
16520
- const newLngs = lngs.filter((lng) => preloaded.indexOf(lng) < 0 && this.services.languageUtils.isSupportedCode(lng));
16521
- if (!newLngs.length) {
16522
- if (callback) callback();
16523
- return Promise.resolve();
16524
- }
16525
- this.options.preload = preloaded.concat(newLngs);
16526
- this.loadResources((err) => {
16527
- deferred.resolve();
16528
- if (callback) callback(err);
16529
- });
16530
- return deferred;
16531
- }
16532
- dir(lng) {
16533
- if (!lng) lng = this.resolvedLanguage || (this.languages && this.languages.length > 0 ? this.languages[0] : this.language);
16534
- if (!lng) return "rtl";
16535
- const rtlLngs = ["ar", "shu", "sqr", "ssh", "xaa", "yhd", "yud", "aao", "abh", "abv", "acm", "acq", "acw", "acx", "acy", "adf", "ads", "aeb", "aec", "afb", "ajp", "apc", "apd", "arb", "arq", "ars", "ary", "arz", "auz", "avl", "ayh", "ayl", "ayn", "ayp", "bbz", "pga", "he", "iw", "ps", "pbt", "pbu", "pst", "prp", "prd", "ug", "ur", "ydd", "yds", "yih", "ji", "yi", "hbo", "men", "xmn", "fa", "jpr", "peo", "pes", "prs", "dv", "sam", "ckb"];
16536
- const languageUtils = this.services && this.services.languageUtils || new LanguageUtil(get());
16537
- return rtlLngs.indexOf(languageUtils.getLanguagePartFromCode(lng)) > -1 || lng.toLowerCase().indexOf("-arab") > 1 ? "rtl" : "ltr";
16538
- }
16539
- static createInstance() {
16540
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
16541
- let callback = arguments.length > 1 ? arguments[1] : void 0;
16542
- return new _I18n(options, callback);
16543
- }
16544
- cloneInstance() {
16545
- let options = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
16546
- let callback = arguments.length > 1 && arguments[1] !== void 0 ? arguments[1] : noop;
16547
- const forkResourceStore = options.forkResourceStore;
16548
- if (forkResourceStore) delete options.forkResourceStore;
16549
- const mergedOptions = {
16550
- ...this.options,
16551
- ...options,
16552
- ...{
16553
- isClone: true
16554
- }
16555
- };
16556
- const clone = new _I18n(mergedOptions);
16557
- if (options.debug !== void 0 || options.prefix !== void 0) {
16558
- clone.logger = clone.logger.clone(options);
16559
- }
16560
- const membersToCopy = ["store", "services", "language"];
16561
- membersToCopy.forEach((m) => {
16562
- clone[m] = this[m];
16563
- });
16564
- clone.services = {
16565
- ...this.services
16566
- };
16567
- clone.services.utils = {
16568
- hasLoadedNamespace: clone.hasLoadedNamespace.bind(clone)
16569
- };
16570
- if (forkResourceStore) {
16571
- clone.store = new ResourceStore(this.store.data, mergedOptions);
16572
- clone.services.resourceStore = clone.store;
16573
- }
16574
- clone.translator = new Translator(clone.services, mergedOptions);
16575
- clone.translator.on("*", function(event) {
16576
- for (var _len4 = arguments.length, args = new Array(_len4 > 1 ? _len4 - 1 : 0), _key4 = 1; _key4 < _len4; _key4++) {
16577
- args[_key4 - 1] = arguments[_key4];
16578
- }
16579
- clone.emit(event, ...args);
16580
- });
16581
- clone.init(mergedOptions, callback);
16582
- clone.translator.options = mergedOptions;
16583
- clone.translator.backendConnector.services.utils = {
16584
- hasLoadedNamespace: clone.hasLoadedNamespace.bind(clone)
16585
- };
16586
- return clone;
16587
- }
16588
- toJSON() {
16589
- return {
16590
- options: this.options,
16591
- store: this.store,
16592
- language: this.language,
16593
- languages: this.languages,
16594
- resolvedLanguage: this.resolvedLanguage
16595
- };
16596
- }
16597
- };
16598
- var instance = I18n.createInstance();
16599
- instance.createInstance = I18n.createInstance;
16600
- instance.createInstance;
16601
- instance.dir;
16602
- instance.init;
16603
- instance.loadResources;
16604
- instance.reloadResources;
16605
- instance.use;
16606
- instance.changeLanguage;
16607
- instance.getFixedT;
16608
- instance.t;
16609
- instance.exists;
16610
- instance.setDefaultNamespace;
16611
- instance.hasLoadedNamespace;
16612
- instance.loadNamespaces;
16613
- instance.loadLanguages;
16614
-
16615
14243
  // src/locales/en/translation.ts
16616
14244
  var translationEN = {
16617
14245
  common: {
@@ -18224,7 +15852,7 @@ var resources = {
18224
15852
  translation: translationVI
18225
15853
  }
18226
15854
  };
18227
- instance.use(LanguageDetector).use(initReactI18next).init({
15855
+ i18n.use(LanguageDetector).use(initReactI18next).init({
18228
15856
  resources,
18229
15857
  fallbackLng: "en",
18230
15858
  // Use English if the detected language is not available
@@ -20598,7 +18226,7 @@ async function generateQuizPlan(clientInput, apiKey, imageContexts = []) {
20598
18226
  topicCount: clientInput.topics.length,
20599
18227
  bloomLevelCount: clientInput.bloomLevels.length
20600
18228
  });
20601
- const totalTopicRatio = clientInput.topics.reduce((sum, t2) => sum + t2.ratio, 0);
18229
+ const totalTopicRatio = clientInput.topics.reduce((sum, t) => sum + t.ratio, 0);
20602
18230
  if (Math.abs(totalTopicRatio - 100) > 1) {
20603
18231
  throw new Error(`Total topic ratio must be 100%. Current sum: ${totalTopicRatio.toFixed(1)}%`);
20604
18232
  }
@@ -20623,11 +18251,11 @@ async function generateQuizPlan(clientInput, apiKey, imageContexts = []) {
20623
18251
  logger.log("AI_INITIALIZATION", { model: modelName }, Date.now() - aiStartTime);
20624
18252
  const { language, totalQuestions, numCodingQuestions = 0 } = clientInput;
20625
18253
  const promptStartTime = Date.now();
20626
- const topicsDistribution = clientInput.topics.map((t2) => {
20627
- let topicString = `- Topic Context: "${t2.topic}", LoId: "${t2.originalLoId || "nil"}", Subject: "${t2.originalSubject || "nil"}", Category: "${t2.originalCategory || "nil"}", Topic: "${t2.originalTopic || "nil"}", Ratio: ${t2.ratio}%`;
20628
- if (t2.commonMisconceptions && t2.commonMisconceptions.length > 0) {
18254
+ const topicsDistribution = clientInput.topics.map((t) => {
18255
+ let topicString = `- Topic Context: "${t.topic}", LoId: "${t.originalLoId || "nil"}", Subject: "${t.originalSubject || "nil"}", Category: "${t.originalCategory || "nil"}", Topic: "${t.originalTopic || "nil"}", Ratio: ${t.ratio}%`;
18256
+ if (t.commonMisconceptions && t.commonMisconceptions.length > 0) {
20629
18257
  topicString += `
20630
- - Common Misconceptions: [${t2.commonMisconceptions.join(", ")}]`;
18258
+ - Common Misconceptions: [${t.commonMisconceptions.join(", ")}]`;
20631
18259
  }
20632
18260
  return topicString;
20633
18261
  }).join("\n ");
@@ -20640,7 +18268,7 @@ async function generateQuizPlan(clientInput, apiKey, imageContexts = []) {
20640
18268
  (type) => type !== "SHORT_ANSWER" && type !== "CODING"
20641
18269
  );
20642
18270
  }
20643
- const allowedQuestionTypes = questionTypesForPrompt.map((t2) => `'${t2}'`).join(", ");
18271
+ const allowedQuestionTypes = questionTypesForPrompt.map((t) => `'${t}'`).join(", ");
20644
18272
  const codingRequirement = numCodingQuestions > 0 ? `
20645
18273
  **CRITICAL CODING REQUIREMENT**: Exactly ${numCodingQuestions} questions in the plan MUST be of type 'CODING'. These should typically be at 'APPLY' or higher Bloom levels and focus on implementation, debugging, or algorithm design.` : "";
20646
18274
  const imageContextSection = imageContexts && imageContexts.length > 0 ? `
@@ -20723,7 +18351,7 @@ Execute this plan with pedagogical precision. The quiz should feel like a carefu
20723
18351
  logger.log("PROMPT_PREPARATION", {
20724
18352
  promptLength: enhancedPromptText.length,
20725
18353
  topicCount: clientInput.topics.length,
20726
- misconceptionCount: clientInput.topics.reduce((sum, t2) => sum + (t2.commonMisconceptions?.length || 0), 0)
18354
+ misconceptionCount: clientInput.topics.reduce((sum, t) => sum + (t.commonMisconceptions?.length || 0), 0)
20727
18355
  }, Date.now() - promptStartTime);
20728
18356
  const generationStartTime = Date.now();
20729
18357
  const contents = [
@@ -21770,6 +19398,12 @@ var ExecutionService = class _ExecutionService {
21770
19398
  }
21771
19399
  return _ExecutionService.instance;
21772
19400
  }
19401
+ /**
19402
+ * Clear all registered providers.
19403
+ */
19404
+ clearProviders() {
19405
+ this.providers.clear();
19406
+ }
21773
19407
  /**
21774
19408
  * Register a provider.
21775
19409
  */
@@ -21786,20 +19420,25 @@ var ExecutionService = class _ExecutionService {
21786
19420
  * Get the best provider for a language based on priority and availability.
21787
19421
  */
21788
19422
  async getBestProvider(language) {
21789
- const sortedProviders = Array.from(this.providers.values()).filter((p) => p.getSupportedLanguages().includes(language)).sort((a, b) => b.getPriority(language) - a.getPriority(language));
19423
+ const lang = language.toLowerCase();
19424
+ const sortedProviders = Array.from(this.providers.values()).filter((p) => p.getSupportedLanguages().map((l) => l.toLowerCase()).includes(lang)).sort((a, b) => b.getPriority(lang) - a.getPriority(lang));
19425
+ console.log(`[ExecutionService] Finding best provider for '${language}' (normalized: '${lang}'). Found ${sortedProviders.length} potential providers.`);
21790
19426
  for (const provider of sortedProviders) {
21791
19427
  if (await provider.isAvailable()) {
19428
+ console.log(`[ExecutionService] Selected provider: ${provider.name} (ID: ${provider.id})`);
21792
19429
  return provider;
21793
19430
  }
21794
19431
  }
21795
19432
  return null;
21796
19433
  }
21797
19434
  /**
21798
- * Execute code using the best available provider.
19435
+ * Execute code using the best available provider with automatic fallback.
21799
19436
  */
21800
19437
  async execute(code, language, stdin) {
21801
- const provider = await this.getBestProvider(language);
21802
- if (!provider) {
19438
+ const lang = language.toLowerCase();
19439
+ const providers = Array.from(this.providers.values()).filter((p) => p.getSupportedLanguages().map((l) => l.toLowerCase()).includes(lang)).sort((a, b) => b.getPriority(lang) - a.getPriority(lang));
19440
+ console.log(`[ExecutionService] Executing for '${language}'. Providers in order:`, providers.map((p) => `${p.name} (${p.id})`));
19441
+ if (providers.length === 0) {
21803
19442
  return {
21804
19443
  stdout: "",
21805
19444
  stderr: `No execution provider available for language: ${language}`,
@@ -21807,25 +19446,35 @@ var ExecutionService = class _ExecutionService {
21807
19446
  message: "EXECUTION_ERROR_NO_PROVIDER"
21808
19447
  };
21809
19448
  }
21810
- try {
21811
- return await provider.execute(code, language, stdin);
21812
- } catch (error) {
21813
- return {
21814
- stdout: "",
21815
- stderr: error.message || "Unknown execution error",
21816
- exitCode: 1,
21817
- message: "EXECUTION_ERROR_INTERNAL"
21818
- };
19449
+ let lastError = null;
19450
+ for (const provider of providers) {
19451
+ try {
19452
+ if (!await provider.isAvailable()) continue;
19453
+ const result = await provider.execute(code, language, stdin);
19454
+ const isRecoverable = result.message === "RATE_LIMIT_EXCEEDED" || result.message === "AUTH_FAILED" || result.message === "UNSUPPORTED_LANGUAGE" || result.message === "EXECUTION_ERROR" || result.status?.id === 13 || // Internal Error
19455
+ result.exitCode === 1 && !result.stderr;
19456
+ if (isRecoverable && providers.indexOf(provider) < providers.length - 1) {
19457
+ lastError = result;
19458
+ continue;
19459
+ }
19460
+ return result;
19461
+ } catch (error) {
19462
+ lastError = error;
19463
+ }
21819
19464
  }
19465
+ return {
19466
+ stdout: "",
19467
+ stderr: lastError?.stderr || lastError?.message || "All execution providers failed",
19468
+ exitCode: 1,
19469
+ message: "EXECUTION_ERROR_ALL_FAILED"
19470
+ };
21820
19471
  }
21821
19472
  };
21822
19473
  var executionService = ExecutionService.getInstance();
21823
19474
 
21824
19475
  // src/lib/execution/providers/Judge0Provider.ts
21825
19476
  var Judge0Provider = class {
21826
- constructor(apiUrl, apiKey) {
21827
- this.id = "judge0";
21828
- this.name = "Judge0 Professional";
19477
+ constructor(apiUrl, apiKey, options) {
21829
19478
  this.languageMap = {
21830
19479
  "python": 71,
21831
19480
  "javascript": 63,
@@ -21838,6 +19487,9 @@ var Judge0Provider = class {
21838
19487
  };
21839
19488
  this.apiUrl = apiUrl;
21840
19489
  this.apiKey = apiKey;
19490
+ this.id = options?.id || "judge0";
19491
+ this.name = options?.name || "Judge0 Professional";
19492
+ this.customPriority = options?.priority;
21841
19493
  }
21842
19494
  async isAvailable() {
21843
19495
  return !!this.apiUrl;
@@ -21873,11 +19525,15 @@ var Judge0Provider = class {
21873
19525
  };
21874
19526
  }
21875
19527
  try {
19528
+ console.log(`[Judge0Provider] Calling ${this.name} at ${this.apiUrl}...`);
21876
19529
  const response = await fetch(`${this.apiUrl}/submissions?base64_encoded=true&wait=true`, {
21877
19530
  method: "POST",
21878
19531
  headers: {
21879
19532
  "Content-Type": "application/json",
21880
- ...this.apiKey && { "X-Auth-Token": this.apiKey }
19533
+ ...this.apiKey && (this.apiUrl.includes("rapidapi.com") ? {
19534
+ "x-rapidapi-key": this.apiKey,
19535
+ "x-rapidapi-host": new URL(this.apiUrl).hostname
19536
+ } : { "X-Auth-Token": this.apiKey })
21881
19537
  },
21882
19538
  body: JSON.stringify({
21883
19539
  source_code: this.toBase64(code),
@@ -21886,9 +19542,45 @@ var Judge0Provider = class {
21886
19542
  })
21887
19543
  });
21888
19544
  if (!response.ok) {
21889
- throw new Error(`Judge0 API error: ${response.statusText}`);
19545
+ const errorText = await response.text();
19546
+ console.error(`[Judge0Provider] ${this.name} HTTP Error ${response.status}:`, errorText);
19547
+ throw new Error(`PROVIDER_HTTP_ERROR: ${response.status} - ${errorText}`);
19548
+ }
19549
+ let result = await response.json();
19550
+ console.log(`[Judge0Provider] ${this.name} initial result:`, result);
19551
+ if (result.message) {
19552
+ if (result.message.includes("not subscribed")) {
19553
+ console.warn(`[Judge0Provider] ${this.name} auth failed, triggering fallback...`);
19554
+ throw new Error("AUTH_FAILED: Not subscribed");
19555
+ }
19556
+ if (result.message.includes("rate limit")) {
19557
+ console.warn(`[Judge0Provider] ${this.name} rate limited, triggering fallback...`);
19558
+ throw new Error("RATE_LIMIT_EXCEEDED");
19559
+ }
19560
+ }
19561
+ let attempts = 0;
19562
+ const maxAttempts = 10;
19563
+ while ((result.status?.id === 1 || result.status?.id === 2) && attempts < maxAttempts) {
19564
+ console.log(`[Judge0Provider] ${this.name} polling... (status: ${result.status?.description})`);
19565
+ await new Promise((resolve) => setTimeout(resolve, 1e3));
19566
+ const pollResponse = await fetch(`${this.apiUrl}/submissions/${result.token}?base64_encoded=true`, {
19567
+ headers: {
19568
+ "Content-Type": "application/json",
19569
+ ...this.apiKey && (this.apiUrl.includes("rapidapi.com") ? {
19570
+ "x-rapidapi-key": this.apiKey,
19571
+ "x-rapidapi-host": new URL(this.apiUrl).hostname
19572
+ } : { "X-Auth-Token": this.apiKey })
19573
+ }
19574
+ });
19575
+ if (pollResponse.ok) {
19576
+ result = await pollResponse.json();
19577
+ console.log(`[Judge0Provider] ${this.name} poll result (attempt ${attempts + 1}):`, result);
19578
+ } else {
19579
+ console.error(`[Judge0Provider] Poll failed: ${pollResponse.status}`);
19580
+ break;
19581
+ }
19582
+ attempts++;
21890
19583
  }
21891
- const result = await response.json();
21892
19584
  return {
21893
19585
  stdout: this.fromBase64(result.stdout),
21894
19586
  stderr: this.fromBase64(result.stderr),
@@ -21898,18 +19590,16 @@ var Judge0Provider = class {
21898
19590
  time: result.time ? parseFloat(result.time) * 1e3 : void 0,
21899
19591
  memory: result.memory ? parseInt(result.memory) : void 0,
21900
19592
  message: result.status?.description,
19593
+ status: result.status,
21901
19594
  token: result.token
21902
19595
  };
21903
19596
  } catch (error) {
21904
- return {
21905
- stdout: "",
21906
- stderr: error instanceof Error ? error.message : String(error),
21907
- exitCode: 1,
21908
- message: "EXECUTION_ERROR"
21909
- };
19597
+ console.error(`[Judge0Provider] ${this.name} execution error:`, error);
19598
+ throw error;
21910
19599
  }
21911
19600
  }
21912
19601
  getPriority(language) {
19602
+ if (this.customPriority !== void 0) return this.customPriority;
21913
19603
  const compiled = ["cpp", "c", "java", "csharp"];
21914
19604
  return compiled.includes(language.toLowerCase()) ? 10 : 5;
21915
19605
  }
@@ -21918,6 +19608,103 @@ var Judge0Provider = class {
21918
19608
  }
21919
19609
  };
21920
19610
 
19611
+ // src/lib/execution/providers/PistonProvider.ts
19612
+ var PistonProvider = class {
19613
+ constructor(apiUrl, apiKey, options) {
19614
+ this.cachedRuntimes = null;
19615
+ this.apiUrl = apiUrl.endsWith("/") ? apiUrl.slice(0, -1) : apiUrl;
19616
+ this.apiKey = apiKey;
19617
+ this.id = options?.id || "piston";
19618
+ this.name = options?.name || "Piston Engine";
19619
+ this.customPriority = options?.priority;
19620
+ }
19621
+ async isAvailable() {
19622
+ try {
19623
+ const response = await fetch(`${this.apiUrl}/runtimes`);
19624
+ if (response.ok) {
19625
+ this.cachedRuntimes = await response.json();
19626
+ return true;
19627
+ }
19628
+ return false;
19629
+ } catch (e) {
19630
+ return false;
19631
+ }
19632
+ }
19633
+ async execute(code, language, stdin) {
19634
+ try {
19635
+ if (!this.cachedRuntimes) {
19636
+ const response2 = await fetch(`${this.apiUrl}/runtimes`);
19637
+ if (response2.ok) {
19638
+ this.cachedRuntimes = await response2.json();
19639
+ } else {
19640
+ throw new Error("Could not fetch Piston runtimes");
19641
+ }
19642
+ }
19643
+ const lowerLang = language.toLowerCase();
19644
+ let targetLang = lowerLang;
19645
+ if (lowerLang === "js") targetLang = "javascript";
19646
+ if (lowerLang === "c" || lowerLang === "cpp") targetLang = "gcc";
19647
+ const runtime = this.cachedRuntimes.find(
19648
+ (r2) => r2.language === targetLang || r2.aliases && r2.aliases.includes(targetLang)
19649
+ );
19650
+ if (!runtime) {
19651
+ return {
19652
+ stdout: "",
19653
+ stderr: `Language '${language}' (mapped to '${targetLang}') is not supported by this Piston instance.`,
19654
+ exitCode: 1,
19655
+ message: "UNSUPPORTED_LANGUAGE"
19656
+ };
19657
+ }
19658
+ console.log(`[PistonProvider] Calling ${this.name} (${runtime.language} ${runtime.version}) at ${this.apiUrl}...`);
19659
+ const headers = {
19660
+ "Content-Type": "application/json"
19661
+ };
19662
+ if (this.apiKey) {
19663
+ headers["X-API-Key"] = this.apiKey;
19664
+ }
19665
+ const response = await fetch(`${this.apiUrl}/execute`, {
19666
+ method: "POST",
19667
+ headers,
19668
+ body: JSON.stringify({
19669
+ language: runtime.language,
19670
+ version: runtime.version,
19671
+ files: [{ content: code }],
19672
+ stdin: stdin || ""
19673
+ })
19674
+ });
19675
+ if (!response.ok) {
19676
+ const errorText = await response.text();
19677
+ console.error(`[PistonProvider] HTTP Error ${response.status}:`, errorText);
19678
+ throw new Error(`PISTON_HTTP_ERROR: ${response.status} - ${errorText}`);
19679
+ }
19680
+ const result = await response.json();
19681
+ console.log(`[PistonProvider] result:`, result);
19682
+ if (result.message) {
19683
+ throw new Error(`PISTON_ERROR: ${result.message}`);
19684
+ }
19685
+ const run = result.run || {};
19686
+ const compile = result.compile || {};
19687
+ return {
19688
+ stdout: run.stdout || "",
19689
+ stderr: (compile.stderr || "") + (run.stderr || ""),
19690
+ compileOutput: compile.stdout || "",
19691
+ exitCode: run.code === 0 ? 0 : 1,
19692
+ message: run.signal ? `Terminated by signal: ${run.signal}` : void 0
19693
+ };
19694
+ } catch (error) {
19695
+ console.error(`[PistonProvider] execution error:`, error);
19696
+ throw error;
19697
+ }
19698
+ }
19699
+ getPriority(language) {
19700
+ if (this.customPriority !== void 0) return this.customPriority;
19701
+ return 20;
19702
+ }
19703
+ getSupportedLanguages() {
19704
+ return ["python", "javascript", "js", "lua", "c", "cpp", "csharp"];
19705
+ }
19706
+ };
19707
+
21921
19708
  // src/lib/execution/providers/LiteProvider.ts
21922
19709
  var LiteProvider = class {
21923
19710
  constructor() {
@@ -22129,9 +19916,40 @@ var AIProvider = class {
22129
19916
 
22130
19917
  // src/lib/execution/index.ts
22131
19918
  function initExecutionSystem(config) {
19919
+ executionService.clearProviders();
22132
19920
  executionService.registerProvider(new LiteProvider());
22133
- if (config?.judge0Url) {
22134
- executionService.registerProvider(new Judge0Provider(config.judge0Url, config.judge0Key));
19921
+ if (config?.judge0Fallback?.url) {
19922
+ executionService.registerProvider(new Judge0Provider(
19923
+ config.judge0Fallback.url,
19924
+ config.judge0Fallback.key,
19925
+ {
19926
+ id: "judge0-fallback",
19927
+ name: config.judge0Fallback.name || "Judge0 Fallback (RapidAPI)",
19928
+ priority: config.judge0Fallback.priority || 8
19929
+ }
19930
+ ));
19931
+ }
19932
+ if (config?.pistonPrimary?.url) {
19933
+ executionService.registerProvider(new PistonProvider(
19934
+ config.pistonPrimary.url,
19935
+ config.pistonPrimary.key,
19936
+ {
19937
+ id: "piston-primary",
19938
+ name: config.pistonPrimary.name || "Piston Primary (Self-hosted)",
19939
+ priority: config.pistonPrimary.priority || 20
19940
+ }
19941
+ ));
19942
+ }
19943
+ if (config?.judge0Primary?.url) {
19944
+ executionService.registerProvider(new Judge0Provider(
19945
+ config.judge0Primary.url,
19946
+ config.judge0Primary.key,
19947
+ {
19948
+ id: "judge0-primary",
19949
+ name: config.judge0Primary.name || "Judge0 Primary (Self-hosted)",
19950
+ priority: config.judge0Primary.priority || 15
19951
+ }
19952
+ ));
22135
19953
  }
22136
19954
  if (config?.geminiKey) {
22137
19955
  executionService.registerProvider(new AIProvider(config.geminiKey));
@@ -22140,8 +19958,11 @@ function initExecutionSystem(config) {
22140
19958
 
22141
19959
  // src/services/APIKeyService.ts
22142
19960
  var GEMINI_API_KEY_SERVICE_NAME = "gemini";
22143
- var JUDGE0_API_KEY_SERVICE_NAME = "judge0";
22144
- var JUDGE0_API_URL_SERVICE_NAME = "judge0_url";
19961
+ var JUDGE0_PRIMARY_API_KEY_SERVICE_NAME = "judge0_primary";
19962
+ var JUDGE0_PRIMARY_API_URL_SERVICE_NAME = "judge0_primary_url";
19963
+ var JUDGE0_FALLBACK_API_KEY_SERVICE_NAME = "judge0_fallback";
19964
+ var JUDGE0_FALLBACK_API_URL_SERVICE_NAME = "judge0_fallback_url";
19965
+ var PISTON_PRIMARY_API_URL_SERVICE_NAME = "piston_primary_url";
22145
19966
  var LOCAL_STORAGE_PREFIX = "iqk_api_keys_";
22146
19967
  function _encode(data) {
22147
19968
  if (typeof window !== "undefined" && typeof window.btoa === "function") {
@@ -22227,6 +20048,95 @@ var APIKeyService = class {
22227
20048
  }
22228
20049
  };
22229
20050
 
20051
+ // src/lib/execution/CodeWrapper.ts
20052
+ var CodeWrapper = class {
20053
+ /**
20054
+ * Wraps code with necessary boilerplate for the given language.
20055
+ */
20056
+ static wrap(code, language, options = {}) {
20057
+ const lang = language.toLowerCase();
20058
+ if (lang === "c" || lang === "cpp") {
20059
+ return this.wrapC(code, options.testCaseInput || [], options.functionSignature);
20060
+ }
20061
+ return code;
20062
+ }
20063
+ static wrapC(code, input, signature) {
20064
+ if (code.includes("int main") || code.includes("void main")) {
20065
+ return code;
20066
+ }
20067
+ if (!signature) {
20068
+ return `
20069
+ #include <stdio.h>
20070
+ #include <stdlib.h>
20071
+ #include <stdbool.h>
20072
+ #include <string.h>
20073
+
20074
+ ${code}
20075
+
20076
+ int main() {
20077
+ // No signature provided, assuming competitive programming style if stdin is used
20078
+ return 0;
20079
+ }
20080
+ `;
20081
+ }
20082
+ const sig = signature?.trim();
20083
+ const match = sig?.match(/(\w+)\s+(\w+)\s*\((.*)\)/);
20084
+ if (!match) {
20085
+ if (input.length === 2) {
20086
+ return `
20087
+ #include <stdio.h>
20088
+ #include <stdlib.h>
20089
+ #include <stdbool.h>
20090
+ #include <string.h>
20091
+
20092
+ ${code}
20093
+
20094
+ int main() {
20095
+ int v0, v1;
20096
+ if (scanf("%d %d", &v0, &v1) == 2) {
20097
+ // Try to call 'add' if it exists in the code
20098
+ ${code.includes("add") ? 'printf("%d", add(v0, v1));' : "// Function not found"}
20099
+ }
20100
+ return 0;
20101
+ }
20102
+ `;
20103
+ }
20104
+ return code;
20105
+ }
20106
+ const [, , funcName, paramsStr] = match;
20107
+ const params = paramsStr.split(",").map((p) => p.trim()).filter((p) => p.length > 0);
20108
+ let scanfFormat = "";
20109
+ let scanfArgs = "";
20110
+ let callArgs = "";
20111
+ params.forEach((p, i) => {
20112
+ const parts = p.split(/\s+/);
20113
+ const type = parts[0];
20114
+ parts[parts.length - 1];
20115
+ let fmt = "%d";
20116
+ if (type === "float" || type === "double") fmt = "%lf";
20117
+ if (type === "char*") fmt = "%s";
20118
+ scanfFormat += (i === 0 ? "" : " ") + fmt;
20119
+ scanfArgs += `, &v${i}`;
20120
+ callArgs += (i === 0 ? "" : ", ") + `v${i}`;
20121
+ });
20122
+ return `
20123
+ #include <stdio.h>
20124
+ #include <stdlib.h>
20125
+ #include <stdbool.h>
20126
+ #include <string.h>
20127
+
20128
+ ${code}
20129
+
20130
+ int main() {
20131
+ ${params.map((p, i) => `${p.split(/\s+/)[0]} v${i};`).join("\n ")}
20132
+ if (scanf("${scanfFormat}"${scanfArgs}) != ${params.length}) return 1;
20133
+ printf("%d", ${funcName}(${callArgs}));
20134
+ return 0;
20135
+ }
20136
+ `;
20137
+ }
20138
+ };
20139
+
22230
20140
  // src/services/CodeEvaluationService.ts
22231
20141
  var CodeEvaluationService = class {
22232
20142
  constructor() {
@@ -22234,27 +20144,46 @@ var CodeEvaluationService = class {
22234
20144
  }
22235
20145
  /**
22236
20146
  * Ensure execution system is initialized with latest keys.
20147
+ * Order of precedence: LocalStorage (User choice) > Environment Variables (System default)
22237
20148
  */
22238
20149
  ensureInitialized() {
22239
20150
  if (typeof window === "undefined") return;
22240
- const geminiKey = APIKeyService.getAPIKey(GEMINI_API_KEY_SERVICE_NAME) || void 0;
22241
- const judge0Url = APIKeyService.getAPIKey(JUDGE0_API_URL_SERVICE_NAME) || void 0;
22242
- const judge0Key = APIKeyService.getAPIKey(JUDGE0_API_KEY_SERVICE_NAME) || void 0;
20151
+ const geminiKey = APIKeyService.getAPIKey(GEMINI_API_KEY_SERVICE_NAME) || "";
20152
+ const judge0PrimaryUrl = APIKeyService.getAPIKey(JUDGE0_PRIMARY_API_URL_SERVICE_NAME) || "/api/judge0";
20153
+ const judge0PrimaryKey = APIKeyService.getAPIKey(JUDGE0_PRIMARY_API_KEY_SERVICE_NAME) || "Code@Orchable";
20154
+ const judge0FallbackUrl = APIKeyService.getAPIKey(JUDGE0_FALLBACK_API_URL_SERVICE_NAME) || "https://judge0-ce.p.rapidapi.com";
20155
+ const judge0FallbackKey = APIKeyService.getAPIKey(JUDGE0_FALLBACK_API_KEY_SERVICE_NAME) || "9343426db9mshd122142ba1d0927p1259d6jsne24390a88e67";
20156
+ const pistonPrimaryUrl = APIKeyService.getAPIKey(PISTON_PRIMARY_API_URL_SERVICE_NAME) || "/api/piston";
20157
+ const pistonPrimaryKey = "Piston@Orchable";
22243
20158
  initExecutionSystem({
22244
- geminiKey,
22245
- judge0Url,
22246
- judge0Key
20159
+ geminiKey: geminiKey || void 0,
20160
+ pistonPrimary: {
20161
+ url: pistonPrimaryUrl,
20162
+ key: pistonPrimaryKey
20163
+ } ,
20164
+ judge0Primary: {
20165
+ url: judge0PrimaryUrl,
20166
+ key: judge0PrimaryKey
20167
+ } ,
20168
+ judge0Fallback: {
20169
+ url: judge0FallbackUrl,
20170
+ key: judge0FallbackKey
20171
+ }
22247
20172
  });
22248
20173
  }
22249
20174
  async evaluateSingleTestCase(question, userCode, testCase) {
22250
20175
  try {
20176
+ const wrappedCode = CodeWrapper.wrap(userCode, question.codingLanguage, {
20177
+ functionSignature: question.functionSignature,
20178
+ testCaseInput: testCase.input
20179
+ });
22251
20180
  const result = await executionService.execute(
22252
- userCode,
20181
+ wrappedCode,
22253
20182
  question.codingLanguage,
22254
20183
  Array.isArray(testCase.input) ? testCase.input.join("\n") : String(testCase.input || "")
22255
20184
  );
22256
- const actual = (result.stdout || "").trim();
22257
- const expected = (testCase.expectedOutput || "").trim();
20185
+ const actual = String(result.stdout || "").trim();
20186
+ const expected = String(testCase.expectedOutput || "").trim();
22258
20187
  const statusPassed = result.exitCode === 0;
22259
20188
  const outputMatches = actual === expected;
22260
20189
  const passed = statusPassed && outputMatches;
@@ -22417,9 +20346,9 @@ var QuizEngine = class {
22417
20346
  let s = seed >>> 0;
22418
20347
  const next = () => {
22419
20348
  s += 1831565813;
22420
- let t2 = Math.imul(s ^ s >>> 15, 1 | s);
22421
- t2 ^= t2 + Math.imul(t2 ^ t2 >>> 7, 61 | t2);
22422
- return ((t2 ^ t2 >>> 14) >>> 0) / 4294967296;
20349
+ let t = Math.imul(s ^ s >>> 15, 1 | s);
20350
+ t ^= t + Math.imul(t ^ t >>> 7, 61 | t);
20351
+ return ((t ^ t >>> 14) >>> 0) / 4294967296;
22423
20352
  };
22424
20353
  for (let i = arr.length - 1; i > 0; i--) {
22425
20354
  const j = Math.floor(next() * (i + 1));
@@ -24261,16 +22190,16 @@ var emptyQuiz = {
24261
22190
 
24262
22191
  // ../../node_modules/.pnpm/clsx@2.1.1/node_modules/clsx/dist/clsx.mjs
24263
22192
  function r(e) {
24264
- var t2, f, n = "";
22193
+ var t, f, n = "";
24265
22194
  if ("string" == typeof e || "number" == typeof e) n += e;
24266
22195
  else if ("object" == typeof e) if (Array.isArray(e)) {
24267
22196
  var o = e.length;
24268
- for (t2 = 0; t2 < o; t2++) e[t2] && (f = r(e[t2])) && (n && (n += " "), n += f);
22197
+ for (t = 0; t < o; t++) e[t] && (f = r(e[t])) && (n && (n += " "), n += f);
24269
22198
  } else for (f in e) e[f] && (n && (n += " "), n += f);
24270
22199
  return n;
24271
22200
  }
24272
22201
  function clsx() {
24273
- for (var e, t2, f = 0, n = "", o = arguments.length; f < o; f++) (e = arguments[f]) && (t2 = r(e)) && (n && (n += " "), n += t2);
22202
+ for (var e, t, f = 0, n = "", o = arguments.length; f < o; f++) (e = arguments[f]) && (t = r(e)) && (n && (n += " "), n += t);
24274
22203
  return n;
24275
22204
  }
24276
22205