joopjs 2.0.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.
Files changed (259) hide show
  1. package/CHANGELOG.md +678 -0
  2. package/README.md +583 -0
  3. package/dist/a11y.service-C-DQQfgO.d.mts +143 -0
  4. package/dist/a11y.service-CauEJrJe.d.ts +143 -0
  5. package/dist/adapters-B6slG6hQ.d.mts +84 -0
  6. package/dist/adapters-B6slG6hQ.d.ts +84 -0
  7. package/dist/aes.service-CkoupAww.d.mts +95 -0
  8. package/dist/aes.service-CkoupAww.d.ts +95 -0
  9. package/dist/ai/index.d.mts +99 -0
  10. package/dist/ai/index.d.ts +99 -0
  11. package/dist/ai/index.js +307 -0
  12. package/dist/ai/index.js.map +1 -0
  13. package/dist/ai/index.mjs +304 -0
  14. package/dist/ai/index.mjs.map +1 -0
  15. package/dist/analytics/index.d.mts +42 -0
  16. package/dist/analytics/index.d.ts +42 -0
  17. package/dist/analytics/index.js +139 -0
  18. package/dist/analytics/index.js.map +1 -0
  19. package/dist/analytics/index.mjs +136 -0
  20. package/dist/analytics/index.mjs.map +1 -0
  21. package/dist/angular/index.d.mts +148 -0
  22. package/dist/angular/index.d.ts +148 -0
  23. package/dist/angular/index.js +122 -0
  24. package/dist/angular/index.js.map +1 -0
  25. package/dist/angular/index.mjs +101 -0
  26. package/dist/angular/index.mjs.map +1 -0
  27. package/dist/api/index.d.mts +128 -0
  28. package/dist/api/index.d.ts +128 -0
  29. package/dist/api/index.js +1358 -0
  30. package/dist/api/index.js.map +1 -0
  31. package/dist/api/index.mjs +1332 -0
  32. package/dist/api/index.mjs.map +1 -0
  33. package/dist/auth/index.d.mts +105 -0
  34. package/dist/auth/index.d.ts +105 -0
  35. package/dist/auth/index.js +989 -0
  36. package/dist/auth/index.js.map +1 -0
  37. package/dist/auth/index.mjs +979 -0
  38. package/dist/auth/index.mjs.map +1 -0
  39. package/dist/auth.service-DNVB-L4U.d.mts +16 -0
  40. package/dist/auth.service-PjUUSUIt.d.ts +16 -0
  41. package/dist/banking/index.d.mts +1530 -0
  42. package/dist/banking/index.d.ts +1530 -0
  43. package/dist/banking/index.js +4739 -0
  44. package/dist/banking/index.js.map +1 -0
  45. package/dist/banking/index.mjs +4661 -0
  46. package/dist/banking/index.mjs.map +1 -0
  47. package/dist/cache/index.d.mts +40 -0
  48. package/dist/cache/index.d.ts +40 -0
  49. package/dist/cache/index.js +174 -0
  50. package/dist/cache/index.js.map +1 -0
  51. package/dist/cache/index.mjs +172 -0
  52. package/dist/cache/index.mjs.map +1 -0
  53. package/dist/client-profile.service-BuPeXVp5.d.mts +28 -0
  54. package/dist/client-profile.service-D5bRRYQp.d.ts +28 -0
  55. package/dist/config.models-Cqg04fAQ.d.mts +84 -0
  56. package/dist/config.models-Cqg04fAQ.d.ts +84 -0
  57. package/dist/config.service-CrCvI-JS.d.ts +31 -0
  58. package/dist/config.service-Cz4QQLlf.d.mts +31 -0
  59. package/dist/core/index.d.mts +4 -0
  60. package/dist/core/index.d.ts +4 -0
  61. package/dist/core/index.js +631 -0
  62. package/dist/core/index.js.map +1 -0
  63. package/dist/core/index.mjs +619 -0
  64. package/dist/core/index.mjs.map +1 -0
  65. package/dist/crypto-utils-DriNhLdx.d.mts +30 -0
  66. package/dist/crypto-utils-DriNhLdx.d.ts +30 -0
  67. package/dist/data-storage.service-DT6xaTxE.d.ts +51 -0
  68. package/dist/data-storage.service-LvhGRCmw.d.mts +51 -0
  69. package/dist/deeplink/index.d.mts +39 -0
  70. package/dist/deeplink/index.d.ts +39 -0
  71. package/dist/deeplink/index.js +268 -0
  72. package/dist/deeplink/index.js.map +1 -0
  73. package/dist/deeplink/index.mjs +265 -0
  74. package/dist/deeplink/index.mjs.map +1 -0
  75. package/dist/deeplink.service-Ctd5u243.d.mts +35 -0
  76. package/dist/deeplink.service-uUuTnY9_.d.ts +35 -0
  77. package/dist/dev/index.d.mts +20 -0
  78. package/dist/dev/index.d.ts +20 -0
  79. package/dist/dev/index.js +51 -0
  80. package/dist/dev/index.js.map +1 -0
  81. package/dist/dev/index.mjs +49 -0
  82. package/dist/dev/index.mjs.map +1 -0
  83. package/dist/device/index.d.mts +108 -0
  84. package/dist/device/index.d.ts +108 -0
  85. package/dist/device/index.js +960 -0
  86. package/dist/device/index.js.map +1 -0
  87. package/dist/device/index.mjs +951 -0
  88. package/dist/device/index.mjs.map +1 -0
  89. package/dist/differential-privacy-BcAv1G80.d.mts +210 -0
  90. package/dist/differential-privacy-C8mAUjZr.d.ts +210 -0
  91. package/dist/encryption/index.d.mts +75 -0
  92. package/dist/encryption/index.d.ts +75 -0
  93. package/dist/encryption/index.js +605 -0
  94. package/dist/encryption/index.js.map +1 -0
  95. package/dist/encryption/index.mjs +598 -0
  96. package/dist/encryption/index.mjs.map +1 -0
  97. package/dist/form-validator-3tkmzr_o.d.mts +72 -0
  98. package/dist/form-validator-3tkmzr_o.d.ts +72 -0
  99. package/dist/forms/index.d.mts +59 -0
  100. package/dist/forms/index.d.ts +59 -0
  101. package/dist/forms/index.js +446 -0
  102. package/dist/forms/index.js.map +1 -0
  103. package/dist/forms/index.mjs +442 -0
  104. package/dist/forms/index.mjs.map +1 -0
  105. package/dist/i18n/index.d.mts +37 -0
  106. package/dist/i18n/index.d.ts +37 -0
  107. package/dist/i18n/index.js +147 -0
  108. package/dist/i18n/index.js.map +1 -0
  109. package/dist/i18n/index.mjs +145 -0
  110. package/dist/i18n/index.mjs.map +1 -0
  111. package/dist/idempotency.service-_6LqhivP.d.mts +372 -0
  112. package/dist/idempotency.service-eOKoISRD.d.ts +372 -0
  113. package/dist/index-B_ksKpS1.d.mts +202 -0
  114. package/dist/index-CqDKWTUP.d.mts +28 -0
  115. package/dist/index-CqDKWTUP.d.ts +28 -0
  116. package/dist/index-DFqEoX_l.d.ts +202 -0
  117. package/dist/index-Dz0gOur2.d.mts +36 -0
  118. package/dist/index-Dz0gOur2.d.ts +36 -0
  119. package/dist/index.d.mts +1336 -0
  120. package/dist/index.d.ts +1336 -0
  121. package/dist/index.js +19464 -0
  122. package/dist/index.js.map +1 -0
  123. package/dist/index.mjs +19155 -0
  124. package/dist/index.mjs.map +1 -0
  125. package/dist/india/index.d.mts +75 -0
  126. package/dist/india/index.d.ts +75 -0
  127. package/dist/india/index.js +325 -0
  128. package/dist/india/index.js.map +1 -0
  129. package/dist/india/index.mjs +303 -0
  130. package/dist/india/index.mjs.map +1 -0
  131. package/dist/joop-Bx7Iwj5p.d.mts +155 -0
  132. package/dist/joop-CA3DMeOO.d.ts +155 -0
  133. package/dist/native-bridge/index.d.mts +27 -0
  134. package/dist/native-bridge/index.d.ts +27 -0
  135. package/dist/native-bridge/index.js +98 -0
  136. package/dist/native-bridge/index.js.map +1 -0
  137. package/dist/native-bridge/index.mjs +96 -0
  138. package/dist/native-bridge/index.mjs.map +1 -0
  139. package/dist/network/index.d.mts +85 -0
  140. package/dist/network/index.d.ts +85 -0
  141. package/dist/network/index.js +454 -0
  142. package/dist/network/index.js.map +1 -0
  143. package/dist/network/index.mjs +451 -0
  144. package/dist/network/index.mjs.map +1 -0
  145. package/dist/network-monitor-BIwPSXme.d.mts +179 -0
  146. package/dist/network-monitor-Bqp2hvZr.d.ts +179 -0
  147. package/dist/notification.service-Dm4fvfZf.d.mts +25 -0
  148. package/dist/notification.service-tEMKatWJ.d.ts +25 -0
  149. package/dist/observability/index.d.mts +179 -0
  150. package/dist/observability/index.d.ts +179 -0
  151. package/dist/observability/index.js +559 -0
  152. package/dist/observability/index.js.map +1 -0
  153. package/dist/observability/index.mjs +552 -0
  154. package/dist/observability/index.mjs.map +1 -0
  155. package/dist/oidc-client-DIJcClmB.d.mts +190 -0
  156. package/dist/oidc-client-DxhyE59t.d.ts +190 -0
  157. package/dist/platform/index.d.mts +73 -0
  158. package/dist/platform/index.d.ts +73 -0
  159. package/dist/platform/index.js +127 -0
  160. package/dist/platform/index.js.map +1 -0
  161. package/dist/platform/index.mjs +125 -0
  162. package/dist/platform/index.mjs.map +1 -0
  163. package/dist/pwa/index.d.mts +31 -0
  164. package/dist/pwa/index.d.ts +31 -0
  165. package/dist/pwa/index.js +247 -0
  166. package/dist/pwa/index.js.map +1 -0
  167. package/dist/pwa/index.mjs +244 -0
  168. package/dist/pwa/index.mjs.map +1 -0
  169. package/dist/react/index.d.mts +133 -0
  170. package/dist/react/index.d.ts +133 -0
  171. package/dist/react/index.js +632 -0
  172. package/dist/react/index.js.map +1 -0
  173. package/dist/react/index.mjs +630 -0
  174. package/dist/react/index.mjs.map +1 -0
  175. package/dist/router/index.d.mts +39 -0
  176. package/dist/router/index.d.ts +39 -0
  177. package/dist/router/index.js +168 -0
  178. package/dist/router/index.js.map +1 -0
  179. package/dist/router/index.mjs +166 -0
  180. package/dist/router/index.mjs.map +1 -0
  181. package/dist/security/index.d.mts +206 -0
  182. package/dist/security/index.d.ts +206 -0
  183. package/dist/security/index.js +1297 -0
  184. package/dist/security/index.js.map +1 -0
  185. package/dist/security/index.mjs +1285 -0
  186. package/dist/security/index.mjs.map +1 -0
  187. package/dist/session/index.d.mts +115 -0
  188. package/dist/session/index.d.ts +115 -0
  189. package/dist/session/index.js +297 -0
  190. package/dist/session/index.js.map +1 -0
  191. package/dist/session/index.mjs +292 -0
  192. package/dist/session/index.mjs.map +1 -0
  193. package/dist/state/index.d.mts +43 -0
  194. package/dist/state/index.d.ts +43 -0
  195. package/dist/state/index.js +156 -0
  196. package/dist/state/index.js.map +1 -0
  197. package/dist/state/index.mjs +152 -0
  198. package/dist/state/index.mjs.map +1 -0
  199. package/dist/statement-parser-BHQtXwCM.d.ts +260 -0
  200. package/dist/statement-parser-C2qNmb49.d.mts +260 -0
  201. package/dist/storage/index.d.mts +40 -0
  202. package/dist/storage/index.d.ts +40 -0
  203. package/dist/storage/index.js +256 -0
  204. package/dist/storage/index.js.map +1 -0
  205. package/dist/storage/index.mjs +252 -0
  206. package/dist/storage/index.mjs.map +1 -0
  207. package/dist/sync/index.d.mts +69 -0
  208. package/dist/sync/index.d.ts +69 -0
  209. package/dist/sync/index.js +330 -0
  210. package/dist/sync/index.js.map +1 -0
  211. package/dist/sync/index.mjs +323 -0
  212. package/dist/sync/index.mjs.map +1 -0
  213. package/dist/sync-engine-DCIMRG5s.d.ts +61 -0
  214. package/dist/sync-engine-DZqyKHkK.d.mts +61 -0
  215. package/dist/theme/index.d.mts +53 -0
  216. package/dist/theme/index.d.ts +53 -0
  217. package/dist/theme/index.js +169 -0
  218. package/dist/theme/index.js.map +1 -0
  219. package/dist/theme/index.mjs +167 -0
  220. package/dist/theme/index.mjs.map +1 -0
  221. package/dist/ui/index.d.mts +66 -0
  222. package/dist/ui/index.d.ts +66 -0
  223. package/dist/ui/index.js +811 -0
  224. package/dist/ui/index.js.map +1 -0
  225. package/dist/ui/index.mjs +803 -0
  226. package/dist/ui/index.mjs.map +1 -0
  227. package/dist/utilities/index.d.mts +199 -0
  228. package/dist/utilities/index.d.ts +199 -0
  229. package/dist/utilities/index.js +1991 -0
  230. package/dist/utilities/index.js.map +1 -0
  231. package/dist/utilities/index.mjs +1923 -0
  232. package/dist/utilities/index.mjs.map +1 -0
  233. package/dist/validation/index.d.mts +60 -0
  234. package/dist/validation/index.d.ts +60 -0
  235. package/dist/validation/index.js +460 -0
  236. package/dist/validation/index.js.map +1 -0
  237. package/dist/validation/index.mjs +455 -0
  238. package/dist/validation/index.mjs.map +1 -0
  239. package/dist/vue/index.d.mts +135 -0
  240. package/dist/vue/index.d.ts +135 -0
  241. package/dist/vue/index.js +621 -0
  242. package/dist/vue/index.js.map +1 -0
  243. package/dist/vue/index.mjs +619 -0
  244. package/dist/vue/index.mjs.map +1 -0
  245. package/dist/watermark.service-Detur5tq.d.ts +235 -0
  246. package/dist/watermark.service-QNegMeQZ.d.mts +235 -0
  247. package/dist/workers/index.d.mts +42 -0
  248. package/dist/workers/index.d.ts +42 -0
  249. package/dist/workers/index.js +359 -0
  250. package/dist/workers/index.js.map +1 -0
  251. package/dist/workers/index.mjs +356 -0
  252. package/dist/workers/index.mjs.map +1 -0
  253. package/dist/workflow/index.d.mts +99 -0
  254. package/dist/workflow/index.d.ts +99 -0
  255. package/dist/workflow/index.js +282 -0
  256. package/dist/workflow/index.js.map +1 -0
  257. package/dist/workflow/index.mjs +279 -0
  258. package/dist/workflow/index.mjs.map +1 -0
  259. package/package.json +226 -0
