noblox.ts 4.10.5

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of noblox.ts might be problematic. Click here for more details.

Files changed (259) hide show
  1. package/.eslintrc.js +21 -0
  2. package/.github/FUNDING.yml +3 -0
  3. package/.github/ISSUE_TEMPLATE/bug_report.md +29 -0
  4. package/.github/ISSUE_TEMPLATE/feature_request.md +22 -0
  5. package/.github/workflows/doc-publish.yml +33 -0
  6. package/.github/workflows/npmpublish.yml +70 -0
  7. package/.travis.yml +13 -0
  8. package/CODE_OF_CONDUCT.md +76 -0
  9. package/LICENSE +21 -0
  10. package/README.md +168 -0
  11. package/examples/cleanPlayers.js +130 -0
  12. package/examples/cleanWall.js +110 -0
  13. package/examples/revertRanks.js +100 -0
  14. package/examples/savePlayers.js +119 -0
  15. package/examples/saveWall.js +96 -0
  16. package/img/moderatedThumbnails/moderatedThumbnail_100x100.png +0 -0
  17. package/img/moderatedThumbnails/moderatedThumbnail_110x110.png +0 -0
  18. package/img/moderatedThumbnails/moderatedThumbnail_140x140.png +0 -0
  19. package/img/moderatedThumbnails/moderatedThumbnail_150x150.png +0 -0
  20. package/img/moderatedThumbnails/moderatedThumbnail_150x200.png +0 -0
  21. package/img/moderatedThumbnails/moderatedThumbnail_180x180.png +0 -0
  22. package/img/moderatedThumbnails/moderatedThumbnail_250x250.png +0 -0
  23. package/img/moderatedThumbnails/moderatedThumbnail_30x30.png +0 -0
  24. package/img/moderatedThumbnails/moderatedThumbnail_352x352.png +0 -0
  25. package/img/moderatedThumbnails/moderatedThumbnail_420x420.png +0 -0
  26. package/img/moderatedThumbnails/moderatedThumbnail_48x48.png +0 -0
  27. package/img/moderatedThumbnails/moderatedThumbnail_50x50.png +0 -0
  28. package/img/moderatedThumbnails/moderatedThumbnail_60x60.png +0 -0
  29. package/img/moderatedThumbnails/moderatedThumbnail_720x720.png +0 -0
  30. package/img/moderatedThumbnails/moderatedThumbnail_75x75.png +0 -0
  31. package/img/noblox-js-small.png +0 -0
  32. package/img/noblox-js.png +0 -0
  33. package/img/thumbnailSizes.png +0 -0
  34. package/jsDocsConfig.json +55 -0
  35. package/lib/accountinformation/getUserSocialLinks.js +42 -0
  36. package/lib/accountsettings/block.js +58 -0
  37. package/lib/accountsettings/unblock.js +58 -0
  38. package/lib/asset/deleteFromInventory.js +69 -0
  39. package/lib/asset/getGamePassProductInfo.js +51 -0
  40. package/lib/asset/getProductInfo.js +56 -0
  41. package/lib/asset/uploadAnimation.js +103 -0
  42. package/lib/asset/uploadItem.js +83 -0
  43. package/lib/asset/uploadModel.js +90 -0
  44. package/lib/avatar/avatarRules.js +38 -0
  45. package/lib/avatar/currentlyWearing.js +32 -0
  46. package/lib/avatar/getAvatar.js +35 -0
  47. package/lib/avatar/getCurrentAvatar.js +37 -0
  48. package/lib/avatar/getRecentItems.js +37 -0
  49. package/lib/avatar/outfitDetails.js +32 -0
  50. package/lib/avatar/outfits.js +37 -0
  51. package/lib/avatar/redrawAvatar.js +48 -0
  52. package/lib/avatar/removeAssetId.js +55 -0
  53. package/lib/avatar/setAvatarBodyColors.js +60 -0
  54. package/lib/avatar/setAvatarScales.js +60 -0
  55. package/lib/avatar/setPlayerAvatarType.js +50 -0
  56. package/lib/avatar/setWearingAssets.js +50 -0
  57. package/lib/avatar/wearAssetId.js +55 -0
  58. package/lib/badges/getAwardedTimestamps.js +52 -0
  59. package/lib/badges/getBadgeInfo.js +43 -0
  60. package/lib/badges/getGameBadges.js +62 -0
  61. package/lib/badges/getPlayerBadges.js +28 -0
  62. package/lib/badges/updateBadgeInfo.js +80 -0
  63. package/lib/cache/add.js +14 -0
  64. package/lib/cache/addIf.js +26 -0
  65. package/lib/cache/clear.js +8 -0
  66. package/lib/cache/get.js +28 -0
  67. package/lib/cache/index.js +17 -0
  68. package/lib/cache/new.js +12 -0
  69. package/lib/cache/wrap.js +25 -0
  70. package/lib/chat/addUsersToConversation.js +61 -0
  71. package/lib/chat/chatSettings.js +33 -0
  72. package/lib/chat/getChatMessages.js +40 -0
  73. package/lib/chat/getConversations.js +43 -0
  74. package/lib/chat/getRolloutSettings.js +35 -0
  75. package/lib/chat/getUnreadConversationCount.js +33 -0
  76. package/lib/chat/getUnreadMessages.js +38 -0
  77. package/lib/chat/getUserConversations.js +37 -0
  78. package/lib/chat/markChatAsRead.js +52 -0
  79. package/lib/chat/markChatAsSeen.js +50 -0
  80. package/lib/chat/multiGetLatestMessages.js +37 -0
  81. package/lib/chat/onNewConversation.js +50 -0
  82. package/lib/chat/onNewMessage.js +53 -0
  83. package/lib/chat/onNewMessageBySelf.js +50 -0
  84. package/lib/chat/onUserOnline.js +50 -0
  85. package/lib/chat/onUserTyping.js +54 -0
  86. package/lib/chat/removeFromGroupConversation.js +62 -0
  87. package/lib/chat/renameGroupConversation.js +57 -0
  88. package/lib/chat/sendChatMessage.js +57 -0
  89. package/lib/chat/setChatUserTyping.js +61 -0
  90. package/lib/chat/start121Conversation.js +50 -0
  91. package/lib/chat/startCloudEditConversation.js +50 -0
  92. package/lib/chat/startGroupConversation.js +62 -0
  93. package/lib/client/onNotification.js +70 -0
  94. package/lib/client/setAPIKey.js +18 -0
  95. package/lib/client/setCookie.js +38 -0
  96. package/lib/datastores/deleteDatastoreEntry.js +66 -0
  97. package/lib/datastores/getDatastoreEntry.js +98 -0
  98. package/lib/datastores/getDatastoreEntryVersions.js +83 -0
  99. package/lib/datastores/getDatastoreKeys.js +73 -0
  100. package/lib/datastores/getDatastores.js +72 -0
  101. package/lib/datastores/incrementDatastoreEntry.js +93 -0
  102. package/lib/datastores/setDatastoreEntry.js +90 -0
  103. package/lib/develop/canManage.js +44 -0
  104. package/lib/develop/configureItem.js +142 -0
  105. package/lib/develop/updateUniverse.js +53 -0
  106. package/lib/develop/updateUniverseAccess.js +55 -0
  107. package/lib/economy/buy.js +99 -0
  108. package/lib/economy/getGroupFunds.js +43 -0
  109. package/lib/economy/getGroupRevenueSummary.js +48 -0
  110. package/lib/economy/getGroupTransactions.js +32 -0
  111. package/lib/economy/getResaleData.js +54 -0
  112. package/lib/economy/getResellers.js +35 -0
  113. package/lib/economy/getUserTransactions.js +34 -0
  114. package/lib/economy/onGroupTransaction.js +74 -0
  115. package/lib/friends/acceptFriendRequest.js +59 -0
  116. package/lib/friends/declineAllFriendRequests.js +57 -0
  117. package/lib/friends/declineFriendRequest.js +59 -0
  118. package/lib/friends/getFollowers.js +61 -0
  119. package/lib/friends/getFollowings.js +61 -0
  120. package/lib/friends/getFriendRequests.js +56 -0
  121. package/lib/friends/getFriends.js +53 -0
  122. package/lib/friends/onFriendRequest.js +58 -0
  123. package/lib/friends/removeFriend.js +58 -0
  124. package/lib/friends/sendFriendRequest.js +59 -0
  125. package/lib/friends/unfollow.js +58 -0
  126. package/lib/games/addDeveloperProduct.js +65 -0
  127. package/lib/games/checkDeveloperProductName.js +39 -0
  128. package/lib/games/configureGamePass.js +146 -0
  129. package/lib/games/getDeveloperProducts.js +51 -0
  130. package/lib/games/getGameInstances.js +31 -0
  131. package/lib/games/getGamePasses.js +39 -0
  132. package/lib/games/getGameRevenue.js +49 -0
  133. package/lib/games/getGameSocialLinks.js +45 -0
  134. package/lib/games/getGroupGames.js +30 -0
  135. package/lib/games/getPlaceInfo.js +48 -0
  136. package/lib/games/getUniverseInfo.js +51 -0
  137. package/lib/games/updateDeveloperProduct.js +69 -0
  138. package/lib/groups/changeRank.js +59 -0
  139. package/lib/groups/deleteWallPost.js +64 -0
  140. package/lib/groups/deleteWallPostsByUser.js +59 -0
  141. package/lib/groups/demote.js +25 -0
  142. package/lib/groups/exile.js +59 -0
  143. package/lib/groups/getAuditLog.js +67 -0
  144. package/lib/groups/getGroup.js +57 -0
  145. package/lib/groups/getGroupSocialLinks.js +44 -0
  146. package/lib/groups/getGroups.js +88 -0
  147. package/lib/groups/getJoinRequest.js +52 -0
  148. package/lib/groups/getJoinRequests.js +58 -0
  149. package/lib/groups/getPlayers.js +108 -0
  150. package/lib/groups/getRankInGroup.js +52 -0
  151. package/lib/groups/getRankNameInGroup.js +52 -0
  152. package/lib/groups/getRole.js +64 -0
  153. package/lib/groups/getRolePermissions.js +51 -0
  154. package/lib/groups/getRoles.js +56 -0
  155. package/lib/groups/getShout.js +49 -0
  156. package/lib/groups/getWall.js +59 -0
  157. package/lib/groups/groupPayout.js +103 -0
  158. package/lib/groups/handleJoinRequest.js +60 -0
  159. package/lib/groups/leaveGroup.js +60 -0
  160. package/lib/groups/onAuditLog.js +62 -0
  161. package/lib/groups/onJoinRequest.js +63 -0
  162. package/lib/groups/onJoinRequestHandle.js +105 -0
  163. package/lib/groups/onShout.js +57 -0
  164. package/lib/groups/onWallPost.js +58 -0
  165. package/lib/groups/promote.js +25 -0
  166. package/lib/groups/searchGroups.js +32 -0
  167. package/lib/groups/setGroupDescription.js +65 -0
  168. package/lib/groups/setGroupName.js +66 -0
  169. package/lib/groups/setRank.js +79 -0
  170. package/lib/groups/shout.js +65 -0
  171. package/lib/index.js +30 -0
  172. package/lib/internal/levelOneCopy.js +16 -0
  173. package/lib/internal/queue.js +61 -0
  174. package/lib/internal/timeout.js +30 -0
  175. package/lib/internal/wrap.js +78 -0
  176. package/lib/inventory/getCollectibles.js +31 -0
  177. package/lib/inventory/getInventory.js +32 -0
  178. package/lib/inventory/getInventoryById.js +31 -0
  179. package/lib/inventory/getOwnership.js +54 -0
  180. package/lib/inventory/getUAIDs.js +47 -0
  181. package/lib/itemconfiguration/getGroupAssets.js +32 -0
  182. package/lib/options.js +26 -0
  183. package/lib/party/onPartyDeleted.js +53 -0
  184. package/lib/party/onPartyInvite.js +53 -0
  185. package/lib/party/onPartyJoinedGame.js +53 -0
  186. package/lib/party/onPartyLeftGame.js +53 -0
  187. package/lib/party/onPartySelfJoined.js +53 -0
  188. package/lib/party/onPartySelfLeft.js +53 -0
  189. package/lib/party/onPartyUserJoined.js +53 -0
  190. package/lib/party/onPartyUserLeft.js +53 -0
  191. package/lib/premiumfeatures/getPremium.js +51 -0
  192. package/lib/presence/getPresences.js +63 -0
  193. package/lib/privatemessages/getMessages.js +60 -0
  194. package/lib/privatemessages/message.js +80 -0
  195. package/lib/privatemessages/onMessage.js +88 -0
  196. package/lib/thumbnails/getLogo.js +60 -0
  197. package/lib/thumbnails/getPlayerThumbnail.js +121 -0
  198. package/lib/thumbnails/getThumbnails.js +93 -0
  199. package/lib/trades/acceptTrade.js +58 -0
  200. package/lib/trades/canTradeWith.js +48 -0
  201. package/lib/trades/counterTrade.js +84 -0
  202. package/lib/trades/declineTrade.js +58 -0
  203. package/lib/trades/getTradeInfo.js +52 -0
  204. package/lib/trades/getTrades.js +37 -0
  205. package/lib/trades/sendTrade.js +82 -0
  206. package/lib/users/getBlurb.js +36 -0
  207. package/lib/users/getIdFromUsername.js +53 -0
  208. package/lib/users/getPlayerInfo.js +100 -0
  209. package/lib/users/getUsernameFromId.js +44 -0
  210. package/lib/users/onBlurbChange.js +46 -0
  211. package/lib/util/clearSession.js +32 -0
  212. package/lib/util/generalRequest.js +61 -0
  213. package/lib/util/getAction.js +45 -0
  214. package/lib/util/getCurrentUser.js +44 -0
  215. package/lib/util/getGeneralToken.js +52 -0
  216. package/lib/util/getHash.js +29 -0
  217. package/lib/util/getInputs.js +37 -0
  218. package/lib/util/getPageResults.js +89 -0
  219. package/lib/util/getSenderUserId.js +30 -0
  220. package/lib/util/getSession.js +38 -0
  221. package/lib/util/getVerification.js +60 -0
  222. package/lib/util/getVerificationInputs.js +31 -0
  223. package/lib/util/http.js +110 -0
  224. package/lib/util/jar.js +24 -0
  225. package/lib/util/refreshCookie.js +52 -0
  226. package/lib/util/relog.js +81 -0
  227. package/lib/util/setOptions.js +54 -0
  228. package/lib/util/shortPoll.js +102 -0
  229. package/lib/util/threaded.js +80 -0
  230. package/package.json +94 -0
  231. package/postinstall.js +1 -0
  232. package/settings.json +107 -0
  233. package/test/accountinformation.test.js +27 -0
  234. package/test/accountsettings.test.js +27 -0
  235. package/test/asset.test.js +81 -0
  236. package/test/assets/Great-White-Shark-Fin.rbxm +0 -0
  237. package/test/assets/KeyframeSequence.rbxm +0 -0
  238. package/test/avatar.test.js +164 -0
  239. package/test/badges.test.js +96 -0
  240. package/test/chat.test.js +104 -0
  241. package/test/datastore.test.js +105 -0
  242. package/test/develop.test.js +53 -0
  243. package/test/economy.test.js +137 -0
  244. package/test/friends.test.js +128 -0
  245. package/test/games.test.js +212 -0
  246. package/test/groups.test.js +311 -0
  247. package/test/inventory.test.js +98 -0
  248. package/test/itemconfiguration.test.js +24 -0
  249. package/test/premiumfeatures.test.js +17 -0
  250. package/test/presence.test.js +25 -0
  251. package/test/privatemessages.test.js +33 -0
  252. package/test/thumbnails.test.js +53 -0
  253. package/test/users.test.js +68 -0
  254. package/tutorials/Authentication.md +75 -0
  255. package/tutorials/Event Emitters.md +26 -0
  256. package/tutorials/Promises.md +86 -0
  257. package/tutorials/VPS Authentication.md +72 -0
  258. package/typings/index.d.ts +2525 -0
  259. package/typings/jsDocs.ts +1927 -0
