sroosh 1.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 (250) hide show
  1. package/CryptoFile-BROWSER.d.ts +2 -0
  2. package/CryptoFile-BROWSER.js +23 -0
  3. package/CryptoFile.d.ts +2 -0
  4. package/CryptoFile.js +23 -0
  5. package/Helpers.d.ts +151 -0
  6. package/Helpers.js +480 -0
  7. package/Password.d.ts +15 -0
  8. package/Password.js +271 -0
  9. package/README.md +105 -0
  10. package/Utils.d.ts +228 -0
  11. package/Utils.js +1248 -0
  12. package/Version.d.ts +1 -0
  13. package/Version.js +4 -0
  14. package/client/2fa.d.ts +48 -0
  15. package/client/2fa.js +109 -0
  16. package/client/TelegramClient.d.ts +1042 -0
  17. package/client/TelegramClient.js +1244 -0
  18. package/client/account.d.ts +0 -0
  19. package/client/account.js +1 -0
  20. package/client/auth.d.ts +93 -0
  21. package/client/auth.js +363 -0
  22. package/client/bots.d.ts +6 -0
  23. package/client/bots.js +24 -0
  24. package/client/buttons.d.ts +4 -0
  25. package/client/buttons.js +87 -0
  26. package/client/chats.d.ts +46 -0
  27. package/client/chats.js +350 -0
  28. package/client/dialogs.d.ts +52 -0
  29. package/client/dialogs.js +174 -0
  30. package/client/downloads.d.ts +157 -0
  31. package/client/downloads.js +598 -0
  32. package/client/fs-BROWSER.d.ts +10 -0
  33. package/client/fs-BROWSER.js +13 -0
  34. package/client/fs.d.ts +1 -0
  35. package/client/fs.js +13 -0
  36. package/client/index.d.ts +15 -0
  37. package/client/index.js +50 -0
  38. package/client/messageParse.d.ts +17 -0
  39. package/client/messageParse.js +191 -0
  40. package/client/messages.d.ts +259 -0
  41. package/client/messages.js +804 -0
  42. package/client/os-BROWSER.d.ts +5 -0
  43. package/client/os-BROWSER.js +10 -0
  44. package/client/os.d.ts +2 -0
  45. package/client/os.js +23 -0
  46. package/client/path-BROWSER.d.ts +7 -0
  47. package/client/path-BROWSER.js +8 -0
  48. package/client/path.d.ts +2 -0
  49. package/client/path.js +7 -0
  50. package/client/telegramBaseClient.d.ts +239 -0
  51. package/client/telegramBaseClient.js +369 -0
  52. package/client/updates.d.ts +31 -0
  53. package/client/updates.js +254 -0
  54. package/client/uploads.d.ts +137 -0
  55. package/client/uploads.js +514 -0
  56. package/client/users.d.ts +29 -0
  57. package/client/users.js +491 -0
  58. package/crypto/AuthKey.d.ts +20 -0
  59. package/crypto/AuthKey.js +76 -0
  60. package/crypto/CTR.d.ts +6 -0
  61. package/crypto/CTR.js +35 -0
  62. package/crypto/Factorizator.d.ts +19 -0
  63. package/crypto/Factorizator.js +74 -0
  64. package/crypto/IGE.d.ts +18 -0
  65. package/crypto/IGE.js +34 -0
  66. package/crypto/RSA.d.ts +15 -0
  67. package/crypto/RSA.js +150 -0
  68. package/crypto/converters.d.ts +19 -0
  69. package/crypto/converters.js +52 -0
  70. package/crypto/crypto.d.ts +27 -0
  71. package/crypto/crypto.js +117 -0
  72. package/crypto/words.d.ts +6 -0
  73. package/crypto/words.js +48 -0
  74. package/entityCache.d.ts +7 -0
  75. package/entityCache.js +79 -0
  76. package/errors/Common.d.ts +72 -0
  77. package/errors/Common.js +122 -0
  78. package/errors/RPCBaseErrors.d.ts +84 -0
  79. package/errors/RPCBaseErrors.js +134 -0
  80. package/errors/RPCErrorList.d.ts +37 -0
  81. package/errors/RPCErrorList.js +117 -0
  82. package/errors/index.d.ts +11 -0
  83. package/errors/index.js +29 -0
  84. package/events/Album.d.ts +36 -0
  85. package/events/Album.js +104 -0
  86. package/events/CallbackQuery.d.ts +74 -0
  87. package/events/CallbackQuery.js +193 -0
  88. package/events/DeletedMessage.d.ts +45 -0
  89. package/events/DeletedMessage.js +63 -0
  90. package/events/EditedMessage.d.ts +30 -0
  91. package/events/EditedMessage.js +41 -0
  92. package/events/NewMessage.d.ts +89 -0
  93. package/events/NewMessage.js +182 -0
  94. package/events/Raw.d.ts +29 -0
  95. package/events/Raw.js +43 -0
  96. package/events/common.d.ts +66 -0
  97. package/events/common.js +141 -0
  98. package/events/index.d.ts +2 -0
  99. package/events/index.js +8 -0
  100. package/extensions/AsyncQueue.d.ts +10 -0
  101. package/extensions/AsyncQueue.js +32 -0
  102. package/extensions/BinaryReader.d.ts +100 -0
  103. package/extensions/BinaryReader.js +242 -0
  104. package/extensions/BinaryWriter.d.ts +7 -0
  105. package/extensions/BinaryWriter.js +15 -0
  106. package/extensions/Deferred.d.ts +8 -0
  107. package/extensions/Deferred.js +16 -0
  108. package/extensions/Logger.d.ts +58 -0
  109. package/extensions/Logger.js +127 -0
  110. package/extensions/MessagePacker.d.ts +22 -0
  111. package/extensions/MessagePacker.js +154 -0
  112. package/extensions/PendingState.d.ts +12 -0
  113. package/extensions/PendingState.js +29 -0
  114. package/extensions/PromisedNetSockets-BROWSER.d.ts +8 -0
  115. package/extensions/PromisedNetSockets-BROWSER.js +12 -0
  116. package/extensions/PromisedNetSockets.d.ts +25 -0
  117. package/extensions/PromisedNetSockets.js +178 -0
  118. package/extensions/PromisedWebSockets.d.ts +19 -0
  119. package/extensions/PromisedWebSockets.js +134 -0
  120. package/extensions/html.d.ts +5 -0
  121. package/extensions/html.js +213 -0
  122. package/extensions/index.d.ts +7 -0
  123. package/extensions/index.js +17 -0
  124. package/extensions/markdown.d.ts +5 -0
  125. package/extensions/markdown.js +76 -0
  126. package/extensions/markdownv2.d.ts +5 -0
  127. package/extensions/markdownv2.js +51 -0
  128. package/extensions/net-BROWSER.d.ts +8 -0
  129. package/extensions/net-BROWSER.js +11 -0
  130. package/extensions/net.d.ts +1 -0
  131. package/extensions/net.js +13 -0
  132. package/extensions/socks-BROWSER.d.ts +3 -0
  133. package/extensions/socks-BROWSER.js +6 -0
  134. package/extensions/socks.d.ts +1 -0
  135. package/extensions/socks.js +13 -0
  136. package/index.d.ts +14 -0
  137. package/index.js +48 -0
  138. package/inspect-BROWSER.d.ts +3 -0
  139. package/inspect-BROWSER.js +6 -0
  140. package/inspect.d.ts +1 -0
  141. package/inspect.js +5 -0
  142. package/network/Authenticator.d.ts +12 -0
  143. package/network/Authenticator.js +193 -0
  144. package/network/MTProtoPlainSender.d.ts +19 -0
  145. package/network/MTProtoPlainSender.js +74 -0
  146. package/network/MTProtoSender.d.ts +291 -0
  147. package/network/MTProtoSender.js +854 -0
  148. package/network/MTProtoState.d.ts +103 -0
  149. package/network/MTProtoState.js +267 -0
  150. package/network/RequestState.d.ts +19 -0
  151. package/network/RequestState.js +35 -0
  152. package/network/connection/Connection.d.ts +71 -0
  153. package/network/connection/Connection.js +157 -0
  154. package/network/connection/ConnectionWebSocket.d.ts +19 -0
  155. package/network/connection/ConnectionWebSocket.js +77 -0
  156. package/network/connection/CustomIntermediatePacketCodec.d.ts +8 -0
  157. package/network/connection/CustomIntermediatePacketCodec.js +25 -0
  158. package/network/connection/CustomPromisedWebSockets.d.ts +22 -0
  159. package/network/connection/CustomPromisedWebSockets.js +170 -0
  160. package/network/connection/ObfuscatedIO.d.ts +12 -0
  161. package/network/connection/ObfuscatedIO.js +64 -0
  162. package/network/connection/TCPAbridged.d.ts +20 -0
  163. package/network/connection/TCPAbridged.js +58 -0
  164. package/network/connection/TCPFull.d.ts +17 -0
  165. package/network/connection/TCPFull.js +61 -0
  166. package/network/connection/TCPMTProxy.d.ts +50 -0
  167. package/network/connection/TCPMTProxy.js +121 -0
  168. package/network/connection/TCPObfuscated.d.ts +18 -0
  169. package/network/connection/TCPObfuscated.js +79 -0
  170. package/network/connection/index.d.ts +5 -0
  171. package/network/connection/index.js +13 -0
  172. package/network/index.d.ts +11 -0
  173. package/network/index.js +24 -0
  174. package/package.json +73 -0
  175. package/platform.d.ts +3 -0
  176. package/platform.js +6 -0
  177. package/requestIter.d.ts +24 -0
  178. package/requestIter.js +107 -0
  179. package/sessions/Abstract.d.ts +103 -0
  180. package/sessions/Abstract.js +6 -0
  181. package/sessions/CacheApiSession.d.ts +18 -0
  182. package/sessions/CacheApiSession.js +99 -0
  183. package/sessions/Memory.d.ts +38 -0
  184. package/sessions/Memory.js +272 -0
  185. package/sessions/StoreSession.d.ts +14 -0
  186. package/sessions/StoreSession.js +77 -0
  187. package/sessions/StringSession.d.ts +33 -0
  188. package/sessions/StringSession.js +116 -0
  189. package/sessions/index.d.ts +4 -0
  190. package/sessions/index.js +13 -0
  191. package/sessions/localStorage-BROWSER.d.ts +3 -0
  192. package/sessions/localStorage-BROWSER.js +9 -0
  193. package/sessions/localStorage.d.ts +1 -0
  194. package/sessions/localStorage.js +4 -0
  195. package/tl/AllTLObjects.d.ts +3 -0
  196. package/tl/AllTLObjects.js +17 -0
  197. package/tl/MTProtoRequest.d.ts +19 -0
  198. package/tl/MTProtoRequest.js +38 -0
  199. package/tl/api.d.ts +2 -0
  200. package/tl/api.js +507 -0
  201. package/tl/apiTl.d.ts +2 -0
  202. package/tl/apiTl.js +1638 -0
  203. package/tl/core/GZIPPacked.d.ts +16 -0
  204. package/tl/core/GZIPPacked.js +51 -0
  205. package/tl/core/MessageContainer.d.ts +12 -0
  206. package/tl/core/MessageContainer.js +42 -0
  207. package/tl/core/RPCResult.d.ts +15 -0
  208. package/tl/core/RPCResult.js +32 -0
  209. package/tl/core/TLMessage.d.ts +10 -0
  210. package/tl/core/TLMessage.js +14 -0
  211. package/tl/core/index.d.ts +6 -0
  212. package/tl/core/index.js +16 -0
  213. package/tl/custom/button.d.ts +25 -0
  214. package/tl/custom/button.js +78 -0
  215. package/tl/custom/chatGetter.d.ts +30 -0
  216. package/tl/custom/chatGetter.js +114 -0
  217. package/tl/custom/dialog.d.ts +31 -0
  218. package/tl/custom/dialog.js +40 -0
  219. package/tl/custom/draft.d.ts +22 -0
  220. package/tl/custom/draft.js +48 -0
  221. package/tl/custom/file.d.ts +22 -0
  222. package/tl/custom/file.js +68 -0
  223. package/tl/custom/forward.d.ts +16 -0
  224. package/tl/custom/forward.js +47 -0
  225. package/tl/custom/index.d.ts +1 -0
  226. package/tl/custom/index.js +5 -0
  227. package/tl/custom/inlineResult.d.ts +33 -0
  228. package/tl/custom/inlineResult.js +87 -0
  229. package/tl/custom/inlineResults.d.ts +21 -0
  230. package/tl/custom/inlineResults.js +26 -0
  231. package/tl/custom/message.d.ts +428 -0
  232. package/tl/custom/message.js +702 -0
  233. package/tl/custom/messageButton.d.ts +55 -0
  234. package/tl/custom/messageButton.js +152 -0
  235. package/tl/custom/senderGetter.d.ts +29 -0
  236. package/tl/custom/senderGetter.js +55 -0
  237. package/tl/generateModule.d.ts +1 -0
  238. package/tl/generateModule.js +17 -0
  239. package/tl/generationHelpers.d.ts +12 -0
  240. package/tl/generationHelpers.js +289 -0
  241. package/tl/index.d.ts +3 -0
  242. package/tl/index.js +10 -0
  243. package/tl/patched/index.d.ts +2 -0
  244. package/tl/patched/index.js +77 -0
  245. package/tl/schemaTl.d.ts +2 -0
  246. package/tl/schemaTl.js +64 -0
  247. package/tl/types-generator/generate.d.ts +1 -0
  248. package/tl/types-generator/generate.js +84 -0
  249. package/tl/types-generator/template.d.ts +6 -0
  250. package/tl/types-generator/template.js +257 -0
