steam-trade 0.3.0 → 0.3.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- data/LICENSE +674 -674
- data/README.md +621 -621
- data/lib/Confirmation.rb +1 -1
- data/lib/EventCards.rb +89 -1
- data/lib/Guard.rb +7 -3
- data/lib/LoginExecutor.rb +156 -156
- data/lib/Trade.rb +36 -0
- data/lib/blueprints/byappid.json +1 -1
- data/lib/meta/version.rb +1 -1
- data/lib/steam-trade.rb +29 -7
- metadata +3 -4
- data/.gitignore +0 -10
data/README.md
CHANGED
@@ -1,621 +1,621 @@
|
|
1
|
-
# steam-trade V0.3.0
|
2
|
-
|
3
|
-
**PLEASE IF SOMETHING DOES NOT WORK PROPERLY MAKE A GITHUB ISSUE**
|
4
|
-
|
5
|
-
Please check constantly for updates cause i'm still making this gem.
|
6
|
-
|
7
|
-
This gem simplifes/allows sending steam trade offers programmatically.
|
8
|
-
|
9
|
-
this gem is primarly for trading cards, tho can be used to CS:GO and other games inventories
|
10
|
-
|
11
|
-
# Changelog
|
12
|
-
```
|
13
|
-
0.3.0:
|
14
|
-
- hotfix for cookie login
|
15
|
-
|
16
|
-
0.2.9:
|
17
|
-
- hotfix for cookie login (remember me)
|
18
|
-
|
19
|
-
0.2.8:
|
20
|
-
- fixed cookie login
|
21
|
-
|
22
|
-
0.2.7:
|
23
|
-
- added salien_card() to collect steam Salien game Trading Cards
|
24
|
-
|
25
|
-
0.2.6:
|
26
|
-
- hotfix
|
27
|
-
|
28
|
-
0.2.5:
|
29
|
-
- added finish_queue() to collect Steam Sale Trading Cards
|
30
|
-
- hotfix
|
31
|
-
|
32
|
-
0.2.4:
|
33
|
-
- hotfix
|
34
|
-
|
35
|
-
0.2.3:
|
36
|
-
- hotfix
|
37
|
-
|
38
|
-
0.2.2:
|
39
|
-
- fixed issues with ruby 2.4+
|
40
|
-
- added class methods for fa(), normal_get_inventory(), raw_get_inventory, sets_count()
|
41
|
-
|
42
|
-
0.2.1:
|
43
|
-
- many many bugs fixed
|
44
|
-
|
45
|
-
0.2.0:
|
46
|
-
- hotfix
|
47
|
-
|
48
|
-
0.1.9:
|
49
|
-
- Handler.new() now accepts a hash contains login cookies.
|
50
|
-
- get_auth_cookies() returns cookies to use for the next login
|
51
|
-
|
52
|
-
0.1.8:
|
53
|
-
- hotfix
|
54
|
-
|
55
|
-
0.1.7:
|
56
|
-
- hotfix
|
57
|
-
|
58
|
-
0.1.6:
|
59
|
-
- hotfix
|
60
|
-
|
61
|
-
0.1.5:
|
62
|
-
- added mobile_login() which allows you to send and receive steam messages
|
63
|
-
- added oauth_login() uses oauth token and steamMachine cookie to login in ( you get those from mobile_login())
|
64
|
-
|
65
|
-
0.1.4:
|
66
|
-
- added Social commands : send friend request, accept friend request, remove friend, send message, get messages
|
67
|
-
- added function to update badges blueprint (useful when there is no gem update)
|
68
|
-
|
69
|
-
0.1.3:
|
70
|
-
- decreased cooldown between requests from 2 seconds to 1 second.
|
71
|
-
- added a 0.6 second wait before attempting to confirm a trade offer (mobile).
|
72
|
-
- added a 3 times retry to get an inventory chunk before raising an error.
|
73
|
-
- exception handling for sets_count, now no longer raises an error if the target inventory contains trading cards which are not specified in the bluepirnt.
|
74
|
-
|
75
|
-
0.1.2:
|
76
|
-
- normal_get_inventory() and raw_get_inventory() now uses Mechanize instead of open-uri.
|
77
|
-
- Handler.new() and fa() now accepts a time difference parameter to adjust your 2FA codes.
|
78
|
-
- sets_count() now writes the txt file faster.
|
79
|
-
- Mechanize session associated with the account now has a 2 second cooldown before each request to avoid spamming steam servers and resulting in a ban.
|
80
|
-
```
|
81
|
-
# Table of content
|
82
|
-
|
83
|
-
- [Installation](#installation)
|
84
|
-
- [Usage & Examples](#usage)
|
85
|
-
- [Logging-in](#logging-in)
|
86
|
-
- [Hander.new() (this is how you login)](#handlernew)
|
87
|
-
- [Handler.new() (normal login)](#handlernewusername-passwordshared_secrettime_differenceremember_me)
|
88
|
-
- [Handler.new() (cookies login)](#handlernewcookies_hashshared_secrettime_differenceremember_me)
|
89
|
-
- [get_auth_cookies()](#get_auth_cookies)
|
90
|
-
- [mobile_info()](#mobile_infoidentity_secret)
|
91
|
-
- [Getting someone's inventory](#getting-someones-inventory)
|
92
|
-
- [normal_get_inventory()](#normal_get_inventorysteamidinventoryappid)
|
93
|
-
- [raw_get_inventory()](#raw_get_inventorytargetinventoryappidtrimming)
|
94
|
-
- [set_inventory_cache()](#set_inventory_cache)
|
95
|
-
- [Sending a trade offer](#sending-a-trade-offer)
|
96
|
-
- [send_offer()](#send_offermyarraytheirarraytrade_offer_linkmessage)
|
97
|
-
- [Handling Trade Offers](#handling-trade-offers)
|
98
|
-
- [set_api_key()](#set_api_keyapi_key)
|
99
|
-
- [get_trade_offers()](#get_trade_offerstime)
|
100
|
-
- [get_trade_offer()](#get_trade_offertrade_offer_id)
|
101
|
-
- [accept_trade_offer()](#accept_trade_offertrade_offer_id)
|
102
|
-
- [decline_trade_offer()](#decline_trade_offertrade_offer_id)
|
103
|
-
- [cancel_trade_offer()](#cancel_trade_offertrade_offer_id)
|
104
|
-
- [Counting badges owned](#counting-badges-owned)
|
105
|
-
- [sets_count()](#sets_counttargetnon_marketable)
|
106
|
-
- [update_blueprint()](#update_blueprint)
|
107
|
-
- [2FA codes](#2fa-codes)
|
108
|
-
- [fa()](#fashared_secret-time_difference)
|
109
|
-
- [Social Features](#social-commands)
|
110
|
-
- [mobile_login()](#mobile_loginusernamepasswordshared_secret)
|
111
|
-
- [oauth_login()](#oauth_loginoauth_tokensteammachine)
|
112
|
-
- [send_message()](#send_messagetarget-message)
|
113
|
-
- [poll_messages()](#poll_messages)
|
114
|
-
- [send_friend_request()](#send_friend_requesttarget)
|
115
|
-
- [accept_friend_request()](#accept_friend_requesttarget)
|
116
|
-
- [remove_friend()](#remove_friendtarget)
|
117
|
-
- [More commands](#more-commands)
|
118
|
-
|
119
|
-
## Installation
|
120
|
-
in your commandline :
|
121
|
-
|
122
|
-
`gem install steam-trade`
|
123
|
-
|
124
|
-
## Usage
|
125
|
-
First you need to require the gem:
|
126
|
-
```ruby
|
127
|
-
require 'steam-trade'
|
128
|
-
```
|
129
|
-
## Logging-in
|
130
|
-
#### `Handler.new()`
|
131
|
-
##### `Handler.new(username, password,shared_secret,time_difference,remember_me)`
|
132
|
-
then you need to login and optionally set your shared_secret and identity_secret:
|
133
|
-
- `shared_secret` is used to generate steam authentication codes so you won't have to write them manually each time you login.
|
134
|
-
- `time_difference`is the difference between your time and steam servers, this affects how 2FA codes are generated (**this MUST BE an integer**)
|
135
|
-
- `remember_me` is a boolean used to indicate whether you want cookies which expire shortly if set to **false** or stay valid for weeks if set to **true**
|
136
|
-
```ruby
|
137
|
-
require 'steam-trade'
|
138
|
-
|
139
|
-
account = Handler.new('username','password','shared_secret') # share secret is optional
|
140
|
-
account = Handler.new('username','password',50) #works
|
141
|
-
account = Handler.new('username','password','shared_secret',50)
|
142
|
-
account = Handler.new('username','password',50,'shared_secret') # this will not work
|
143
|
-
|
144
|
-
account = Handler.new('username','password','shared_secret',20,true) # works
|
145
|
-
account = Handler.new('username','password','shared_secret',true) #works
|
146
|
-
account = Handler.new('username','password',20,true) #works
|
147
|
-
account = Handler.new('username','password',true) #works
|
148
|
-
|
149
|
-
account = Handler.new('username','password','shared_secret',true,20) # will not work
|
150
|
-
##########
|
151
|
-
account = Handler.new('username') #this of course counts as non logged in
|
152
|
-
|
153
|
-
```
|
154
|
-
keep in mind you can initialize a Handler without params however the commands you will be able to use will be limited
|
155
|
-
```ruby
|
156
|
-
require 'steam-trade'
|
157
|
-
|
158
|
-
account = Handler.new()
|
159
|
-
puts account.fa('v3dWNq2Ncutc7RelwRVXswT8CJX=v3dWNq2Ncutc7WelwRVXswT8CJk=') => random code
|
160
|
-
|
161
|
-
```
|
162
|
-
|
163
|
-
##### `Handler.new(cookies_hash,shared_secret,time_difference,remember_me)`
|
164
|
-
- `cookies_hash` is hash containing `steamLogin`, `steamLoginSecure` and `steamMachineAuth` cookies.
|
165
|
-
this can be used with `get_auth_cookies()` for faster login.
|
166
|
-
- `shared_secret` is used to generate steam authentication codes so you won't have to write them manually each time you login.
|
167
|
-
- `time_difference`is the difference between your time and steam servers, this affects how 2FA codes are generated (**this MUST BE an integer**)
|
168
|
-
- `remember_me` is a boolean used to indicate whether you want cookies which expire shortly if set to **false** or stay valid for weeks if set to **true**
|
169
|
-
|
170
|
-
|
171
|
-
```ruby
|
172
|
-
require 'steam-trade'
|
173
|
-
account = Handler.new(JSON.parse(File.read('./creds.json'))) # creds.json is created by get_auth_cookies()
|
174
|
-
|
175
|
-
account = Handler.new(JSON.parse(File.read('./creds.json')), 'shared_secret', 50)
|
176
|
-
```
|
177
|
-
|
178
|
-
#### `get_auth_cookies()`
|
179
|
-
- returns the current logged in account cookies to use in the future.
|
180
|
-
```ruby
|
181
|
-
require 'steam-trade'
|
182
|
-
account = Handler.new('username','password','shared_secret',true)
|
183
|
-
cookies = h.get_auth_cookies
|
184
|
-
|
185
|
-
File.open('creds.json', 'w') {|f| f.puts cookies.to_json}
|
186
|
-
```
|
187
|
-
next time :
|
188
|
-
```ruby
|
189
|
-
require 'steam-trade'
|
190
|
-
account = Handler.new(JSON.parse(File.read('./creds.json')))
|
191
|
-
```
|
192
|
-
|
193
|
-
#### `mobile_info(identity_secret)`
|
194
|
-
- `identity_secret` is your account's identity secret (try using google if you don't know what this is).
|
195
|
-
- `identity_secret` is used to automatically confirm trade offers.
|
196
|
-
```ruby
|
197
|
-
require 'steam-trade'
|
198
|
-
|
199
|
-
account = Handler.new('username','password','shared_secret')
|
200
|
-
account.mobile_info('identity_secret')
|
201
|
-
```
|
202
|
-
|
203
|
-
## Getting someone's inventory
|
204
|
-
you might want to read this [guide](https://dev.doctormckay.com/topic/332-identifying-steam-items/)
|
205
|
-
#### `normal_get_inventory('steamid','inventoryappid')`
|
206
|
-
- `steamid` is the target's steamID, or profileID, or trade link
|
207
|
-
- `inventoryappid` is the inventory type you want to load, `ex : normal inventory(the one which holds trading cards), it's is 753`
|
208
|
-
- if you call `normal_get_inventory()` with no params, it will be default use the current logged-in account `steamid`, `inventoryappid = 753`
|
209
|
-
|
210
|
-
```ruby
|
211
|
-
require 'steam-trade'
|
212
|
-
inventory = Handler.normal_get_inventory("nomg3r")
|
213
|
-
|
214
|
-
|
215
|
-
logged = Handler.new('username','password','shared_secret')
|
216
|
-
logged.mobile_info('identity_secret')
|
217
|
-
# while logged in
|
218
|
-
my_inventory = logged.normal_get_inventory() #will get your normal inventory(753) if you are logged in else raise an exception
|
219
|
-
my_inventory = logged.normal_get_inventory('730') # will get your CS:GO inventory if you are logged in else raise an exeception
|
220
|
-
|
221
|
-
|
222
|
-
#whatever can be done while **not** logged in, can be of course used while logged in
|
223
|
-
#while not logged in
|
224
|
-
nonlogged = Handler.new()
|
225
|
-
my_inventory = nonlogged.normal_get_inventory() #will raise an exception
|
226
|
-
my_inventory = nonlogged.normal_get_inventory('730') #will raise an exception
|
227
|
-
|
228
|
-
#whenever
|
229
|
-
partner_inventory = nonlogged.normal_get_inventory('76561198044170935') #using steamid
|
230
|
-
partner_inventory = nonlogged.normal_get_inventory('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt') #using trade link
|
231
|
-
partner_inventory = nonlogged.normal_get_inventory('CardExchange') #using profile id
|
232
|
-
|
233
|
-
|
234
|
-
partner_inventory = nonlogged.normal_get_inventory('76561198044170935',730) #will get that steamid CS:GO inventory
|
235
|
-
partner_inventory = nonlogged.normal_get_inventory('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt', '730') #will get that trade link owner's CS:GO inventory
|
236
|
-
partner_inventory = nonlogged.normal_get_inventory('CardExchange',730) # will get CardExchange's CS:GO inventory
|
237
|
-
|
238
|
-
|
239
|
-
```
|
240
|
-
the returned items from `normal_get_inventory()` are in the form of an array example : `[item1,item2,item3...itemN]`.
|
241
|
-
|
242
|
-
each item is a hash which contains information about the item in the form of `{"appid"=>'xxx',"contextid"=>'xxx',"assetid" => 'xxx',"classid"=> 'xxx',......"name"=> 'xxxx',"market_fee_app" => 'xxx',....}`.
|
243
|
-
|
244
|
-
`market_fee_app` key gives you the appid of the game's app (for trading cards), for other items technically `inventoryappid` is the games appid.
|
245
|
-
|
246
|
-
`name` key gives you the item name.
|
247
|
-
#### `raw_get_inventory(target,inventoryappid,trimming)`
|
248
|
-
**IMPORTANT**: this command efficiency is better than `normal_get_inventory`, therefore i **recommend** using this one.
|
249
|
-
- `target` is a steamID/profileID/trade link
|
250
|
-
- `inventoryappid` is the inventory type you want to load, `ex : normal inventory(the one which holds trading cards), it's is 753`
|
251
|
-
- `trimming`, defaults to `true` this will remove images link and steam-server-side related informations from the descriptions hash, drastically reducing the size of data received.
|
252
|
-
|
253
|
-
This command will return a hash nearly identitical to the one received from steam the hash will have 2 keys `assets` and `descriptions`:
|
254
|
-
- `assets` has an array as value, identical to steam's [(example)](https://steamcommunity.com/inventory/76561198044170935/753/6?start_assetid=0&count=100)
|
255
|
-
- `descriptions` has an array as a value identical to steam's [(example)](https://steamcommunity.com/inventory/76561198044170935/753/6?start_assetid=0&count=100)
|
256
|
-
|
257
|
-
```ruby
|
258
|
-
require 'steam-trade'
|
259
|
-
inv = Handler.raw_get_inventory("nomg3r")
|
260
|
-
|
261
|
-
|
262
|
-
logged = Handler.new('username','password','shared_secret')
|
263
|
-
inv = logged.raw_get_inventory() #works
|
264
|
-
inv = logged.raw_get_inventory(false) # returns non trimmed
|
265
|
-
inv = logged.raw_get_inventory(440) #works
|
266
|
-
inv = logged.raw_get_inventory(76561198044170935,false) #works
|
267
|
-
inv = logged.raw_get_inventory(76561198044170935,440) # works
|
268
|
-
|
269
|
-
print inv['assets'] #will print all the assets
|
270
|
-
print inv['descriptions'] #will print all the descriptions
|
271
|
-
|
272
|
-
### how to accurately use this
|
273
|
-
|
274
|
-
class_instance = {}
|
275
|
-
## map all the items
|
276
|
-
inv['descriptions'].each { |desc|
|
277
|
-
identifier = desc['classid'] + '_' + desc['instanceid']
|
278
|
-
class_instance[identifier] = desc
|
279
|
-
}
|
280
|
-
|
281
|
-
## identify your items
|
282
|
-
|
283
|
-
inv['assets'].each { |asset|
|
284
|
-
identifier = asset['classid'] + '_' + asset['instanceid']
|
285
|
-
puts class_instance[identifier] this will output the item's description
|
286
|
-
}
|
287
|
-
|
288
|
-
```
|
289
|
-
|
290
|
-
#### `set_inventory_cache()`
|
291
|
-
`set_inventory_cache()` is:
|
292
|
-
|
293
|
-
- a switch to locally save each inventory you get to a local file.
|
294
|
-
- disabled by default, you need to initiate it by calling the command
|
295
|
-
- accepts a parameter `timer` which defaults to `timer = 120`, this parameter is the difference between the save file was created and the moment it was checked (upong trying to retrieve the inventory).
|
296
|
-
|
297
|
-
- this switch is useful if you are getting a "static" inventory or testing your code.
|
298
|
-
```ruby
|
299
|
-
require 'steam-trade'
|
300
|
-
|
301
|
-
logged = Handler.new('username','password','shared_secret')
|
302
|
-
logged.mobile_info('identity_secret')
|
303
|
-
logged.set_inventory_cache(150)
|
304
|
-
|
305
|
-
|
306
|
-
partner_inventory = loggedlogged.normal_get_inventory('CardExchange') #this will save CardExchange's inventory to a local file and return the inventory
|
307
|
-
|
308
|
-
partner_inventory = loggedlogged.normal_get_inventory('CardExchange') # this will load the locally saved file
|
309
|
-
|
310
|
-
|
311
|
-
```
|
312
|
-
|
313
|
-
**IMPORTANT**: `normal_get_inventory()` will load the whole target inventory, for each **5k** of items, you are adding **~40MB** to your memory and of course will affect performance of the code and the computer
|
314
|
-
## Sending a trade offer
|
315
|
-
#### `send_offer(myarray,theirarray,trade_offer_link,message)`
|
316
|
-
**MUST be logged in to use this command**
|
317
|
-
then you can send your offer
|
318
|
-
- `myarray` is an array which contains hashes of selected items to send in the offer. (currently you must get this alone)
|
319
|
-
- `Theirarray` is an array which contains hashes of selected items to receive in the offer. (currently you must get this alone)
|
320
|
-
- `trade_offer_link` can be the trade link of you partner `ex: https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt`
|
321
|
-
- `trade_offer_link` can be a steamID, however using a steamID requires you and your partner to be friends on steam
|
322
|
-
- `trade_offer_link` can be a profileID, however using a profileID requires you and your partner to be friends on steam
|
323
|
-
- `message` is the comment you want to include in the trade offer
|
324
|
-
|
325
|
-
- `myarray`, `theirarray`, `trade_offer_link` are required, `message` is optional
|
326
|
-
```ruby
|
327
|
-
require 'steam-trade'
|
328
|
-
|
329
|
-
account = Handler.new('username','password','shared_secret')
|
330
|
-
account.mobile_info('identity_secret')
|
331
|
-
|
332
|
-
me = account.normal_get_inventory()
|
333
|
-
his = account.normal_get_inventory("nomg3r")
|
334
|
-
|
335
|
-
myarray = [me[5] , me[20] , me[60]].compact!
|
336
|
-
theirarray = [his[1], his[20], his[30]].compact!
|
337
|
-
|
338
|
-
# if you are friends
|
339
|
-
account.send_offer(myarray,theirarray,"nomg3r",message)
|
340
|
-
#or (as friends)
|
341
|
-
account.send_offer(myarray,theirarray,'76561198370420964',message)
|
342
|
-
|
343
|
-
# whenever
|
344
|
-
account.send_offer(myarray,theirarray,"https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt",message)
|
345
|
-
|
346
|
-
```
|
347
|
-
## Handling Trade Offers
|
348
|
-
you might want to read [Steam Trading API](https://developer.valvesoftware.com/wiki/Steam_Web_API/IEconService)
|
349
|
-
|
350
|
-
**ALL OF THE COMMANDS BELOW REQUIRE AN API_KEY**
|
351
|
-
|
352
|
-
#### `set_api_key(API_KEY)`
|
353
|
-
**NOTE**:If you are using a **logged in** Handler there is no need to set the API_KEY.
|
354
|
-
- `API_KEY` is your apikey, you can get that from [here](https://steamcommunity.com/dev/apikey).
|
355
|
-
```ruby
|
356
|
-
require 'steam-trade'
|
357
|
-
acc = Handler.new()
|
358
|
-
trade_offers = acc.get_trade_offers() # will raise an exception
|
359
|
-
acc.set_api_key('mykey')
|
360
|
-
trade_offers = acc.get_trade_offers() # after setting an API_KEY this will succeed
|
361
|
-
```
|
362
|
-
#### `get_trade_offers(time)`
|
363
|
-
- `time` is the moment from which you want to get updates (explained in the example)
|
364
|
-
this will return a hash with `trade_offers_sent`, `trade_offers_received`, `descriptions` as keys.
|
365
|
-
`descriptions` includes the descriptions of all items returned from `trade_offers_sent` or `trade_offers_received`
|
366
|
-
|
367
|
-
```ruby
|
368
|
-
require 'steam-trade'
|
369
|
-
logged = Handler.new('username','password','shared_secret')
|
370
|
-
logged.mobile_info('identity_secret')
|
371
|
-
|
372
|
-
time = '' # this is the initial check for offers so we want them all
|
373
|
-
polling = Thread.new(logged) { |logged|
|
374
|
-
loop do
|
375
|
-
offers = logged.get_trade_offers(time)
|
376
|
-
time = Time.new.to_i # we save the time of the last check
|
377
|
-
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
378
|
-
puts offers['trade_offers_received'] # puts the trades
|
379
|
-
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
380
|
-
end
|
381
|
-
}
|
382
|
-
```
|
383
|
-
#### `get_trade_offer(trade_offer_id)`
|
384
|
-
gets more information about a specific trade offer
|
385
|
-
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
386
|
-
|
387
|
-
have no example how to actually use this cause `get_trade_offers(time)` is probably better
|
388
|
-
|
389
|
-
#### `accept_trade_offer(trade_offer_id)`
|
390
|
-
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
391
|
-
```ruby
|
392
|
-
require 'steam-trade'
|
393
|
-
logged = Handler.new('username','password','shared_secret')
|
394
|
-
logged.mobile_info('identity_secret')
|
395
|
-
|
396
|
-
time = '' # this is the initial check for offers so we want them all
|
397
|
-
polling = Thread.new(logged) { |logged|
|
398
|
-
loop do
|
399
|
-
offers = logged.get_trade_offers(time)
|
400
|
-
time = Time.new.to_i # we save the time of the last check
|
401
|
-
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
402
|
-
offers['trade_offers_received'].each { |trade|
|
403
|
-
if trade['accountid_other'].to_i == 83905207 ## this will accept all trade received from 83905207 (Steam32 ID)
|
404
|
-
logged.accept_trade_offer(trade['tradeofferid']) # to accept the trade
|
405
|
-
end
|
406
|
-
}
|
407
|
-
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
408
|
-
end
|
409
|
-
}
|
410
|
-
```
|
411
|
-
#### `decline_trade_offer(trade_offer_id)`
|
412
|
-
this declines a trade offer you **RECEIVED**
|
413
|
-
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
414
|
-
|
415
|
-
```ruby
|
416
|
-
require 'steam-trade'
|
417
|
-
logged = Handler.new('username','password','shared_secret')
|
418
|
-
logged.mobile_info('identity_secret')
|
419
|
-
|
420
|
-
time = '' # this is the initial check for offers so we want them all
|
421
|
-
polling = Thread.new(logged) { |logged|
|
422
|
-
loop do
|
423
|
-
offers = logged.get_trade_offers(time)
|
424
|
-
time = Time.new.to_i # we save the time of the last check
|
425
|
-
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
426
|
-
offers['trade_offers_received'].each { |trade| # we need to check received offers to use 'decline'
|
427
|
-
if trade['accountid_other'].to_i != 83905207 ## notice the '!='
|
428
|
-
logged.decline_trade_offer(trade['tradeofferid']) # decline the trade
|
429
|
-
end
|
430
|
-
}
|
431
|
-
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
432
|
-
end
|
433
|
-
}
|
434
|
-
```
|
435
|
-
#### `cancel_trade_offer(trade_offer_id)`
|
436
|
-
this cancels a trade offer you **SENT**
|
437
|
-
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
438
|
-
```ruby
|
439
|
-
require 'steam-trade'
|
440
|
-
logged = Handler.new('username','password','shared_secret')
|
441
|
-
logged.mobile_info('identity_secret')
|
442
|
-
|
443
|
-
time = '' # this is the initial check for offers so we want them all
|
444
|
-
polling = Thread.new(logged) { |logged|
|
445
|
-
loop do
|
446
|
-
offers = logged.get_trade_offers(time)
|
447
|
-
time = Time.new.to_i # we save the time of the last check
|
448
|
-
next if offers['trade_offers_sent'] == nil # do nothing, if there is no trades
|
449
|
-
offers['trade_offers_sent'].each { |trade| # we need to check sentoffers to use 'cancel'
|
450
|
-
if trade['accountid_other'].to_i != 83905207 ## notice the '!='
|
451
|
-
logged.cancel_trade_offer(trade['tradeofferid']) # cancel the trade
|
452
|
-
end
|
453
|
-
}
|
454
|
-
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
455
|
-
end
|
456
|
-
}
|
457
|
-
```
|
458
|
-
## Counting badges owned
|
459
|
-
#### `sets_count(target,non_marketable)`
|
460
|
-
**this command does not count foil badges (only normal trading cards)**
|
461
|
-
- `target` can be a steamID, a profileID or a trade link
|
462
|
-
- `non_marketable` this is a switch to count **non**-marketable trading cards(defaults to **true** if not specified)
|
463
|
-
- a .txt will be created from this command to read the badges
|
464
|
-
- this returns a hash `{'sets' => appsets, 'appxsets' => setsowned, 'totalsets' => numberofsets, 'totalcards' => total_non_foil, 'marketable' => true}`
|
465
|
-
- `'sets'` is a hash with game appids as keys and each card and number of copies owned of each card `{'appid1' => {'card1' => 5,'card2' => 3, ... 'cardN' => Z},{'appid1' => {'card1' => 0,'card2' => 2, ... 'cardN' => K} }`
|
466
|
-
- `'appxsets'` is a hash containing the number of sets available of each set `{'appid1' => 5,'appid2' => 20,...'appidN' => Z}`
|
467
|
-
- `'totalsets'` is an integer equals to the number of sets owned
|
468
|
-
- `'totalcards'` is an integer equals to the number of non-foil cards account for
|
469
|
-
```ruby
|
470
|
-
require 'steam-trade'
|
471
|
-
data = Handler.sets_count("CardExchange")
|
472
|
-
|
473
|
-
|
474
|
-
logged = Handler.new('username','password','shared_secret')
|
475
|
-
logged.mobile_info('identity_secret')
|
476
|
-
#with login
|
477
|
-
logged = account.sets_count()
|
478
|
-
logged = account.sets_count(false)
|
479
|
-
hash = account.sets_count('CardExchange',false)
|
480
|
-
hash = account.sets_count(76561198370420964)
|
481
|
-
hash = account.sets_count('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt',false)
|
482
|
-
|
483
|
-
|
484
|
-
#without login
|
485
|
-
nonlogged = Handler.new()
|
486
|
-
logged = account.sets_count() #raise exception
|
487
|
-
logged = account.sets_count(false) # raise exception
|
488
|
-
hash = account.sets_count('CardExchange')
|
489
|
-
hash = account.sets_count(76561198370420964)
|
490
|
-
hash = account.sets_count('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt',false)
|
491
|
-
|
492
|
-
```
|
493
|
-
|
494
|
-
#### `update_blueprint()`
|
495
|
-
- updates your locally saved badges blueprint
|
496
|
-
```ruby
|
497
|
-
require 'steam-trade'
|
498
|
-
|
499
|
-
handler = Handler.new
|
500
|
-
|
501
|
-
handler.update_blueprint()
|
502
|
-
```
|
503
|
-
## 2FA codes
|
504
|
-
#### `fa(shared_secret, time_difference)`
|
505
|
-
- `shared_secret` is the account's shared secret (if you don't know what is this try googling 'steam shared_secret'), defaults to the logged in account's steamid if logged in.
|
506
|
-
- `time_difference` is the difference between your pc's time and steam's time (**this MUST BE an integer**)
|
507
|
-
**NOTE**: using this command with a new shared_secret will not change/set the current saved shared_secret for the account
|
508
|
-
```ruby
|
509
|
-
require 'steam-trade'
|
510
|
-
puts Hander.fa('random_shared_secret')
|
511
|
-
|
512
|
-
|
513
|
-
logged = Handler.new('username','password','inital_shared_secret')
|
514
|
-
puts logged.fa() #=> random code for your account
|
515
|
-
puts logged.fa('new_shared_secret') # => this will give you a random code for another account, AND will not edit your initial_shared_secret
|
516
|
-
|
517
|
-
####
|
518
|
-
logged_without_shared_secret = Handler.new('username','password') # this is possible of course
|
519
|
-
puts logged_without_shared_secret.fa() # this will not work
|
520
|
-
puts logged_without_shared_secret.fa('shared_secret') ## will give a random code
|
521
|
-
###
|
522
|
-
nonlogged = Handler.new()
|
523
|
-
puts nonlogged.fa() # will not work
|
524
|
-
puts logged.fa() # will give a random code
|
525
|
-
|
526
|
-
```
|
527
|
-
## Social Commands
|
528
|
-
#### `mobile_login('username','password','shared_secret')`
|
529
|
-
- this command will be called automatically if you attempt to use `send_message()` or `poll_messages()` without authentication
|
530
|
-
- calling this explicitly allows you to painlessly retrieve the OAuth token and `SteamMachine#{steamid}` cookie to use in `oauth_login()`
|
531
|
-
- this function returns a hash with `oauth_token` and `machine` as keys
|
532
|
-
```ruby
|
533
|
-
require 'steam-trade'
|
534
|
-
|
535
|
-
h = Handler.new('user','pass','secret')
|
536
|
-
data = h.mobile_login() #this works are you have setted username and password
|
537
|
-
puts data ## will output with oauth token and steamMachine cookie
|
538
|
-
|
539
|
-
###################
|
540
|
-
h = Handler.new()
|
541
|
-
data = h.mobile_login() # will raise an error cause there is no username or password
|
542
|
-
|
543
|
-
##########
|
544
|
-
|
545
|
-
h = Handler.new()
|
546
|
-
data = h.mobile_login('user','pass','secret') ## will work, you are not logged in ( talking about community) here you can't use most of the commands (send_offer() etc) and those parameters you passed will not be setted as the Handler's
|
547
|
-
|
548
|
-
######
|
549
|
-
h = Handler.new('user1','pass1','secret1')
|
550
|
-
data = mobile_login('user2','pass2','secret2') # this works but trading commands etc will be called using user1, and chat commands will be called using user2
|
551
|
-
```
|
552
|
-
#### `oauth_login(oauth_token,SteamMachine)`
|
553
|
-
- `oauth_token` and `SteamMachine` can be retrieved from `mobile_login()`
|
554
|
-
```ruby
|
555
|
-
require 'steam-trade'
|
556
|
-
h = Handler.new()
|
557
|
-
h.oauth_login('oauth_token','SteamMachine')
|
558
|
-
```
|
559
|
-
#### `send_message(target, message)`
|
560
|
-
sends a message to the target
|
561
|
-
- `target` can be a steamID64, tradelink, or profileID
|
562
|
-
- `message` the message to send
|
563
|
-
```ruby
|
564
|
-
require 'steam-trade'
|
565
|
-
|
566
|
-
h = Handler.new('username', 'password')
|
567
|
-
h.send_message('nomg3r', "Hello, Friend")
|
568
|
-
```
|
569
|
-
|
570
|
-
#### `poll_messages()`
|
571
|
-
gives you the messages you receieved (after mobile login is initiated (after you call send_message() or poll_messages() ) )
|
572
|
-
|
573
|
-
```ruby
|
574
|
-
require 'steam-trade'
|
575
|
-
|
576
|
-
h = Handler.new('username', 'password')
|
577
|
-
print h.poll_messages() # will not return messages so you call at again ( only the first time in the whole program )
|
578
|
-
puts ""
|
579
|
-
puts "------"
|
580
|
-
sleep(10) #send a message to the logged in account
|
581
|
-
print h.poll_messages() # actually have messages ( if you received some in the time between the first and the second request )
|
582
|
-
```
|
583
|
-
**ALL OF THE COMMANDS BELOW REQUIRES LOGIN**
|
584
|
-
#### `send_friend_request(target)`
|
585
|
-
sends a friend request to the target
|
586
|
-
- `target` can be a steamID64, tradelink, or profileID
|
587
|
-
|
588
|
-
```ruby
|
589
|
-
require 'steam-trade'
|
590
|
-
|
591
|
-
h = Handler.new('username', 'password')
|
592
|
-
h.send_friend_request('nomg3r')
|
593
|
-
```
|
594
|
-
|
595
|
-
#### `accept_friend_request(target)`
|
596
|
-
accepts a friend request from the target
|
597
|
-
- `target` can be a steamID64, tradelink, or profileID
|
598
|
-
|
599
|
-
```ruby
|
600
|
-
require 'steam-trade'
|
601
|
-
|
602
|
-
h = Handler.new('username', 'password')
|
603
|
-
h.accept_friend_request('nomg3r')
|
604
|
-
```
|
605
|
-
|
606
|
-
### `remove_friend(target)`
|
607
|
-
removes a friend
|
608
|
-
- `target` can be a steamID64, tradelink, or profileID
|
609
|
-
|
610
|
-
```ruby
|
611
|
-
require 'steam-trade'
|
612
|
-
|
613
|
-
h = Handler.new('username', 'password')
|
614
|
-
h.remove_friend('nomg3r')
|
615
|
-
```
|
616
|
-
|
617
|
-
## More commands
|
618
|
-
you can find more non-vital commands in the [wiki](https://github.com/OmG3r/steam-trade/wiki)
|
619
|
-
## License
|
620
|
-
|
621
|
-
The gem is available as open source under the terms of the [GNU GPLV3](https://github.com/OmG3r/steam-trade/blob/master/LICENSE).
|
1
|
+
# steam-trade V0.3.0
|
2
|
+
|
3
|
+
**PLEASE IF SOMETHING DOES NOT WORK PROPERLY MAKE A GITHUB ISSUE**
|
4
|
+
|
5
|
+
Please check constantly for updates cause i'm still making this gem.
|
6
|
+
|
7
|
+
This gem simplifes/allows sending steam trade offers programmatically.
|
8
|
+
|
9
|
+
this gem is primarly for trading cards, tho can be used to CS:GO and other games inventories
|
10
|
+
|
11
|
+
# Changelog
|
12
|
+
```
|
13
|
+
0.3.0:
|
14
|
+
- hotfix for cookie login
|
15
|
+
|
16
|
+
0.2.9:
|
17
|
+
- hotfix for cookie login (remember me)
|
18
|
+
|
19
|
+
0.2.8:
|
20
|
+
- fixed cookie login
|
21
|
+
|
22
|
+
0.2.7:
|
23
|
+
- added salien_card() to collect steam Salien game Trading Cards
|
24
|
+
|
25
|
+
0.2.6:
|
26
|
+
- hotfix
|
27
|
+
|
28
|
+
0.2.5:
|
29
|
+
- added finish_queue() to collect Steam Sale Trading Cards
|
30
|
+
- hotfix
|
31
|
+
|
32
|
+
0.2.4:
|
33
|
+
- hotfix
|
34
|
+
|
35
|
+
0.2.3:
|
36
|
+
- hotfix
|
37
|
+
|
38
|
+
0.2.2:
|
39
|
+
- fixed issues with ruby 2.4+
|
40
|
+
- added class methods for fa(), normal_get_inventory(), raw_get_inventory, sets_count()
|
41
|
+
|
42
|
+
0.2.1:
|
43
|
+
- many many bugs fixed
|
44
|
+
|
45
|
+
0.2.0:
|
46
|
+
- hotfix
|
47
|
+
|
48
|
+
0.1.9:
|
49
|
+
- Handler.new() now accepts a hash contains login cookies.
|
50
|
+
- get_auth_cookies() returns cookies to use for the next login
|
51
|
+
|
52
|
+
0.1.8:
|
53
|
+
- hotfix
|
54
|
+
|
55
|
+
0.1.7:
|
56
|
+
- hotfix
|
57
|
+
|
58
|
+
0.1.6:
|
59
|
+
- hotfix
|
60
|
+
|
61
|
+
0.1.5:
|
62
|
+
- added mobile_login() which allows you to send and receive steam messages
|
63
|
+
- added oauth_login() uses oauth token and steamMachine cookie to login in ( you get those from mobile_login())
|
64
|
+
|
65
|
+
0.1.4:
|
66
|
+
- added Social commands : send friend request, accept friend request, remove friend, send message, get messages
|
67
|
+
- added function to update badges blueprint (useful when there is no gem update)
|
68
|
+
|
69
|
+
0.1.3:
|
70
|
+
- decreased cooldown between requests from 2 seconds to 1 second.
|
71
|
+
- added a 0.6 second wait before attempting to confirm a trade offer (mobile).
|
72
|
+
- added a 3 times retry to get an inventory chunk before raising an error.
|
73
|
+
- exception handling for sets_count, now no longer raises an error if the target inventory contains trading cards which are not specified in the bluepirnt.
|
74
|
+
|
75
|
+
0.1.2:
|
76
|
+
- normal_get_inventory() and raw_get_inventory() now uses Mechanize instead of open-uri.
|
77
|
+
- Handler.new() and fa() now accepts a time difference parameter to adjust your 2FA codes.
|
78
|
+
- sets_count() now writes the txt file faster.
|
79
|
+
- Mechanize session associated with the account now has a 2 second cooldown before each request to avoid spamming steam servers and resulting in a ban.
|
80
|
+
```
|
81
|
+
# Table of content
|
82
|
+
|
83
|
+
- [Installation](#installation)
|
84
|
+
- [Usage & Examples](#usage)
|
85
|
+
- [Logging-in](#logging-in)
|
86
|
+
- [Hander.new() (this is how you login)](#handlernew)
|
87
|
+
- [Handler.new() (normal login)](#handlernewusername-passwordshared_secrettime_differenceremember_me)
|
88
|
+
- [Handler.new() (cookies login)](#handlernewcookies_hashshared_secrettime_differenceremember_me)
|
89
|
+
- [get_auth_cookies()](#get_auth_cookies)
|
90
|
+
- [mobile_info()](#mobile_infoidentity_secret)
|
91
|
+
- [Getting someone's inventory](#getting-someones-inventory)
|
92
|
+
- [normal_get_inventory()](#normal_get_inventorysteamidinventoryappid)
|
93
|
+
- [raw_get_inventory()](#raw_get_inventorytargetinventoryappidtrimming)
|
94
|
+
- [set_inventory_cache()](#set_inventory_cache)
|
95
|
+
- [Sending a trade offer](#sending-a-trade-offer)
|
96
|
+
- [send_offer()](#send_offermyarraytheirarraytrade_offer_linkmessage)
|
97
|
+
- [Handling Trade Offers](#handling-trade-offers)
|
98
|
+
- [set_api_key()](#set_api_keyapi_key)
|
99
|
+
- [get_trade_offers()](#get_trade_offerstime)
|
100
|
+
- [get_trade_offer()](#get_trade_offertrade_offer_id)
|
101
|
+
- [accept_trade_offer()](#accept_trade_offertrade_offer_id)
|
102
|
+
- [decline_trade_offer()](#decline_trade_offertrade_offer_id)
|
103
|
+
- [cancel_trade_offer()](#cancel_trade_offertrade_offer_id)
|
104
|
+
- [Counting badges owned](#counting-badges-owned)
|
105
|
+
- [sets_count()](#sets_counttargetnon_marketable)
|
106
|
+
- [update_blueprint()](#update_blueprint)
|
107
|
+
- [2FA codes](#2fa-codes)
|
108
|
+
- [fa()](#fashared_secret-time_difference)
|
109
|
+
- [Social Features](#social-commands)
|
110
|
+
- [mobile_login()](#mobile_loginusernamepasswordshared_secret)
|
111
|
+
- [oauth_login()](#oauth_loginoauth_tokensteammachine)
|
112
|
+
- [send_message()](#send_messagetarget-message)
|
113
|
+
- [poll_messages()](#poll_messages)
|
114
|
+
- [send_friend_request()](#send_friend_requesttarget)
|
115
|
+
- [accept_friend_request()](#accept_friend_requesttarget)
|
116
|
+
- [remove_friend()](#remove_friendtarget)
|
117
|
+
- [More commands](#more-commands)
|
118
|
+
|
119
|
+
## Installation
|
120
|
+
in your commandline :
|
121
|
+
|
122
|
+
`gem install steam-trade`
|
123
|
+
|
124
|
+
## Usage
|
125
|
+
First you need to require the gem:
|
126
|
+
```ruby
|
127
|
+
require 'steam-trade'
|
128
|
+
```
|
129
|
+
## Logging-in
|
130
|
+
#### `Handler.new()`
|
131
|
+
##### `Handler.new(username, password,shared_secret,time_difference,remember_me)`
|
132
|
+
then you need to login and optionally set your shared_secret and identity_secret:
|
133
|
+
- `shared_secret` is used to generate steam authentication codes so you won't have to write them manually each time you login.
|
134
|
+
- `time_difference`is the difference between your time and steam servers, this affects how 2FA codes are generated (**this MUST BE an integer**)
|
135
|
+
- `remember_me` is a boolean used to indicate whether you want cookies which expire shortly if set to **false** or stay valid for weeks if set to **true**
|
136
|
+
```ruby
|
137
|
+
require 'steam-trade'
|
138
|
+
|
139
|
+
account = Handler.new('username','password','shared_secret') # share secret is optional
|
140
|
+
account = Handler.new('username','password',50) #works
|
141
|
+
account = Handler.new('username','password','shared_secret',50)
|
142
|
+
account = Handler.new('username','password',50,'shared_secret') # this will not work
|
143
|
+
|
144
|
+
account = Handler.new('username','password','shared_secret',20,true) # works
|
145
|
+
account = Handler.new('username','password','shared_secret',true) #works
|
146
|
+
account = Handler.new('username','password',20,true) #works
|
147
|
+
account = Handler.new('username','password',true) #works
|
148
|
+
|
149
|
+
account = Handler.new('username','password','shared_secret',true,20) # will not work
|
150
|
+
##########
|
151
|
+
account = Handler.new('username') #this of course counts as non logged in
|
152
|
+
|
153
|
+
```
|
154
|
+
keep in mind you can initialize a Handler without params however the commands you will be able to use will be limited
|
155
|
+
```ruby
|
156
|
+
require 'steam-trade'
|
157
|
+
|
158
|
+
account = Handler.new()
|
159
|
+
puts account.fa('v3dWNq2Ncutc7RelwRVXswT8CJX=v3dWNq2Ncutc7WelwRVXswT8CJk=') => random code
|
160
|
+
|
161
|
+
```
|
162
|
+
|
163
|
+
##### `Handler.new(cookies_hash,shared_secret,time_difference,remember_me)`
|
164
|
+
- `cookies_hash` is hash containing `steamLogin`, `steamLoginSecure` and `steamMachineAuth` cookies.
|
165
|
+
this can be used with `get_auth_cookies()` for faster login.
|
166
|
+
- `shared_secret` is used to generate steam authentication codes so you won't have to write them manually each time you login.
|
167
|
+
- `time_difference`is the difference between your time and steam servers, this affects how 2FA codes are generated (**this MUST BE an integer**)
|
168
|
+
- `remember_me` is a boolean used to indicate whether you want cookies which expire shortly if set to **false** or stay valid for weeks if set to **true**
|
169
|
+
|
170
|
+
|
171
|
+
```ruby
|
172
|
+
require 'steam-trade'
|
173
|
+
account = Handler.new(JSON.parse(File.read('./creds.json'))) # creds.json is created by get_auth_cookies()
|
174
|
+
|
175
|
+
account = Handler.new(JSON.parse(File.read('./creds.json')), 'shared_secret', 50)
|
176
|
+
```
|
177
|
+
|
178
|
+
#### `get_auth_cookies()`
|
179
|
+
- returns the current logged in account cookies to use in the future.
|
180
|
+
```ruby
|
181
|
+
require 'steam-trade'
|
182
|
+
account = Handler.new('username','password','shared_secret',true)
|
183
|
+
cookies = h.get_auth_cookies
|
184
|
+
|
185
|
+
File.open('creds.json', 'w') {|f| f.puts cookies.to_json}
|
186
|
+
```
|
187
|
+
next time :
|
188
|
+
```ruby
|
189
|
+
require 'steam-trade'
|
190
|
+
account = Handler.new(JSON.parse(File.read('./creds.json')))
|
191
|
+
```
|
192
|
+
|
193
|
+
#### `mobile_info(identity_secret)`
|
194
|
+
- `identity_secret` is your account's identity secret (try using google if you don't know what this is).
|
195
|
+
- `identity_secret` is used to automatically confirm trade offers.
|
196
|
+
```ruby
|
197
|
+
require 'steam-trade'
|
198
|
+
|
199
|
+
account = Handler.new('username','password','shared_secret')
|
200
|
+
account.mobile_info('identity_secret')
|
201
|
+
```
|
202
|
+
|
203
|
+
## Getting someone's inventory
|
204
|
+
you might want to read this [guide](https://dev.doctormckay.com/topic/332-identifying-steam-items/)
|
205
|
+
#### `normal_get_inventory('steamid','inventoryappid')`
|
206
|
+
- `steamid` is the target's steamID, or profileID, or trade link
|
207
|
+
- `inventoryappid` is the inventory type you want to load, `ex : normal inventory(the one which holds trading cards), it's is 753`
|
208
|
+
- if you call `normal_get_inventory()` with no params, it will be default use the current logged-in account `steamid`, `inventoryappid = 753`
|
209
|
+
|
210
|
+
```ruby
|
211
|
+
require 'steam-trade'
|
212
|
+
inventory = Handler.normal_get_inventory("nomg3r")
|
213
|
+
|
214
|
+
|
215
|
+
logged = Handler.new('username','password','shared_secret')
|
216
|
+
logged.mobile_info('identity_secret')
|
217
|
+
# while logged in
|
218
|
+
my_inventory = logged.normal_get_inventory() #will get your normal inventory(753) if you are logged in else raise an exception
|
219
|
+
my_inventory = logged.normal_get_inventory('730') # will get your CS:GO inventory if you are logged in else raise an exeception
|
220
|
+
|
221
|
+
|
222
|
+
#whatever can be done while **not** logged in, can be of course used while logged in
|
223
|
+
#while not logged in
|
224
|
+
nonlogged = Handler.new()
|
225
|
+
my_inventory = nonlogged.normal_get_inventory() #will raise an exception
|
226
|
+
my_inventory = nonlogged.normal_get_inventory('730') #will raise an exception
|
227
|
+
|
228
|
+
#whenever
|
229
|
+
partner_inventory = nonlogged.normal_get_inventory('76561198044170935') #using steamid
|
230
|
+
partner_inventory = nonlogged.normal_get_inventory('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt') #using trade link
|
231
|
+
partner_inventory = nonlogged.normal_get_inventory('CardExchange') #using profile id
|
232
|
+
|
233
|
+
|
234
|
+
partner_inventory = nonlogged.normal_get_inventory('76561198044170935',730) #will get that steamid CS:GO inventory
|
235
|
+
partner_inventory = nonlogged.normal_get_inventory('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt', '730') #will get that trade link owner's CS:GO inventory
|
236
|
+
partner_inventory = nonlogged.normal_get_inventory('CardExchange',730) # will get CardExchange's CS:GO inventory
|
237
|
+
|
238
|
+
|
239
|
+
```
|
240
|
+
the returned items from `normal_get_inventory()` are in the form of an array example : `[item1,item2,item3...itemN]`.
|
241
|
+
|
242
|
+
each item is a hash which contains information about the item in the form of `{"appid"=>'xxx',"contextid"=>'xxx',"assetid" => 'xxx',"classid"=> 'xxx',......"name"=> 'xxxx',"market_fee_app" => 'xxx',....}`.
|
243
|
+
|
244
|
+
`market_fee_app` key gives you the appid of the game's app (for trading cards), for other items technically `inventoryappid` is the games appid.
|
245
|
+
|
246
|
+
`name` key gives you the item name.
|
247
|
+
#### `raw_get_inventory(target,inventoryappid,trimming)`
|
248
|
+
**IMPORTANT**: this command efficiency is better than `normal_get_inventory`, therefore i **recommend** using this one.
|
249
|
+
- `target` is a steamID/profileID/trade link
|
250
|
+
- `inventoryappid` is the inventory type you want to load, `ex : normal inventory(the one which holds trading cards), it's is 753`
|
251
|
+
- `trimming`, defaults to `true` this will remove images link and steam-server-side related informations from the descriptions hash, drastically reducing the size of data received.
|
252
|
+
|
253
|
+
This command will return a hash nearly identitical to the one received from steam the hash will have 2 keys `assets` and `descriptions`:
|
254
|
+
- `assets` has an array as value, identical to steam's [(example)](https://steamcommunity.com/inventory/76561198044170935/753/6?start_assetid=0&count=100)
|
255
|
+
- `descriptions` has an array as a value identical to steam's [(example)](https://steamcommunity.com/inventory/76561198044170935/753/6?start_assetid=0&count=100)
|
256
|
+
|
257
|
+
```ruby
|
258
|
+
require 'steam-trade'
|
259
|
+
inv = Handler.raw_get_inventory("nomg3r")
|
260
|
+
|
261
|
+
|
262
|
+
logged = Handler.new('username','password','shared_secret')
|
263
|
+
inv = logged.raw_get_inventory() #works
|
264
|
+
inv = logged.raw_get_inventory(false) # returns non trimmed
|
265
|
+
inv = logged.raw_get_inventory(440) #works
|
266
|
+
inv = logged.raw_get_inventory(76561198044170935,false) #works
|
267
|
+
inv = logged.raw_get_inventory(76561198044170935,440) # works
|
268
|
+
|
269
|
+
print inv['assets'] #will print all the assets
|
270
|
+
print inv['descriptions'] #will print all the descriptions
|
271
|
+
|
272
|
+
### how to accurately use this
|
273
|
+
|
274
|
+
class_instance = {}
|
275
|
+
## map all the items
|
276
|
+
inv['descriptions'].each { |desc|
|
277
|
+
identifier = desc['classid'] + '_' + desc['instanceid']
|
278
|
+
class_instance[identifier] = desc
|
279
|
+
}
|
280
|
+
|
281
|
+
## identify your items
|
282
|
+
|
283
|
+
inv['assets'].each { |asset|
|
284
|
+
identifier = asset['classid'] + '_' + asset['instanceid']
|
285
|
+
puts class_instance[identifier] this will output the item's description
|
286
|
+
}
|
287
|
+
|
288
|
+
```
|
289
|
+
|
290
|
+
#### `set_inventory_cache()`
|
291
|
+
`set_inventory_cache()` is:
|
292
|
+
|
293
|
+
- a switch to locally save each inventory you get to a local file.
|
294
|
+
- disabled by default, you need to initiate it by calling the command
|
295
|
+
- accepts a parameter `timer` which defaults to `timer = 120`, this parameter is the difference between the save file was created and the moment it was checked (upong trying to retrieve the inventory).
|
296
|
+
|
297
|
+
- this switch is useful if you are getting a "static" inventory or testing your code.
|
298
|
+
```ruby
|
299
|
+
require 'steam-trade'
|
300
|
+
|
301
|
+
logged = Handler.new('username','password','shared_secret')
|
302
|
+
logged.mobile_info('identity_secret')
|
303
|
+
logged.set_inventory_cache(150)
|
304
|
+
|
305
|
+
|
306
|
+
partner_inventory = loggedlogged.normal_get_inventory('CardExchange') #this will save CardExchange's inventory to a local file and return the inventory
|
307
|
+
|
308
|
+
partner_inventory = loggedlogged.normal_get_inventory('CardExchange') # this will load the locally saved file
|
309
|
+
|
310
|
+
|
311
|
+
```
|
312
|
+
|
313
|
+
**IMPORTANT**: `normal_get_inventory()` will load the whole target inventory, for each **5k** of items, you are adding **~40MB** to your memory and of course will affect performance of the code and the computer
|
314
|
+
## Sending a trade offer
|
315
|
+
#### `send_offer(myarray,theirarray,trade_offer_link,message)`
|
316
|
+
**MUST be logged in to use this command**
|
317
|
+
then you can send your offer
|
318
|
+
- `myarray` is an array which contains hashes of selected items to send in the offer. (currently you must get this alone)
|
319
|
+
- `Theirarray` is an array which contains hashes of selected items to receive in the offer. (currently you must get this alone)
|
320
|
+
- `trade_offer_link` can be the trade link of you partner `ex: https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt`
|
321
|
+
- `trade_offer_link` can be a steamID, however using a steamID requires you and your partner to be friends on steam
|
322
|
+
- `trade_offer_link` can be a profileID, however using a profileID requires you and your partner to be friends on steam
|
323
|
+
- `message` is the comment you want to include in the trade offer
|
324
|
+
|
325
|
+
- `myarray`, `theirarray`, `trade_offer_link` are required, `message` is optional
|
326
|
+
```ruby
|
327
|
+
require 'steam-trade'
|
328
|
+
|
329
|
+
account = Handler.new('username','password','shared_secret')
|
330
|
+
account.mobile_info('identity_secret')
|
331
|
+
|
332
|
+
me = account.normal_get_inventory()
|
333
|
+
his = account.normal_get_inventory("nomg3r")
|
334
|
+
|
335
|
+
myarray = [me[5] , me[20] , me[60]].compact!
|
336
|
+
theirarray = [his[1], his[20], his[30]].compact!
|
337
|
+
|
338
|
+
# if you are friends
|
339
|
+
account.send_offer(myarray,theirarray,"nomg3r",message)
|
340
|
+
#or (as friends)
|
341
|
+
account.send_offer(myarray,theirarray,'76561198370420964',message)
|
342
|
+
|
343
|
+
# whenever
|
344
|
+
account.send_offer(myarray,theirarray,"https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt",message)
|
345
|
+
|
346
|
+
```
|
347
|
+
## Handling Trade Offers
|
348
|
+
you might want to read [Steam Trading API](https://developer.valvesoftware.com/wiki/Steam_Web_API/IEconService)
|
349
|
+
|
350
|
+
**ALL OF THE COMMANDS BELOW REQUIRE AN API_KEY**
|
351
|
+
|
352
|
+
#### `set_api_key(API_KEY)`
|
353
|
+
**NOTE**:If you are using a **logged in** Handler there is no need to set the API_KEY.
|
354
|
+
- `API_KEY` is your apikey, you can get that from [here](https://steamcommunity.com/dev/apikey).
|
355
|
+
```ruby
|
356
|
+
require 'steam-trade'
|
357
|
+
acc = Handler.new()
|
358
|
+
trade_offers = acc.get_trade_offers() # will raise an exception
|
359
|
+
acc.set_api_key('mykey')
|
360
|
+
trade_offers = acc.get_trade_offers() # after setting an API_KEY this will succeed
|
361
|
+
```
|
362
|
+
#### `get_trade_offers(time)`
|
363
|
+
- `time` is the moment from which you want to get updates (explained in the example)
|
364
|
+
this will return a hash with `trade_offers_sent`, `trade_offers_received`, `descriptions` as keys.
|
365
|
+
`descriptions` includes the descriptions of all items returned from `trade_offers_sent` or `trade_offers_received`
|
366
|
+
|
367
|
+
```ruby
|
368
|
+
require 'steam-trade'
|
369
|
+
logged = Handler.new('username','password','shared_secret')
|
370
|
+
logged.mobile_info('identity_secret')
|
371
|
+
|
372
|
+
time = '' # this is the initial check for offers so we want them all
|
373
|
+
polling = Thread.new(logged) { |logged|
|
374
|
+
loop do
|
375
|
+
offers = logged.get_trade_offers(time)
|
376
|
+
time = Time.new.to_i # we save the time of the last check
|
377
|
+
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
378
|
+
puts offers['trade_offers_received'] # puts the trades
|
379
|
+
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
380
|
+
end
|
381
|
+
}
|
382
|
+
```
|
383
|
+
#### `get_trade_offer(trade_offer_id)`
|
384
|
+
gets more information about a specific trade offer
|
385
|
+
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
386
|
+
|
387
|
+
have no example how to actually use this cause `get_trade_offers(time)` is probably better
|
388
|
+
|
389
|
+
#### `accept_trade_offer(trade_offer_id)`
|
390
|
+
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
391
|
+
```ruby
|
392
|
+
require 'steam-trade'
|
393
|
+
logged = Handler.new('username','password','shared_secret')
|
394
|
+
logged.mobile_info('identity_secret')
|
395
|
+
|
396
|
+
time = '' # this is the initial check for offers so we want them all
|
397
|
+
polling = Thread.new(logged) { |logged|
|
398
|
+
loop do
|
399
|
+
offers = logged.get_trade_offers(time)
|
400
|
+
time = Time.new.to_i # we save the time of the last check
|
401
|
+
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
402
|
+
offers['trade_offers_received'].each { |trade|
|
403
|
+
if trade['accountid_other'].to_i == 83905207 ## this will accept all trade received from 83905207 (Steam32 ID)
|
404
|
+
logged.accept_trade_offer(trade['tradeofferid']) # to accept the trade
|
405
|
+
end
|
406
|
+
}
|
407
|
+
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
408
|
+
end
|
409
|
+
}
|
410
|
+
```
|
411
|
+
#### `decline_trade_offer(trade_offer_id)`
|
412
|
+
this declines a trade offer you **RECEIVED**
|
413
|
+
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
414
|
+
|
415
|
+
```ruby
|
416
|
+
require 'steam-trade'
|
417
|
+
logged = Handler.new('username','password','shared_secret')
|
418
|
+
logged.mobile_info('identity_secret')
|
419
|
+
|
420
|
+
time = '' # this is the initial check for offers so we want them all
|
421
|
+
polling = Thread.new(logged) { |logged|
|
422
|
+
loop do
|
423
|
+
offers = logged.get_trade_offers(time)
|
424
|
+
time = Time.new.to_i # we save the time of the last check
|
425
|
+
next if offers['trade_offers_received'] == nil # do nothing, if there is no trades
|
426
|
+
offers['trade_offers_received'].each { |trade| # we need to check received offers to use 'decline'
|
427
|
+
if trade['accountid_other'].to_i != 83905207 ## notice the '!='
|
428
|
+
logged.decline_trade_offer(trade['tradeofferid']) # decline the trade
|
429
|
+
end
|
430
|
+
}
|
431
|
+
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
432
|
+
end
|
433
|
+
}
|
434
|
+
```
|
435
|
+
#### `cancel_trade_offer(trade_offer_id)`
|
436
|
+
this cancels a trade offer you **SENT**
|
437
|
+
- `trade_offer_id` is the id of the offer you want to confirm (you can get the id using [this](#get_trade_offerstime) to get the offerID
|
438
|
+
```ruby
|
439
|
+
require 'steam-trade'
|
440
|
+
logged = Handler.new('username','password','shared_secret')
|
441
|
+
logged.mobile_info('identity_secret')
|
442
|
+
|
443
|
+
time = '' # this is the initial check for offers so we want them all
|
444
|
+
polling = Thread.new(logged) { |logged|
|
445
|
+
loop do
|
446
|
+
offers = logged.get_trade_offers(time)
|
447
|
+
time = Time.new.to_i # we save the time of the last check
|
448
|
+
next if offers['trade_offers_sent'] == nil # do nothing, if there is no trades
|
449
|
+
offers['trade_offers_sent'].each { |trade| # we need to check sentoffers to use 'cancel'
|
450
|
+
if trade['accountid_other'].to_i != 83905207 ## notice the '!='
|
451
|
+
logged.cancel_trade_offer(trade['tradeofferid']) # cancel the trade
|
452
|
+
end
|
453
|
+
}
|
454
|
+
sleep(15) # make sure not to spam steam's server or they will block list your IP for a period of time therefore you can't make requests
|
455
|
+
end
|
456
|
+
}
|
457
|
+
```
|
458
|
+
## Counting badges owned
|
459
|
+
#### `sets_count(target,non_marketable)`
|
460
|
+
**this command does not count foil badges (only normal trading cards)**
|
461
|
+
- `target` can be a steamID, a profileID or a trade link
|
462
|
+
- `non_marketable` this is a switch to count **non**-marketable trading cards(defaults to **true** if not specified)
|
463
|
+
- a .txt will be created from this command to read the badges
|
464
|
+
- this returns a hash `{'sets' => appsets, 'appxsets' => setsowned, 'totalsets' => numberofsets, 'totalcards' => total_non_foil, 'marketable' => true}`
|
465
|
+
- `'sets'` is a hash with game appids as keys and each card and number of copies owned of each card `{'appid1' => {'card1' => 5,'card2' => 3, ... 'cardN' => Z},{'appid1' => {'card1' => 0,'card2' => 2, ... 'cardN' => K} }`
|
466
|
+
- `'appxsets'` is a hash containing the number of sets available of each set `{'appid1' => 5,'appid2' => 20,...'appidN' => Z}`
|
467
|
+
- `'totalsets'` is an integer equals to the number of sets owned
|
468
|
+
- `'totalcards'` is an integer equals to the number of non-foil cards account for
|
469
|
+
```ruby
|
470
|
+
require 'steam-trade'
|
471
|
+
data = Handler.sets_count("CardExchange")
|
472
|
+
|
473
|
+
|
474
|
+
logged = Handler.new('username','password','shared_secret')
|
475
|
+
logged.mobile_info('identity_secret')
|
476
|
+
#with login
|
477
|
+
logged = account.sets_count()
|
478
|
+
logged = account.sets_count(false)
|
479
|
+
hash = account.sets_count('CardExchange',false)
|
480
|
+
hash = account.sets_count(76561198370420964)
|
481
|
+
hash = account.sets_count('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt',false)
|
482
|
+
|
483
|
+
|
484
|
+
#without login
|
485
|
+
nonlogged = Handler.new()
|
486
|
+
logged = account.sets_count() #raise exception
|
487
|
+
logged = account.sets_count(false) # raise exception
|
488
|
+
hash = account.sets_count('CardExchange')
|
489
|
+
hash = account.sets_count(76561198370420964)
|
490
|
+
hash = account.sets_count('https://steamcommunity.com/tradeoffer/new/?partner=410155236&token=H-yK-GFt',false)
|
491
|
+
|
492
|
+
```
|
493
|
+
|
494
|
+
#### `update_blueprint()`
|
495
|
+
- updates your locally saved badges blueprint
|
496
|
+
```ruby
|
497
|
+
require 'steam-trade'
|
498
|
+
|
499
|
+
handler = Handler.new
|
500
|
+
|
501
|
+
handler.update_blueprint()
|
502
|
+
```
|
503
|
+
## 2FA codes
|
504
|
+
#### `fa(shared_secret, time_difference)`
|
505
|
+
- `shared_secret` is the account's shared secret (if you don't know what is this try googling 'steam shared_secret'), defaults to the logged in account's steamid if logged in.
|
506
|
+
- `time_difference` is the difference between your pc's time and steam's time (**this MUST BE an integer**)
|
507
|
+
**NOTE**: using this command with a new shared_secret will not change/set the current saved shared_secret for the account
|
508
|
+
```ruby
|
509
|
+
require 'steam-trade'
|
510
|
+
puts Hander.fa('random_shared_secret')
|
511
|
+
|
512
|
+
|
513
|
+
logged = Handler.new('username','password','inital_shared_secret')
|
514
|
+
puts logged.fa() #=> random code for your account
|
515
|
+
puts logged.fa('new_shared_secret') # => this will give you a random code for another account, AND will not edit your initial_shared_secret
|
516
|
+
|
517
|
+
####
|
518
|
+
logged_without_shared_secret = Handler.new('username','password') # this is possible of course
|
519
|
+
puts logged_without_shared_secret.fa() # this will not work
|
520
|
+
puts logged_without_shared_secret.fa('shared_secret') ## will give a random code
|
521
|
+
###
|
522
|
+
nonlogged = Handler.new()
|
523
|
+
puts nonlogged.fa() # will not work
|
524
|
+
puts logged.fa() # will give a random code
|
525
|
+
|
526
|
+
```
|
527
|
+
## Social Commands
|
528
|
+
#### `mobile_login('username','password','shared_secret')`
|
529
|
+
- this command will be called automatically if you attempt to use `send_message()` or `poll_messages()` without authentication
|
530
|
+
- calling this explicitly allows you to painlessly retrieve the OAuth token and `SteamMachine#{steamid}` cookie to use in `oauth_login()`
|
531
|
+
- this function returns a hash with `oauth_token` and `machine` as keys
|
532
|
+
```ruby
|
533
|
+
require 'steam-trade'
|
534
|
+
|
535
|
+
h = Handler.new('user','pass','secret')
|
536
|
+
data = h.mobile_login() #this works are you have setted username and password
|
537
|
+
puts data ## will output with oauth token and steamMachine cookie
|
538
|
+
|
539
|
+
###################
|
540
|
+
h = Handler.new()
|
541
|
+
data = h.mobile_login() # will raise an error cause there is no username or password
|
542
|
+
|
543
|
+
##########
|
544
|
+
|
545
|
+
h = Handler.new()
|
546
|
+
data = h.mobile_login('user','pass','secret') ## will work, you are not logged in ( talking about community) here you can't use most of the commands (send_offer() etc) and those parameters you passed will not be setted as the Handler's
|
547
|
+
|
548
|
+
######
|
549
|
+
h = Handler.new('user1','pass1','secret1')
|
550
|
+
data = mobile_login('user2','pass2','secret2') # this works but trading commands etc will be called using user1, and chat commands will be called using user2
|
551
|
+
```
|
552
|
+
#### `oauth_login(oauth_token,SteamMachine)`
|
553
|
+
- `oauth_token` and `SteamMachine` can be retrieved from `mobile_login()`
|
554
|
+
```ruby
|
555
|
+
require 'steam-trade'
|
556
|
+
h = Handler.new()
|
557
|
+
h.oauth_login('oauth_token','SteamMachine')
|
558
|
+
```
|
559
|
+
#### `send_message(target, message)`
|
560
|
+
sends a message to the target
|
561
|
+
- `target` can be a steamID64, tradelink, or profileID
|
562
|
+
- `message` the message to send
|
563
|
+
```ruby
|
564
|
+
require 'steam-trade'
|
565
|
+
|
566
|
+
h = Handler.new('username', 'password')
|
567
|
+
h.send_message('nomg3r', "Hello, Friend")
|
568
|
+
```
|
569
|
+
|
570
|
+
#### `poll_messages()`
|
571
|
+
gives you the messages you receieved (after mobile login is initiated (after you call send_message() or poll_messages() ) )
|
572
|
+
|
573
|
+
```ruby
|
574
|
+
require 'steam-trade'
|
575
|
+
|
576
|
+
h = Handler.new('username', 'password')
|
577
|
+
print h.poll_messages() # will not return messages so you call at again ( only the first time in the whole program )
|
578
|
+
puts ""
|
579
|
+
puts "------"
|
580
|
+
sleep(10) #send a message to the logged in account
|
581
|
+
print h.poll_messages() # actually have messages ( if you received some in the time between the first and the second request )
|
582
|
+
```
|
583
|
+
**ALL OF THE COMMANDS BELOW REQUIRES LOGIN**
|
584
|
+
#### `send_friend_request(target)`
|
585
|
+
sends a friend request to the target
|
586
|
+
- `target` can be a steamID64, tradelink, or profileID
|
587
|
+
|
588
|
+
```ruby
|
589
|
+
require 'steam-trade'
|
590
|
+
|
591
|
+
h = Handler.new('username', 'password')
|
592
|
+
h.send_friend_request('nomg3r')
|
593
|
+
```
|
594
|
+
|
595
|
+
#### `accept_friend_request(target)`
|
596
|
+
accepts a friend request from the target
|
597
|
+
- `target` can be a steamID64, tradelink, or profileID
|
598
|
+
|
599
|
+
```ruby
|
600
|
+
require 'steam-trade'
|
601
|
+
|
602
|
+
h = Handler.new('username', 'password')
|
603
|
+
h.accept_friend_request('nomg3r')
|
604
|
+
```
|
605
|
+
|
606
|
+
### `remove_friend(target)`
|
607
|
+
removes a friend
|
608
|
+
- `target` can be a steamID64, tradelink, or profileID
|
609
|
+
|
610
|
+
```ruby
|
611
|
+
require 'steam-trade'
|
612
|
+
|
613
|
+
h = Handler.new('username', 'password')
|
614
|
+
h.remove_friend('nomg3r')
|
615
|
+
```
|
616
|
+
|
617
|
+
## More commands
|
618
|
+
you can find more non-vital commands in the [wiki](https://github.com/OmG3r/steam-trade/wiki)
|
619
|
+
## License
|
620
|
+
|
621
|
+
The gem is available as open source under the terms of the [GNU GPLV3](https://github.com/OmG3r/steam-trade/blob/master/LICENSE).
|