@@ -0,0 +1,89 @@
1
+ // Includes
2
+ const http = require('./http.js').func
3
+
4
+ // Args
5
+ exports.required = ['url', 'query', 'limit']
6
+ exports.optional = ['jar', 'sortOrder']
7
+
8
+ // Docs
9
+ /**
10
+ * ✅ Handle pagination returned by Roblox.
11
+ * @category Utility
12
+ * @alias getPageResults
13
+ * @param {string} url - The url to retrieve the page results from.
14
+ * @param {string} query - Any query parameters to add to the url.
15
+ * @param {SortOrder=} sortOrder - The order to sort the results by.
16
+ * @param {Limit=} limit - The maximum number of results to return. Following 'pages' of results will be requested until
17
+ * this limit of results is reached.
18
+ * @param {string=} pageCursor - Current page index
19
+ * @returns {Promise<Array>}
20
+ * @example const noblox = require("noblox.js")
21
+ * const inventory = await noblox.getPageResults("//inventory.roblox.com/v2/users/1/inventory", "Shirt", "Asc", 100)
22
+ **/
23
+
24
+ // Define
25
+ function getPageResults (jar, url, query, sortOrder, limit, pageCursor, results) {
26
+ return new Promise((resolve, reject) => {
27
+ const allowedLimits = [10, 25, 50, 100]
28
+
29
+ const httpOpt = {
30
+ url: url,
31
+ options: {
32
+ qs: {
33
+ limit: limit <= 100 ? allowedLimits.reduce((prev, curr) => Math.abs(curr - limit) < Math.abs(prev - limit) ? curr : prev) : 100, // Get the most fit page limit within the boundries.
34
+ cursor: pageCursor || '', // Add page cursor.
35
+ ...query // Add asset types.
36
+ },
37
+ method: 'GET',
38
+ resolveWithFullResponse: true,
39
+ jar: jar,
40
+ json: true
41
+ }
42
+ }
43
+ return http(httpOpt).then((res) => {
44
+ let body = res.body
45
+ if (typeof (body) === 'string') body = JSON.parse(body.trim())
46
+
47
+ const data = body.data
48
+
49
+ if (body.errors && body.errors.length > 0) {
50
+ const errors = body.errors.map((e) => {
51
+ return e.message
52
+ })
53
+
54
+ return reject(new Error(`${res.statusCode} ${errors.join(', ')}`))
55
+ }
56
+
57
+ results = results ? results.concat(data) : data
58
+
59
+ if (results.length > limit) {
60
+ results = results.slice(0, limit)
61
+ }
62
+
63
+ if (results.length >= limit || data.length === 0 || !body.nextPageCursor) {
64
+ return resolve(results)
65
+ }
66
+
67
+ resolve(getPageResults(jar, url, query, sortOrder, limit, body.nextPageCursor, results))
68
+ })
69
+ .catch(error => reject(error))
70
+ })
71
+ }
72
+
73
+ function parseDates (results) {
74
+ return new Promise((resolve, reject) => {
75
+ if (!results) return resolve([])
76
+
77
+ resolve(results.map(result => {
78
+ if (result.created) result.created = new Date(result.created)
79
+ if (result.updated) result.updated = new Date(result.updated)
80
+ return result
81
+ }))
82
+ })
83
+ }
84
+
85
+ exports.func = function (args) {
86
+ return getPageResults(args.jar, args.url, args.query, args.sortOrder, args.limit).then(results => {
87
+ return parseDates(results)
88
+ })
89
+ }
@@ -0,0 +1,30 @@
1
+ // Includes
2
+ const getCurrentUser = require('./getCurrentUser.js').func
3
+ const getHash = require('./getHash.js').func
4
+ const cache = require('../cache')
5
+
6
+ // Args
7
+ exports.optional = ['jar']
8
+
9
+ // Docs
10
+ /**
11
+ * 🔐 Get the userId of the current user and cache it.
12
+ * @category Utility
13
+ * @alias getSenderUserId
14
+ * @param {CookieJar=} jar - The CookieJar containing the .ROBLOSECURITY cookie.
15
+ * @returns {Promise<number>}
16
+ * @example const noblox = require("noblox.js")
17
+ * // Login using your cookie.
18
+ * const userId = await noblox.getSenderUserId()
19
+ **/
20
+
21
+ // Define
22
+ exports.func = function (args) {
23
+ const jar = args.jar
24
+ return cache.wrap('SenderID', getHash({ jar: jar }), function () {
25
+ return getCurrentUser({ jar: jar })
26
+ .then(function (info) {
27
+ return info.UserID
28
+ })
29
+ })
30
+ }
@@ -0,0 +1,38 @@
1
+ // Includes
2
+ const settings = require('../../settings.json')
3
+ const options = require('../options.js')
4
+
5
+ // Args
6
+ exports.optional = ['jar']
7
+
8
+ // Docs
9
+ /**
10
+ * 🔐 Get the .ROBLOSECURITY cookie from the jar.
11
+ * @category Utility
12
+ * @alias getSession
13
+ * @param {CookieJar=} jar - The cookie jar containing the .ROBLOSECURITY cookie.
14
+ * @returns {string}
15
+ * @example const noblox = require("noblox.js")
16
+ * // Login using your cookie.
17
+ * const cookie = await noblox.getSession()
18
+ **/
19
+
20
+ // Define
21
+ exports.func = function (args) {
22
+ const jar = args.jar || options.jar
23
+ if (settings.session_only) {
24
+ if (typeof jar === 'string') {
25
+ return jar
26
+ }
27
+ return jar.session
28
+ } else {
29
+ const cookies = jar.getCookies('https://roblox.com')
30
+ for (let i = 0; i < cookies.length; i++) {
31
+ const element = cookies[i]
32
+ if (element.key === '.ROBLOSECURITY') {
33
+ return element.value
34
+ }
35
+ }
36
+ return ''
37
+ }
38
+ }
@@ -0,0 +1,60 @@
1
+ // Includes
2
+ const http = require('./http.js').func
3
+ const getHash = require('./getHash.js').func
4
+ const getVerificationInputs = require('./getVerificationInputs.js').func
5
+ const cache = require('../cache')
6
+ const URL = require('url').URL
7
+
8
+ // Args
9
+ exports.required = ['url']
10
+ exports.optional = ['ignoreCache', 'getBody', 'jar']
11
+
12
+ // Docs
13
+ /**
14
+ * 🔐 Get the RequestVerificationToken from a url.
15
+ * @category Utility
16
+ * @alias getVerification
17
+ * @param {string} url - The url to get the token from.
18
+ * @param {boolean=} [ignoreCache=false] - Determines whether the cache be ignored or not.
19
+ * @param {boolean=} [getBody=false] - If the body and inputs should be returned in an object
20
+ * @param {CookieJar=} jar - The CookieJar containing the .ROBLOSECURITY cookie.
21
+ * @returns {Promise<GetVerificationResponse>}
22
+ * @example const noblox = require("noblox.js")
23
+ * // Login using your cookie.
24
+ * const verificationTokenInfo = await noblox.getVerification()
25
+ **/
26
+
27
+ // Define
28
+ function getVerification (jar, url, getBody) {
29
+ const httpOpt = {
30
+ url: url,
31
+ options: {
32
+ resolveWithFullResponse: true,
33
+ jar: jar
34
+ }
35
+ }
36
+ return http(httpOpt)
37
+ .then(function (res) {
38
+ const inputs = getVerificationInputs({ html: res.body })
39
+ let match
40
+ if (res.headers && res.headers['set-cookie']) {
41
+ match = res.headers['set-cookie'].toString().match(/__RequestVerificationToken=(.*?);/)
42
+ }
43
+ return {
44
+ body: (getBody ? res.body : null),
45
+ inputs: inputs,
46
+ header: match && match[1]
47
+ }
48
+ })
49
+ }
50
+
51
+ exports.func = function (args) {
52
+ const jar = args.jar
53
+ if (args.ignoreCache) {
54
+ return getVerification(jar, args.url, args.getBody)
55
+ } else {
56
+ return cache.wrap('Verify', new URL(args.url).pathname + getHash({ jar: jar }), function () {
57
+ return getVerification(jar, args.url, args.getBody)
58
+ })
59
+ }
60
+ }
@@ -0,0 +1,31 @@
1
+ // Dependencies
2
+ const parser = require('cheerio')
3
+
4
+ // Args
5
+ exports.required = [['html', 'selector']]
6
+
7
+ // Docs
8
+ /**
9
+ * ✅ Get the verification inputs from the html.
10
+ * @category Utility
11
+ * @alias getVerificationInputs
12
+ * @param {string | function} html | selector - The html to search or the cheerio selector to use.
13
+ * @returns {Inputs}
14
+ * @example const noblox = require("noblox.js")
15
+ * const inputs = noblox.getVerificationInputs("htmlstuff")
16
+ **/
17
+
18
+ // Define
19
+ exports.func = function (args) {
20
+ let $ = args.selector
21
+ if (!$) {
22
+ $ = parser.load(args.html)
23
+ }
24
+ const inputs = {}
25
+ const find = ['__VIEWSTATE', '__VIEWSTATEGENERATOR', '__EVENTVALIDATION', '__RequestVerificationToken']
26
+ for (let i = 0; i < find.length; i++) {
27
+ const get = find[i]
28
+ inputs[get] = $('input[name=' + get + ']').val()
29
+ }
30
+ return inputs
31
+ }
@@ -0,0 +1,110 @@
1
+ // Dependencies
2
+ let request = require('request-promise')
3
+
4
+ // Includes
5
+ const options = require('../options.js')
6
+ const settings = require('../../settings.json')
7
+ const cache = require('../cache')
8
+ const getHash = require('./getHash.js').func
9
+
10
+ // Args
11
+ exports.required = ['url']
12
+ exports.optional = ['options', 'ignoreLoginError']
13
+
14
+ // Define
15
+ request = request.defaults({
16
+ forever: true,
17
+ agentOptions: {
18
+ maxSockets: Infinity
19
+ },
20
+ simple: false,
21
+ gzip: true,
22
+ timeout: settings.timeout
23
+ })
24
+
25
+ // Docs
26
+ /**
27
+ * ✅ Send an http request to url with options.
28
+ * @category Utility
29
+ * @alias http
30
+ * @param {string} url - The url to request to.
31
+ * @param {object} options - The options to send with the request.
32
+ * @param {boolean} ignoreLoginError - If any login errors should be ignored.
33
+ * @returns {Promise<string>}
34
+ * @example const noblox = require("noblox.js")
35
+ * const body = await noblox.http("https://roblox.com/login", { method: "GET" })
36
+ **/
37
+
38
+ function http (url, opt) {
39
+ if (opt && !opt.jar && Object.keys(opt).indexOf('jar') > -1) {
40
+ opt.jar = options.jar
41
+ }
42
+ if (settings.session_only && opt && opt.jar) {
43
+ if (!opt.headers) {
44
+ opt.headers = {}
45
+ }
46
+ opt.headers.cookie = '.ROBLOSECURITY=' + opt.jar.session + ';'
47
+ opt.headers['x-api-key'] = opt.jar.apiKey
48
+ opt.jar = null
49
+ }
50
+ if (opt && opt.verification) {
51
+ if (!opt.headers) {
52
+ opt.headers = {}
53
+ }
54
+ const verify = '__RequestVerificationToken=' + opt.verification + ';'
55
+ if (opt.headers.cookie) {
56
+ opt.headers.cookie += verify
57
+ } else {
58
+ opt.headers.cookie = verify
59
+ }
60
+ }
61
+ if (url.indexOf('http') !== 0) {
62
+ url = 'https:' + url
63
+ }
64
+ return request(url, opt)
65
+ }
66
+
67
+ exports.func = function (args) {
68
+ const opt = args.options || {}
69
+ if (typeof opt.jar === 'string') {
70
+ opt.jar = { session: opt.jar }
71
+ }
72
+ const jar = opt.jar
73
+ let depth = args.depth || 0
74
+ const full = opt.resolveWithFullResponse || false
75
+ opt.resolveWithFullResponse = true
76
+ const follow = opt.followRedirect === undefined || opt.followRedirect
77
+ opt.followRedirect = function (res) {
78
+ if (!args.ignoreLoginError && res.headers.location && (res.headers.location.startsWith('https://www.roblox.com/newlogin') || res.headers.location.startsWith('/Login/Default.aspx'))) {
79
+ return false
80
+ }
81
+ return follow
82
+ }
83
+ return http(args.url, opt).then(function (res) {
84
+ if (opt && opt.headers && opt.headers['X-CSRF-TOKEN']) {
85
+ if (res.statusCode === 403 && (res.statusMessage === 'XSRF Token Validation Failed' || res.statusMessage === 'Token Validation Failed')) {
86
+ depth++
87
+ if (depth >= 3) {
88
+ throw new Error('Tried ' + depth + ' times and could not refresh XCSRF token successfully')
89
+ }
90
+ const token = res.headers['x-csrf-token']
91
+ if (token) {
92
+ opt.headers['X-CSRF-TOKEN'] = token
93
+ opt.jar = jar
94
+ args.depth = depth + 1
95
+ return exports.func(args)
96
+ } else {
97
+ throw new Error('Could not refresh X-CSRF-TOKEN')
98
+ }
99
+ } else {
100
+ if (depth > 0) {
101
+ cache.add(options.cache, 'XCSRF', getHash({ jar: jar }), opt.headers['X-CSRF-TOKEN'])
102
+ }
103
+ }
104
+ }
105
+ if (res.statusCode === 302 && !args.ignoreLoginError && res.headers.location && (res.headers.location.startsWith('https://www.roblox.com/newlogin') || res.headers.location.startsWith('/Login/Default.aspx'))) {
106
+ throw new Error('You are not logged in')
107
+ }
108
+ return full ? res : res.body
109
+ })
110
+ }
@@ -0,0 +1,24 @@
1
+ // Dependencies
2
+ const request = require('request-promise')
3
+
4
+ // Includes
5
+ const settings = require('../../settings.json')
6
+
7
+ // Docs
8
+ /**
9
+ * ✅ Create a jar file based on sessionOnly.
10
+ * @category Utility
11
+ * @alias jar
12
+ * @param {boolean=} sessionOnly - The session to use to create the jar file.
13
+ * @returns {CookieJar}
14
+ * @example const noblox = require("noblox.js")
15
+ * const jar = noblox.jar()
16
+ **/
17
+
18
+ // Define
19
+ exports.func = function (sessionOnly) {
20
+ if (!sessionOnly) {
21
+ sessionOnly = settings.session_only
22
+ }
23
+ return (sessionOnly ? { session: '' } : request.jar())
24
+ }
@@ -0,0 +1,52 @@
1
+ // Includes
2
+ const options = require('../options.js')
3
+ const getGeneralToken = require('./getGeneralToken.js').func
4
+ const http = require('./http.js').func
5
+ // Args
6
+ exports.required = []
7
+ exports.optional = ['cookie']
8
+
9
+ // Docs
10
+ /**
11
+ * 🔐 Refreshes the stored cookie, stores it, and returns it.
12
+ * @category Utility
13
+ * @deprecated [Retrieving your .ROBLOSECURITY cookie in incognito mode should make a cookie that does not expire.]{@link https://noblox.js.org/tutorial-Authentication.html}
14
+ * @alias refreshCookie
15
+ * @param {string=} cookie - The cookie to refresh.
16
+ * @returns {Promise<string>}
17
+ * @example const noblox = require("noblox.js")
18
+ * const newCookie = await noblox.refreshCookie("COOKIEHERE")
19
+ **/
20
+
21
+ // Refreshes the internally stored cookie, or the cookie provided
22
+ // Stores the new cookie & returns it
23
+ function refreshCookie (cookie) {
24
+ if (cookie) {
25
+ options.jar.session = cookie
26
+ }
27
+
28
+ return getGeneralToken({}).then((token) => {
29
+ return http({
30
+ url: 'https://www.roblox.com/authentication/signoutfromallsessionsandreauthenticate',
31
+ options: {
32
+ method: 'POST',
33
+ resolveWithFullResponse: true,
34
+ jar: null,
35
+ headers: {
36
+ 'X-CSRF-TOKEN': token
37
+ }
38
+ }
39
+ }).then((res) => {
40
+ const cookies = res.headers['set-cookie']
41
+ if (cookies) {
42
+ const cookie = cookies.toString().match(/\.ROBLOSECURITY=(.*?);/)[1]
43
+ options.jar.session = cookie
44
+ return cookie
45
+ } else {
46
+ throw new Error('Failed to refresh cookie: None returned.')
47
+ }
48
+ })
49
+ })
50
+ }
51
+
52
+ module.exports = refreshCookie
@@ -0,0 +1,81 @@
1
+ // Includes
2
+ const options = require('../options.js')
3
+ const getGeneralToken = require('./getGeneralToken.js').func
4
+ const getVerification = require('./getVerification.js').func
5
+ const getCurrentUser = require('./getCurrentUser.js').func
6
+ const http = require('./http.js').func
7
+ const cookieFile = './cookie'
8
+ const fs = require('fs')
9
+ // Args
10
+ exports.required = ['cookie']
11
+ exports.optional = []
12
+
13
+ const day = 86400000
14
+
15
+ // Define
16
+ const relog = (cookie) => {
17
+ if (!cookie) throw new Error('no cookie supplied?')
18
+ options.jar.session = cookie
19
+ return getVerification({ url: 'https://www.roblox.com/my/account#!/security' })
20
+ .then((ver) => {
21
+ if (!ver.header) console.log('Bad cookie.')
22
+ return getGeneralToken({}).then((token) => {
23
+ return http({
24
+ url: 'https://www.roblox.com/authentication/signoutfromallsessionsandreauthenticate',
25
+ options: {
26
+ method: 'POST',
27
+ resolveWithFullResponse: true,
28
+ verification: ver.header,
29
+ jar: null,
30
+ headers: {
31
+ 'X-CSRF-TOKEN': token
32
+ },
33
+ form: {
34
+ __RequestVerificationToken: ver.inputs.__RequestVerificationToken
35
+ }
36
+ }
37
+ }).then((res) => {
38
+ const cookies = res.headers['set-cookie']
39
+ if (cookies) {
40
+ options.jar.session = cookies.toString().match(/\.ROBLOSECURITY=(.*?);/)[1]
41
+
42
+ fs.writeFile(cookieFile, JSON.stringify({ cookie: options.jar.session, time: Date.now() }), (err) => {
43
+ if (err) {
44
+ console.error('Failed to write cookie')
45
+ }
46
+ return true
47
+ })
48
+ }
49
+ })
50
+ })
51
+ })
52
+ }
53
+ module.exports = c
54
+
55
+ async function c (cookie) {
56
+ // Check for file
57
+ if (fs.existsSync(cookieFile)) {
58
+ const json = JSON.parse(fs.readFileSync(cookieFile))
59
+
60
+ // Check its new enough
61
+ if (json.time + day > Date.now()) {
62
+ // Its recent enough. Try it.
63
+ try {
64
+ await relog(json.cookie)
65
+ return getCurrentUser({})
66
+ } catch (e) {
67
+ console.log('Stored relog failed. Trying with given.')
68
+ }
69
+ }
70
+ }
71
+ if (cookie) {
72
+ // Try the user's cookie
73
+ try {
74
+ await relog(cookie)
75
+ return getCurrentUser({})
76
+ } catch (e) {
77
+ console.error(e)
78
+ }
79
+ }
80
+ throw new Error('No cookie supplied and no cookie file available.')
81
+ }
@@ -0,0 +1,54 @@
1
+ const settings = require('../../settings.json')
2
+
3
+ // Docs
4
+ /**
5
+ * ✅ Updates library options. This allows you to modify settings such as time-out, or number of event retries without
6
+ * altering the settings.json file. Objects passed to this function should match the format of the settings.json file.
7
+ * Unknown keys, or malformed options will be rejected with an error.
8
+ * @category Utility
9
+ * @param {NobloxOptions} newOptions - The new options to set, structured as per [settings.json](https://github.com/noblox/noblox.js/blob/master/settings.json)
10
+ * @returns void
11
+ * @see [settings.json](https://github.com/noblox/noblox.js/blob/master/settings.json) - default package settings
12
+ * @example const noblox = require("noblox.js")
13
+ * // This example overrides getPlayerThumbnail()'s response URL when a thumbnail is moderated.
14
+ * // You usually want to run this before logging in with your cookie.
15
+ * noblox.setOptions({
16
+ * thumbnail: {
17
+ * failedUrl: {
18
+ * blocked: "https://raw.githubusercontent.com/noblox/noblox.js/master/img/noblox-js.png"
19
+ * }
20
+ * }
21
+ * })
22
+ */
23
+ function setOptions (newOptions) {
24
+ return setOptionsLevel(settings, newOptions)
25
+ }
26
+
27
+ // This function allows key validation to be performed at different "levels" of nesting.
28
+ // Ensures the provided keys already exist, and discards invalid keys.
29
+ function setOptionsLevel (settingsLevel, inputObj) {
30
+ const keys = Object.keys(inputObj)
31
+
32
+ for (const key of keys) {
33
+ const newValue = inputObj[key]
34
+ const currentValue = settingsLevel[key]
35
+
36
+ if (currentValue !== undefined) {
37
+ if (typeof currentValue === 'object') {
38
+ if (typeof inputObj[key] !== 'object') {
39
+ throw new Error(`Tried to set options key ${key}, an object, to a non-object value: ${newValue}`)
40
+ }
41
+
42
+ setOptionsLevel(currentValue, newValue)
43
+ } else {
44
+ // it's not undefined, and it's not a nested object - set the value.
45
+ settingsLevel[key] = newValue
46
+ }
47
+ } else {
48
+ // The key doesn't exist
49
+ throw new Error(`Tried to set option "${key}". This option does not exist, or has been nested incorrectly.`)
50
+ }
51
+ }
52
+ }
53
+
54
+ exports.func = setOptions
@@ -0,0 +1,102 @@
1
+ // Dependencies
2
+ const events = require('events')
3
+
4
+ // Includes
5
+ const settings = require('../../settings.json')
6
+ const promiseTimeout = require('../internal/timeout')
7
+
8
+ // Args
9
+ exports.required = ['getLatest', 'delay']
10
+ exports.optional = ['timeout']
11
+
12
+ // Docs
13
+ /**
14
+ * @typedef {function} getLatest
15
+ * @param {number} latest - A value representing the latest version.
16
+ * @param {EventEmitter} event - The event emitter to emit to.
17
+ */
18
+
19
+ /**
20
+ * ✅ This is the base for events that do not rely on true streams. The `getLatest` function receives some value that represents the latest version of something (eg. a date or unique ID) and determines if there is new information, every time it is fired it waits `delay` ms before being fired again. Every time it must return an object with the field `latest`, representing the latest value (which will not change if new information was not received), and an array `data` which has the new values (if there are multiple they each have their own index, if there is only one then it is by itself in the array). If `latest` is equal to -2, the returned data will be processed even if it is the initial run (which usually only establishes the latest value). If the return object has a true `repeat` value, the function latest will be run again immediately after. If `delay` is a string it will take the number from that string key in the `event` object of the settings.json file.
21
+ * When the function is first called it will initialize `getLatest` with the value -1 and then emit the `connect` event. Whenever data is received, it will emit the `data` event for each value. If the `close` event is emitted the function will no longer run. If an error occurs the `error` event will be emitted, the function will log a retry and after the number of max retries as specified by settings, it will emit the `close` event.
22
+ * The `getLatest` function will be marked as failed if it does not resolve within `timeout` ms (which can be disabled if timeout is negative). If getLatest fails for any reason (including timeout) it will be retried `maxRetries` times before stopping.
23
+ * @category Utility
24
+ * @alias shortPoll
25
+ * @param {function} getLatest - The function to use to get the latest. Should return an object with key 'data' - an array containing output data,
26
+ * and the new 'latest' value.
27
+ * @returns {Promise<GetLatestResponse>}
28
+ **/
29
+
30
+ // Define
31
+ exports.func = function (args) {
32
+ const latest = args.getLatest
33
+ let delay = args.delay
34
+ delay = (typeof delay === 'string' || delay instanceof String ? settings.event[delay] : delay) || settings.event.defaultDelay
35
+ let retries = 0
36
+ const max = settings.event.maxRetries
37
+ const timeout = args.timeout || settings.event.timeout
38
+ let stop = false
39
+ let current
40
+ const evt = new events.EventEmitter()
41
+ const run = function (value) {
42
+ if (stop) {
43
+ return
44
+ }
45
+ let promise = latest(value, evt)
46
+ if (timeout > 0) {
47
+ promise = promiseTimeout(promise, timeout)
48
+ }
49
+ return promise.then(function (response) {
50
+ if (stop) {
51
+ return
52
+ }
53
+ if (value === -1) {
54
+ current = response.latest
55
+ }
56
+ retries = 0
57
+ const data = response.data
58
+ if (data.length > 0 && (value !== -1 || current === -2)) {
59
+ current = response.latest
60
+ for (let i = 0; i < data.length; i++) {
61
+ evt.emit('data', data[i])
62
+ }
63
+ }
64
+ if (response.repeat) {
65
+ run(current)
66
+ } else {
67
+ setTimeout(run, delay, current)
68
+ }
69
+ return response
70
+ })
71
+ .catch(function (err) {
72
+ if (stop) {
73
+ return
74
+ }
75
+ evt.emit('error', err)
76
+ retries++
77
+ if (retries > max) {
78
+ evt.emit('close', new Error('Max retries reached'))
79
+ } else {
80
+ setTimeout(run, delay, current)
81
+ }
82
+ })
83
+ }
84
+
85
+ run(-1)
86
+ .then(function (response) {
87
+ if (stop) {
88
+ return
89
+ }
90
+ evt.emit('connect', response.latest)
91
+ })
92
+ .catch(function (err) {
93
+ evt.emit('close', new Error('Initialization failed: ' + err.message))
94
+ })
95
+ evt.on('close', function (err) {
96
+ stop = true
97
+ if (err) {
98
+ evt.emit('error', err)
99
+ }
100
+ })
101
+ return evt
102
+ }