package/Password.js ADDED
@@ -0,0 +1,271 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.computeDigest = exports.computeCheck = void 0;
7
+ const tl_1 = require("./tl");
8
+ const Helpers_1 = require("./Helpers");
9
+ const big_integer_1 = __importDefault(require("big-integer"));
10
+ const CryptoFile_1 = __importDefault(require("./CryptoFile"));
11
+ const SIZE_FOR_HASH = 256;
12
+ /**
13
+ *
14
+ *
15
+ * @param prime{BigInteger}
16
+ * @param g{BigInteger}
17
+ */
18
+ /*
19
+ We don't support changing passwords yet
20
+ function checkPrimeAndGoodCheck(prime, g) {
21
+ console.error('Unsupported function `checkPrimeAndGoodCheck` call. Arguments:', prime, g)
22
+
23
+ const goodPrimeBitsCount = 2048
24
+ if (prime < 0 || prime.bitLength() !== goodPrimeBitsCount) {
25
+ throw new Error(`bad prime count ${prime.bitLength()},expected ${goodPrimeBitsCount}`)
26
+ }
27
+ // TODO this is kinda slow
28
+ if (Factorizator.factorize(prime)[0] !== 1) {
29
+ throw new Error('give "prime" is not prime')
30
+ }
31
+ if (g.eq(bigInt(2))) {
32
+ if ((prime.remainder(bigInt(8))).neq(bigInt(7))) {
33
+ throw new Error(`bad g ${g}, mod8 ${prime % 8}`)
34
+ }
35
+ } else if (g.eq(bigInt(3))) {
36
+ if ((prime.remainder(bigInt(3))).neq(bigInt(2))) {
37
+ throw new Error(`bad g ${g}, mod3 ${prime % 3}`)
38
+ }
39
+ // eslint-disable-next-line no-empty
40
+ } else if (g.eq(bigInt(4))) {
41
+
42
+ } else if (g.eq(bigInt(5))) {
43
+ if (!([ bigInt(1), bigInt(4) ].includes(prime.remainder(bigInt(5))))) {
44
+ throw new Error(`bad g ${g}, mod8 ${prime % 5}`)
45
+ }
46
+ } else if (g.eq(bigInt(6))) {
47
+ if (!([ bigInt(19), bigInt(23) ].includes(prime.remainder(bigInt(24))))) {
48
+ throw new Error(`bad g ${g}, mod8 ${prime % 24}`)
49
+ }
50
+ } else if (g.eq(bigInt(7))) {
51
+ if (!([ bigInt(3), bigInt(5), bigInt(6) ].includes(prime.remainder(bigInt(7))))) {
52
+ throw new Error(`bad g ${g}, mod8 ${prime % 7}`)
53
+ }
54
+ } else {
55
+ throw new Error(`bad g ${g}`)
56
+ }
57
+ const primeSub1Div2 = (prime.subtract(bigInt(1))).divide(bigInt(2))
58
+ if (Factorizator.factorize(primeSub1Div2)[0] !== 1) {
59
+ throw new Error('(prime - 1) // 2 is not prime')
60
+ }
61
+ }
62
+ */
63
+ /**
64
+ *
65
+ * @param primeBytes{Buffer}
66
+ * @param g{number}
67
+ */
68
+ function checkPrimeAndGood(primeBytes, g) {
69
+ const goodPrime = Buffer.from([
70
+ 0xc7, 0x1c, 0xae, 0xb9, 0xc6, 0xb1, 0xc9, 0x04, 0x8e, 0x6c, 0x52, 0x2f,
71
+ 0x70, 0xf1, 0x3f, 0x73, 0x98, 0x0d, 0x40, 0x23, 0x8e, 0x3e, 0x21, 0xc1,
72
+ 0x49, 0x34, 0xd0, 0x37, 0x56, 0x3d, 0x93, 0x0f, 0x48, 0x19, 0x8a, 0x0a,
73
+ 0xa7, 0xc1, 0x40, 0x58, 0x22, 0x94, 0x93, 0xd2, 0x25, 0x30, 0xf4, 0xdb,
74
+ 0xfa, 0x33, 0x6f, 0x6e, 0x0a, 0xc9, 0x25, 0x13, 0x95, 0x43, 0xae, 0xd4,
75
+ 0x4c, 0xce, 0x7c, 0x37, 0x20, 0xfd, 0x51, 0xf6, 0x94, 0x58, 0x70, 0x5a,
76
+ 0xc6, 0x8c, 0xd4, 0xfe, 0x6b, 0x6b, 0x13, 0xab, 0xdc, 0x97, 0x46, 0x51,
77
+ 0x29, 0x69, 0x32, 0x84, 0x54, 0xf1, 0x8f, 0xaf, 0x8c, 0x59, 0x5f, 0x64,
78
+ 0x24, 0x77, 0xfe, 0x96, 0xbb, 0x2a, 0x94, 0x1d, 0x5b, 0xcd, 0x1d, 0x4a,
79
+ 0xc8, 0xcc, 0x49, 0x88, 0x07, 0x08, 0xfa, 0x9b, 0x37, 0x8e, 0x3c, 0x4f,
80
+ 0x3a, 0x90, 0x60, 0xbe, 0xe6, 0x7c, 0xf9, 0xa4, 0xa4, 0xa6, 0x95, 0x81,
81
+ 0x10, 0x51, 0x90, 0x7e, 0x16, 0x27, 0x53, 0xb5, 0x6b, 0x0f, 0x6b, 0x41,
82
+ 0x0d, 0xba, 0x74, 0xd8, 0xa8, 0x4b, 0x2a, 0x14, 0xb3, 0x14, 0x4e, 0x0e,
83
+ 0xf1, 0x28, 0x47, 0x54, 0xfd, 0x17, 0xed, 0x95, 0x0d, 0x59, 0x65, 0xb4,
84
+ 0xb9, 0xdd, 0x46, 0x58, 0x2d, 0xb1, 0x17, 0x8d, 0x16, 0x9c, 0x6b, 0xc4,
85
+ 0x65, 0xb0, 0xd6, 0xff, 0x9c, 0xa3, 0x92, 0x8f, 0xef, 0x5b, 0x9a, 0xe4,
86
+ 0xe4, 0x18, 0xfc, 0x15, 0xe8, 0x3e, 0xbe, 0xa0, 0xf8, 0x7f, 0xa9, 0xff,
87
+ 0x5e, 0xed, 0x70, 0x05, 0x0d, 0xed, 0x28, 0x49, 0xf4, 0x7b, 0xf9, 0x59,
88
+ 0xd9, 0x56, 0x85, 0x0c, 0xe9, 0x29, 0x85, 0x1f, 0x0d, 0x81, 0x15, 0xf6,
89
+ 0x35, 0xb1, 0x05, 0xee, 0x2e, 0x4e, 0x15, 0xd0, 0x4b, 0x24, 0x54, 0xbf,
90
+ 0x6f, 0x4f, 0xad, 0xf0, 0x34, 0xb1, 0x04, 0x03, 0x11, 0x9c, 0xd8, 0xe3,
91
+ 0xb9, 0x2f, 0xcc, 0x5b,
92
+ ]);
93
+ if (goodPrime.equals(primeBytes)) {
94
+ if ([3, 4, 5, 7].includes(g)) {
95
+ return; // It's good
96
+ }
97
+ }
98
+ throw new Error("Changing passwords unsupported");
99
+ //checkPrimeAndGoodCheck(readBigIntFromBuffer(primeBytes, false), g)
100
+ }
101
+ /**
102
+ *
103
+ * @param number{BigInteger}
104
+ * @param p{BigInteger}
105
+ * @returns {boolean}
106
+ */
107
+ function isGoodLarge(number, p) {
108
+ return number.greater((0, big_integer_1.default)(0)) && p.subtract(number).greater((0, big_integer_1.default)(0));
109
+ }
110
+ /**
111
+ *
112
+ * @param number {Buffer}
113
+ * @returns {Buffer}
114
+ */
115
+ function numBytesForHash(number) {
116
+ return Buffer.concat([Buffer.alloc(SIZE_FOR_HASH - number.length), number]);
117
+ }
118
+ /**
119
+ *
120
+ * @param g {bigInt}
121
+ * @returns {Buffer}
122
+ */
123
+ function bigNumForHash(g) {
124
+ return (0, Helpers_1.readBufferFromBigInt)(g, SIZE_FOR_HASH, false);
125
+ }
126
+ /**
127
+ *
128
+ * @param modexp {BigInteger}
129
+ * @param prime {BigInteger}
130
+ * @returns {Boolean}
131
+ */
132
+ function isGoodModExpFirst(modexp, prime) {
133
+ const diff = prime.subtract(modexp);
134
+ const minDiffBitsCount = 2048 - 64;
135
+ const maxModExpSize = 256;
136
+ return !(diff.lesser((0, big_integer_1.default)(0)) ||
137
+ diff.bitLength().toJSNumber() < minDiffBitsCount ||
138
+ modexp.bitLength().toJSNumber() < minDiffBitsCount ||
139
+ Math.floor((modexp.bitLength().toJSNumber() + 7) / 8) > maxModExpSize);
140
+ }
141
+ function xor(a, b) {
142
+ const length = Math.min(a.length, b.length);
143
+ for (let i = 0; i < length; i++) {
144
+ a[i] = a[i] ^ b[i];
145
+ }
146
+ return a;
147
+ }
148
+ /**
149
+ *
150
+ * @param password{Buffer}
151
+ * @param salt{Buffer}
152
+ * @param iterations{number}
153
+ * @returns {*}
154
+ */
155
+ function pbkdf2sha512(password, salt, iterations) {
156
+ return CryptoFile_1.default.pbkdf2Sync(password, salt, iterations, 64, "sha512");
157
+ }
158
+ /**
159
+ *
160
+ * @param algo {constructors.PasswordKdfAlgoSHA256SHA256PBKDF2HMACSHA512iter100000SHA256ModPow}
161
+ * @param password
162
+ * @returns {Buffer|*}
163
+ */
164
+ async function computeHash(algo, password) {
165
+ const hash1 = await (0, Helpers_1.sha256)(Buffer.concat([algo.salt1, Buffer.from(password, "utf-8"), algo.salt1]));
166
+ const hash2 = await (0, Helpers_1.sha256)(Buffer.concat([algo.salt2, hash1, algo.salt2]));
167
+ const hash3 = await pbkdf2sha512(hash2, algo.salt1, 100000);
168
+ return (0, Helpers_1.sha256)(Buffer.concat([algo.salt2, hash3, algo.salt2]));
169
+ }
170
+ /**
171
+ *
172
+ * @param algo {constructors.PasswordKdfAlgoSHA256SHA256PBKDF2HMACSHA512iter100000SHA256ModPow}
173
+ * @param password
174
+ */
175
+ async function computeDigest(algo, password) {
176
+ try {
177
+ checkPrimeAndGood(algo.p, algo.g);
178
+ }
179
+ catch (e) {
180
+ throw new Error("bad p/g in password");
181
+ }
182
+ const value = (0, Helpers_1.modExp)((0, big_integer_1.default)(algo.g), (0, Helpers_1.readBigIntFromBuffer)(await computeHash(algo, password), false), (0, Helpers_1.readBigIntFromBuffer)(algo.p, false));
183
+ return bigNumForHash(value);
184
+ }
185
+ exports.computeDigest = computeDigest;
186
+ /**
187
+ *
188
+ * @param request {constructors.account.Password}
189
+ * @param password {string}
190
+ */
191
+ async function computeCheck(request, password) {
192
+ const algo = request.currentAlgo;
193
+ if (!(algo instanceof
194
+ tl_1.Api.PasswordKdfAlgoSHA256SHA256PBKDF2HMACSHA512iter100000SHA256ModPow)) {
195
+ throw new Error(`Unsupported password algorithm ${algo === null || algo === void 0 ? void 0 : algo.className}`);
196
+ }
197
+ const srp_B = request.srp_B;
198
+ const srpId = request.srpId;
199
+ if (!srp_B || !srpId) {
200
+ throw new Error(`Undefined srp_b ${request}`);
201
+ }
202
+ const pwHash = await computeHash(algo, password);
203
+ const p = (0, Helpers_1.readBigIntFromBuffer)(algo.p, false);
204
+ const g = algo.g;
205
+ const B = (0, Helpers_1.readBigIntFromBuffer)(srp_B, false);
206
+ try {
207
+ checkPrimeAndGood(algo.p, g);
208
+ }
209
+ catch (e) {
210
+ throw new Error("bad /g in password");
211
+ }
212
+ if (!isGoodLarge(B, p)) {
213
+ throw new Error("bad b in check");
214
+ }
215
+ const x = (0, Helpers_1.readBigIntFromBuffer)(pwHash, false);
216
+ const pForHash = numBytesForHash(algo.p);
217
+ const gForHash = bigNumForHash((0, big_integer_1.default)(g));
218
+ const bForHash = numBytesForHash(srp_B);
219
+ const gX = (0, Helpers_1.modExp)((0, big_integer_1.default)(g), x, p);
220
+ const k = (0, Helpers_1.readBigIntFromBuffer)(await (0, Helpers_1.sha256)(Buffer.concat([pForHash, gForHash])), false);
221
+ const kgX = (0, Helpers_1.bigIntMod)(k.multiply(gX), p);
222
+ const generateAndCheckRandom = async () => {
223
+ const randomSize = 256;
224
+ // eslint-disable-next-line no-constant-condition
225
+ while (true) {
226
+ const random = (0, Helpers_1.generateRandomBytes)(randomSize);
227
+ const a = (0, Helpers_1.readBigIntFromBuffer)(random, false);
228
+ const A = (0, Helpers_1.modExp)((0, big_integer_1.default)(g), a, p);
229
+ if (isGoodModExpFirst(A, p)) {
230
+ const aForHash = bigNumForHash(A);
231
+ const u = (0, Helpers_1.readBigIntFromBuffer)(await (0, Helpers_1.sha256)(Buffer.concat([aForHash, bForHash])), false);
232
+ if (u.greater((0, big_integer_1.default)(0))) {
233
+ return {
234
+ a: a,
235
+ aForHash: aForHash,
236
+ u: u,
237
+ };
238
+ }
239
+ }
240
+ }
241
+ };
242
+ const { a, aForHash, u } = await generateAndCheckRandom();
243
+ const gB = (0, Helpers_1.bigIntMod)(B.subtract(kgX), p);
244
+ if (!isGoodModExpFirst(gB, p)) {
245
+ throw new Error("bad gB");
246
+ }
247
+ const ux = u.multiply(x);
248
+ const aUx = a.add(ux);
249
+ const S = (0, Helpers_1.modExp)(gB, aUx, p);
250
+ const [K, pSha, gSha, salt1Sha, salt2Sha] = await Promise.all([
251
+ (0, Helpers_1.sha256)(bigNumForHash(S)),
252
+ (0, Helpers_1.sha256)(pForHash),
253
+ (0, Helpers_1.sha256)(gForHash),
254
+ (0, Helpers_1.sha256)(algo.salt1),
255
+ (0, Helpers_1.sha256)(algo.salt2),
256
+ ]);
257
+ const M1 = await (0, Helpers_1.sha256)(Buffer.concat([
258
+ xor(pSha, gSha),
259
+ salt1Sha,
260
+ salt2Sha,
261
+ aForHash,
262
+ bForHash,
263
+ K,
264
+ ]));
265
+ return new tl_1.Api.InputCheckPasswordSRP({
266
+ srpId: srpId,
267
+ A: Buffer.from(aForHash),
268
+ M1: M1,
269
+ });
270
+ }
271
+ exports.computeCheck = computeCheck;
package/README.md ADDED
@@ -0,0 +1,105 @@
1
+ # SrooshJS
2
+
3
+ A Srooosh client written in JavaScript for Node.js and browsers, with its core being based on
4
+ [Telethon](https://github.com/LonamiWebs/Telethon).
5
+
6
+ ## How to get started
7
+
8
+ Here you'll learn how to obtain necessary information to create sroosh application, authorize into your account and send yourself a message.
9
+
10
+ > **Note** that if you want to use a SrooshJS inside of a browser, refer to [this instructions](https://gram.js.org/introduction/advanced-installation).
11
+
12
+ Install SrooshJS:
13
+
14
+ ```bash
15
+ $ npm i sroosh
16
+ ```
17
+
18
+ After installation, you'll need to obtain an API ID and hash:
19
+
20
+ 1. Sroosh ApiID: `1030400`
21
+ 2. Sroosh ApiHash: `6edb16cf88714a4e9a805e928c39c937`
22
+
23
+ Then run this code to send a message to yourself.
24
+
25
+ ```javascript
26
+ import { SrooshClient } from "sroosh";
27
+ import { StringSession } from "sroosh/sessions";
28
+ import readline from "readline";
29
+
30
+ const apiId = 1030400;
31
+ const apiHash = "6edb16cf88714a4e9a805e928c39c937";
32
+ const stringSession = new StringSession(""); // fill this later with the value from session.save()
33
+
34
+ const rl = readline.createInterface({
35
+ input: process.stdin,
36
+ output: process.stdout,
37
+ });
38
+
39
+ (async () => {
40
+ console.log("Loading interactive example...");
41
+ const client = new TelegramClient(stringSession, apiId, apiHash, {
42
+ connectionRetries: 5,
43
+ });
44
+ await client.start({
45
+ phoneNumber: async () =>
46
+ new Promise((resolve) =>
47
+ rl.question("Please enter your number: ", resolve)
48
+ ),
49
+ password: async () =>
50
+ new Promise((resolve) =>
51
+ rl.question("Please enter your password: ", resolve)
52
+ ),
53
+ phoneCode: async () =>
54
+ new Promise((resolve) =>
55
+ rl.question("Please enter the code you received: ", resolve)
56
+ ),
57
+ onError: (err) => console.log(err),
58
+ });
59
+ console.log("You should now be connected.");
60
+ console.log(client.session.save()); // Save this string to avoid logging in again
61
+ await client.sendMessage("me", { message: "Hello!" });
62
+ })();
63
+ ```
64
+
65
+ > **Note** that you can also save auth key to a folder instead of a string, change `stringSession` into this:
66
+ >
67
+ > ```javascript
68
+ > const storeSession = new StoreSession("folder_name");
69
+ > ```
70
+
71
+ Be sure to save output of `client.session.save()` into `stringSession` or `storeSession` variable to avoid logging in again.
72
+
73
+ ## Running SrooshJS inside browsers
74
+
75
+ SrooshJS works great in combination with frontend libraries such as React, Vue and others.
76
+
77
+ While working within browsers, SrooshJS is using `localStorage` to cache the layers.
78
+
79
+ To get a browser bundle of SrooshJS, use the following command:
80
+
81
+ ```bash
82
+ NODE_ENV=production npx webpack
83
+ ```
84
+
85
+ You can also use the helpful script `generate_webpack.js`
86
+
87
+ ```bash
88
+ node generate_webpack.js
89
+ ```
90
+
91
+ ## Calling the raw API
92
+
93
+ To use raw telegram API methods use [invoke function](https://gram.js.org/beta/classes/TelegramClient.html#invoke).
94
+
95
+ ```javascript
96
+ await client.invoke(new RequestClass(args));
97
+ ```
98
+
99
+ ## Documentation
100
+
101
+ General documentation, use cases, quick start, refer to [gram.js.org](https://gram.js.org), or [older version of documentation](https://painor.gitbook.io/SrooshJS) (will be removed in the future).
102
+
103
+ For more advanced documentation refer to [gram.js.org/beta](https://gram.js.org/beta) (work in progress).
104
+
105
+ If your ISP is blocking Telegram, you can check [My ISP blocks Telegram. How can I still use SrooshJS?](https://gist.github.com/SecurityAndStuff/7cd04b28216c49b73b30a64d56d630ab)
package/Utils.d.ts ADDED
@@ -0,0 +1,228 @@
1
+ /// <reference types="node" />
2
+ import bigInt from "big-integer";
3
+ import type { ParseInterface } from "./client/messageParse";
4
+ import { CustomFile } from "./client/uploads";
5
+ import type { Entity, EntityLike, MessageIDLike } from "./define";
6
+ import { EntityCache } from "./entityCache";
7
+ import { Api } from "./tl";
8
+ export declare function getFileInfo(fileLocation: Api.Message | Api.MessageMediaDocument | Api.MessageMediaPhoto | Api.TypeInputFileLocation): {
9
+ dcId?: number;
10
+ location: Api.TypeInputFileLocation;
11
+ size?: bigInt.BigInteger;
12
+ };
13
+ /**
14
+ * Turns the given iterable into chunks of the specified size,
15
+ * which is 100 by default since that's what Telegram uses the most.
16
+ */
17
+ export declare function chunks<T>(arr: T[], size?: number): Generator<T[]>;
18
+ import TypeInputFile = Api.TypeInputFile;
19
+ /**
20
+ Gets the input peer for the given "entity" (user, chat or channel).
21
+
22
+ A ``TypeError`` is raised if the given entity isn't a supported type
23
+ or if ``check_hash is True`` but the entity's ``accessHash is None``
24
+ *or* the entity contains ``min`` information. In this case, the hash
25
+ cannot be used for general purposes, and thus is not returned to avoid
26
+ any issues which can derive from invalid access hashes.
27
+
28
+ Note that ``checkHash`` **is ignored** if an input peer is already
29
+ passed since in that case we assume the user knows what they're doing.
30
+ This is key to getting entities by explicitly passing ``hash = 0``.
31
+
32
+ * @param entity
33
+ * @param allowSelf
34
+ * @param checkHash
35
+ */
36
+ export declare function getInputPeer(entity: any, allowSelf?: boolean, checkHash?: boolean): Api.TypeInputPeer;
37
+ export declare function _photoSizeByteCount(size: Api.TypePhotoSize): number | undefined;
38
+ export declare function _getEntityPair(entityId: string, entities: Map<string, Entity>, cache: EntityCache, getInputPeerFunction?: any): [Entity?, Api.TypeInputPeer?];
39
+ export declare function getInnerText(text: string, entities: Api.TypeMessageEntity[]): string[];
40
+ /**
41
+ Similar to :meth:`get_input_peer`, but for :tl:`InputChannel`'s alone.
42
+
43
+ .. important::
44
+
45
+ This method does not validate for invalid general-purpose access
46
+ hashes, unlike `get_input_peer`. Consider using instead:
47
+ ``get_input_channel(get_input_peer(channel))``.
48
+
49
+ * @param entity
50
+ * @returns {InputChannel|*}
51
+ */
52
+ export declare function getInputChannel(entity: EntityLike): Api.InputChannelEmpty | Api.InputChannel | Api.InputChannelFromMessage;
53
+ /**
54
+ Similar to :meth:`getInputPeer`, but for :tl:`InputUser`'s alone.
55
+
56
+ .. important::
57
+
58
+ This method does not validate for invalid general-purpose access
59
+ hashes, unlike `get_input_peer`. Consider using instead:
60
+ ``get_input_channel(get_input_peer(channel))``.
61
+
62
+ * @param entity
63
+ */
64
+ export declare function getInputUser(entity: EntityLike): Api.TypeInputUser;
65
+ /**
66
+ Similar to :meth:`get_input_peer`, but for dialogs
67
+ * @param dialog
68
+ */
69
+ /**
70
+ * Similar to :meth:`get_input_peer`, but for input messages.
71
+ */
72
+ export declare function getInputMessage(message: any): Api.InputMessageID;
73
+ /**
74
+ * Similar to :meth:`get_input_peer`, but for input messages.
75
+ */
76
+ export declare function getInputChatPhoto(photo: any): Api.TypeInputChatPhoto;
77
+ /**
78
+ * Adds the JPG header and footer to a stripped image.
79
+ * Ported from https://github.com/telegramdesktop/tdesktop/blob/bec39d89e19670eb436dc794a8f20b657cb87c71/Telegram/SourceFiles/ui/image/image.cpp#L225
80
+
81
+ * @param stripped{Buffer}
82
+ * @returns {Buffer}
83
+ */
84
+ export declare function strippedPhotoToJpg(stripped: Buffer): Buffer;
85
+ /**
86
+ * Similar to :meth:`get_input_peer`, but for photos
87
+ */
88
+ export declare function getInputPhoto(photo: any): Api.TypeInputPhoto;
89
+ /**
90
+ * Similar to :meth:`get_input_peer`, but for documents
91
+ */
92
+ export declare function getInputDocument(document: any): Api.InputDocument | Api.InputDocumentEmpty;
93
+ interface GetAttributesParams {
94
+ attributes?: any;
95
+ mimeType?: string;
96
+ forceDocument?: boolean;
97
+ voiceNote?: boolean;
98
+ videoNote?: boolean;
99
+ supportsStreaming?: boolean;
100
+ thumb?: any;
101
+ }
102
+ /**
103
+ * Returns `True` if the file has an audio mime type.
104
+ */
105
+ export declare function isAudio(file: any): boolean;
106
+ /**
107
+ * Returns `True` if the file has an image mime type.
108
+ */
109
+ export declare function isImage(file: any): boolean;
110
+ export declare function getExtension(media: any): string;
111
+ /**
112
+ Get a list of attributes for the given file and
113
+ the mime type as a tuple ([attribute], mime_type).
114
+ */
115
+ export declare function getAttributes(file: File | CustomFile | TypeInputFile | string, { attributes, mimeType, forceDocument, voiceNote, videoNote, supportsStreaming, thumb, }: GetAttributesParams): {
116
+ attrs: Api.TypeDocumentAttribute[];
117
+ mimeType: string;
118
+ };
119
+ /**
120
+ * Similar to :meth:`get_input_peer`, but for geo points
121
+ */
122
+ export declare function getInputGeo(geo: any): Api.TypeInputGeoPoint;
123
+ export interface GetInputMediaInterface {
124
+ isPhoto?: boolean;
125
+ attributes?: Api.TypeDocumentAttribute[];
126
+ forceDocument?: boolean;
127
+ voiceNote?: boolean;
128
+ videoNote?: boolean;
129
+ supportsStreaming?: boolean;
130
+ }
131
+ /**
132
+ *
133
+ Similar to :meth:`get_input_peer`, but for media.
134
+
135
+ If the media is :tl:`InputFile` and ``is_photo`` is known to be `True`,
136
+ it will be treated as an :tl:`InputMediaUploadedPhoto`. Else, the rest
137
+ of parameters will indicate how to treat it.
138
+ * @param media
139
+ * @param isPhoto - whether it's a photo or not
140
+ * @param attributes
141
+ * @param forceDocument
142
+ * @param voiceNote
143
+ * @param videoNote
144
+ * @param supportsStreaming
145
+ */
146
+ export declare function getInputMedia(media: any, { isPhoto, attributes, forceDocument, voiceNote, videoNote, supportsStreaming, }?: GetInputMediaInterface): Api.TypeInputMedia;
147
+ /**
148
+ * Gets the appropriated part size when uploading or downloading files,
149
+ * given an initial file size.
150
+ * @param fileSize
151
+ * @returns {Number}
152
+ */
153
+ export declare function getAppropriatedPartSize(fileSize: bigInt.BigInteger): 512 | 256 | 128;
154
+ export declare function getPeer(peer: EntityLike | any): any;
155
+ export declare function sanitizeParseMode(mode: string | ParseInterface): ParseInterface;
156
+ /**
157
+ Convert the given peer into its marked ID by default.
158
+
159
+ This "mark" comes from the "bot api" format, and with it the peer type
160
+ can be identified back. User ID is left unmodified, chat ID is negated,
161
+ and channel ID is prefixed with -100:
162
+
163
+ * ``userId``
164
+ * ``-chatId``
165
+ * ``-100channel_id``
166
+
167
+ The original ID and the peer type class can be returned with
168
+ a call to :meth:`resolve_id(marked_id)`.
169
+ * @param peer
170
+ * @param addMark
171
+ */
172
+ export declare function getPeerId(peer: EntityLike, addMark?: boolean): string;
173
+ /**
174
+ * Given a marked ID, returns the original ID and its :tl:`Peer` type.
175
+ * @param markedId
176
+ */
177
+ export declare function resolveId(markedId: bigInt.BigInteger): [
178
+ bigInt.BigInteger,
179
+ typeof Api.PeerUser | typeof Api.PeerChannel | typeof Api.PeerChat
180
+ ];
181
+ /**
182
+ * returns an entity pair
183
+ * @param entityId
184
+ * @param entities
185
+ * @param cache
186
+ * @param getInputPeer
187
+ * @returns {{inputEntity: *, entity: *}}
188
+ * @private
189
+ */
190
+ export declare function getMessageId(message: number | Api.TypeMessage | MessageIDLike | undefined): number | undefined;
191
+ /**
192
+ * Parses the given phone, or returns `undefined` if it's invalid.
193
+ * @param phone
194
+ */
195
+ export declare function parsePhone(phone: string): string | undefined;
196
+ /**
197
+ * Parses a string ID into a big int
198
+ * @param id
199
+ */
200
+ export declare function parseID(id: string): bigInt.BigInteger | undefined;
201
+ export declare function resolveInviteLink(link: string): [number, number, number];
202
+ /**
203
+ Parses the given username or channel access hash, given
204
+ a string, username or URL. Returns a tuple consisting of
205
+ both the stripped, lowercase username and whether it is
206
+ a joinchat/ hash (in which case is not lowercase'd).
207
+
208
+ Returns ``(undefined, false)`` if the ``username`` or link is not valid.
209
+
210
+ * @param username {string}
211
+ */
212
+ export declare function parseUsername(username: string): {
213
+ username?: string;
214
+ isInvite: boolean;
215
+ };
216
+ export declare function rtrim(s: string, mask: string): string;
217
+ /**
218
+ * Gets the display name for the given :tl:`User`,
219
+ :tl:`Chat` or :tl:`Channel`. Returns an empty string otherwise
220
+ * @param entity
221
+ */
222
+ export declare function getDisplayName(entity: EntityLike): string;
223
+ export {};
224
+ /**
225
+ * check if a given item is an array like or not
226
+ * @param item
227
+ * @returns {boolean}
228
+ */