@@ -0,0 +1,147 @@
1
+ 'use strict';
2
+
3
+ // src/events/index.ts
4
+ var JoopSubject = class {
5
+ _listeners = [];
6
+ subscribe(listener) {
7
+ this._listeners.push(listener);
8
+ return () => {
9
+ this._listeners = this._listeners.filter((l) => l !== listener);
10
+ };
11
+ }
12
+ next(value) {
13
+ for (const listener of this._listeners) {
14
+ listener(value);
15
+ }
16
+ }
17
+ asObservable() {
18
+ return new JoopObservable((listener) => this.subscribe(listener));
19
+ }
20
+ };
21
+ var JoopBehaviorSubject = class extends JoopSubject {
22
+ _value;
23
+ constructor(initialValue) {
24
+ super();
25
+ this._value = initialValue;
26
+ }
27
+ getValue() {
28
+ return this._value;
29
+ }
30
+ next(value) {
31
+ this._value = value;
32
+ super.next(value);
33
+ }
34
+ subscribe(listener) {
35
+ listener(this._value);
36
+ return super.subscribe(listener);
37
+ }
38
+ asObservable() {
39
+ return new JoopObservable((listener) => this.subscribe(listener));
40
+ }
41
+ };
42
+ var JoopObservable = class {
43
+ constructor(_subscribeFn) {
44
+ this._subscribeFn = _subscribeFn;
45
+ }
46
+ _subscribeFn;
47
+ subscribe(listener) {
48
+ return this._subscribeFn(listener);
49
+ }
50
+ /** Returns the current value without subscribing (only meaningful for BehaviorSubject-backed observables). */
51
+ getOnce() {
52
+ let result;
53
+ const unsub = this.subscribe((v) => {
54
+ result = v;
55
+ });
56
+ unsub();
57
+ return result;
58
+ }
59
+ };
60
+
61
+ // src/i18n/i18n.service.ts
62
+ var RTL_LANGUAGES = ["ar", "arc", "ckb", "dv", "fa", "ha", "he", "khw", "ks", "ps", "sd", "ur", "uz_AF", "yi"];
63
+ var JoopI18nService = class {
64
+ _lang$ = new JoopBehaviorSubject("");
65
+ _culture$ = new JoopBehaviorSubject("");
66
+ _translations = {};
67
+ _fallback = "en";
68
+ setFallback(lang) {
69
+ this._fallback = lang;
70
+ }
71
+ setLanguage(lang) {
72
+ this._lang$.next(lang);
73
+ }
74
+ setLanguageCulture(culture) {
75
+ this._culture$.next(culture);
76
+ }
77
+ getLanguage() {
78
+ return this._lang$.getValue();
79
+ }
80
+ getLanguageCulture() {
81
+ return this._culture$.getValue();
82
+ }
83
+ language$() {
84
+ return this._lang$.asObservable();
85
+ }
86
+ culture$() {
87
+ return this._culture$.asObservable();
88
+ }
89
+ getDirection() {
90
+ return RTL_LANGUAGES.includes(this._lang$.getValue()) ? "rtl" : "ltr";
91
+ }
92
+ isRtl() {
93
+ return this.getDirection() === "rtl";
94
+ }
95
+ getDetails() {
96
+ return { code: this.getLanguage(), culture: this.getLanguageCulture(), direction: this.getDirection() };
97
+ }
98
+ /** Load translations for a language — merges if called multiple times */
99
+ async loadFromUrl(lang, url) {
100
+ const res = await fetch(url);
101
+ const data = await res.json();
102
+ this.loadFromObject(lang, data);
103
+ }
104
+ loadFromObject(lang, translations) {
105
+ this._translations[lang] = { ...this._translations[lang] ?? {}, ...translations };
106
+ }
107
+ /** Get a translated string. Supports dot-notation keys: 'ERRORS.TITLE' */
108
+ t(key, params) {
109
+ const lang = this.getLanguage();
110
+ let result = this._resolve(lang, key) ?? this._resolve(this._fallback, key) ?? key;
111
+ if (params) {
112
+ Object.entries(params).forEach(([k, v]) => {
113
+ result = result.replace(new RegExp(`\\{\\{\\s*${k}\\s*\\}\\}`, "g"), v);
114
+ });
115
+ }
116
+ return result;
117
+ }
118
+ has(key) {
119
+ return this._resolve(this.getLanguage(), key) !== null;
120
+ }
121
+ /** Apply direction to a DOM element (defaults to document.documentElement) */
122
+ applyDirection(el) {
123
+ if (typeof document === "undefined") return;
124
+ const target = el ?? document.documentElement;
125
+ const dir = this.getDirection();
126
+ target.setAttribute("dir", dir);
127
+ target.setAttribute("lang", this.getLanguage());
128
+ }
129
+ getRtlLanguages() {
130
+ return [...RTL_LANGUAGES];
131
+ }
132
+ _resolve(lang, key) {
133
+ const translations = this._translations[lang];
134
+ if (!translations) return null;
135
+ const parts = key.split(".");
136
+ let current = translations;
137
+ for (const part of parts) {
138
+ if (current == null || typeof current !== "object") return null;
139
+ current = current[part];
140
+ }
141
+ return typeof current === "string" ? current : null;
142
+ }
143
+ };
144
+
145
+ exports.JoopI18nService = JoopI18nService;
146
+ //# sourceMappingURL=index.js.map
147
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/events/index.ts","../../src/i18n/i18n.service.ts"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["export type Unsubscribe = () => void;\nexport type Listener<T> = (value: T) => void;\n\n/**\n * Lightweight pub/sub subject — emits to all current subscribers.\n * Replaces RxJS Subject without pulling in the full RxJS dependency.\n */\nexport class JoopSubject<T> {\n private _listeners: Listener<T>[] = [];\n\n subscribe(listener: Listener<T>): Unsubscribe {\n this._listeners.push(listener);\n return () => {\n this._listeners = this._listeners.filter(l => l !== listener);\n };\n }\n\n next(value: T): void {\n for (const listener of this._listeners) {\n listener(value);\n }\n }\n\n asObservable(): JoopObservable<T> {\n return new JoopObservable<T>(listener => this.subscribe(listener));\n }\n}\n\n/**\n * Stateful subject — replays the current value to any new subscriber immediately.\n * Replaces RxJS BehaviorSubject.\n */\nexport class JoopBehaviorSubject<T> extends JoopSubject<T> {\n private _value: T;\n\n constructor(initialValue: T) {\n super();\n this._value = initialValue;\n }\n\n getValue(): T {\n return this._value;\n }\n\n override next(value: T): void {\n this._value = value;\n super.next(value);\n }\n\n override subscribe(listener: Listener<T>): Unsubscribe {\n listener(this._value);\n return super.subscribe(listener);\n }\n\n override asObservable(): JoopObservable<T> {\n return new JoopObservable<T>(listener => this.subscribe(listener));\n }\n}\n\n/**\n * Read-only observable handle returned from asObservable().\n */\nexport class JoopObservable<T> {\n constructor(private _subscribeFn: (listener: Listener<T>) => Unsubscribe) {}\n\n subscribe(listener: Listener<T>): Unsubscribe {\n return this._subscribeFn(listener);\n }\n\n /** Returns the current value without subscribing (only meaningful for BehaviorSubject-backed observables). */\n getOnce(): T | undefined {\n let result: T | undefined;\n const unsub = this.subscribe(v => { result = v; });\n unsub();\n return result;\n }\n}\n","import { JoopBehaviorSubject } from '../events';\n\nexport type JoopDirection = 'ltr' | 'rtl';\nexport type JoopTranslations = Record<string, unknown>;\n\nexport interface JoopLanguageDetail {\n code: string;\n culture: string;\n direction: JoopDirection;\n}\n\nconst RTL_LANGUAGES = ['ar', 'arc', 'ckb', 'dv', 'fa', 'ha', 'he', 'khw', 'ks', 'ps', 'sd', 'ur', 'uz_AF', 'yi'];\n\nexport class JoopI18nService {\n private _lang$ = new JoopBehaviorSubject<string>('');\n private _culture$ = new JoopBehaviorSubject<string>('');\n private _translations: Record<string, JoopTranslations> = {};\n private _fallback = 'en';\n\n setFallback(lang: string): void { this._fallback = lang; }\n\n setLanguage(lang: string): void { this._lang$.next(lang); }\n setLanguageCulture(culture: string): void { this._culture$.next(culture); }\n\n getLanguage(): string { return this._lang$.getValue(); }\n getLanguageCulture(): string { return this._culture$.getValue(); }\n\n language$() { return this._lang$.asObservable(); }\n culture$() { return this._culture$.asObservable(); }\n\n getDirection(): JoopDirection {\n return RTL_LANGUAGES.includes(this._lang$.getValue()) ? 'rtl' : 'ltr';\n }\n\n isRtl(): boolean { return this.getDirection() === 'rtl'; }\n\n getDetails(): JoopLanguageDetail {\n return { code: this.getLanguage(), culture: this.getLanguageCulture(), direction: this.getDirection() };\n }\n\n /** Load translations for a language — merges if called multiple times */\n async loadFromUrl(lang: string, url: string): Promise<void> {\n const res = await fetch(url);\n const data = await res.json();\n this.loadFromObject(lang, data);\n }\n\n loadFromObject(lang: string, translations: JoopTranslations): void {\n this._translations[lang] = { ...(this._translations[lang] ?? {}), ...translations };\n }\n\n /** Get a translated string. Supports dot-notation keys: 'ERRORS.TITLE' */\n t(key: string, params?: Record<string, string>): string {\n const lang = this.getLanguage();\n let result = this._resolve(lang, key) ?? this._resolve(this._fallback, key) ?? key;\n if (params) {\n Object.entries(params).forEach(([k, v]) => {\n result = result.replace(new RegExp(`\\\\{\\\\{\\\\s*${k}\\\\s*\\\\}\\\\}`, 'g'), v);\n });\n }\n return result;\n }\n\n has(key: string): boolean {\n return this._resolve(this.getLanguage(), key) !== null;\n }\n\n /** Apply direction to a DOM element (defaults to document.documentElement) */\n applyDirection(el?: HTMLElement): void {\n if (typeof document === 'undefined') return;\n const target = el ?? document.documentElement;\n const dir = this.getDirection();\n target.setAttribute('dir', dir);\n target.setAttribute('lang', this.getLanguage());\n }\n\n getRtlLanguages(): string[] { return [...RTL_LANGUAGES]; }\n\n private _resolve(lang: string, key: string): string | null {\n const translations = this._translations[lang];\n if (!translations) return null;\n const parts = key.split('.');\n let current: unknown = translations;\n for (const part of parts) {\n if (current == null || typeof current !== 'object') return null;\n current = (current as Record<string, unknown>)[part];\n }\n return typeof current === 'string' ? current : null;\n }\n}\n"]}
@@ -0,0 +1,145 @@
1
+ // src/events/index.ts
2
+ var JoopSubject = class {
3
+ _listeners = [];
4
+ subscribe(listener) {
5
+ this._listeners.push(listener);
6
+ return () => {
7
+ this._listeners = this._listeners.filter((l) => l !== listener);
8
+ };
9
+ }
10
+ next(value) {
11
+ for (const listener of this._listeners) {
12
+ listener(value);
13
+ }
14
+ }
15
+ asObservable() {
16
+ return new JoopObservable((listener) => this.subscribe(listener));
17
+ }
18
+ };
19
+ var JoopBehaviorSubject = class extends JoopSubject {
20
+ _value;
21
+ constructor(initialValue) {
22
+ super();
23
+ this._value = initialValue;
24
+ }
25
+ getValue() {
26
+ return this._value;
27
+ }
28
+ next(value) {
29
+ this._value = value;
30
+ super.next(value);
31
+ }
32
+ subscribe(listener) {
33
+ listener(this._value);
34
+ return super.subscribe(listener);
35
+ }
36
+ asObservable() {
37
+ return new JoopObservable((listener) => this.subscribe(listener));
38
+ }
39
+ };
40
+ var JoopObservable = class {
41
+ constructor(_subscribeFn) {
42
+ this._subscribeFn = _subscribeFn;
43
+ }
44
+ _subscribeFn;
45
+ subscribe(listener) {
46
+ return this._subscribeFn(listener);
47
+ }
48
+ /** Returns the current value without subscribing (only meaningful for BehaviorSubject-backed observables). */
49
+ getOnce() {
50
+ let result;
51
+ const unsub = this.subscribe((v) => {
52
+ result = v;
53
+ });
54
+ unsub();
55
+ return result;
56
+ }
57
+ };
58
+
59
+ // src/i18n/i18n.service.ts
60
+ var RTL_LANGUAGES = ["ar", "arc", "ckb", "dv", "fa", "ha", "he", "khw", "ks", "ps", "sd", "ur", "uz_AF", "yi"];
61
+ var JoopI18nService = class {
62
+ _lang$ = new JoopBehaviorSubject("");
63
+ _culture$ = new JoopBehaviorSubject("");
64
+ _translations = {};
65
+ _fallback = "en";
66
+ setFallback(lang) {
67
+ this._fallback = lang;
68
+ }
69
+ setLanguage(lang) {
70
+ this._lang$.next(lang);
71
+ }
72
+ setLanguageCulture(culture) {
73
+ this._culture$.next(culture);
74
+ }
75
+ getLanguage() {
76
+ return this._lang$.getValue();
77
+ }
78
+ getLanguageCulture() {
79
+ return this._culture$.getValue();
80
+ }
81
+ language$() {
82
+ return this._lang$.asObservable();
83
+ }
84
+ culture$() {
85
+ return this._culture$.asObservable();
86
+ }
87
+ getDirection() {
88
+ return RTL_LANGUAGES.includes(this._lang$.getValue()) ? "rtl" : "ltr";
89
+ }
90
+ isRtl() {
91
+ return this.getDirection() === "rtl";
92
+ }
93
+ getDetails() {
94
+ return { code: this.getLanguage(), culture: this.getLanguageCulture(), direction: this.getDirection() };
95
+ }
96
+ /** Load translations for a language — merges if called multiple times */
97
+ async loadFromUrl(lang, url) {
98
+ const res = await fetch(url);
99
+ const data = await res.json();
100
+ this.loadFromObject(lang, data);
101
+ }
102
+ loadFromObject(lang, translations) {
103
+ this._translations[lang] = { ...this._translations[lang] ?? {}, ...translations };
104
+ }
105
+ /** Get a translated string. Supports dot-notation keys: 'ERRORS.TITLE' */
106
+ t(key, params) {
107
+ const lang = this.getLanguage();
108
+ let result = this._resolve(lang, key) ?? this._resolve(this._fallback, key) ?? key;
109
+ if (params) {
110
+ Object.entries(params).forEach(([k, v]) => {
111
+ result = result.replace(new RegExp(`\\{\\{\\s*${k}\\s*\\}\\}`, "g"), v);
112
+ });
113
+ }
114
+ return result;
115
+ }
116
+ has(key) {
117
+ return this._resolve(this.getLanguage(), key) !== null;
118
+ }
119
+ /** Apply direction to a DOM element (defaults to document.documentElement) */
120
+ applyDirection(el) {
121
+ if (typeof document === "undefined") return;
122
+ const target = el ?? document.documentElement;
123
+ const dir = this.getDirection();
124
+ target.setAttribute("dir", dir);
125
+ target.setAttribute("lang", this.getLanguage());
126
+ }
127
+ getRtlLanguages() {
128
+ return [...RTL_LANGUAGES];
129
+ }
130
+ _resolve(lang, key) {
131
+ const translations = this._translations[lang];
132
+ if (!translations) return null;
133
+ const parts = key.split(".");
134
+ let current = translations;
135
+ for (const part of parts) {
136
+ if (current == null || typeof current !== "object") return null;
137
+ current = current[part];
138
+ }
139
+ return typeof current === "string" ? current : null;
140
+ }
141
+ };
142
+
143
+ export { JoopI18nService };
144
+ //# sourceMappingURL=index.mjs.map
145
+ //# sourceMappingURL=index.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/events/index.ts","../../src/i18n/i18n.service.ts"],"names":[],"mappings":";AAOO,IAAM,cAAN,MAAqB;AAAA,EAClB,aAA4B,EAAC;AAAA,EAErC,UAAU,QAAA,EAAoC;AAC5C,IAAA,IAAA,CAAK,UAAA,CAAW,KAAK,QAAQ,CAAA;AAC7B,IAAA,OAAO,MAAM;AACX,MAAA,IAAA,CAAK,aAAa,IAAA,CAAK,UAAA,CAAW,MAAA,CAAO,CAAA,CAAA,KAAK,MAAM,QAAQ,CAAA;AAAA,IAC9D,CAAA;AAAA,EACF;AAAA,EAEA,KAAK,KAAA,EAAgB;AACnB,IAAA,KAAA,MAAW,QAAA,IAAY,KAAK,UAAA,EAAY;AACtC,MAAA,QAAA,CAAS,KAAK,CAAA;AAAA,IAChB;AAAA,EACF;AAAA,EAEA,YAAA,GAAkC;AAChC,IAAA,OAAO,IAAI,cAAA,CAAkB,CAAA,QAAA,KAAY,IAAA,CAAK,SAAA,CAAU,QAAQ,CAAC,CAAA;AAAA,EACnE;AACF,CAAA;AAMO,IAAM,mBAAA,GAAN,cAAqC,WAAA,CAAe;AAAA,EACjD,MAAA;AAAA,EAER,YAAY,YAAA,EAAiB;AAC3B,IAAA,KAAA,EAAM;AACN,IAAA,IAAA,CAAK,MAAA,GAAS,YAAA;AAAA,EAChB;AAAA,EAEA,QAAA,GAAc;AACZ,IAAA,OAAO,IAAA,CAAK,MAAA;AAAA,EACd;AAAA,EAES,KAAK,KAAA,EAAgB;AAC5B,IAAA,IAAA,CAAK,MAAA,GAAS,KAAA;AACd,IAAA,KAAA,CAAM,KAAK,KAAK,CAAA;AAAA,EAClB;AAAA,EAES,UAAU,QAAA,EAAoC;AACrD,IAAA,QAAA,CAAS,KAAK,MAAM,CAAA;AACpB,IAAA,OAAO,KAAA,CAAM,UAAU,QAAQ,CAAA;AAAA,EACjC;AAAA,EAES,YAAA,GAAkC;AACzC,IAAA,OAAO,IAAI,cAAA,CAAkB,CAAA,QAAA,KAAY,IAAA,CAAK,SAAA,CAAU,QAAQ,CAAC,CAAA;AAAA,EACnE;AACF,CAAA;AAKO,IAAM,iBAAN,MAAwB;AAAA,EAC7B,YAAoB,YAAA,EAAsD;AAAtD,IAAA,IAAA,CAAA,YAAA,GAAA,YAAA;AAAA,EAAuD;AAAA,EAAvD,YAAA;AAAA,EAEpB,UAAU,QAAA,EAAoC;AAC5C,IAAA,OAAO,IAAA,CAAK,aAAa,QAAQ,CAAA;AAAA,EACnC;AAAA;AAAA,EAGA,OAAA,GAAyB;AACvB,IAAA,IAAI,MAAA;AACJ,IAAA,MAAM,KAAA,GAAQ,IAAA,CAAK,SAAA,CAAU,CAAA,CAAA,KAAK;AAAE,MAAA,MAAA,GAAS,CAAA;AAAA,IAAG,CAAC,CAAA;AACjD,IAAA,KAAA,EAAM;AACN,IAAA,OAAO,MAAA;AAAA,EACT;AACF,CAAA;;;ACjEA,IAAM,aAAA,GAAgB,CAAC,IAAA,EAAM,KAAA,EAAO,OAAO,IAAA,EAAM,IAAA,EAAM,IAAA,EAAM,IAAA,EAAM,OAAO,IAAA,EAAM,IAAA,EAAM,IAAA,EAAM,IAAA,EAAM,SAAS,IAAI,CAAA;AAExG,IAAM,kBAAN,MAAsB;AAAA,EACnB,MAAA,GAAS,IAAI,mBAAA,CAA4B,EAAE,CAAA;AAAA,EAC3C,SAAA,GAAY,IAAI,mBAAA,CAA4B,EAAE,CAAA;AAAA,EAC9C,gBAAkD,EAAC;AAAA,EACnD,SAAA,GAAY,IAAA;AAAA,EAEpB,YAAY,IAAA,EAAoB;AAAE,IAAA,IAAA,CAAK,SAAA,GAAY,IAAA;AAAA,EAAM;AAAA,EAEzD,YAAY,IAAA,EAAoB;AAAE,IAAA,IAAA,CAAK,MAAA,CAAO,KAAK,IAAI,CAAA;AAAA,EAAG;AAAA,EAC1D,mBAAmB,OAAA,EAAuB;AAAE,IAAA,IAAA,CAAK,SAAA,CAAU,KAAK,OAAO,CAAA;AAAA,EAAG;AAAA,EAE1E,WAAA,GAAsB;AAAE,IAAA,OAAO,IAAA,CAAK,OAAO,QAAA,EAAS;AAAA,EAAG;AAAA,EACvD,kBAAA,GAA6B;AAAE,IAAA,OAAO,IAAA,CAAK,UAAU,QAAA,EAAS;AAAA,EAAG;AAAA,EAEjE,SAAA,GAAY;AAAE,IAAA,OAAO,IAAA,CAAK,OAAO,YAAA,EAAa;AAAA,EAAG;AAAA,EACjD,QAAA,GAAW;AAAE,IAAA,OAAO,IAAA,CAAK,UAAU,YAAA,EAAa;AAAA,EAAG;AAAA,EAEnD,YAAA,GAA8B;AAC5B,IAAA,OAAO,cAAc,QAAA,CAAS,IAAA,CAAK,OAAO,QAAA,EAAU,IAAI,KAAA,GAAQ,KAAA;AAAA,EAClE;AAAA,EAEA,KAAA,GAAiB;AAAE,IAAA,OAAO,IAAA,CAAK,cAAa,KAAM,KAAA;AAAA,EAAO;AAAA,EAEzD,UAAA,GAAiC;AAC/B,IAAA,OAAO,EAAE,IAAA,EAAM,IAAA,CAAK,WAAA,EAAY,EAAG,OAAA,EAAS,IAAA,CAAK,kBAAA,EAAmB,EAAG,SAAA,EAAW,IAAA,CAAK,YAAA,EAAa,EAAE;AAAA,EACxG;AAAA;AAAA,EAGA,MAAM,WAAA,CAAY,IAAA,EAAc,GAAA,EAA4B;AAC1D,IAAA,MAAM,GAAA,GAAM,MAAM,KAAA,CAAM,GAAG,CAAA;AAC3B,IAAA,MAAM,IAAA,GAAO,MAAM,GAAA,CAAI,IAAA,EAAK;AAC5B,IAAA,IAAA,CAAK,cAAA,CAAe,MAAM,IAAI,CAAA;AAAA,EAChC;AAAA,EAEA,cAAA,CAAe,MAAc,YAAA,EAAsC;AACjE,IAAA,IAAA,CAAK,aAAA,CAAc,IAAI,CAAA,GAAI,EAAE,GAAI,IAAA,CAAK,aAAA,CAAc,IAAI,CAAA,IAAK,EAAC,EAAI,GAAG,YAAA,EAAa;AAAA,EACpF;AAAA;AAAA,EAGA,CAAA,CAAE,KAAa,MAAA,EAAyC;AACtD,IAAA,MAAM,IAAA,GAAO,KAAK,WAAA,EAAY;AAC9B,IAAA,IAAI,MAAA,GAAS,IAAA,CAAK,QAAA,CAAS,IAAA,EAAM,GAAG,CAAA,IAAK,IAAA,CAAK,QAAA,CAAS,IAAA,CAAK,SAAA,EAAW,GAAG,CAAA,IAAK,GAAA;AAC/E,IAAA,IAAI,MAAA,EAAQ;AACV,MAAA,MAAA,CAAO,OAAA,CAAQ,MAAM,CAAA,CAAE,OAAA,CAAQ,CAAC,CAAC,CAAA,EAAG,CAAC,CAAA,KAAM;AACzC,QAAA,MAAA,GAAS,MAAA,CAAO,QAAQ,IAAI,MAAA,CAAO,aAAa,CAAC,CAAA,UAAA,CAAA,EAAc,GAAG,CAAA,EAAG,CAAC,CAAA;AAAA,MACxE,CAAC,CAAA;AAAA,IACH;AACA,IAAA,OAAO,MAAA;AAAA,EACT;AAAA,EAEA,IAAI,GAAA,EAAsB;AACxB,IAAA,OAAO,KAAK,QAAA,CAAS,IAAA,CAAK,WAAA,EAAY,EAAG,GAAG,CAAA,KAAM,IAAA;AAAA,EACpD;AAAA;AAAA,EAGA,eAAe,EAAA,EAAwB;AACrC,IAAA,IAAI,OAAO,aAAa,WAAA,EAAa;AACrC,IAAA,MAAM,MAAA,GAAS,MAAM,QAAA,CAAS,eAAA;AAC9B,IAAA,MAAM,GAAA,GAAM,KAAK,YAAA,EAAa;AAC9B,IAAA,MAAA,CAAO,YAAA,CAAa,OAAO,GAAG,CAAA;AAC9B,IAAA,MAAA,CAAO,YAAA,CAAa,MAAA,EAAQ,IAAA,CAAK,WAAA,EAAa,CAAA;AAAA,EAChD;AAAA,EAEA,eAAA,GAA4B;AAAE,IAAA,OAAO,CAAC,GAAG,aAAa,CAAA;AAAA,EAAG;AAAA,EAEjD,QAAA,CAAS,MAAc,GAAA,EAA4B;AACzD,IAAA,MAAM,YAAA,GAAe,IAAA,CAAK,aAAA,CAAc,IAAI,CAAA;AAC5C,IAAA,IAAI,CAAC,cAAc,OAAO,IAAA;AAC1B,IAAA,MAAM,KAAA,GAAQ,GAAA,CAAI,KAAA,CAAM,GAAG,CAAA;AAC3B,IAAA,IAAI,OAAA,GAAmB,YAAA;AACvB,IAAA,KAAA,MAAW,QAAQ,KAAA,EAAO;AACxB,MAAA,IAAI,OAAA,IAAW,IAAA,IAAQ,OAAO,OAAA,KAAY,UAAU,OAAO,IAAA;AAC3D,MAAA,OAAA,GAAW,QAAoC,IAAI,CAAA;AAAA,IACrD;AACA,IAAA,OAAO,OAAO,OAAA,KAAY,QAAA,GAAW,OAAA,GAAU,IAAA;AAAA,EACjD;AACF","file":"index.mjs","sourcesContent":["export type Unsubscribe = () => void;\nexport type Listener<T> = (value: T) => void;\n\n/**\n * Lightweight pub/sub subject — emits to all current subscribers.\n * Replaces RxJS Subject without pulling in the full RxJS dependency.\n */\nexport class JoopSubject<T> {\n private _listeners: Listener<T>[] = [];\n\n subscribe(listener: Listener<T>): Unsubscribe {\n this._listeners.push(listener);\n return () => {\n this._listeners = this._listeners.filter(l => l !== listener);\n };\n }\n\n next(value: T): void {\n for (const listener of this._listeners) {\n listener(value);\n }\n }\n\n asObservable(): JoopObservable<T> {\n return new JoopObservable<T>(listener => this.subscribe(listener));\n }\n}\n\n/**\n * Stateful subject — replays the current value to any new subscriber immediately.\n * Replaces RxJS BehaviorSubject.\n */\nexport class JoopBehaviorSubject<T> extends JoopSubject<T> {\n private _value: T;\n\n constructor(initialValue: T) {\n super();\n this._value = initialValue;\n }\n\n getValue(): T {\n return this._value;\n }\n\n override next(value: T): void {\n this._value = value;\n super.next(value);\n }\n\n override subscribe(listener: Listener<T>): Unsubscribe {\n listener(this._value);\n return super.subscribe(listener);\n }\n\n override asObservable(): JoopObservable<T> {\n return new JoopObservable<T>(listener => this.subscribe(listener));\n }\n}\n\n/**\n * Read-only observable handle returned from asObservable().\n */\nexport class JoopObservable<T> {\n constructor(private _subscribeFn: (listener: Listener<T>) => Unsubscribe) {}\n\n subscribe(listener: Listener<T>): Unsubscribe {\n return this._subscribeFn(listener);\n }\n\n /** Returns the current value without subscribing (only meaningful for BehaviorSubject-backed observables). */\n getOnce(): T | undefined {\n let result: T | undefined;\n const unsub = this.subscribe(v => { result = v; });\n unsub();\n return result;\n }\n}\n","import { JoopBehaviorSubject } from '../events';\n\nexport type JoopDirection = 'ltr' | 'rtl';\nexport type JoopTranslations = Record<string, unknown>;\n\nexport interface JoopLanguageDetail {\n code: string;\n culture: string;\n direction: JoopDirection;\n}\n\nconst RTL_LANGUAGES = ['ar', 'arc', 'ckb', 'dv', 'fa', 'ha', 'he', 'khw', 'ks', 'ps', 'sd', 'ur', 'uz_AF', 'yi'];\n\nexport class JoopI18nService {\n private _lang$ = new JoopBehaviorSubject<string>('');\n private _culture$ = new JoopBehaviorSubject<string>('');\n private _translations: Record<string, JoopTranslations> = {};\n private _fallback = 'en';\n\n setFallback(lang: string): void { this._fallback = lang; }\n\n setLanguage(lang: string): void { this._lang$.next(lang); }\n setLanguageCulture(culture: string): void { this._culture$.next(culture); }\n\n getLanguage(): string { return this._lang$.getValue(); }\n getLanguageCulture(): string { return this._culture$.getValue(); }\n\n language$() { return this._lang$.asObservable(); }\n culture$() { return this._culture$.asObservable(); }\n\n getDirection(): JoopDirection {\n return RTL_LANGUAGES.includes(this._lang$.getValue()) ? 'rtl' : 'ltr';\n }\n\n isRtl(): boolean { return this.getDirection() === 'rtl'; }\n\n getDetails(): JoopLanguageDetail {\n return { code: this.getLanguage(), culture: this.getLanguageCulture(), direction: this.getDirection() };\n }\n\n /** Load translations for a language — merges if called multiple times */\n async loadFromUrl(lang: string, url: string): Promise<void> {\n const res = await fetch(url);\n const data = await res.json();\n this.loadFromObject(lang, data);\n }\n\n loadFromObject(lang: string, translations: JoopTranslations): void {\n this._translations[lang] = { ...(this._translations[lang] ?? {}), ...translations };\n }\n\n /** Get a translated string. Supports dot-notation keys: 'ERRORS.TITLE' */\n t(key: string, params?: Record<string, string>): string {\n const lang = this.getLanguage();\n let result = this._resolve(lang, key) ?? this._resolve(this._fallback, key) ?? key;\n if (params) {\n Object.entries(params).forEach(([k, v]) => {\n result = result.replace(new RegExp(`\\\\{\\\\{\\\\s*${k}\\\\s*\\\\}\\\\}`, 'g'), v);\n });\n }\n return result;\n }\n\n has(key: string): boolean {\n return this._resolve(this.getLanguage(), key) !== null;\n }\n\n /** Apply direction to a DOM element (defaults to document.documentElement) */\n applyDirection(el?: HTMLElement): void {\n if (typeof document === 'undefined') return;\n const target = el ?? document.documentElement;\n const dir = this.getDirection();\n target.setAttribute('dir', dir);\n target.setAttribute('lang', this.getLanguage());\n }\n\n getRtlLanguages(): string[] { return [...RTL_LANGUAGES]; }\n\n private _resolve(lang: string, key: string): string | null {\n const translations = this._translations[lang];\n if (!translations) return null;\n const parts = key.split('.');\n let current: unknown = translations;\n for (const part of parts) {\n if (current == null || typeof current !== 'object') return null;\n current = (current as Record<string, unknown>)[part];\n }\n return typeof current === 'string' ? current : null;\n }\n}\n"]}