Compare commits

..

20 Commits

Author SHA1 Message Date
Alexander Corn
eb2081c325 2.2.0 2015-06-18 00:57:23 -04:00
Alexander Corn
c60d4942e0 Removed useless timestamp parameter from chatMessage event 2015-06-18 00:41:55 -04:00
Alexander Corn
1aa42b89f7 Added public static CSteamUser.getAvatarURL method 2015-06-18 00:41:26 -04:00
Alexander Corn
e01d05c140 Added PersonaStateFlag enum 2015-06-18 00:36:26 -04:00
Alexander Corn
8ec0ef84c2 Added PersonaState enum 2015-06-18 00:33:34 -04:00
Alexander Corn
0e5929df24 Lowered chat poll interval to 500ms 2015-06-18 00:24:54 -04:00
Alexander Corn
74bf2dcfca Added webchat 2015-06-18 00:22:05 -04:00
Alexander Corn
e8634e17ca 2.1.0 2015-06-09 14:45:34 -04:00
Alexander Corn
2a2947344f Export request 2015-06-09 14:45:07 -04:00
Alexander Corn
e789d07833 2.0.0 2015-05-30 23:53:59 -04:00
Alexander Corn
88059596b3 Use a string for the steamguard value instead of an object 2015-05-30 23:45:46 -04:00
Alexander Corn
399cc5ee84 1.0.8 2015-05-29 01:03:22 -04:00
Alexander Corn
a24bb9d4ad Fixed API key registration not working 2015-05-29 01:03:07 -04:00
Alexander Corn
81eb26b30d 1.0.7 2015-05-25 13:43:38 -04:00
Alexander Corn
0c95e75e39 Added getNotifications method 2015-05-25 13:37:01 -04:00
Alexander Corn
2eaa5b057d Added resetItemNotifications method 2015-05-25 13:20:47 -04:00
Alexander Corn
d5592246cf 1.0.6 2015-05-16 00:44:42 -04:00
Alexander Corn
22ab86434a Fixed repository URL 2015-05-16 00:44:33 -04:00
Alexander Corn
d367ceb2a6 1.0.5 2015-05-11 15:56:57 -04:00
Alexander Corn
5ab5a6d401 Made callback optional for parentalUnlock 2015-05-11 15:56:41 -04:00
5 changed files with 343 additions and 29 deletions

View File

