noblox.ts-fetch 4.6.8
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-fetch might be problematic. Click here for more details.
- package/.eslintrc.js +21 -0
- package/.github/FUNDING.yml +3 -0
- package/.github/ISSUE_TEMPLATE/bug_report.md +29 -0
- package/.github/ISSUE_TEMPLATE/feature_request.md +22 -0
- package/.github/workflows/doc-publish.yml +33 -0
- package/.github/workflows/npmpublish.yml +70 -0
- package/.travis.yml +13 -0
- package/CODE_OF_CONDUCT.md +76 -0
- package/LICENSE +21 -0
- package/README.md +168 -0
- package/examples/cleanPlayers.js +130 -0
- package/examples/cleanWall.js +110 -0
- package/examples/revertRanks.js +100 -0
- package/examples/savePlayers.js +119 -0
- package/examples/saveWall.js +96 -0
- package/img/moderatedThumbnails/moderatedThumbnail_100x100.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_110x110.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_140x140.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_150x150.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_150x200.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_180x180.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_250x250.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_30x30.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_352x352.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_420x420.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_48x48.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_50x50.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_60x60.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_720x720.png +0 -0
- package/img/moderatedThumbnails/moderatedThumbnail_75x75.png +0 -0
- package/img/noblox-js-small.png +0 -0
- package/img/noblox-js.png +0 -0
- package/img/thumbnailSizes.png +0 -0
- package/jsDocsConfig.json +55 -0
- package/lib/accountinformation/getUserSocialLinks.js +42 -0
- package/lib/accountsettings/block.js +58 -0
- package/lib/accountsettings/unblock.js +58 -0
- package/lib/asset/deleteFromInventory.js +69 -0
- package/lib/asset/getGamePassProductInfo.js +51 -0
- package/lib/asset/getProductInfo.js +56 -0
- package/lib/asset/uploadAnimation.js +103 -0
- package/lib/asset/uploadItem.js +83 -0
- package/lib/asset/uploadModel.js +90 -0
- package/lib/avatar/avatarRules.js +38 -0
- package/lib/avatar/currentlyWearing.js +32 -0
- package/lib/avatar/getAvatar.js +35 -0
- package/lib/avatar/getCurrentAvatar.js +37 -0
- package/lib/avatar/getRecentItems.js +37 -0
- package/lib/avatar/outfitDetails.js +32 -0
- package/lib/avatar/outfits.js +37 -0
- package/lib/avatar/redrawAvatar.js +48 -0
- package/lib/avatar/removeAssetId.js +55 -0
- package/lib/avatar/setAvatarBodyColors.js +60 -0
- package/lib/avatar/setAvatarScales.js +60 -0
- package/lib/avatar/setPlayerAvatarType.js +50 -0
- package/lib/avatar/setWearingAssets.js +50 -0
- package/lib/avatar/wearAssetId.js +55 -0
- package/lib/badges/getAwardedTimestamps.js +52 -0
- package/lib/badges/getBadgeInfo.js +43 -0
- package/lib/badges/getGameBadges.js +62 -0
- package/lib/badges/getPlayerBadges.js +28 -0
- package/lib/badges/updateBadgeInfo.js +80 -0
- package/lib/cache/add.js +14 -0
- package/lib/cache/addIf.js +26 -0
- package/lib/cache/clear.js +8 -0
- package/lib/cache/get.js +28 -0
- package/lib/cache/index.js +17 -0
- package/lib/cache/new.js +12 -0
- package/lib/cache/wrap.js +25 -0
- package/lib/chat/addUsersToConversation.js +61 -0
- package/lib/chat/chatSettings.js +33 -0
- package/lib/chat/getChatMessages.js +40 -0
- package/lib/chat/getConversations.js +43 -0
- package/lib/chat/getRolloutSettings.js +35 -0
- package/lib/chat/getUnreadConversationCount.js +33 -0
- package/lib/chat/getUnreadMessages.js +38 -0
- package/lib/chat/getUserConversations.js +37 -0
- package/lib/chat/markChatAsRead.js +52 -0
- package/lib/chat/markChatAsSeen.js +50 -0
- package/lib/chat/multiGetLatestMessages.js +37 -0
- package/lib/chat/onNewConversation.js +50 -0
- package/lib/chat/onNewMessage.js +53 -0
- package/lib/chat/onNewMessageBySelf.js +50 -0
- package/lib/chat/onUserOnline.js +50 -0
- package/lib/chat/onUserTyping.js +54 -0
- package/lib/chat/removeFromGroupConversation.js +62 -0
- package/lib/chat/renameGroupConversation.js +57 -0
- package/lib/chat/sendChatMessage.js +57 -0
- package/lib/chat/setChatUserTyping.js +61 -0
- package/lib/chat/start121Conversation.js +50 -0
- package/lib/chat/startCloudEditConversation.js +50 -0
- package/lib/chat/startGroupConversation.js +62 -0
- package/lib/client/onNotification.js +70 -0
- package/lib/client/setAPIKey.js +18 -0
- package/lib/client/setCookie.js +38 -0
- package/lib/datastores/deleteDatastoreEntry.js +66 -0
- package/lib/datastores/getDatastoreEntry.js +98 -0
- package/lib/datastores/getDatastoreEntryVersions.js +83 -0
- package/lib/datastores/getDatastoreKeys.js +73 -0
- package/lib/datastores/getDatastores.js +72 -0
- package/lib/datastores/incrementDatastoreEntry.js +93 -0
- package/lib/datastores/setDatastoreEntry.js +90 -0
- package/lib/develop/canManage.js +44 -0
- package/lib/develop/configureItem.js +142 -0
- package/lib/develop/updateUniverse.js +53 -0
- package/lib/develop/updateUniverseAccess.js +55 -0
- package/lib/economy/buy.js +99 -0
- package/lib/economy/getGroupFunds.js +43 -0
- package/lib/economy/getGroupRevenueSummary.js +48 -0
- package/lib/economy/getGroupTransactions.js +32 -0
- package/lib/economy/getResaleData.js +54 -0
- package/lib/economy/getResellers.js +35 -0
- package/lib/economy/getUserTransactions.js +34 -0
- package/lib/economy/onGroupTransaction.js +74 -0
- package/lib/friends/acceptFriendRequest.js +59 -0
- package/lib/friends/declineAllFriendRequests.js +57 -0
- package/lib/friends/declineFriendRequest.js +59 -0
- package/lib/friends/getFollowers.js +61 -0
- package/lib/friends/getFollowings.js +61 -0
- package/lib/friends/getFriendRequests.js +56 -0
- package/lib/friends/getFriends.js +53 -0
- package/lib/friends/onFriendRequest.js +58 -0
- package/lib/friends/removeFriend.js +58 -0
- package/lib/friends/sendFriendRequest.js +59 -0
- package/lib/friends/unfollow.js +58 -0
- package/lib/games/addDeveloperProduct.js +65 -0
- package/lib/games/checkDeveloperProductName.js +39 -0
- package/lib/games/configureGamePass.js +146 -0
- package/lib/games/getDeveloperProducts.js +51 -0
- package/lib/games/getGameInstances.js +31 -0
- package/lib/games/getGamePasses.js +39 -0
- package/lib/games/getGameRevenue.js +49 -0
- package/lib/games/getGameSocialLinks.js +45 -0
- package/lib/games/getGroupGames.js +30 -0
- package/lib/games/getPlaceInfo.js +48 -0
- package/lib/games/getUniverseInfo.js +51 -0
- package/lib/games/updateDeveloperProduct.js +69 -0
- package/lib/groups/changeRank.js +59 -0
- package/lib/groups/deleteWallPost.js +64 -0
- package/lib/groups/deleteWallPostsByUser.js +59 -0
- package/lib/groups/demote.js +25 -0
- package/lib/groups/exile.js +59 -0
- package/lib/groups/getAuditLog.js +67 -0
- package/lib/groups/getGroup.js +57 -0
- package/lib/groups/getGroupSocialLinks.js +44 -0
- package/lib/groups/getGroups.js +88 -0
- package/lib/groups/getJoinRequest.js +52 -0
- package/lib/groups/getJoinRequests.js +58 -0
- package/lib/groups/getPlayers.js +108 -0
- package/lib/groups/getRankInGroup.js +52 -0
- package/lib/groups/getRankNameInGroup.js +52 -0
- package/lib/groups/getRole.js +64 -0
- package/lib/groups/getRolePermissions.js +51 -0
- package/lib/groups/getRoles.js +56 -0
- package/lib/groups/getShout.js +49 -0
- package/lib/groups/getWall.js +59 -0
- package/lib/groups/groupPayout.js +103 -0
- package/lib/groups/handleJoinRequest.js +60 -0
- package/lib/groups/leaveGroup.js +60 -0
- package/lib/groups/onAuditLog.js +62 -0
- package/lib/groups/onJoinRequest.js +63 -0
- package/lib/groups/onJoinRequestHandle.js +105 -0
- package/lib/groups/onShout.js +57 -0
- package/lib/groups/onWallPost.js +58 -0
- package/lib/groups/promote.js +25 -0
- package/lib/groups/searchGroups.js +32 -0
- package/lib/groups/setGroupDescription.js +65 -0
- package/lib/groups/setGroupName.js +66 -0
- package/lib/groups/setRank.js +79 -0
- package/lib/groups/shout.js +65 -0
- package/lib/index.js +30 -0
- package/lib/internal/levelOneCopy.js +16 -0
- package/lib/internal/queue.js +61 -0
- package/lib/internal/timeout.js +30 -0
- package/lib/internal/wrap.js +78 -0
- package/lib/inventory/getCollectibles.js +31 -0
- package/lib/inventory/getInventory.js +32 -0
- package/lib/inventory/getInventoryById.js +31 -0
- package/lib/inventory/getOwnership.js +54 -0
- package/lib/inventory/getUAIDs.js +47 -0
- package/lib/itemconfiguration/getGroupAssets.js +32 -0
- package/lib/options.js +26 -0
- package/lib/party/onPartyDeleted.js +53 -0
- package/lib/party/onPartyInvite.js +53 -0
- package/lib/party/onPartyJoinedGame.js +53 -0
- package/lib/party/onPartyLeftGame.js +53 -0
- package/lib/party/onPartySelfJoined.js +53 -0
- package/lib/party/onPartySelfLeft.js +53 -0
- package/lib/party/onPartyUserJoined.js +53 -0
- package/lib/party/onPartyUserLeft.js +53 -0
- package/lib/premiumfeatures/getPremium.js +51 -0
- package/lib/presence/getPresences.js +63 -0
- package/lib/privatemessages/getMessages.js +60 -0
- package/lib/privatemessages/message.js +80 -0
- package/lib/privatemessages/onMessage.js +88 -0
- package/lib/thumbnails/getLogo.js +60 -0
- package/lib/thumbnails/getPlayerThumbnail.js +121 -0
- package/lib/thumbnails/getThumbnails.js +93 -0
- package/lib/trades/acceptTrade.js +58 -0
- package/lib/trades/canTradeWith.js +48 -0
- package/lib/trades/counterTrade.js +84 -0
- package/lib/trades/declineTrade.js +58 -0
- package/lib/trades/getTradeInfo.js +52 -0
- package/lib/trades/getTrades.js +37 -0
- package/lib/trades/sendTrade.js +82 -0
- package/lib/users/getBlurb.js +36 -0
- package/lib/users/getIdFromUsername.js +53 -0
- package/lib/users/getPlayerInfo.js +100 -0
- package/lib/users/getUsernameFromId.js +44 -0
- package/lib/users/onBlurbChange.js +46 -0
- package/lib/util/clearSession.js +32 -0
- package/lib/util/generalRequest.js +61 -0
- package/lib/util/getAction.js +45 -0
- package/lib/util/getCurrentUser.js +44 -0
- package/lib/util/getGeneralToken.js +52 -0
- package/lib/util/getHash.js +29 -0
- package/lib/util/getInputs.js +37 -0
- package/lib/util/getPageResults.js +89 -0
- package/lib/util/getSenderUserId.js +30 -0
- package/lib/util/getSession.js +38 -0
- package/lib/util/getVerification.js +60 -0
- package/lib/util/getVerificationInputs.js +31 -0
- package/lib/util/http.js +110 -0
- package/lib/util/jar.js +24 -0
- package/lib/util/refreshCookie.js +52 -0
- package/lib/util/relog.js +81 -0
- package/lib/util/setOptions.js +54 -0
- package/lib/util/shortPoll.js +102 -0
- package/lib/util/threaded.js +80 -0
- package/package.json +94 -0
- package/postinstall.js +1 -0
- package/settings.json +107 -0
- package/test/accountinformation.test.js +27 -0
- package/test/accountsettings.test.js +27 -0
- package/test/asset.test.js +81 -0
- package/test/assets/Great-White-Shark-Fin.rbxm +0 -0
- package/test/assets/KeyframeSequence.rbxm +0 -0
- package/test/avatar.test.js +164 -0
- package/test/badges.test.js +96 -0
- package/test/chat.test.js +104 -0
- package/test/datastore.test.js +105 -0
- package/test/develop.test.js +53 -0
- package/test/economy.test.js +137 -0
- package/test/friends.test.js +128 -0
- package/test/games.test.js +212 -0
- package/test/groups.test.js +311 -0
- package/test/inventory.test.js +98 -0
- package/test/itemconfiguration.test.js +24 -0
- package/test/premiumfeatures.test.js +17 -0
- package/test/presence.test.js +25 -0
- package/test/privatemessages.test.js +33 -0
- package/test/thumbnails.test.js +53 -0
- package/test/users.test.js +68 -0
- package/tutorials/Authentication.md +75 -0
- package/tutorials/Event Emitters.md +26 -0
- package/tutorials/Promises.md +86 -0
- package/tutorials/VPS Authentication.md +72 -0
- package/typings/index.d.ts +2525 -0
- package/typings/jsDocs.ts +1927 -0
@@ -0,0 +1,65 @@
|
|
1
|
+
const http = require('../util/http.js').func
|
2
|
+
const getGeneralToken = require('../util/getGeneralToken.js').func
|
3
|
+
const checkProductName = require('./checkDeveloperProductName.js').func
|
4
|
+
|
5
|
+
exports.required = ['universeId', 'name', 'priceInRobux']
|
6
|
+
exports.optional = ['description', 'jar']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* 🔐 Create a developer product.
|
11
|
+
* @category Game
|
12
|
+
* @alias addDeveloperProduct
|
13
|
+
* @param {number} universeId - The id of the universe.
|
14
|
+
* @param {string} name - The name of the developer product.
|
15
|
+
* @param {number} priceInRobux - The price of the product.
|
16
|
+
* @param {string=} description - The description of the developer product.
|
17
|
+
* @returns {Promise<DeveloperProductAddResult>}
|
18
|
+
* @example const noblox = require("noblox.js")
|
19
|
+
* // Login using your cookie
|
20
|
+
* noblox.addDeveloperProduct(1, "A Developer Product", 100, "A cool item.")
|
21
|
+
**/
|
22
|
+
|
23
|
+
const nextFunction = (jar, token, universeId, name, priceInRobux, description) => {
|
24
|
+
return checkProductName({
|
25
|
+
universeId,
|
26
|
+
productName: name
|
27
|
+
}).then((res) => {
|
28
|
+
if (res.Success && res.Message === 'Name available') {
|
29
|
+
return http({
|
30
|
+
url: `//apis.roblox.com/developer-products/v1/universes/${universeId}/developerproducts?name=${name}&description=${description}&priceInRobux=${priceInRobux}`,
|
31
|
+
options: {
|
32
|
+
method: 'POST',
|
33
|
+
jar: jar,
|
34
|
+
headers: {
|
35
|
+
'X-CSRF-TOKEN': token
|
36
|
+
},
|
37
|
+
resolveWithFullResponse: true
|
38
|
+
}
|
39
|
+
}).then((res) => {
|
40
|
+
console.log(res)
|
41
|
+
if (res.statusCode === 200) {
|
42
|
+
return {
|
43
|
+
universeId,
|
44
|
+
name,
|
45
|
+
priceInRobux,
|
46
|
+
description,
|
47
|
+
productId: typeof res.body === 'object' ? res.body.id : JSON.parse(res.body).id
|
48
|
+
}
|
49
|
+
} else {
|
50
|
+
throw new Error(`Create product failed, ${res.statusCode} ${res.statusMessage}`)
|
51
|
+
}
|
52
|
+
})
|
53
|
+
} else {
|
54
|
+
throw new Error('Product with this name already exists')
|
55
|
+
}
|
56
|
+
})
|
57
|
+
}
|
58
|
+
|
59
|
+
exports.func = (args) => {
|
60
|
+
const jar = args.jar
|
61
|
+
|
62
|
+
return getGeneralToken({ jar: jar }).then((xcsrf) => {
|
63
|
+
return nextFunction(jar, xcsrf, args.universeId, args.name, args.priceInRobux, args.description)
|
64
|
+
})
|
65
|
+
}
|
@@ -0,0 +1,39 @@
|
|
1
|
+
const http = require('../util/http.js').func
|
2
|
+
|
3
|
+
exports.required = ['universeId', 'productName']
|
4
|
+
exports.optional = ['jar', 'productId']
|
5
|
+
|
6
|
+
// Docs
|
7
|
+
/**
|
8
|
+
* 🔐 Check if a provided name is in use by another developer product.
|
9
|
+
* @category Game
|
10
|
+
* @alias checkDeveloperProductName
|
11
|
+
* @param {number} universeId - The id of the universe.
|
12
|
+
* @param {string} productName - The name of the developer product.
|
13
|
+
* @param {number=} productId - The id of the developer product.
|
14
|
+
* @returns {Promise<CheckDeveloperProductNameResult>}
|
15
|
+
* @example const noblox = require("noblox.js")
|
16
|
+
* // Login using your cookie
|
17
|
+
* const productInfo = await noblox.checkDeveloperProductName(1, "A Developer Product")
|
18
|
+
**/
|
19
|
+
|
20
|
+
exports.func = (args) => {
|
21
|
+
const jar = args.jar
|
22
|
+
const universeId = parseInt(args.universeId) ? parseInt(args.universeId) : 0
|
23
|
+
const productId = parseInt(args.productId) ? parseInt(args.productId) : 0
|
24
|
+
|
25
|
+
return http({
|
26
|
+
url: '//www.roblox.com/places/check-developerproduct-name?universeId=' + universeId + '&developerProductId=' + productId + '&developerProductName=' + args.productName + '&_=1515792139751',
|
27
|
+
options: {
|
28
|
+
method: 'GET',
|
29
|
+
jar: jar,
|
30
|
+
resolveWithFullResponse: true
|
31
|
+
}
|
32
|
+
}).then((res) => {
|
33
|
+
if (res.statusCode !== 200) {
|
34
|
+
throw new Error('You are not logged in')
|
35
|
+
} else {
|
36
|
+
return JSON.parse(res.body)
|
37
|
+
}
|
38
|
+
})
|
39
|
+
}
|
@@ -0,0 +1,146 @@
|
|
1
|
+
// Includes
|
2
|
+
const http = require('../util/http').func
|
3
|
+
const getGeneralToken = require('../util/getGeneralToken').func
|
4
|
+
|
5
|
+
// Args
|
6
|
+
exports.required = ['gamePassId', 'name']
|
7
|
+
exports.optional = ['description', 'price', 'icon', 'jar']
|
8
|
+
|
9
|
+
// Docs
|
10
|
+
/**
|
11
|
+
* 🔐 Modifies an existing game pass.
|
12
|
+
* @category Game
|
13
|
+
* @alias configureGamePass
|
14
|
+
* @param {number} gamePassId - The id of the game pass.
|
15
|
+
* @param {string} name - The name of the game pass; skips name, description, and icon if set to "".
|
16
|
+
* @param {string=} description - The description of the game pass; description is updated when name is modified.
|
17
|
+
* @param {number|boolean=} price - The price of the game pass in Robux; sets to 'Off Sale' if 0, false, or a negative value; skips if true.
|
18
|
+
* @param {ReadStream=} icon - The read stream for the game pass icon being uploaded; .png, .jpg, .gif
|
19
|
+
* @returns {Promise<GamePassResponse>}
|
20
|
+
* @example const noblox = require("noblox.js")
|
21
|
+
* const fs = require("fs")
|
22
|
+
* // Login using your cookie
|
23
|
+
* noblox.configureGamePass(12345678, "Game Pass Title", "Game Pass Description", 1234, fs.createReadStream("./Image.png"))
|
24
|
+
**/
|
25
|
+
|
26
|
+
// Define
|
27
|
+
function configureGamePass (gamePassId, name, description, price, icon, jar, token) {
|
28
|
+
return new Promise((resolve, reject) => {
|
29
|
+
const file = icon && {
|
30
|
+
value: icon,
|
31
|
+
options: {
|
32
|
+
filename: 'icon.png',
|
33
|
+
contentType: 'image/png'
|
34
|
+
}
|
35
|
+
}
|
36
|
+
|
37
|
+
const httpOpt = {
|
38
|
+
url: '//www.roblox.com/game-pass/update',
|
39
|
+
options: {
|
40
|
+
method: 'POST',
|
41
|
+
jar: jar,
|
42
|
+
headers: {
|
43
|
+
'X-CSRF-TOKEN': token,
|
44
|
+
'Content-Type': 'multipart/form-data; boundary=----WebKitFormBoundaryKMFaNaAn4j7XeMO'
|
45
|
+
},
|
46
|
+
resolveWithFullResponse: true,
|
47
|
+
formData: {
|
48
|
+
id: gamePassId,
|
49
|
+
name,
|
50
|
+
description,
|
51
|
+
file
|
52
|
+
}
|
53
|
+
}
|
54
|
+
}
|
55
|
+
|
56
|
+
// Skip updating name and description if name is empty.
|
57
|
+
if (!name) {
|
58
|
+
resolve({
|
59
|
+
gamePassId,
|
60
|
+
...price
|
61
|
+
})
|
62
|
+
}
|
63
|
+
|
64
|
+
return http(httpOpt).then(function (res) {
|
65
|
+
const json = JSON.parse(res.body)
|
66
|
+
if (json.isValid) {
|
67
|
+
resolve({
|
68
|
+
gamePassId,
|
69
|
+
name,
|
70
|
+
description: description || '',
|
71
|
+
...price,
|
72
|
+
iconChanged: !!file // Boolean Cast
|
73
|
+
})
|
74
|
+
} else {
|
75
|
+
const priceComment = (typeof (price) === 'number') ? ` | NOTE: Price has successfully been changed to ${price}R.` : ''
|
76
|
+
if (res.statusCode === 403) {
|
77
|
+
reject(new Error(`You do not have permission to edit this game pass.${priceComment}`))
|
78
|
+
} else if (json.error) {
|
79
|
+
reject(new Error(json.error + priceComment)) // 'The name or description contains inappropriate text.' or 'Text filtering service is unavailable at this time.'
|
80
|
+
} else {
|
81
|
+
reject(new Error(`An unexpected error occurred with status code ${res.statusCode}.${priceComment}`))
|
82
|
+
}
|
83
|
+
}
|
84
|
+
}).catch(error => reject(error))
|
85
|
+
})
|
86
|
+
}
|
87
|
+
|
88
|
+
// Configuring the name/description and Robux must be done in separate calls, albeit to the same end-point.
|
89
|
+
function configureRobux (args, token) {
|
90
|
+
const httpOpt = {
|
91
|
+
url: '//www.roblox.com/game-pass/update',
|
92
|
+
options: {
|
93
|
+
method: 'POST',
|
94
|
+
jar: args.jar,
|
95
|
+
headers: {
|
96
|
+
'X-CSRF-TOKEN': token
|
97
|
+
},
|
98
|
+
resolveWithFullResponse: true,
|
99
|
+
json: {
|
100
|
+
id: args.gamePassId,
|
101
|
+
price: Math.floor(args.price || 0), // Prevent Decimals
|
102
|
+
isForSale: !!Math.max(args.price, 0) // Boolean Cast
|
103
|
+
}
|
104
|
+
}
|
105
|
+
}
|
106
|
+
return http(httpOpt).then(function (res) {
|
107
|
+
if (res.body.isValid) {
|
108
|
+
// Passing price as an object, so they can be omitted if configureRobux is not run.
|
109
|
+
return configureGamePass(
|
110
|
+
args.gamePassId,
|
111
|
+
args.name,
|
112
|
+
args.description,
|
113
|
+
{
|
114
|
+
price: Math.max(Math.floor(args.price || 0), 0),
|
115
|
+
isForSale: !!Math.max(args.price, 0)
|
116
|
+
},
|
117
|
+
args.icon,
|
118
|
+
args.jar,
|
119
|
+
token
|
120
|
+
)
|
121
|
+
} else {
|
122
|
+
if (res.statusCode === 403) {
|
123
|
+
throw new Error('You do not have permission to edit this game pass.')
|
124
|
+
} else if (res.body.error) {
|
125
|
+
throw new Error(res.body.error)
|
126
|
+
} else {
|
127
|
+
throw new Error(`An unexpected error occurred with status code ${res.statusCode}.`)
|
128
|
+
}
|
129
|
+
}
|
130
|
+
})
|
131
|
+
}
|
132
|
+
|
133
|
+
exports.func = function (args) {
|
134
|
+
const jar = args.jar
|
135
|
+
|
136
|
+
return getGeneralToken({
|
137
|
+
jar
|
138
|
+
}).then(function (token) {
|
139
|
+
// Needs to catch falsy input of `false` and `0` as they should change the gamepass to offsale; price updating will be skipped if undefined.
|
140
|
+
if (typeof (args.price) === 'boolean' || typeof (args.price) === 'number') {
|
141
|
+
return configureRobux(args, token)
|
142
|
+
} else {
|
143
|
+
return configureGamePass(args.gamePassId, args.name, args.description, undefined, args.icon, jar, token)
|
144
|
+
}
|
145
|
+
})
|
146
|
+
}
|
@@ -0,0 +1,51 @@
|
|
1
|
+
// Includes
|
2
|
+
const http = require('../util/http.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['placeId']
|
6
|
+
exports.optional = ['page', 'jar']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* 🔐 Returns the existing developer products in a specified game.
|
11
|
+
* @category Game
|
12
|
+
* @alias getDeveloperProducts
|
13
|
+
* @param {number} placeId - The ID of the place whose developer products you want to retrieve
|
14
|
+
* @param {number} [page=1] - Which page of developer products to return (pageSize is 50)
|
15
|
+
* @returns {Promise<DeveloperProductsResult>}
|
16
|
+
*/
|
17
|
+
|
18
|
+
function getDeveloperProducts (jar, placeId, page) {
|
19
|
+
return new Promise((resolve, reject) => {
|
20
|
+
const httpOpt = {
|
21
|
+
url: `//api.roblox.com/developerproducts/list?placeid=${placeId}&page=${page}`,
|
22
|
+
options: {
|
23
|
+
method: 'GET',
|
24
|
+
jar: jar,
|
25
|
+
resolveWithFullResponse: true
|
26
|
+
}
|
27
|
+
}
|
28
|
+
return http(httpOpt)
|
29
|
+
.then(function (res) {
|
30
|
+
if (res.statusCode === 200) {
|
31
|
+
resolve(JSON.parse(res.body))
|
32
|
+
} else {
|
33
|
+
const body = res.body || {}
|
34
|
+
if (body.errors && body.errors.length > 0) {
|
35
|
+
const errors = body.errors.map((e) => {
|
36
|
+
return e.message
|
37
|
+
})
|
38
|
+
reject(new Error(`${res.statusCode} ${errors.join(', ')}`))
|
39
|
+
} else {
|
40
|
+
reject(new Error(`${res.statusCode} An error has occurred ${res.body ? res.body : ''}`))
|
41
|
+
}
|
42
|
+
}
|
43
|
+
})
|
44
|
+
.catch(error => reject(error))
|
45
|
+
})
|
46
|
+
}
|
47
|
+
|
48
|
+
// Define
|
49
|
+
exports.func = function (args) {
|
50
|
+
return getDeveloperProducts(args.jar, args.placeId, args.page || 1)
|
51
|
+
}
|
@@ -0,0 +1,31 @@
|
|
1
|
+
// Includes
|
2
|
+
const getPageResults = require('../util/getPageResults.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['placeId']
|
6
|
+
exports.optional = ['serverType', 'sortOrder', 'limit', 'jar']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* 🔓 Get the servers in a game.
|
11
|
+
* @category Game
|
12
|
+
* @alias getGameInstances
|
13
|
+
* @param {number} placeId - The id of the place.
|
14
|
+
* @param {("Public" | "Friend" | "VIP")=} [serverType=Public] - The type of server to get
|
15
|
+
* @param {SortOrder=} [sortOrder=Asc] - The order that the servers will be sorted by (Asc or Desc)
|
16
|
+
* @param {number=} [limit=∞] - The maximum number of results.
|
17
|
+
* @returns {Promise<GameInstance[]>}
|
18
|
+
* @example const noblox = require("noblox.js")
|
19
|
+
* // Login using your cookie
|
20
|
+
* const servers = await noblox.getGameInstances(1)
|
21
|
+
**/
|
22
|
+
|
23
|
+
// Define
|
24
|
+
exports.func = function (args) {
|
25
|
+
return getPageResults({
|
26
|
+
jar: args.jar,
|
27
|
+
url: `//games.roblox.com/v1/games/${args.placeId}/servers/${args.serverType || 'Public'}`,
|
28
|
+
sortOrder: args.sortOrder,
|
29
|
+
limit: args.limit
|
30
|
+
})
|
31
|
+
}
|
@@ -0,0 +1,39 @@
|
|
1
|
+
// Includes
|
2
|
+
const getPageResults = require('../util/getPageResults.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['universeId']
|
6
|
+
exports.optional = ['limit']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* ✅ Gets a game's game passes.
|
11
|
+
* @category Game
|
12
|
+
* @alias getGamePasses
|
13
|
+
* @param {number} universeId - The id of the universe.
|
14
|
+
* @param {Limit=} limit - The max number of game passes to return.
|
15
|
+
* @returns {Promise<GamePassData[]>}
|
16
|
+
* @example const noblox = require("noblox.js")
|
17
|
+
* const gamePasses = await noblox.getGamePasses(1686885941)
|
18
|
+
**/
|
19
|
+
|
20
|
+
// Define
|
21
|
+
const getGamePasses = async (universeId, limit) => {
|
22
|
+
return getPageResults({
|
23
|
+
url: `//games.roblox.com/v1/games/${universeId}/game-passes`,
|
24
|
+
limit
|
25
|
+
}).catch(err => {
|
26
|
+
if (err.message === '404 The requested universe does not exist.') {
|
27
|
+
err.message += '\n\nYou are possibly providing a placeId instead of a universeId.\nUse getPlaceInfo() to retrieve the universeId: https://noblox.js.org/global.html#getPlaceInfo\n'
|
28
|
+
throw err
|
29
|
+
}
|
30
|
+
throw err
|
31
|
+
})
|
32
|
+
}
|
33
|
+
|
34
|
+
exports.func = function ({ universeId, limit }) {
|
35
|
+
if (isNaN(universeId)) {
|
36
|
+
throw new Error('The provided universe ID is not a number.')
|
37
|
+
}
|
38
|
+
return getGamePasses(universeId, limit)
|
39
|
+
}
|
@@ -0,0 +1,49 @@
|
|
1
|
+
const http = require('../util/http.js').func
|
2
|
+
const getGeneralToken = require('../util/getGeneralToken.js').func
|
3
|
+
|
4
|
+
exports.required = ['placeId', 'type', 'granularity']
|
5
|
+
exports.optional = ['jar']
|
6
|
+
|
7
|
+
/**
|
8
|
+
* 🔐 Get the Game Revenue data.
|
9
|
+
* @category Game
|
10
|
+
* @alias getGameRevenue
|
11
|
+
* @param {number} placeId - The id of the game.
|
12
|
+
* @param {"Revenue" | "RevenuePerVisit" | "AverageVisitLength" | "Visits"} type - The type of revenue. Options: Revenue, RevenuePerVisit, AverageVisitLength, Visits
|
13
|
+
* @param {"Hourly" | "Daily" | "Monthly"} granularity - The type of revenue. Options: Hourly, Daily, Monthly
|
14
|
+
* @returns {Promise<GameRevenueResponse>}
|
15
|
+
* @example const noblox = require("noblox.js")
|
16
|
+
* const gameRevenue = await noblox.getGameRevenue(936068308, "Revenue", "Hourly");
|
17
|
+
**/
|
18
|
+
|
19
|
+
function getGameRevenue (placeId, type, granularity, jar, token) {
|
20
|
+
return new Promise((resolve, reject) => {
|
21
|
+
const httpOpt = {
|
22
|
+
url: `//develop.roblox.com/v1/places/${placeId}/stats/${type}?granularity=${granularity}`,
|
23
|
+
options: {
|
24
|
+
method: 'GET',
|
25
|
+
jar: jar,
|
26
|
+
headers: {
|
27
|
+
'X-CSRF-TOKEN': token
|
28
|
+
},
|
29
|
+
resolveWithFullResponse: true
|
30
|
+
}
|
31
|
+
}
|
32
|
+
return http(httpOpt)
|
33
|
+
.then(function (res) {
|
34
|
+
if (res.statusCode === 200) resolve(JSON.parse(res.body))
|
35
|
+
else if (res.statusCode === 401) reject(new Error('You are not logged in.'))
|
36
|
+
else if (res.statusCode === 403) reject(new Error('You do not have permission to view this game.'))
|
37
|
+
else reject(new Error('An unknown error occurred.'))
|
38
|
+
})
|
39
|
+
.catch(function (err) { console.error(err); reject(err) })
|
40
|
+
})
|
41
|
+
}
|
42
|
+
|
43
|
+
exports.func = function (args) {
|
44
|
+
const jar = args.jar
|
45
|
+
return getGeneralToken({ jar: jar })
|
46
|
+
.then(function (xcsrf) {
|
47
|
+
return getGameRevenue(args.placeId, args.type, args.granularity, jar, xcsrf)
|
48
|
+
})
|
49
|
+
}
|
@@ -0,0 +1,45 @@
|
|
1
|
+
// Includes
|
2
|
+
const http = require('../util/http.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['universeId']
|
6
|
+
exports.optional = ['jar']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* 🔐 Get the social link data associated with a game.
|
11
|
+
* @category Game
|
12
|
+
* @alias getGameSocialLinks
|
13
|
+
* @param {number} universeId - The universe id of the game.
|
14
|
+
* @returns {Promise<SocialLinkResponse[]>}
|
15
|
+
* @see [getPlaceInfo()](global.html#getPlaceInfo) - can be used to convert a placeId to a universeId
|
16
|
+
* @example const noblox = require("noblox.js")
|
17
|
+
* const gameSocialLinks = await noblox.getGameSocialLinks(2615802125)
|
18
|
+
**/
|
19
|
+
|
20
|
+
// Define
|
21
|
+
function getGameSocialLinks (universeId, jar) {
|
22
|
+
return http({
|
23
|
+
url: `//games.roblox.com/v1/games/${universeId}/social-links/list`,
|
24
|
+
options: {
|
25
|
+
jar: jar,
|
26
|
+
resolveWithFullResponse: true
|
27
|
+
}
|
28
|
+
})
|
29
|
+
.then(({ statusCode, body }) => {
|
30
|
+
const { errors, data } = JSON.parse(body)
|
31
|
+
if (statusCode === 200 && data) {
|
32
|
+
return data
|
33
|
+
} else if (statusCode === 400 || statusCode === 403 || statusCode === 404) {
|
34
|
+
throw new Error(`${errors[0].message} | universeId: ${universeId}`)
|
35
|
+
} else if (statusCode === 401) {
|
36
|
+
throw new Error(`${errors[0].message} (Are you logged in?) | universeId: ${universeId}`)
|
37
|
+
} else {
|
38
|
+
throw new Error(`An unknown error occurred with getGameSocialLinks() | [${statusCode}] universeId: ${universeId}`)
|
39
|
+
}
|
40
|
+
})
|
41
|
+
}
|
42
|
+
|
43
|
+
exports.func = function ({ universeId, jar }) {
|
44
|
+
return getGameSocialLinks(universeId, jar)
|
45
|
+
}
|
@@ -0,0 +1,30 @@
|
|
1
|
+
// Includes
|
2
|
+
const getPageResults = require('../util/getPageResults.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['groupId']
|
6
|
+
exports.optional = ['accessFilter', 'sortOrder', 'limit']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* ✅ Get a group's games.
|
11
|
+
* @category Group
|
12
|
+
* @alias getGroupGames
|
13
|
+
* @param {number} groupId - The id of the group.
|
14
|
+
* @param {("All" | "Public" | "Private")=} [accessFilter=All] - Filtering games via access level.
|
15
|
+
* @param {SortOrder=} [sortOrder=Asc] - The order results are sorted in.
|
16
|
+
* @param {Limit=} [limit=∞] - The maximum number of games to return
|
17
|
+
* @returns {Promise<GroupGameInfo[]>}
|
18
|
+
* @example const noblox = require("noblox.js")
|
19
|
+
* const groupGames = await noblox.getGroupGames({groupId: 1, accessFilter: 'All', sortOrder: 'Asc', limit: '100'})
|
20
|
+
**/
|
21
|
+
|
22
|
+
// Define
|
23
|
+
exports.func = function (args) {
|
24
|
+
return getPageResults({
|
25
|
+
url: `//games.roblox.com/v2/groups/${args.groupId}/games`,
|
26
|
+
query: { accessFilter: args.accessFilter || 'All' },
|
27
|
+
sortOrder: args.sortOrder || 'Asc',
|
28
|
+
limit: args.limit
|
29
|
+
})
|
30
|
+
}
|
@@ -0,0 +1,48 @@
|
|
1
|
+
// Includes
|
2
|
+
const http = require('../util/http.js').func
|
3
|
+
|
4
|
+
// Args
|
5
|
+
exports.required = ['placeId']
|
6
|
+
exports.optional = ['jar']
|
7
|
+
|
8
|
+
// Docs
|
9
|
+
/**
|
10
|
+
* 🔓 Get the info for a universe.
|
11
|
+
* @category Game
|
12
|
+
* @alias getPlaceInfo
|
13
|
+
* @param {number | Array<number>} universeId - The id(s) of the place(s).
|
14
|
+
* @returns {Promise<PlaceInformation[]>}
|
15
|
+
* @example const noblox = require("noblox.js")
|
16
|
+
* const universeInfo = await noblox.getPlaceInfo([ 10905034443 ])
|
17
|
+
**/
|
18
|
+
|
19
|
+
function getPlaceInfo (placeIds, jar) {
|
20
|
+
return new Promise((resolve, reject) => {
|
21
|
+
if (typeof (placeIds) === 'number') placeIds = [placeIds]
|
22
|
+
|
23
|
+
const httpOpt = {
|
24
|
+
url: `//games.roblox.com/v1/games/multiget-place-details?placeIds=${placeIds.join(',')}`,
|
25
|
+
options: {
|
26
|
+
json: true,
|
27
|
+
resolveWithFullResponse: true,
|
28
|
+
jar: jar,
|
29
|
+
method: 'GET'
|
30
|
+
}
|
31
|
+
}
|
32
|
+
|
33
|
+
return http(httpOpt)
|
34
|
+
.then(function ({ statusCode, body }) {
|
35
|
+
if (statusCode === 200) {
|
36
|
+
resolve(body)
|
37
|
+
} else if (body && body.errors) {
|
38
|
+
reject(new Error(`[${statusCode}] ${body.errors[0].message} | placeIds: ${placeIds.join(',')} ${body.errors.field ? ` | ${body.errors.field} is incorrect` : ''}`))
|
39
|
+
} else {
|
40
|
+
reject(new Error(`An unknown error occurred with getPlaceInfo() | [${statusCode}] placeIds: ${placeIds.join(',')}`))
|
41
|
+
}
|
42
|
+
}).catch(reject)
|
43
|
+
})
|
44
|
+
}
|
45
|
+
|
46
|
+
exports.func = function (args) {
|
47
|
+
return getPlaceInfo(args.placeId, args.jar)
|
48
|
+
}
|
@@ -0,0 +1,51 @@
|
|
1
|
+
const http = require('../util/http.js').func
|
2
|
+
|
3
|
+
exports.required = ['universeId']
|
4
|
+
exports.optional = ['jar']
|
5
|
+
|
6
|
+
// Docs
|
7
|
+
/**
|
8
|
+
* 🔓 Get the info for a universe.
|
9
|
+
* @category Game
|
10
|
+
* @alias getUniverseInfo
|
11
|
+
* @param {number | Array<number>} universeId - The id(s) of the universe(s).
|
12
|
+
* @returns {Promise<UniverseInformation[]>}
|
13
|
+
* @example const noblox = require("noblox.js")
|
14
|
+
* const universeInfo = await noblox.getUniverseInfo([ 2152417643 ])
|
15
|
+
**/
|
16
|
+
|
17
|
+
function getUniverseInfo (universeIds, jar) {
|
18
|
+
return new Promise((resolve, reject) => {
|
19
|
+
if (typeof (universeIds) === 'number') universeIds = [universeIds]
|
20
|
+
|
21
|
+
const httpOpt = {
|
22
|
+
url: `//games.roblox.com/v1/games?universeIds=${universeIds.join(',')}`,
|
23
|
+
options: {
|
24
|
+
json: true,
|
25
|
+
resolveWithFullResponse: true,
|
26
|
+
jar: jar,
|
27
|
+
method: 'GET'
|
28
|
+
}
|
29
|
+
}
|
30
|
+
|
31
|
+
return http(httpOpt)
|
32
|
+
.then(function ({ statusCode, body }) {
|
33
|
+
if (statusCode === 200) {
|
34
|
+
resolve(body.data.map((universe) => {
|
35
|
+
universe.created = new Date(universe.created)
|
36
|
+
universe.updated = new Date(universe.updated)
|
37
|
+
|
38
|
+
return universe
|
39
|
+
}))
|
40
|
+
} else if (body && body.errors) {
|
41
|
+
reject(new Error(`[${statusCode}] ${body.errors[0].message} | universeIds: ${universeIds.join(',')} ${body.errors.field ? ` | ${body.errors.field} is incorrect` : ''}`))
|
42
|
+
} else {
|
43
|
+
reject(new Error(`An unknown error occurred with getUniverseInfo() | [${statusCode}] universeIds: ${universeIds.join(',')}`))
|
44
|
+
}
|
45
|
+
}).catch(reject)
|
46
|
+
})
|
47
|
+
}
|
48
|
+
|
49
|
+
exports.func = function (args) {
|
50
|
+
return getUniverseInfo(args.universeId, args.jar)
|
51
|
+
}
|
@@ -0,0 +1,69 @@
|
|
1
|
+
const http = require('../util/http.js').func
|
2
|
+
const getGeneralToken = require('../util/getGeneralToken.js').func
|
3
|
+
|
4
|
+
exports.required = ['universeId', 'productId', 'priceInRobux']
|
5
|
+
exports.optional = ['name', 'description', 'iconImageAssetId', 'jar']
|
6
|
+
|
7
|
+
// Docs
|
8
|
+
/**
|
9
|
+
* 🔐 Update a developer product.
|
10
|
+
* @category Game
|
11
|
+
* @alias updateDeveloperProduct
|
12
|
+
* @param {number} universeId - The id of the universe.
|
13
|
+
* @param {number} productId - The id of the product.
|
14
|
+
* @param {number} priceInRobux - The new price of the product.
|
15
|
+
* @param {string=} name - The new name of the product.
|
16
|
+
* @param {string=} description - The new description of the product.
|
17
|
+
* @param {iconImageAssetId=} iconImageAssetId - The new icon image asset ID for the product.
|
18
|
+
* @returns {Promise<void>}
|
19
|
+
* @example const noblox = require("noblox.js")
|
20
|
+
* // Login using your cookie
|
21
|
+
* noblox.updateDeveloperProduct(1, 2, 10, "An Updated Developer Product", "My new updated product.")
|
22
|
+
**/
|
23
|
+
|
24
|
+
function updateDeveloperProduct (universeId, productId, priceInRobux, name, description, iconImageAssetId, jar, token) {
|
25
|
+
return new Promise((resolve, reject) => {
|
26
|
+
return http({
|
27
|
+
url: `//develop.roblox.com/v1/universes/${universeId}/developerproducts/${productId}/update`,
|
28
|
+
options: {
|
29
|
+
method: 'POST',
|
30
|
+
jar: jar,
|
31
|
+
headers: {
|
32
|
+
'X-CSRF-TOKEN': token
|
33
|
+
},
|
34
|
+
json: {
|
35
|
+
Name: name,
|
36
|
+
Description: description,
|
37
|
+
IconImageAssetId: iconImageAssetId,
|
38
|
+
PriceInRobux: priceInRobux
|
39
|
+
},
|
40
|
+
resolveWithFullResponse: true
|
41
|
+
}
|
42
|
+
}).then(({ statusCode, body }) => {
|
43
|
+
if (statusCode === 200) {
|
44
|
+
resolve(body)
|
45
|
+
} else if (body && body.errors) {
|
46
|
+
reject(new Error(`[${statusCode}] ${body.errors[0].message} | universeId: ${universeId}, body: ${JSON.stringify({
|
47
|
+
Name: name,
|
48
|
+
Description: description,
|
49
|
+
IconImageAssetId: iconImageAssetId,
|
50
|
+
PriceInRobux: priceInRobux
|
51
|
+
})}`))
|
52
|
+
} else {
|
53
|
+
reject(new Error(`An unknown error occurred with updateDeveloperProduct() | [${statusCode}] universeId: ${universeId}, body: ${JSON.stringify({
|
54
|
+
Name: name,
|
55
|
+
Description: description,
|
56
|
+
IconImageAssetId: iconImageAssetId,
|
57
|
+
PriceInRobux: priceInRobux
|
58
|
+
})}`))
|
59
|
+
}
|
60
|
+
}).catch(reject)
|
61
|
+
})
|
62
|
+
}
|
63
|
+
|
64
|
+
exports.func = function ({ universeId, productId, priceInRobux, name, description, iconImageAssetId, jar }) {
|
65
|
+
return getGeneralToken({ jar })
|
66
|
+
.then((token) => {
|
67
|
+
return updateDeveloperProduct(universeId, productId, priceInRobux, name, description, iconImageAssetId, jar, token)
|
68
|
+
})
|
69
|
+
}
|