@@ -12,7 +12,7 @@ SteamCommunity.prototype.getSteamGroup = function(id, callback) {
}
var self = this;
this._request("https://steamcommunity.com/" + (typeof id === 'string' ? "groups/" + id : "gid/" + id.toString()) + "/memberslistxml/?xml=1", function(err, response, body) {
this.request("https://steamcommunity.com/" + (typeof id === 'string' ? "groups/" + id : "gid/" + id.toString()) + "/memberslistxml/?xml=1", function(err, response, body) {
if(err || response.statusCode != 200) {
callback(err || "HTTP error " + response.statusCode);
return;
@@ -65,7 +65,7 @@ CSteamGroup.prototype.getMembers = function(callback, members, link) {
link = link || "http://steamcommunity.com/gid/" + this.steamID.toString() + "/memberslistxml/?xml=1";
var self = this;
this._community._request(link, function(err, response, body) {
this._community.request(link, function(err, response, body) {
if(err || response.statusCode != 200) {
callback(err || "HTTP error " + response.statusCode);
return;
@@ -97,7 +97,7 @@ CSteamGroup.prototype.join = function(callback) {
};
var self = this;
this._community._request.post("https://steamcommunity.com/gid/" + this.steamID.toString(), {"form": form}, function(err, response, body) {
this._community.request.post("https://steamcommunity.com/gid/" + this.steamID.toString(), {"form": form}, function(err, response, body) {
if(!callback) {
return;
}
@@ -149,7 +149,7 @@ CSteamGroup.prototype.postAnnouncement = function(headline, content, callback) {
"body": content
};
this._community._request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/announcements", {"form": form}, function(err, response, body) {
this._community.request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/announcements", {"form": form}, function(err, response, body) {
if(!callback) {
return;
}
@@ -208,7 +208,7 @@ CSteamGroup.prototype.scheduleEvent = function(name, type, description, time, se
}
var self = this;
this._community._request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/eventEdit", {"form": form}, function(err, response, body) {
this._community.request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/eventEdit", {"form": form}, function(err, response, body) {
if(!callback) {
return;
}
@@ -235,7 +235,7 @@ CSteamGroup.prototype.setPlayerOfTheWeek = function(steamID, callback) {
};
var self = this;
this._community._request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/potwEdit", {"form": form}, function(err, response, body) {
this._community.request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/potwEdit", {"form": form}, function(err, response, body) {
if(!callback) {
return;
}
@@ -269,7 +269,7 @@ CSteamGroup.prototype.kick = function(steamID, callback) {
};
var self = this;
this._community._request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/membersManage", {"form": form}, function(err, response, body) {
this._community.request.post("https://steamcommunity.com/gid/" + this.steamID.toString() + "/membersManage", {"form": form}, function(err, response, body) {
if(!callback) {
return;
}

View File

@@ -12,7 +12,7 @@ SteamCommunity.prototype.getSteamUser = function(id, callback) {
}
var self = this;
this._request("http://steamcommunity.com/" + (typeof id === 'string' ? "id/" + id : "profiles/" + id.toString()) + "/?xml=1", function(err, response, body) {
this.request("http://steamcommunity.com/" + (typeof id === 'string' ? "id/" + id : "profiles/" + id.toString()) + "/?xml=1", function(err, response, body) {
if(err || response.statusCode != 200) {
callback(err || "HTTP error " + response.statusCode);
return;
@@ -91,11 +91,11 @@ function CSteamUser(community, userData, customurl) {
}
}
CSteamUser.prototype.getAvatarURL = function(size, protocol) {
CSteamUser.getAvatarURL = function(hash, size, protocol) {
size = size || '';
protocol = protocol || 'http://';
var url = protocol + "steamcdn-a.akamaihd.net/steamcommunity/public/images/avatars/" + this.avatarHash.substring(0, 2) + "/" + this.avatarHash;
var url = protocol + "steamcdn-a.akamaihd.net/steamcommunity/public/images/avatars/" + hash.substring(0, 2) + "/" + hash;
if(size == 'full' || size == 'medium') {
return url + "_" + size + ".jpg";
} else {
@@ -103,8 +103,12 @@ CSteamUser.prototype.getAvatarURL = function(size, protocol) {
}
};
CSteamUser.prototype.getAvatarURL = function(size, protocol) {
return CSteamUser.getAvatarURL(this.avatarHash, size, protocol);
};
CSteamUser.prototype.addFriend = function(callback) {
this._community._request.post('https://steamcommunity.com/actions/AddFriendAjax', {"form": {"accept_invite": 0, "sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
this._community.request.post('https://steamcommunity.com/actions/AddFriendAjax', {"form": {"accept_invite": 0, "sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
if(!callback) {
return;
}
@@ -131,7 +135,7 @@ CSteamUser.prototype.addFriend = function(callback) {
};
CSteamUser.prototype.acceptFriendRequest = function(callback) {
this._community._request.post('https://steamcommunity.com/actions/AddFriendAjax', {"form": {"accept_invite": 1, "sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
this._community.request.post('https://steamcommunity.com/actions/AddFriendAjax', {"form": {"accept_invite": 1, "sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
if(!callback) {
return;
}
@@ -146,7 +150,7 @@ CSteamUser.prototype.acceptFriendRequest = function(callback) {
};
CSteamUser.prototype.removeFriend = function(callback) {
this._community._request.post('https://steamcommunity.com/actions/RemoveFriendAjax', {"form": {"sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
this._community.request.post('https://steamcommunity.com/actions/RemoveFriendAjax', {"form": {"sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
if(!callback) {
return;
}
@@ -161,7 +165,7 @@ CSteamUser.prototype.removeFriend = function(callback) {
};
CSteamUser.prototype.blockCommunication = function(callback) {
this._community._request.post('https://steamcommunity.com/actions/BlockUserAjax', {"form": {"sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
this._community.request.post('https://steamcommunity.com/actions/BlockUserAjax', {"form": {"sessionID": this._community.getSessionID(), "steamid": this.steamID.toString()}}, function(err, response, body) {
if(!callback) {
return;
}
@@ -194,7 +198,7 @@ CSteamUser.prototype.unblockCommunication = function(callback) {
};
CSteamUser.prototype.comment = function(message, callback) {
this._community._request.post('https://steamcommunity.com/comment/Profile/post/' + this.steamID.toString() + '/-1/', {"form": {
this._community.request.post('https://steamcommunity.com/comment/Profile/post/' + this.steamID.toString() + '/-1/', {"form": {
"comment": message,
"count": 6,
"sessionid": this._community.getSessionID()

250
components/chat.js Normal file
View File

@@ -0,0 +1,250 @@
var SteamCommunity = require('../index.js');
var SteamID = require('steamid');
SteamCommunity.ChatState = {
"Offline": 0,
"LoggingOn": 1,
"LogOnFailed": 2,
"LoggedOn": 3
};
SteamCommunity.PersonaState = {
"Offline": 0,
"Online": 1,
"Busy": 2,
"Away": 3,
"Snooze": 4,
"LookingToTrade": 5,
"LookingToPlay": 6,
"Max": 7
};
SteamCommunity.PersonaStateFlag = {
"HasRichPresence": 1,
"InJoinableGame": 2,
"OnlineUsingWeb": 256,
"OnlineUsingMobile": 512,
"OnlineUsingBigPicture": 1024
};
SteamCommunity.prototype.chatLogon = function(interval) {
if(this.chatState == SteamCommunity.ChatState.LoggingOn || this.chatState == SteamCommunity.ChatState.LoggedOn) {
return;
}
interval = interval || 500;
this.emit('debug', 'Requesting chat WebAPI token');
this.chatState = SteamCommunity.ChatState.LoggingOn;
var self = this;
this.request("https://steamcommunity.com/chat", function(err, response, body) {
if(err || response.statusCode != 200) {
self.emit('debug', 'Error requesting chat WebAPI token: ' + (err ? err.message : "HTTP error " + response.statusCode));
self.chatState = SteamCommunity.ChatState.LogOnFailed;
setTimeout(self.chatLogon.bind(self), 5000);
return;
}
var match = body.match(/[0-9a-f]{32}/);
if(!match) {
self.emit('debug', 'Couldn\'t find a WebAPI chat token in the response.');
self.chatState = SteamCommunity.ChatState.LogOnFailed;
setTimeout(self.chatLogon.bind(self), 5000);
return;
}
self.request.post({
"uri": "https://api.steampowered.com/ISteamWebUserPresenceOAuth/Logon/v1",
"form": {
"ui_mode": "web",
"access_token": match[0]
},
"json": true
}, function(err, response, body) {
if(err || response.statusCode != 200) {
self.emit('debug', 'Error logging into webchat: ' + (err ? err.message : "HTTP error " + response.statusCode));
self.chatState = SteamCommunity.ChatState.LogOnFailed;
setTimeout(self.chatLogon.bind(self), 5000);
return;
}
if(body.error != 'OK') {
self.emit('debug', 'Error logging into webchat: ' + body.error);
self.chatState = SteamCommunity.ChatState.LogOnFailed;
setTimeout(self.chatLogon.bind(self), 5000);
return;
}
self._chat = {
"umqid": body.umqid,
"message": body.message,
"accessToken": match[0],
"interval": interval
};
self.chatFriends = {};
self.chatState = SteamCommunity.ChatState.LoggedOn;
self.emit('chatLoggedOn');
self._chatPoll();
});
});
};
SteamCommunity.prototype.chatMessage = function(recipient, text, type, callback) {
if(this.chatState != SteamCommunity.ChatState.LoggedOn) {
throw new Error("Chat must be logged on before messages can be sent");
}
if(typeof recipient === 'string') {
recipient = new SteamID(recipient);
}
if(typeof type === 'function') {
callback = type;
type = 'saytext';
}
type = type || 'saytext';
this.request.post({
"uri": "https://api.steampowered.com/ISteamWebUserPresenceOAuth/Message/v1",
"form": {
"access_token": this._chat.accessToken,
"steamid_dst": recipient.toString(),
"text": text,
"type": type,
"umqid": this._chat.umqid
},
"json": true
}, function(err, response, body) {
if(!callback) {
return;
}
if(err || response.statusCode != 200) {
callback(err ? err.message : "HTTP error " + response.statusCode);
} else if(body.error != 'OK') {
callback(body.error);
} else {
callback();
}
});
};
SteamCommunity.prototype.chatLogoff = function() {
var self = this;
this.request.post({
"uri": "https://api.steampowered.com/ISteamWebUserPresenceOAuth/Logoff/v1",
"form": {
"access_token": this._chat.accessToken,
"umqid": this._chat.umqid
}
}, function(err, response, body) {
if(err || response.statusCode != 200) {
self.emit('debug', 'Error logging off of chat: ' + (err ? err.message : "HTTP error " + response.statusCode));
setTimeout(self.chatLogoff.bind(self), 1000);
} else {
self.emit('chatLoggedOff');
clearTimeout(self._chat.timer);
delete self._chat;
delete self.chatFriends;
self.chatState = SteamCommunity.ChatState.Offline;
}
});
};
SteamCommunity.prototype._chatPoll = function() {
this.emit('debug', 'Doing chat poll');
var self = this;
this.request.post({
"uri": "https://api.steampowered.com/ISteamWebUserPresenceOAuth/Poll/v1",
"form": {
"umqid": self._chat.umqid,
"message": self._chat.message,
"pollid": 1,
"sectimeout": 20,
"secidletime": 0,
"use_accountids": 1,
"access_token": self._chat.accessToken
},
"json": true
}, function(err, response, body) {
if(self.chatState == SteamCommunity.ChatState.Offline) {
return;
}
self._chat.timer = setTimeout(self._chatPoll.bind(self), self._chat.interval);
if(err || response.statusCode != 200) {
self.emit('debug', 'Error in chat poll: ' + (err ? err.message : "HTTP error " + response.statusCode));
return;
}
if(body.error != 'OK') {
self.emit('debug', 'Error in chat poll: ' + body.error);
return;
}
self._chat.message = body.messagelast;
(body.messages || []).forEach(function(message) {
var sender = new SteamID();
sender.universe = SteamID.Universe.PUBLIC;
sender.type = SteamID.Type.INDIVIDUAL;
sender.instance = SteamID.Instance.DESKTOP;
sender.accountid = message.accountid_from;
switch(message.type) {
case 'personastate':
self._chatUpdatePersona(sender);
break;
case 'saytext':
self.emit('chatMessage', sender, message.text);
break;
case 'typing':
self.emit('chatTyping', sender);
break;
default:
self.emit('debug', 'Unhandled chat message type: ' + message.type);
}
});
});
};
SteamCommunity.prototype._chatUpdatePersona = function(steamID) {
this.emit('debug', 'Updating persona data for ' + steamID);
var self = this;
this.request({
"uri": "https://steamcommunity.com/chat/friendstate/" + steamID.accountid,
"json": true
}, function(err, response, body) {
if(err || response.statusCode != 200) {
self.emit('debug', 'Chat update persona error: ' + (err ? err.message : "HTTP error " + response.statusCode));
setTimeout(function() {
self._chatUpdatePersona(steamID);
}, 2000);
return;
}
var persona = {
"steamID": steamID,
"personaName": body.m_strName,
"personaState": body.m_ePersonaState,
"personaStateFlags": body.m_nPersonaStateFlags || 0,
"avatarHash": body.m_strAvatarHash,
"inGame": !!body.m_bInGame,
"inGameAppID": body.m_nInGameAppID ? parseInt(body.m_nInGameAppID, 10) : null,
"inGameName": body.m_strInGameName || null
};
self.emit('chatPersonaState', steamID, persona);
self.chatFriends[steamID.getSteamID64()] = persona;
});
};

View File

@@ -3,22 +3,26 @@ var RSA = require('node-bignumber').Key;
var hex2b64 = require('node-bignumber').hex2b64;
var SteamID = require('steamid');
require('util').inherits(SteamCommunity, require('events').EventEmitter);
module.exports = SteamCommunity;
SteamCommunity.SteamID = SteamID;
function SteamCommunity() {
this._jar = Request.jar();
this._request = Request.defaults({"jar": this._jar});
this.request = Request.defaults({"jar": this._jar});
this.chatState = SteamCommunity.ChatState.Offline;
}
SteamCommunity.prototype.login = function(details, callback) {
if(details.steamID && details.sentry) {
this._jar.setCookie(Request.cookie('steamMachineAuth' + details.steamID.getSteamID64() + '=' + encodeURIComponent(details.sentry)), 'https://steamcommunity.com');
if(details.steamguard) {
var parts = details.steamguard.split('||');
this._jar.setCookie(Request.cookie('steamMachineAuth' + parts[0] + '=' + encodeURIComponent(parts[1])), 'https://steamcommunity.com');
}
var self = this;
this._request.post("https://steamcommunity.com/login/getrsakey/", {"form": {"username": details.accountName}}, function(err, response, body) {
this.request.post("https://steamcommunity.com/login/getrsakey/", {"form": {"username": details.accountName}}, function(err, response, body) {
if(err) {
callback(err);
return;
@@ -48,7 +52,7 @@ SteamCommunity.prototype.login = function(details, callback) {
"username": details.accountName
};
self._request.post("https://steamcommunity.com/login/dologin/", {"form": form}, function(err, response, body) {
self.request.post("https://steamcommunity.com/login/dologin/", {"form": form}, function(err, response, body) {
if(err) {
callback(err);
return;
@@ -80,7 +84,7 @@ SteamCommunity.prototype.login = function(details, callback) {
for(var i = 0; i < cookies.length; i++) {
var parts = cookies[i].split('=');
if(parts[0] == 'steamMachineAuth' + self.steamID) {
steamguard = {"steamID": self.steamID, "sentry": decodeURIComponent(parts[1])};
steamguard = self.steamID.toString() + '||' + decodeURIComponent(parts[1]);
break;
}
}
@@ -123,7 +127,7 @@ function generateSessionID() {
SteamCommunity.prototype.getWebApiKey = function(domain, callback) {
var self = this;
this._request("https://steamcommunity.com/dev/apikey", function(err, response, body) {
this.request("https://steamcommunity.com/dev/apikey", function(err, response, body) {
if(err || response.statusCode != 200) {
return callback(err.message || "HTTP error " + response.statusCode);
}
@@ -138,10 +142,12 @@ SteamCommunity.prototype.getWebApiKey = function(domain, callback) {
callback(null, match[1]);
} else {
// We need to register a new API key
self._request.post('https://steamcommunity.com/dev/registerkey', {
self.request.post('https://steamcommunity.com/dev/registerkey', {
"form": {
"domain": domain,
"agreeToTerms": 1
"agreeToTerms": "agreed",
"sessionid": self.getSessionID(),
"Submit": "Register"
}
}, function(err, response, body) {
if(err || response.statusCode >= 400) {
@@ -155,12 +161,16 @@ SteamCommunity.prototype.getWebApiKey = function(domain, callback) {
};
SteamCommunity.prototype.parentalUnlock = function(pin, callback) {
this._request.post("https://steamcommunity.com/parental/ajaxunlock", {
this.request.post("https://steamcommunity.com/parental/ajaxunlock", {
"json": true,
"form": {
"pin": pin
}
}, function(err, response, body) {
if(!callback) {
return;
}
if(err || response.statusCode != 200) {
return callback(err.message || "HTTP error " + response.statusCode);
}
@@ -177,6 +187,55 @@ SteamCommunity.prototype.parentalUnlock = function(pin, callback) {
}.bind(this));
};
SteamCommunity.prototype.getNotifications = function(callback) {
this.request.get("https://steamcommunity.com/actions/RefreshNotificationArea", function(err, response, body) {
if(err || response.statusCode != 200) {
return callback(err.message || "HTTP error " + response.statusCode);
}
var notifications = {
"comments": 0,
"items": 0,
"invites": 0,
"gifts": 0,
"chat": 0,
"trades": 0
};
var items = {
"comments": /(\d+) new comments?/,
"items": /(\d+) new items? in your inventory/,
"invites": /(\d+) new invites?/,
"gifts": /(\d+) new gifts?/,
"chat": /(\d+) unread chat messages?/,
"trades": /(\d+) new trade notifications?/
};
var match;
for(var i in items) {
if(match = body.match(items[i])) {
notifications[i] = parseInt(match[1], 10);
}
}
callback(null, notifications);
});
};
SteamCommunity.prototype.resetItemNotifications = function(callback) {
this.request.get("https://steamcommunity.com/my/inventory", function(err, response, body) {
if(!callback) {
return;
}
if(err || response.statusCode != 200) {
callback(err.message || "HTTP error " + response.statusCode);
} else {
callback();
}
});
};
SteamCommunity.prototype._checkCommunityError = function(html, callback) {
if(html.match(/<h1>Sorry!<\/h1>/)) {
var match = html.match(/<h3>(.+)<\/h3>/);
@@ -189,7 +248,7 @@ SteamCommunity.prototype._checkCommunityError = function(html, callback) {
SteamCommunity.prototype._myProfile = function(endpoint, form, callback) {
var self = this;
this._request("https://steamcommunity.com/my", {"followRedirect": false}, function(err, response, body) {
this.request("https://steamcommunity.com/my", {"followRedirect": false}, function(err, response, body) {
if(err || response.statusCode != 302) {
callback(err || "HTTP error " + response.statusCode);
return;
@@ -201,9 +260,10 @@ SteamCommunity.prototype._myProfile = function(endpoint, form, callback) {
return;
}
(form ? self._request.post : self._request)("https://steamcommunity.com" + match[1] + "/" + endpoint, form ? {"form": form} : {}, callback);
(form ? self.request.post : self.request)("https://steamcommunity.com" + match[1] + "/" + endpoint, form ? {"form": form} : {}, callback);
});
};
require('./classes/CSteamGroup.js');
require('./classes/CSteamUser.js');
require('./components/chat.js');

View File

@@ -1,6 +1,6 @@
{
"name": "steamcommunity",
"version": "1.0.4",
"version": "2.2.0",
"description": "Provides an interface for logging into and interacting with the Steam Community website",
"keywords": ["steam", "steam community"],
"homepage": "https://github.com/DoctorMcKay/node-steamcommunity",
@@ -10,7 +10,7 @@
"license": "MIT",
"repository": {
"type": "git",
"url": "https://github.com/Doctor_McKay/node-steamcommunity.git"
"url": "https://github.com/DoctorMcKay/node-steamcommunity.git"
},
"dependencies": {
"request": "2.51.x",