Compare commits

...

513 Commits

Author SHA1 Message Date
Łukasz Domeradzki
2f09e74f1a Update prometheus exporter to fixed version
Apparently all of our issues should be resolved by now
2024-07-07 04:52:10 +02:00
ArchiBot
f30fcb3941 Automatic translations update 2024-07-07 02:14:46 +00:00
renovate[bot]
06254a9afc chore(deps): update dependency jetbrains.annotations to v2024 (#3243)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-07-06 23:29:44 +02:00
renovate[bot]
fd95c6cac7 chore(deps): update asf-ui digest to cd60876 2024-07-06 03:38:32 +00:00
ArchiBot
2196bccda5 Automatic translations update 2024-07-06 02:08:42 +00:00
renovate[bot]
b0ac2b4147 chore(deps): update actions/upload-artifact action to v4.3.4 2024-07-05 18:17:25 +00:00
renovate[bot]
5322321944 chore(deps): update actions/download-artifact action to v4.1.8 2024-07-05 16:24:38 +00:00
renovate[bot]
2f951e0ef6 chore(deps): update wiki digest to 743294a 2024-07-05 14:26:37 +00:00
renovate[bot]
1e6dcc88d2 chore(deps): update docker/setup-buildx-action action to v3.4.0 2024-07-04 11:47:22 +00:00
ArchiBot
8bbcfc40dc Automatic translations update 2024-07-04 02:10:45 +00:00
Łukasz Domeradzki
811ea46523 Remove deprecated functionality, bump 2024-07-04 01:33:45 +02:00
renovate[bot]
c37e54cf9b chore(deps): update jetbrains/qodana-action action to v2024.1.8 2024-07-03 16:30:15 +00:00
renovate[bot]
4c095e8eb5 chore(deps): update docker/build-push-action action to v6.3.0 2024-07-03 09:04:29 +00:00
ArchiBot
c580ec7b92 Automatic translations update 2024-07-03 02:09:58 +00:00
renovate[bot]
0c45d3c5ba chore(deps): update asf-ui digest to 6a4b92a 2024-07-02 21:48:17 +00:00
ArchiBot
2bc8a4cefd Automatic translations update 2024-07-02 02:10:59 +00:00
ArchiBot
92d28adb07 Automatic translations update 2024-06-30 02:14:26 +00:00
renovate[bot]
cc2b1dbbaa chore(deps): update asf-ui digest to 91c39f3 2024-06-29 03:30:07 +00:00
ArchiBot
bd98cadab3 Automatic translations update 2024-06-29 02:08:57 +00:00
renovate[bot]
c417f88e3b chore(deps): update github/codeql-action action to v3.25.11 2024-06-28 19:30:05 +00:00
renovate[bot]
b26a9af49b chore(deps): update docker/build-push-action action to v6.2.0 2024-06-26 15:51:30 +00:00
Łukasz Domeradzki
e4b00b35f2 Bump 2024-06-26 17:50:58 +02:00
Łukasz Domeradzki
11bab46b8b Add deprecation helper 2024-06-26 13:53:48 +02:00
ArchiBot
7eb24d7bd6 Automatic translations update 2024-06-25 02:10:23 +00:00
Łukasz Domeradzki
9a26366ff8 Misc 2024-06-25 00:34:13 +02:00
Łukasz Domeradzki
0058bc6fa5 Move dockerfiles from legacy KV format
https://docs.docker.com/reference/build-checks/legacy-key-value-format/
2024-06-25 00:32:15 +02:00
Łukasz Domeradzki
ca3f3e0cab Resolve selected .NET 9 analyzer warnings 2024-06-25 00:18:38 +02:00
ArchiBot
cf51ca454d Automatic translations update 2024-06-24 02:11:32 +00:00
ArchiBot
35c3c2a2b3 Automatic translations update 2024-06-23 02:12:06 +00:00
renovate[bot]
12bb61c23d chore(deps): update docker/build-push-action action to v6.1.0 2024-06-21 09:36:21 +00:00
ArchiBot
2e5a2a1393 Automatic translations update 2024-06-21 02:09:19 +00:00
Łukasz Domeradzki
4259bb088e Bump 2024-06-21 02:36:20 +02:00
Jack Nolddor
0768765f21 chore: blacklist summer sale 2024 appid (#3226)
refers to https://steamcommunity.com/my/gamecards/2861690
2024-06-21 00:22:06 +02:00
renovate[bot]
dc7ee7fadc Update docker/build-push-action action to v6.0.2 2024-06-20 15:04:34 +00:00
Łukasz Domeradzki
7665a1c339 Bump 2024-06-20 12:44:15 +02:00
renovate[bot]
6015cd5cb7 Update dependency Microsoft.IdentityModel.JsonWebTokens to v7.6.2 2024-06-20 08:03:03 +00:00
renovate[bot]
08aa8f2136 Update ASF-ui digest to 3ae4df4 2024-06-20 04:09:34 +00:00
ArchiBot
c27e447f57 Automatic translations update 2024-06-20 02:08:54 +00:00
Łukasz Domeradzki
9f1a3a0304 Add support for selected bot groups 2024-06-19 23:46:03 +02:00
renovate[bot]
7714478fdc Update docker/build-push-action action to v6.0.1 2024-06-18 16:00:11 +00:00
renovate[bot]
91bca33a54 Update dependency OpenTelemetry.Instrumentation.Runtime to v1.9.0 2024-06-18 11:13:05 +00:00
renovate[bot]
c67b967817 Update ASF-ui digest to 1c49bcf 2024-06-18 07:00:45 +00:00
renovate[bot]
150ed2c733 Update dependency Microsoft.IdentityModel.JsonWebTokens to v7.6.1 2024-06-18 04:30:51 +00:00
renovate[bot]
1c23e4b5b3 Update opentelemetry-dotnet-contrib monorepo to v1.9.0 2024-06-18 01:47:02 +00:00
renovate[bot]
77c4dee6a8 Update actions/attest-build-provenance action to v1.3.2 2024-06-17 18:19:05 +00:00
renovate[bot]
d6fe8eec38 Update docker/build-push-action action to v6 (#3222)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-06-17 12:18:15 +02:00
Łukasz Domeradzki
c12d83bbf0 Bump 2024-06-17 09:22:34 +02:00
Łukasz Domeradzki
0e6b75aa5c Update IBotTradeOffer2.cs 2024-06-17 09:19:54 +02:00
Łukasz Domeradzki
dd1dfdcf34 Closes #3221 2024-06-17 09:17:14 +02:00
ArchiBot
792d8dab34 Automatic translations update 2024-06-16 02:13:31 +00:00
Łukasz Domeradzki
4f23434f81 Update renovate.json5 2024-06-15 21:54:23 +02:00
renovate[bot]
7797c4e0b0 Update dependency OpenTelemetry.Extensions.Hosting to v1.9.0 2024-06-14 21:20:44 +00:00
renovate[bot]
6463a2be2d Update actions/attest-build-provenance action to v1.3.1 2024-06-13 22:55:17 +00:00
renovate[bot]
972a46ac2e Update github/codeql-action action to v3.25.10 2024-06-13 16:58:07 +00:00
renovate[bot]
db3091b21b Update ASF-ui digest to 51952a3 2024-06-13 01:16:01 +00:00
renovate[bot]
476733ca19 Update github/codeql-action action to v3.25.9 2024-06-12 22:57:22 +00:00
renovate[bot]
d0c302c1f1 Update actions/checkout action to v4.1.7 2024-06-12 20:57:14 +00:00
renovate[bot]
164deb1096 Update ASF-ui digest to 7efd77d 2024-06-12 06:22:34 +00:00
ArchiBot
b39ea679e7 Automatic translations update 2024-06-12 02:09:52 +00:00
renovate[bot]
062a5f470c Update ASF-ui digest to 185cc47 2024-06-11 22:28:20 +00:00
Łukasz Domeradzki
48fb388da2 Make PICS changes happen a bit more often 2024-06-11 10:11:15 +02:00
ArchiBot
a23cdc9605 Automatic translations update 2024-06-11 02:09:42 +00:00
renovate[bot]
1c7eb0f5a1 Update docker/build-push-action action to v5.4.0 2024-06-10 11:56:11 +00:00
Łukasz Domeradzki
58050c9ec3 CI: Fix failure when in PR mode 2024-06-10 13:55:47 +02:00
ArchiBot
5908cc40a8 Automatic translations update 2024-06-09 02:13:14 +00:00
Łukasz Domeradzki
bffb5e53bf Bump 2024-06-08 00:08:14 +02:00
Łukasz Domeradzki
4a0b79f1a1 Misc
Paused could be flipped in the meantime between starting the background check and finishing it, we can check it again after having games to farm.
2024-06-08 00:07:11 +02:00
renovate[bot]
3ddb77e9f8 Update ASF-ui digest to c5a2ac4 2024-06-07 11:09:07 +00:00
renovate[bot]
16f7bccb11 Update dependency Humanizer to v3.0.0-beta.54 2024-06-06 19:53:34 +00:00
ArchiBot
ecec5cdde2 Automatic translations update 2024-06-06 02:08:48 +00:00
renovate[bot]
cf4fca9836 Update ASF-ui digest to 1e68294 2024-06-05 16:44:47 +00:00
ArchiBot
e5d61b2796 Automatic translations update 2024-06-05 02:08:55 +00:00
renovate[bot]
fc493ea510 Update github/codeql-action action to v3.25.8 2024-06-04 17:07:49 +00:00
ArchiBot
7983dc01f1 Automatic translations update 2024-06-04 02:09:03 +00:00
renovate[bot]
09f914cecd Update actions/attest-build-provenance action to v1.2.0 2024-06-03 18:21:05 +00:00
renovate[bot]
9968b0ac36 Update wiki digest to f05654b 2024-06-03 10:46:12 +00:00
ArchiBot
969a5f711c Automatic translations update 2024-06-03 02:09:44 +00:00
Łukasz Domeradzki
ccb4601c85 Bump 2024-06-03 00:19:16 +02:00
Łukasz Domeradzki
25aabe7553 Use native Rfc2898DeriveBytes for Pbkdf2 instead of CryptSharp implementation
I've verified it generates the same results
2024-06-02 21:54:45 +02:00
Łukasz Domeradzki
13755d4d06 Make ASF compatible with global invariant mode
Requires Humanizer update
2024-06-02 21:33:44 +02:00
Łukasz Domeradzki
1d6e87d103 Bump 2024-05-31 23:22:59 +02:00
Łukasz Domeradzki
8673ef8420 Closes #3210 2024-05-31 23:21:33 +02:00
renovate[bot]
ab1fb70f4c Update github/codeql-action action to v3.25.7 2024-05-31 11:07:58 +00:00
renovate[bot]
31fe6923ff Update ASF-ui digest to 7818887 2024-05-31 03:38:49 +00:00
renovate[bot]
0b07b7c4a7 Update ASF-ui digest to 605cbf7 2024-05-30 19:23:31 +00:00
renovate[bot]
0abe05b7bd Update dependency MSTest to v3.4.3 2024-05-30 15:29:53 +00:00
renovate[bot]
45ff19f9ae Update dependency MSTest to v3.4.2 2024-05-30 11:07:17 +00:00
renovate[bot]
d25883ff1b Update ASF-ui digest to a72c668 2024-05-29 12:29:08 +00:00
Łukasz Domeradzki
d2f43e4e50 CI: Misc 2024-05-29 14:28:18 +02:00
Łukasz Domeradzki
792167a71c CI: Misc 2024-05-29 11:21:39 +02:00
renovate[bot]
f2586d7cb0 Update crowdin/github-action action to v2 (#3209)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-05-29 11:21:17 +02:00
Łukasz Domeradzki
c37846b4cd Bump 2024-05-28 22:50:04 +02:00
Łukasz Domeradzki
17c4ec6790 Fix observable counters 2024-05-28 21:38:56 +02:00
Łukasz Domeradzki
7023040882 Add initial support for build attestations 2024-05-28 19:34:47 +02:00
Łukasz Domeradzki
8c38de1b26 Downgrade prometheus exporter again 2024-05-28 19:10:34 +02:00
Łukasz Domeradzki
1917c9da95 Misc 2024-05-28 19:07:48 +02:00
Sebastian Göls
668bf5009b Monitor incoming trades (#3201)
* Monitor incoming trades

* Apply feedback

* Misc.
2024-05-28 19:03:52 +02:00
renovate[bot]
e9ca1e3537 Update docker/login-action action to v3.2.0 2024-05-28 09:56:27 +00:00
renovate[bot]
ebdb412adf Update dependency Microsoft.IdentityModel.JsonWebTokens to v7.6.0 2024-05-28 02:07:48 +00:00
renovate[bot]
e73c72d148 Update dependency MSTest to v3.4.1 2024-05-27 17:05:17 +00:00
ArchiBot
d1d843c583 Automatic translations update 2024-05-27 02:08:42 +00:00
renovate[bot]
464e375529 Update ASF-ui digest to 8e361ae 2024-05-26 01:02:04 +00:00
Łukasz Domeradzki
2b12f8a294 Update donation options 2024-05-26 01:19:53 +02:00
renovate[bot]
b305e98519 Update ASF-ui digest to 491227c 2024-05-24 16:36:11 +00:00
renovate[bot]
5431e49c2a Update ASF-ui digest to b1521b7 2024-05-23 22:01:31 +00:00
Łukasz Domeradzki
6098cdc31d Bump 2024-05-23 20:10:29 +02:00
Łukasz Domeradzki
308d7c2c1c Merge branch 'main' of https://github.com/JustArchiNET/ArchiSteamFarm 2024-05-23 20:06:11 +02:00
Łukasz Domeradzki
454f40ffb9 CI: Divide environments further 2024-05-23 20:06:09 +02:00
renovate[bot]
dd3b3dec33 Update ASF-ui digest to 63254c3 2024-05-23 13:49:00 +00:00
renovate[bot]
bc2831c066 Update dependency MSTest to v3.4.0 2024-05-23 10:20:09 +00:00
renovate[bot]
905d2acdbd Update swashbuckle-aspnetcore monorepo to v6.6.2 2024-05-22 12:27:49 +00:00
renovate[bot]
54c2b6b6d5 Update github/codeql-action action to v3.25.6 2024-05-22 05:05:58 +00:00
ArchiBot
b6a4ccac7f Automatic translations update 2024-05-22 02:08:08 +00:00
Łukasz Domeradzki
3fce1cc934 Monitoring: Bump OpenTelemetry dependencies, since the upstream issue is fixed 2024-05-21 22:57:13 +02:00
Łukasz Domeradzki
375a888a37 CI: Run first part of publish in test environment 2024-05-21 22:25:29 +02:00
Łukasz Domeradzki
0d62034f32 CI: Run qodana in different environment 2024-05-21 22:21:47 +02:00
Łukasz Domeradzki
f7d722aaf0 CI: Switch to using environment variables 2024-05-21 22:18:55 +02:00
Łukasz Domeradzki
56759bc710 Make some inventory description properties public 2024-05-21 12:12:31 +02:00
renovate[bot]
d27b5c28ef chore(deps): update asf-ui digest to fe1f167 2024-05-20 19:33:05 +00:00
renovate[bot]
a0d1cada54 chore(deps): update asf-ui digest to 2b02ee9 2024-05-20 00:29:51 +00:00
Łukasz Domeradzki
ca7e1da585 CI: Misc 2024-05-20 02:29:23 +02:00
Łukasz Domeradzki
5f097c4002 CI: Split crowdin to standalone action 2024-05-20 02:25:35 +02:00
Łukasz Domeradzki
203dc6daf6 Misc 2024-05-19 21:36:37 +02:00
Łukasz Domeradzki
e895850f17 Misc 2024-05-19 21:35:20 +02:00
Łukasz Domeradzki
f776e7947c Misc corrections of ASF API structures 2024-05-19 20:07:52 +02:00
Łukasz Domeradzki
416ec920cb Add AddLicense to ASF API 2024-05-19 20:07:41 +02:00
renovate[bot]
b5da72eb40 chore(deps): update asf-ui digest to a885733 2024-05-18 05:56:09 +00:00
ArchiBot
3dde77608e Automatic translations update 2024-05-18 02:07:36 +00:00
renovate[bot]
a0407553ec chore(deps): update jetbrains/qodana-action action to v2024.1.5 (#3207)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-05-18 03:37:15 +02:00
renovate[bot]
8d594fe0b6 chore(deps): update crowdin/github-action action to v1.20.4 2024-05-17 09:18:01 +00:00
renovate[bot]
e68e87d388 chore(deps): update actions/checkout action to v4.1.6 2024-05-17 02:23:30 +00:00
ArchiBot
4cabd42c0b Automatic translations update 2024-05-17 02:07:31 +00:00
ArchiBot
df33f7d0fc Automatic translations update 2024-05-16 02:07:07 +00:00
Łukasz Domeradzki
d6b5e3981c Misc swagger UI enhancements 2024-05-15 15:59:09 +02:00
ArchiBot
6aa0300c85 Automatic translations update 2024-05-15 02:09:46 +00:00
renovate[bot]
264ca84513 chore(deps): update swashbuckle-aspnetcore monorepo to v6.6.1 2024-05-14 12:02:17 +00:00
Łukasz Domeradzki
816306872d Misc 2024-05-14 13:14:14 +02:00
renovate[bot]
13aced705a chore(deps): update github/codeql-action action to v3.25.5 2024-05-14 05:03:02 +00:00
ArchiBot
95d0f879ca Automatic translations update 2024-05-14 02:07:17 +00:00
renovate[bot]
f37d2297bb chore(deps): update dependency microsoft.identitymodel.jsonwebtokens to v7.5.2 2024-05-13 22:47:12 +00:00
renovate[bot]
0d90a53b8e chore(deps): update wiki digest to fa6284b 2024-05-13 16:10:04 +00:00
Łukasz Domeradzki
f91dfe7efa Misc optimization 2024-05-13 17:01:33 +02:00
Łukasz Domeradzki
ec757e3ef8 Bump 2024-05-13 09:53:14 +02:00
Łukasz Domeradzki
3b2ca10b05 Closes #3203
When excessive amount of "missing amounts", so items in the set was missing on our side, there was a possibility for our logic to classify a good trade as bad one, because we didn't fill in enough holes, as the subtraction in the condition was calculated on each loop rather than once initially.

Since this could only worsen the neutrality score, but never improve it (as the amounts were sorted ascending), there was no abusive possibility due to that, only ignoring otherwise valid trades classifying them as worse than they were in reality.
2024-05-13 09:29:30 +02:00
ArchiBot
b438e38268 Automatic translations update 2024-05-12 02:08:51 +00:00
renovate[bot]
bb405f2824 chore(deps): update asf-ui digest to eae2d67 2024-05-11 08:24:00 +00:00
ArchiBot
1d640fbec0 Automatic translations update 2024-05-11 02:06:27 +00:00
renovate[bot]
ecc820333e chore(deps): update asf-ui digest to f09861b 2024-05-10 18:35:22 +00:00
Łukasz Domeradzki
9cc227aa61 Misc 2024-05-10 19:40:46 +02:00
Łukasz Domeradzki
93420eebc0 Misc 2024-05-10 19:40:02 +02:00
Łukasz Domeradzki
6014b3bdc6 Add missing LicenseID inheritance from current 2024-05-10 13:27:49 +02:00
Sebastian Göls
81789c717f Misc. security improvements (#3200)
* Add x-security-critical to swagger schema and do not serialize LicenseID on IPC

* Apply feedback

* Misc.
2024-05-10 13:22:26 +02:00
renovate[bot]
dfa6330821 chore(deps): update crowdin/github-action action to v1.20.3 2024-05-10 07:54:33 +00:00
renovate[bot]
1d5d9c12a7 chore(deps): update actions/checkout action to v4.1.5 2024-05-08 23:34:56 +00:00
renovate[bot]
2cbbbe7359 chore(deps): update github/codeql-action action to v3.25.4 2024-05-08 14:36:22 +00:00
renovate[bot]
4706cedbf9 chore(deps): update jetbrains/qodana-action action to v2024.1.4 2024-05-07 21:52:16 +00:00
renovate[bot]
a11b955a9d chore(deps): update dependency nlog.web.aspnetcore to v5.3.11 2024-05-07 20:25:51 +00:00
renovate[bot]
e1366f6267 chore(deps): update asf-ui digest to 34bbcc9 2024-05-07 11:50:49 +00:00
ArchiBot
6bff839821 Automatic translations update 2024-05-07 02:08:46 +00:00
renovate[bot]
0b37acf16e chore(deps): update asf-ui digest to 073867b 2024-05-05 03:11:22 +00:00
ArchiBot
70c39eef0a Automatic translations update 2024-05-05 02:07:59 +00:00
ArchiBot
1988b18053 Automatic translations update 2024-05-04 02:06:04 +00:00
renovate[bot]
67f87396e8 chore(deps): update wiki digest to 4029f5f 2024-05-03 16:17:08 +00:00
Łukasz Domeradzki
3734721c58 Bump 2024-05-03 15:52:00 +02:00
Łukasz Domeradzki
0f6a3f2ec8 Misc 2024-05-03 15:18:17 +02:00
Łukasz Domeradzki
ab9ca4b9c3 Bump 2024-05-03 13:52:55 +02:00
ArchiBot
c05cffbd88 Automatic translations update 2024-05-03 02:07:39 +00:00
renovate[bot]
0e3f3d1143 chore(deps): update jetbrains/qodana-action action to v2024.1.3 2024-05-02 19:55:25 +00:00
Łukasz Domeradzki
ff02a4a8d4 Remove zxcvbn dependency
Pushing external lib purely to save user's from eventual stupidity is just simply not worth the bytes in the final zip archive.
2024-05-02 21:54:54 +02:00
renovate[bot]
c8c35b5bf7 chore(deps): update asf-ui digest to f537840 2024-05-01 09:33:49 +00:00
renovate[bot]
18daa6a8c7 chore(deps): update dependency nlog.web.aspnetcore to v5.3.10 2024-04-30 23:00:34 +00:00
renovate[bot]
c95b58852c chore(deps): update asf-ui digest to d857ce5 2024-04-30 02:25:57 +00:00
ArchiBot
80ccceb9b0 Automatic translations update 2024-04-29 02:06:57 +00:00
renovate[bot]
eaa308d3ce chore(deps): update asf-ui digest to 491c89d 2024-04-28 03:10:41 +00:00
ArchiBot
d05ac7e10d Automatic translations update 2024-04-28 02:08:21 +00:00
renovate[bot]
a80aef16a0 chore(deps): update dependency nlog.web.aspnetcore to v5.3.9 2024-04-27 19:55:05 +00:00
ArchiBot
338560fedb Automatic translations update 2024-04-27 02:06:20 +00:00
Łukasz Domeradzki
632830278f Misc 2024-04-26 20:57:57 +02:00
Łukasz Domeradzki
8b614bd3c4 Misc 2024-04-26 20:56:17 +02:00
renovate[bot]
657354c2e8 chore(deps): update jetbrains/qodana-action action to v2024.1.2 2024-04-26 04:07:53 +00:00
renovate[bot]
7a0d9f2325 chore(deps): update github/codeql-action action to v3.25.3 2024-04-26 02:14:43 +00:00
ArchiBot
ae45c0c7ae Automatic translations update 2024-04-26 02:06:28 +00:00
renovate[bot]
c3b0e31a0a chore(deps): update asf-ui digest to 6dd170c 2024-04-25 20:28:00 +00:00
renovate[bot]
f7207c1326 chore(deps): update actions/checkout action to v4.1.4 2024-04-25 14:19:37 +00:00
ArchiBot
9a9817c6b3 Automatic translations update 2024-04-25 02:06:39 +00:00
Łukasz Domeradzki
1b4ac9da8b Squashed commit of the following:
commit 2f206cd822f615ad215c6e09f83ceb653c0dbd75
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Wed Apr 24 20:16:24 2024 +0200

    Further improvements

commit 66b60c028c652db1644c3efd400dd00f6559ba40
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Wed Apr 24 20:00:13 2024 +0200

    Try new heredoc syntax
2024-04-24 20:27:22 +02:00
renovate[bot]
d98310fc0e chore(deps): update actions/download-artifact action to v4.1.7 2024-04-24 15:25:40 +00:00
Łukasz Domeradzki
3240fca63e Misc qodana improvements 2024-04-24 15:22:38 +02:00
renovate[bot]
f1631b7f06 chore(deps): update jetbrains/qodana-action action to v2024 (#3195)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-04-24 15:14:48 +02:00
ArchiBot
30e5c5f91b Automatic translations update 2024-04-24 02:06:35 +00:00
Łukasz Domeradzki
257026144d Misc 2024-04-23 21:15:40 +02:00
Łukasz Domeradzki
9f786dce97 Misc 2024-04-23 21:11:32 +02:00
Łukasz Domeradzki
c2f582164c Misc 2024-04-23 20:54:07 +02:00
Łukasz Domeradzki
464ed3b614 Misc 2024-04-23 19:27:39 +02:00
renovate[bot]
5bb9494ecc chore(deps): update github/codeql-action action to v3.25.2 2024-04-23 08:22:38 +00:00
renovate[bot]
0fb583a094 chore(deps): update actions/upload-artifact action to v4.3.3 2024-04-23 04:51:37 +00:00
ArchiBot
358b1a7dbe Automatic translations update 2024-04-23 02:06:47 +00:00
renovate[bot]
bd91f439c8 chore(deps): update asf-ui digest to d7e3ef5 2024-04-22 23:04:12 +00:00
renovate[bot]
4181ada887 chore(deps): update actions/download-artifact action to v4.1.6 2024-04-22 19:50:54 +00:00
renovate[bot]
32d116d106 chore(deps): update actions/checkout action to v4.1.3 2024-04-22 16:27:01 +00:00
Łukasz Domeradzki
30c27f9faf Misc, documentation day! 2024-04-22 16:29:02 +02:00
Łukasz Domeradzki
b332d576ab Misc 2024-04-22 15:20:01 +02:00
Łukasz Domeradzki
9def43cef0 Update README.md 2024-04-22 15:03:29 +02:00
ArchiBot
0820b39a35 Automatic translations update 2024-04-22 02:06:52 +00:00
Łukasz Domeradzki
2a0be85d14 Bump 2024-04-21 21:35:22 +02:00
Łukasz Domeradzki
efb7262113 Prevent official plugins from updating to unmatched versions 2024-04-21 21:31:37 +02:00
renovate[bot]
1a732bbb93 chore(deps): update wiki digest to 74ee175 2024-04-21 16:10:17 +00:00
Łukasz Domeradzki
b8fe380b61 Bump 2024-04-21 18:09:47 +02:00
Łukasz Domeradzki
8670cea7a3 Misc 2024-04-21 18:09:21 +02:00
Sebastian Göls
e2a5ec3616 Fix monitoring plugin (#3191)
* Misc.

* Fix ASF crash

* Remove warning about automatic update of custom plugins if there is only official plugins enabled

* Fix previous mistake

* Revert "Fix ASF crash"

This reverts commit 42209e93ce.
2024-04-21 16:21:33 +02:00
renovate[bot]
d013366c9a chore(deps): update asf-ui digest to d64880d 2024-04-21 03:05:41 +00:00
ArchiBot
e9093cda6d Automatic translations update 2024-04-21 02:07:18 +00:00
Łukasz Domeradzki
0f30a0ef3d Fix IWebInterface with root WebPath 2024-04-20 23:37:57 +02:00
ArchiBot
b1a64e346c Automatic translations update 2024-04-20 02:05:36 +00:00
ArchiBot
c524a89c5e Automatic translations update 2024-04-19 02:06:39 +00:00
renovate[bot]
e73d90e697 chore(deps): update asf-ui digest to 0714df0 2024-04-18 21:40:19 +00:00
renovate[bot]
ee470d9ce9 chore(deps): update actions/upload-artifact action to v4.3.2 2024-04-18 20:16:48 +00:00
renovate[bot]
aab5b3aaab chore(deps): update actions/download-artifact action to v4.1.5 2024-04-18 17:09:08 +00:00
renovate[bot]
86281b5fdb chore(deps): update dependency opentelemetry.extensions.hosting to v1.8.1 2024-04-18 04:45:31 +00:00
ArchiBot
ddabf7db49 Automatic translations update 2024-04-18 02:06:09 +00:00
Łukasz Domeradzki
1c7523e98e Modernize docker builds, add attestations 2024-04-18 01:46:49 +02:00
Łukasz Domeradzki
120d084b12 Misc CI 2024-04-18 01:04:54 +02:00
renovate[bot]
1e69ec4634 chore(deps): update github/codeql-action action to v3.25.1 2024-04-17 15:33:32 +00:00
renovate[bot]
31a680ce1c chore(deps): update wiki digest to 7ec0ec5 2024-04-17 14:36:06 +00:00
Łukasz Domeradzki
3bad19530e Bump 2024-04-17 12:14:38 +02:00
Łukasz Domeradzki
10986289e6 Make --process-required default, add ShutdownIfPossible instead 2024-04-17 12:02:26 +02:00
ArchiBot
656c1b8d5d Automatic translations update 2024-04-17 02:06:21 +00:00
renovate[bot]
ef0037aa25 chore(deps): update asf-ui digest to 46a15c5 2024-04-16 22:20:35 +00:00
renovate[bot]
af02ccbd6f chore(deps): update wiki digest to dc78a43 2024-04-16 14:20:48 +00:00
Łukasz Domeradzki
978f3f63bd Bump 2024-04-16 11:39:51 +02:00
Łukasz Domeradzki
e550cc0f43 Misc 2024-04-16 10:39:03 +02:00
Łukasz Domeradzki
5894226e93 Add optional health checks to ASF API 2024-04-16 10:37:32 +02:00
ArchiBot
d50fa8eeb7 Automatic translations update 2024-04-16 02:05:41 +00:00
renovate[bot]
6efd333684 chore(deps): update github/codeql-action action to v3.25.0 2024-04-15 16:57:49 +00:00
renovate[bot]
05701b60c1 chore(deps): update wiki digest to 60a1965 2024-04-15 12:55:35 +00:00
ArchiBot
f8e7e55a00 Automatic translations update 2024-04-15 02:52:50 +00:00
renovate[bot]
20663f0226 chore(deps): update wiki digest to 05e8868 2024-04-14 22:52:10 +00:00
renovate[bot]
ad175ba2ac chore(deps): update asf-ui digest to 58779f5 2024-04-14 16:09:13 +00:00
Łukasz Domeradzki
bdf90a5e51 Enable ArchiSteamFarm.OfficialPlugins.Monitoring for publishing 2024-04-14 16:58:05 +02:00
Łukasz Domeradzki
49618534ce Ship grafana dashboard together with the plugin 2024-04-14 16:54:57 +02:00
Łukasz Domeradzki
f2bb2a6bee Create grafana_dashboard.json 2024-04-14 16:46:48 +02:00
ArchiBot
ba4f3aea7b Automatic translations update 2024-04-14 02:27:34 +00:00
Łukasz Domeradzki
b30068103b Bump 2024-04-13 23:54:05 +02:00
renovate[bot]
7062928c32 chore(deps): update opentelemetry-dotnet monorepo to v1.8.1 2024-04-13 03:38:50 +00:00
ArchiBot
7f0764b7b1 Automatic translations update 2024-04-13 01:56:55 +00:00
Łukasz Domeradzki
8b21f4f869 Misc 2024-04-12 11:58:46 +02:00
renovate[bot]
8d634b9b1b chore(deps): update asf-ui digest to d3082d3 2024-04-12 04:53:14 +00:00
ArchiBot
698e567c63 Automatic translations update 2024-04-12 02:06:30 +00:00
Łukasz Domeradzki
6d697c3dda Misc bulletproofing 2024-04-12 01:29:32 +02:00
Łukasz Domeradzki
746e28c3a2 Misc 2024-04-12 01:00:05 +02:00
Łukasz Domeradzki
df0f087505 Misc code style 2024-04-12 00:21:49 +02:00
Łukasz Domeradzki
0ccec4c8c1 Address latest Rider code inspections 2024-04-11 23:24:01 +02:00
renovate[bot]
e18e1533e3 chore(deps): update asf-ui digest to 386bfeb 2024-04-11 02:15:55 +00:00
ArchiBot
c077381e45 Automatic translations update 2024-04-11 02:06:12 +00:00
Łukasz Domeradzki
a0ecb78086 Misc 2024-04-10 15:42:00 +02:00
Łukasz Domeradzki
e47bd9faa4 Revert "Closes #3180"
This reverts commit 5d83807357.
2024-04-10 01:57:35 +02:00
Łukasz Domeradzki
e2bf6117dd Merge branch 'main' of https://github.com/JustArchiNET/ArchiSteamFarm 2024-04-10 01:52:17 +02:00
Łukasz Domeradzki
14b0b332c5 Fix 2024-04-10 01:52:11 +02:00
renovate[bot]
76f74dabbe chore(deps): update dependency markdig.signed to v0.37.0 2024-04-09 19:54:33 +00:00
Łukasz Domeradzki
42dec2de39 Misc
Thanks @xPaw
2024-04-09 16:33:54 +02:00
renovate[bot]
b965971c79 chore(deps): update asf-ui digest to 1c055dc 2024-04-09 02:36:57 +00:00
ArchiBot
3a7ab02f88 Automatic translations update 2024-04-09 02:05:31 +00:00
Łukasz Domeradzki
b931e935b5 Misc MonitoringPlugin enhancements 2024-04-09 03:45:06 +02:00
renovate[bot]
521a1b7d34 chore(deps): update docker/setup-buildx-action action to v3.3.0 2024-04-08 10:20:58 +00:00
Łukasz Domeradzki
fffcef2d30 Misc 2024-04-08 09:33:27 +02:00
ArchiBot
cf1216a667 Automatic translations update 2024-04-08 02:06:13 +00:00
Łukasz Domeradzki
68ee647ed2 Misc 2024-04-08 03:08:37 +02:00
Łukasz Domeradzki
2eda952cd0 Misc 2024-04-08 03:03:35 +02:00
Łukasz Domeradzki
7fac4ac298 Misc 2024-04-08 00:32:18 +02:00
Sebastian Göls
9016a5109d Fix monitoring integration with actual prometheus (#3183)
* Downgrade OpenTelemetry.Exporter.Prometheus.AspNetCore due to issues with latest version

* Add unit to asf_bot_farming_minutes_remaining

* Upgrade some packages released last night (already tested to work)

* Don't forget about unit suffix

* Add build and runtime information metrics

It is not recommended to include this information as labels in all
metrics. Instead, we add two special metrics with a constant value of
"1" and restrict those static pieces of information to them

* Remove module version from metrics as it does not work

* Apply feedback

* Deduplicate code

* Reference related issue in upstream repo
2024-04-07 23:56:44 +02:00
Łukasz Domeradzki
8e055fe587 Kill unused packageRules 2024-04-07 16:46:50 +02:00
renovate[bot]
3b2bb0590f chore(deps): update opentelemetry-dotnet monorepo to v1.8.0 2024-04-06 13:14:22 +00:00
renovate[bot]
134d3e2d0d chore(deps): update dependency opentelemetry.instrumentation.runtime to v1.8.0 2024-04-06 11:22:56 +00:00
renovate[bot]
b735f8e567 chore(deps): update github/codeql-action action to v3.24.10 2024-04-06 07:03:44 +00:00
renovate[bot]
3992ea6656 chore(deps): update dependency microsoft.identitymodel.jsonwebtokens to v7.5.1 2024-04-06 03:04:47 +00:00
Łukasz Domeradzki
03840990be Bump 2024-04-06 05:04:18 +02:00
Łukasz Domeradzki
27bafb1552 Resolve files in-use during update on Windows 2024-04-06 04:53:16 +02:00
ArchiBot
9b3ab17902 Automatic translations update 2024-04-06 02:04:31 +00:00
Łukasz Domeradzki
df0ede4ccc Remove unnecessary logging confusing people 2024-04-06 01:13:09 +02:00
Łukasz Domeradzki
ecf6846255 Misc 2024-04-05 12:29:41 +02:00
Łukasz Domeradzki
173e22dde2 Misc 2024-04-05 11:48:42 +02:00
renovate[bot]
c5799c561a chore(deps): update dependency mstest to v3.3.1 2024-04-05 04:44:28 +00:00
renovate[bot]
6736ca8fd4 chore(deps): update asf-ui digest to c74b93b 2024-04-05 02:14:52 +00:00
ArchiBot
8f3cacd32f Automatic translations update 2024-04-05 02:05:30 +00:00
Łukasz Domeradzki
d3cb3a1486 Bump 2024-04-04 23:05:27 +02:00
Łukasz Domeradzki
ae9dfca3b3 Closes #3156 (#3182)
* Closes #3156

* Misc

* Misc

* Rewrite update mechanism ONCE AGAIN, this time to eradicate FSW

* Make creating debug directory non-fatal again, like it used to be

* Deduplicate code

* Remove dead code

* Print update cleanup just once

* Address remaining feedback, go back to _old and _new

* One more nice improvement
2024-04-04 21:21:58 +02:00
Łukasz Domeradzki
edc7c38ba0 Misc 2024-04-04 21:20:23 +02:00
Łukasz Domeradzki
54e76cf559 Handle EResult.Fail in inventory request 2024-04-04 19:08:23 +02:00
Łukasz Domeradzki
477cc8ba74 Reduce AngleSharp overhead 2024-04-04 15:35:54 +02:00
renovate[bot]
573d4c8151 chore(deps): update asf-ui digest to e1b4949 2024-04-04 09:16:02 +00:00
renovate[bot]
5bdaec6980 chore(deps): update dependency mstest to v3.3.0 2024-04-04 03:20:35 +00:00
ArchiBot
400ff1ff6a Automatic translations update 2024-04-04 02:06:01 +00:00
Łukasz Domeradzki
1841cde776 Misc code enhancements 2024-04-04 02:15:16 +02:00
renovate[bot]
990e696b37 chore(deps): update wiki digest to 5ab9665 2024-04-03 20:08:37 +00:00
Łukasz Domeradzki
d591c67276 Remove ArchiSteamFarm.OfficialPlugins.Monitoring from publishing 2024-04-03 22:07:54 +02:00
Łukasz Domeradzki
423cd154a7 Better sessionID generation 2024-04-03 17:25:00 +02:00
renovate[bot]
44dec3ab3f chore(deps): update dependency opentelemetry.extensions.hosting to v1.8.0 2024-04-03 04:19:18 +00:00
ArchiBot
7fb7c9146b Automatic translations update 2024-04-03 02:05:45 +00:00
Łukasz Domeradzki
f060ba2094 Bump 2024-04-03 01:16:43 +02:00
Łukasz Domeradzki
457828260b Merge remote-tracking branch 'origin/renovate/asf-ui-digest' 2024-04-03 01:04:50 +02:00
renovate[bot]
4b080d4d0b chore(deps): update asf-ui digest to f70253c 2024-04-02 22:47:24 +00:00
Łukasz Domeradzki
5d83807357 Closes #3180 2024-04-03 00:46:46 +02:00
Łukasz Domeradzki
2b794becff Clear GamesToFarm on farming stopped
GamesToFarm is not used after farming has stopped, so this doesn't solve any bug or misbehaviour, but some plugin creators might prefer to have up-to-date state just in case.
2024-04-03 00:32:59 +02:00
renovate[bot]
e69c5a0138 chore(deps): update crowdin/github-action action to v1.20.2 2024-04-02 09:40:38 +00:00
ArchiBot
90a11c2ffc Automatic translations update 2024-04-02 02:07:14 +00:00
renovate[bot]
497da6487d chore(deps): update dependency anglesharp.xpath to v2.0.4 2024-04-01 23:24:14 +00:00
renovate[bot]
8ffabf3db3 chore(deps): update wiki digest to 9303271 2024-04-01 19:43:33 +00:00
ArchiBot
bf42605f88 Automatic translations update 2024-04-01 02:08:38 +00:00
Łukasz Domeradzki
7e12f17c48 Create ASF-troll.png
I'm not going to look after it each year!
2024-04-01 01:05:13 +02:00
Łukasz Domeradzki
9360a588ea Bump 2024-04-01 00:05:55 +02:00
Łukasz Domeradzki
e02e597102 Apply similar logic to build checksums 2024-04-01 00:03:11 +02:00
Łukasz Domeradzki
a952a2e1e7 Bump 2024-03-31 23:40:49 +02:00
Łukasz Domeradzki
cb8668ffb8 Resolve trade offers being stuck for too long when ASF API connection is down 2024-03-31 23:30:54 +02:00
Łukasz Domeradzki
79fb392a9a Update from ASFB 2024-03-30 04:03:16 +01:00
ArchiBot
7b490ae26a Automatic translations update 2024-03-30 02:03:23 +00:00
renovate[bot]
69b05f932f chore(deps): update asf-ui digest to 003d022 2024-03-29 19:00:22 +00:00
Łukasz Domeradzki
e0d614fe2f Bump 2024-03-29 14:48:09 +01:00
Łukasz Domeradzki
5e81c3fdef Closes #3175 2024-03-29 14:44:07 +01:00
ArchiBot
4707b60ee4 Automatic translations update 2024-03-29 02:04:44 +00:00
Łukasz Domeradzki
158b1a87b3 Bump 2024-03-29 01:05:40 +01:00
Łukasz Domeradzki
a72f833c67 Fix ASF crash when account is used as new family sharing kid 2024-03-29 01:04:41 +01:00
renovate[bot]
a9d0092bd2 chore(deps): update opentelemetry-dotnet monorepo to v1.8.0-rc.1 2024-03-28 11:46:37 +00:00
Łukasz Domeradzki
154655c35c Update from ASFB 2024-03-28 12:29:18 +01:00
renovate[bot]
2a2f9c27a4 chore(deps): update asf-ui digest to ab80b24 2024-03-28 04:48:23 +00:00
Łukasz Domeradzki
d50b8a7723 Update from ASFB 2024-03-28 03:11:16 +01:00
Łukasz Domeradzki
63421f7ed4 Update from ASFB 2024-03-28 03:08:50 +01:00
ArchiBot
8ad24e2f9f Automatic translations update 2024-03-28 02:06:02 +00:00
renovate[bot]
941539ce23 chore(deps): update asf-ui digest to 218f3b4 2024-03-27 22:53:07 +00:00
Łukasz Domeradzki
74c4a80e3b Bump 2024-03-27 23:52:32 +01:00
Łukasz Domeradzki
6e30b31e9e Sync inventory parsing with ASFB 2024-03-27 23:47:51 +01:00
Łukasz Domeradzki
b63161c73e Start logging AWH more extensively
We don't use it anymore, but it's beneficial to catch potential AH issues as well.

I'll make ASFB report potential issues.
2024-03-27 20:36:10 +01:00
Łukasz Domeradzki
9c362dced2 Bump 2024-03-27 19:57:26 +01:00
Łukasz Domeradzki
9a02c79e0a Closes #3174 2024-03-27 19:55:07 +01:00
renovate[bot]
0ae4b6ff18 chore(deps): update crowdin/github-action action to v1.20.1 2024-03-27 09:52:07 +00:00
Łukasz Domeradzki
7b4166f28d Bump 2024-03-27 09:23:33 +01:00
Łukasz Domeradzki
bd87673db3 Misc 2024-03-27 09:22:46 +01:00
Łukasz Domeradzki
4cb3eabd4c Add missing error-handling to GetMyInventoryAsync() 2024-03-27 09:19:22 +01:00
renovate[bot]
d3957b5604 chore(deps): update dependency microsoft.identitymodel.jsonwebtokens to v7.5.0 2024-03-27 04:15:12 +00:00
ArchiBot
de072bc5dd Automatic translations update 2024-03-27 02:05:15 +00:00
Łukasz Domeradzki
7bb23efc2f Misc 2024-03-26 22:04:19 +01:00
Łukasz Domeradzki
88be284117 Misc 2024-03-26 18:51:11 +01:00
Łukasz Domeradzki
bc983e9f5d Bump 2024-03-26 17:51:16 +01:00
Łukasz Domeradzki
4c38de75ab Further enhance plugin updates selection 2024-03-26 17:44:42 +01:00
Łukasz Domeradzki
b58469ce40 Fix occassional failures by not publishing plugins in parallel 2024-03-26 17:12:50 +01:00
Łukasz Domeradzki
ab7f12058f Skip restore if possible 2024-03-26 16:50:12 +01:00
renovate[bot]
0dda5a93c9 chore(deps): update asf-ui digest to 8a550a2 2024-03-26 03:43:18 +00:00
Łukasz Domeradzki
30092cc326 Squashed commit of the following:
commit a5dd19643edd71ba3bcf9d120cc0ef20c1904104
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 03:43:50 2024 +0100

    How about this one

commit 7f44554a5433931339dc479a6101f942c5d5fb97
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 03:14:04 2024 +0100

    Here as well

commit 8593cd169949dc5876c1a3c4e4561d2ca38d7350
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 03:13:36 2024 +0100

    Okay

commit 9d17fee1f8f9bd3ae91f144761885d10e52b67ae
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 03:08:49 2024 +0100

    Restore everything first

commit 2835332dabf17a9dcdea3fc4f75e0c650add622c
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 03:00:33 2024 +0100

    Ah right

commit 85e2db40c8d6c184e5732724ea928486456767e4
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 02:59:31 2024 +0100

    And this?

commit 974cffb61782a4dbc83dfd93a66a627a69d04fd9
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 02:33:52 2024 +0100

    Docker improvements

commit 95f40803615f7056f59a522b068600dfbb87b4de
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 02:22:30 2024 +0100

    Misc

commit 0f5b526c603d5cfe0f29b4f4b8420d01f76161fc
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Tue Mar 26 02:09:42 2024 +0100

    Make bundled plugins variant-specific

    Since we're including them as part of OS-specific builds, we can also limit their dependencies to those OSes exclusively.

    Might help cut some unnecessary dependencies.
2024-03-26 04:42:31 +01:00
ArchiBot
721380b153 Automatic translations update 2024-03-26 02:07:25 +00:00
renovate[bot]
09a0f21506 chore(deps): update asf-ui digest to 5b599bc 2024-03-26 00:48:04 +00:00
Łukasz Domeradzki
c9f2fdc847 Bump 2024-03-26 01:47:35 +01:00
Łukasz Domeradzki
e326cc94d0 Misc 2024-03-26 01:43:15 +01:00
Łukasz Domeradzki
66237dab24 Back to .15... 2024-03-26 01:16:18 +01:00
Łukasz Domeradzki
53ec07a7f1 Correct plugin names we distribute outselves 2024-03-26 01:15:17 +01:00
Łukasz Domeradzki
bbad80ae0e Bump 2024-03-26 00:39:32 +01:00
Łukasz Domeradzki
e6021a4f11 Misc 2024-03-26 00:36:04 +01:00
Łukasz Domeradzki
b3f792a2f3 Misc 2024-03-26 00:31:35 +01:00
Łukasz Domeradzki
7083a397b8 Squashed commit of the following:
commit ea03c2dab0fe884ed2c2db1acc6ab003ef71a684
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Mon Mar 25 23:59:50 2024 +0100

    Attempt 2

commit cb9e67d0d94df76f49ad58f225b35a2661b44100
Author: Łukasz Domeradzki <JustArchi@JustArchi.net>
Date:   Mon Mar 25 23:45:13 2024 +0100

    Ship monitoring plugin attempt 1
2024-03-26 00:29:23 +01:00
Łukasz Domeradzki
f98fd85fe9 Misc 2024-03-25 23:03:49 +01:00
Sebastian Göls
f9f6e207d4 Add official monitoring plugin (#3160)
* Add Monitoring plugin

* Prepare pipeline

* Fix Rider stupidity

* Fix Windows build

* Remove translation files

* Apply feedback

* Add steam id as additional tag to metrics

* Apply feedback

* Add runtime metrics

* Fix my brain not braining

* Use extension methods to add instrumentation and Add monitoring for outbound HTTP traffic

* Upgrade OpenTelemetry.Extensions.Hosting to prerelease due to runtime exception

* Remove config and add file that was supposed to be committed yesterday to fix the runtime exception

* Revert changes to publish.yml

* Remove localization

* Apply feedback

* Apply feedback

* Fix version number

* Revert use of property in Kestrel (even tho it's an outside caller to the source class)
2024-03-25 22:58:03 +01:00
Sebastian Göls
0c4e4e709f Add POST /Api/Plugins/Update (#3173) 2024-03-25 22:57:47 +01:00
renovate[bot]
d7f9ad4916 chore(deps): update asf-ui digest to b57627e 2024-03-25 17:40:33 +00:00
renovate[bot]
b04f92ca3c chore(deps): update jetbrains/qodana-action action to v2023.3.2 2024-03-25 09:55:54 +00:00
ArchiBot
16a0174cf1 Automatic translations update 2024-03-24 02:06:44 +00:00
renovate[bot]
c92d78e088 chore(deps): update asf-ui digest to bdb3808 2024-03-23 03:19:40 +00:00
ArchiBot
1f7b8d2416 Automatic translations update 2024-03-23 02:04:54 +00:00
renovate[bot]
7ca9b23aa3 chore(deps): update github/codeql-action action to v3.24.9 2024-03-22 16:16:04 +00:00
Archi
f0acd8ddfd Bump 2024-03-22 17:15:35 +01:00
Archi
c5009dad31 Decrease itemsCountPerRequest to 5000, optimize performance a bit, closes #3171 2024-03-22 16:34:46 +01:00
Archi
9682d1d5ef Down to 5000? 2024-03-22 16:16:38 +01:00
Archi
a4e8fca784 Keep decreasing itemsCountPerRequest 2024-03-22 15:50:29 +01:00
Archi
8f25040bf5 Decrease itemsCountPerRequest to help resolve #3171 2024-03-22 15:17:28 +01:00
renovate[bot]
34beec8d6b chore(deps): update asf-ui digest to 2f7a98e 2024-03-22 07:39:05 +00:00
ArchiBot
6c0fd638a5 Automatic translations update 2024-03-22 02:04:31 +00:00
Archi
0b94213af7 Misc
We originally had ifdefs here for netf, so const made sense, they don't anymore.
2024-03-22 01:10:39 +01:00
Archi
f874598fd8 Misc 2024-03-21 22:37:09 +01:00
Archi
a1adcd3a5a Misc refactor 2024-03-21 22:32:15 +01:00
Archi
1596b98e25 Misc 2024-03-21 21:55:46 +01:00
renovate[bot]
9b0ad5c545 chore(deps): update wiki digest to 4869495 2024-03-21 07:57:02 +00:00
renovate[bot]
6a47b30987 chore(deps): update asf-ui digest to 2b813a2 2024-03-21 03:31:32 +00:00
renovate[bot]
79594a9d00 chore(deps): update crowdin/github-action action to v1.20.0 2024-03-20 22:10:52 +00:00
renovate[bot]
38a9818482 chore(deps): update asf-ui digest to e91b9a0 2024-03-20 20:52:25 +00:00
Archi
a407d538f5 Bump 2024-03-20 21:52:03 +01:00
Archi
44bea85296 Fix and derequire type text in confirmation
Even if we have it always available, we don't need use it 99.9% of time, and even in 0.1% it's only supportive attribute for debugging. Make it optional, will help with robustness.
2024-03-20 21:51:28 +01:00
renovate[bot]
915d26adfa chore(deps): update wiki digest to 5e52590 2024-03-20 12:52:53 +00:00
Archi
3dd4248587 Bump 2024-03-20 13:52:15 +01:00
Archi
7969e58fbf Remove wrong failsafe 2024-03-20 13:51:43 +01:00
Archi
7043ebda23 Bump 2024-03-20 11:58:17 +01:00
Archi
4c0a5b7553 Make it possible to call updateplugins without args 2024-03-20 11:50:51 +01:00
Archi
533fbe0c2f Respect updateOverride when updating plugins 2024-03-20 11:36:14 +01:00
Archi
437dfd5f02 Allow forced plugin updates as well 2024-03-20 11:13:10 +01:00
Archi
5f4962ddcc Update IPluginUpdates.cs 2024-03-20 09:49:52 +01:00
Archi
7efa609a13 Update IPluginUpdates.cs 2024-03-20 04:47:12 +01:00
Archi
0d7049ea7c Misc 2024-03-20 04:46:09 +01:00
Archi
997e7f0420 Add bool asfUpdate to IPluginUpdates 2024-03-20 04:42:18 +01:00
Archi
96619b9565 Bump 2024-03-20 04:20:05 +01:00
Archi
4c2a786e54 Add downgrade possibility in update command 2024-03-20 04:16:22 +01:00
Archi
469b1571e1 Misc refactor of login results 2024-03-20 03:44:21 +01:00
Vita Chumakova
3bc66e0d27 Add family join confirmation type (#3166) 2024-03-20 03:20:23 +01:00
ArchiBot
9a4fac600a Automatic translations update 2024-03-20 02:04:23 +00:00
renovate[bot]
546ba8b68f chore(deps): update asf-ui digest to 25ce8ef 2024-03-19 19:28:12 +00:00
Archi
ed29c0633f Bump 2024-03-19 15:05:56 +01:00
Archi
35b1135b50 Update Bot.cs 2024-03-19 14:50:22 +01:00
Archi
90403c98c9 Bump 2024-03-19 13:55:34 +01:00
Archi
71a1c0574a Of course I had to forget about something important 2024-03-19 13:55:09 +01:00
Archi
ba64a50bb5 Bump 2024-03-19 13:28:52 +01:00
Archi
05131b2b76 Misc 2024-03-19 13:26:44 +01:00
Archi
0894eaee28 Closes #3162 2024-03-19 13:24:24 +01:00
Archi
6f2fd4eccc Closes #3163 2024-03-19 13:03:09 +01:00
Archi
04b534bda1 SK2 3.0 2024-03-19 12:40:54 +01:00
Archi
3620796d6d Misc 2024-03-19 11:07:50 +01:00
Archi
a321a38ccd Update publish.yml 2024-03-19 10:29:45 +01:00
Archi
ea965dfa85 Bump 2024-03-19 09:58:40 +01:00
Archi
f381106de2 Misc enhancements 2024-03-19 09:53:04 +01:00
Citrinate
b9ab3d6490 Fix GetTradeOffer exception (#3164) 2024-03-19 09:35:05 +01:00
renovate[bot]
4cf1d1e08b chore(deps): update asf-ui digest to a0ab4b2 2024-03-19 04:33:21 +00:00
ArchiBot
cba6e4df64 Automatic translations update 2024-03-19 02:05:23 +00:00
Archi
0dd6f38748 Move GetServerTime() from AWH to AH 2024-03-18 23:48:30 +01:00
renovate[bot]
970ba437a0 chore(deps): update github/codeql-action action to v3.24.8 2024-03-18 14:46:04 +00:00
Archi
e0bbbe3894 Update publish.yml 2024-03-18 15:45:37 +01:00
Archi
504791b5b6 Misc 2024-03-18 15:44:36 +01:00
Archi
6a6d0b48b9 Bump 2024-03-18 14:18:23 +01:00
Archi
84ff83bbe2 Improve performance when matching multiple users 2024-03-18 13:52:12 +01:00
Archi
787bcc3546 Extract ItemsMatcher-exclusively parts out of ASF core, decrease dependency on DeepClone() 2024-03-18 13:45:13 +01:00
Archi
fd811d8cf4 Implement DeepClone() for asset and description 2024-03-18 12:44:29 +01:00
Archi
3fa743f64b Add body for asset
It makes sense to expose entire underlying asset to the callers, as underlying body might have features they like, such as currencyid or est_usd - values that do not exist in json and we're not making use of them, but we still want to keep if provided e.g. by ArchiHandler.
2024-03-18 12:22:07 +01:00
Archi
ec374c050a Misc 2024-03-18 11:54:42 +01:00
Archi
5a07f8a2a3 Make descriptions optional, open constructors for plugins
In rare occurances, we might not have a description assigned to the item. This is most notable in inactive trade offers, but we permit this to happen even in inventory fetches.

Assigning "default" description is unwanted if caller wants to have a way to determine that description wasn't there to begin with. It makes more sense to make it nullable and *expect* it to be null, then caller can do appropriate checking and decide what they want to do with that.

Also open constructors for plugins usage in case they'd like to construct assets manually, e.g. for sending.
2024-03-18 11:53:14 +01:00
renovate[bot]
91b09dc43f chore(deps): update asf-ui digest to b112518 2024-03-18 04:33:16 +00:00
ArchiBot
8d6d355a3b Automatic translations update 2024-03-18 02:04:51 +00:00
renovate[bot]
da6fd69398 chore(deps): update wiki digest to be281d8 2024-03-17 21:07:32 +00:00
Archi
0e623cfd15 Bump 2024-03-17 22:06:55 +01:00
Archi
1c01d8f59f Fix tradableOnly/marketableOnly not working properly 2024-03-17 22:06:30 +01:00
Archi
5723ee7b19 Misc 2024-03-17 17:16:45 +01:00
Archi
1d85292451 Bump 2024-03-17 16:03:58 +01:00
renovate[bot]
0d65f5174b chore(deps): update asf-ui digest to b241705 2024-03-17 07:14:25 +00:00
Archi
b7f34f0d5d Misc 2024-03-17 03:47:08 +01:00
Archi
4ffcea72b0 Misc 2024-03-17 03:40:28 +01:00
Archi
9c5fade596 Final touches 2024-03-17 03:36:02 +01:00
Archi
331ecc1cc8 Add edge cases compatibility for plugins 2024-03-17 03:11:22 +01:00
ArchiBot
6428e5abd1 Automatic translations update 2024-03-17 02:05:53 +00:00
Archi
b86f83a634 Misc 2024-03-17 02:54:28 +01:00
Archi
ff55e09783 Apply guid json converter only where we need it 2024-03-17 02:44:49 +01:00
Archi
d7d24d5e47 Misc fix 2024-03-17 02:44:40 +01:00
Archi
48a14136a9 Update all file headers, again 2024-03-17 02:35:40 +01:00
Archi
c9acbb7bf2 Big post-PR cleanup 2024-03-17 02:29:04 +01:00
Archi
f98a159799 File header update 2024-03-17 00:06:13 +01:00
Vita Chumakova
184232995d Inventory fetching through CM (#3155)
* New inventory fetching

* use new method everywhere

* Store description in the asset, add protobuf body as a backing field for InventoryDescription, add properties to description

* parse trade offers as json, stub descriptions, fix build

* formatting, misc fixes

* fix pragma comments

* fix passing tradable property

* fix convesion of assets, add compatibility method

* fix fetching tradeoffers

* use 40k as default count per request

* throw an exception instead of silencing the error
2024-03-16 23:57:25 +01:00
Łukasz Domeradzki
aedede3ba4 Implement plugin updates with IPluginUpdates interface (#3151)
* Initial implementation of plugin updates

* Update PluginsCore.cs

* Update IPluginUpdates.cs

* Update PluginsCore.cs

* Make it work

* Misc

* Revert "Misc"

This reverts commit bccd1bb2b8.

* Proper fix

* Make plugin updates independent of GitHub

* Final touches

* Misc

* Allow plugin creators for more flexibility in picking from GitHub releases

* Misc rename

* Make changelog internal again

This is ASF implementation detail, make body available instead and let people implement changelogs themselves

* Misc

* Add missing localization

* Add a way to disable plugin updates

* Update PluginsCore.cs

* Update PluginsCore.cs

* Misc

* Update IGitHubPluginUpdates.cs

* Update IGitHubPluginUpdates.cs

* Update IGitHubPluginUpdates.cs

* Update IGitHubPluginUpdates.cs

* Make zip selection ignore case

* Update ArchiSteamFarm/Core/Utilities.cs

Co-authored-by: Vita Chumakova <me@ezhevita.dev>

* Misc error notify

* Add commands and finally call it a day

* Misc progress percentages text

* Misc

* Flip DefaultPluginsUpdateMode as per the voting

* Misc

---------

Co-authored-by: Vita Chumakova <me@ezhevita.dev>
2024-03-16 23:56:57 +01:00
renovate[bot]
c874779c0d chore(deps): update dependency microsoft.identitymodel.jsonwebtokens to v7.4.1 2024-03-16 00:47:06 +00:00
renovate[bot]
4a2457d571 chore(deps): update asf-ui digest to 8b1b833 2024-03-15 23:20:40 +00:00
ArchiBot
65fdd4196a Automatic translations update 2024-03-15 02:05:20 +00:00
renovate[bot]
19eefff525 chore(deps): update dependency markdig.signed to v0.36.2 2024-03-14 19:16:09 +00:00
renovate[bot]
626c18ba23 chore(deps): update docker/setup-buildx-action action to v3.2.0 2024-03-14 16:43:54 +00:00
renovate[bot]
d9c8dc1e2d chore(deps): update docker/build-push-action action to v5.3.0 2024-03-14 14:39:15 +00:00
renovate[bot]
25fa5cabbb chore(deps): update dependency markdig.signed to v0.36.0 2024-03-14 11:13:36 +00:00
Vita Chumakova
21c9dac593 Misc minimize fixes after #3158 (#3159)
* Misc minimize fixes after #3158

* only "iconify" escape sequence support is needed
2024-03-14 12:13:16 +01:00
renovate[bot]
617dccbd9a chore(deps): update asf-ui digest to 49f688e 2024-03-14 04:39:59 +00:00
ArchiBot
2f2665e2ad Automatic translations update 2024-03-14 02:04:37 +00:00
Archi
fcc0d70cd1 Fix build 2024-03-14 01:23:29 +01:00
Archi
06b2cf4ff5 Misc 2024-03-14 01:11:49 +01:00
Vita Chumakova
8642b0775e Flash console window on input request on Windows (#3158)
* Flash console window on input request

* Use BELL character instead of Beep, fix flash struct, add support for minimizing and flashing with Windows Terminal

* cross-platform minimization, use alert char instead of number, fix struct again

* remove console window

* formatting

* use MainWindowHandle if it's set (fix flashing winterm if ASF is launched in conhost)

* fix build

* remove support for flashing winterm
2024-03-14 01:08:00 +01:00
renovate[bot]
c193858973 chore(deps): update docker/login-action action to v3.1.0 2024-03-13 17:41:19 +00:00
renovate[bot]
362e921a27 chore(deps): update asf-ui digest to 9faaefe 2024-03-13 03:57:24 +00:00
ArchiBot
e21fa45718 Automatic translations update 2024-03-13 02:05:37 +00:00
renovate[bot]
caae270ea8 chore(deps): update github/codeql-action action to v3.24.7 2024-03-12 19:43:24 +00:00
ArchiBot
4843d539f0 Automatic translations update 2024-03-12 02:04:54 +00:00
Archi
fa8e649288 Fix JB header
Don't update all files just yet, wait for ongoing PRs to finish
2024-03-12 00:05:34 +01:00
Archi
20708ad900 Open ToSteamClientLanguage() for plugins usage 2024-03-11 23:56:47 +01:00
ArchiBot
5e0b9551da Automatic translations update 2024-03-11 02:04:50 +00:00
ArchiBot
e43adf4de7 Automatic translations update 2024-03-10 02:06:54 +00:00
Archi
afe16b8eb1 Bump 2024-03-09 22:15:22 +01:00
Archi
e9f9663714 Fix https crash for kestrel core 2024-03-09 21:54:14 +01:00
renovate[bot]
d514157903 chore(deps): update wiki digest to c156e89 2024-03-09 17:37:26 +00:00
Archi
56490f2d86 Bump 2024-03-09 18:36:48 +01:00
Archi
1fd6c8a477 Minimize dependencies for starting IPC server
Previously WebApplication didn't offer any advantages over generic Host, but with release of .NET 8 there is now slim and empty builders, which limit amount of initialized dependencies and allow us to skip some unnecessary features in default pipeline.
2024-03-09 18:24:15 +01:00
Archi
e7bdd408be Bump, misc 2024-03-09 16:59:05 +01:00
renovate[bot]
f73b4737b6 chore(deps): update docker/build-push-action action to v5.2.0 2024-03-08 10:22:24 +00:00
ArchiBot
14c905b8ef Automatic translations update 2024-03-07 01:56:16 +00:00
Łukasz Domeradzki
fa7849460c Update Bug-report.yml 2024-03-06 00:23:41 +01:00
renovate[bot]
4d12c9117f chore(deps): update actions/download-artifact action to v4.1.4 2024-03-02 04:14:53 +00:00
ArchiBot
e2f08fe35b Automatic translations update 2024-03-02 02:03:09 +00:00
Archi
0089a87018 Misc 2024-03-02 01:22:47 +01:00
ArchiBot
6325c454bc Automatic translations update 2024-03-01 02:06:50 +00:00
renovate[bot]
6b1f64579a chore(deps): update github/codeql-action action to v3.24.6 2024-02-29 17:05:50 +00:00
renovate[bot]
14cfd61615 chore(deps): update asf-ui digest to 3c96528 2024-02-29 04:11:33 +00:00
ArchiBot
f2a8768f80 Automatic translations update 2024-02-29 02:03:36 +00:00
Archi
556f3fdac0 Misc 2024-02-28 21:40:54 +01:00
renovate[bot]
59124fcf68 chore(deps): update asf-ui digest to bec199f 2024-02-28 17:47:01 +00:00
ArchiBot
71643446db Automatic translations update 2024-02-28 02:04:29 +00:00
renovate[bot]
a93ca58e9c chore(deps): update dependency microsoft.identitymodel.jsonwebtokens to v7.4.0 2024-02-27 23:03:52 +00:00
Archi
f12e87c2f4 Update SUPPORT.md 2024-02-27 23:58:35 +01:00
renovate[bot]
d48c96604b chore(deps): update docker/setup-buildx-action action to v3.1.0 2024-02-27 10:07:20 +00:00
renovate[bot]
0976bbfd2d chore(deps): update actions/download-artifact action to v4.1.3 2024-02-27 00:46:20 +00:00
Archi
6f66518607 Bump 2024-02-27 01:45:51 +01:00
Archi
e4c20df4a8 Misc 2024-02-27 01:44:21 +01:00
Archi
5135677360 Add back missing STJ feature of non-standard Guid deserialization 2024-02-27 01:34:56 +01:00
Archi
f6004f558b Closes #3147 2024-02-27 00:42:32 +01:00
renovate[bot]
ddf08c4dc0 chore(deps): update asf-ui digest to f916fb3 2024-02-26 19:35:51 +00:00
ArchiBot
388eaf614d Automatic translations update 2024-02-26 02:05:51 +00:00
renovate[bot]
3a0768f9ef chore(deps): update asf-ui digest to 05de7b9 2024-02-25 21:40:17 +00:00
ArchiBot
cb0e04c022 Automatic translations update 2024-02-25 02:05:54 +00:00
Archi
55cdac205d Merge branch 'main' of https://github.com/JustArchiNET/ArchiSteamFarm 2024-02-24 18:39:16 +01:00
Archi
1bc0d6f16c Archi had too much coding lately 2024-02-24 18:39:09 +01:00
renovate[bot]
f7377a7043 chore(deps): update asf-ui digest to d0d90a5 2024-02-24 04:29:58 +00:00
ArchiBot
76f1ad45dd Automatic translations update 2024-02-24 02:03:45 +00:00
renovate[bot]
f21ffde803 chore(deps): update github/codeql-action action to v3.24.5 2024-02-23 16:55:14 +00:00
renovate[bot]
e9c96f175f chore(deps): update asf-ui digest to f2ef756 2024-02-23 14:02:04 +00:00
Archi
0f9a4c7c31 Update Commands.cs 2024-02-23 14:19:09 +01:00
Archi
87451615e8 Extract addlicense logic to actions 2024-02-23 14:14:16 +01:00
ArchiBot
fa19aaae2e Automatic translations update 2024-02-23 02:08:38 +00:00
Archi
6b8280fceb Bump 2024-02-23 02:49:20 +01:00
Archi
7a13895429 Fix false positives 2024-02-23 02:49:03 +01:00
Archi
75668ea099 Bump 2024-02-23 02:43:06 +01:00
414 changed files with 12620 additions and 4358 deletions

4
.github/FUNDING.yml vendored
View File

@@ -1,4 +1,2 @@
# These are supported funding model platforms
github: JustArchi
custom: ["https://paypal.me/JustArchi", "https://pay.revolut.com/justarchi", "https://commerce.coinbase.com/checkout/0c23b844-c51b-45f4-9135-8db7c6fcf98e", "https://steamcommunity.com/tradeoffer/new/?partner=46697991&token=0ix2Ruv_"]
custom: ["https://paypal.me/JustArchi", "https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=HD2P2P3WGS5Y4", "https://pay.revolut.com/justarchi", "https://steamcommunity.com/tradeoffer/new/?partner=46697991&token=0ix2Ruv_"]

View File

@@ -149,6 +149,7 @@ body:
Ensure that your config has redacted (but NOT removed) potentially-sensitive properties, such as:
- IPCPassword (recommended)
- LicenseID (mandatory)
- SteamOwnerID (optionally)
- WebProxy (optionally, if exposing private details)
- WebProxyPassword (optionally, if exposing private details)

View File

@@ -14,4 +14,6 @@ This is automated GitHub deployment, human-readable changelog should be availabl
ASF is available for free, this release was made possible thanks to the people that decided to support the project. If you're grateful for what we're doing, please consider a donation. Developing ASF requires massive amount of time and knowledge, especially when it comes to Steam (and its problems). Even $1 is highly appreciated and shows that you care. Thank you!
[![GitHub sponsor](https://img.shields.io/badge/GitHub-sponsor-ea4aaa.svg?logo=github-sponsors)](https://github.com/sponsors/JustArchi) [![Crypto donate](https://img.shields.io/badge/Crypto-donate-f7931a.svg?logo=bitcoin)](https://commerce.coinbase.com/checkout/0c23b844-c51b-45f4-9135-8db7c6fcf98e) [![PayPal.me donate](https://img.shields.io/badge/PayPal.me-donate-00457c.svg?logo=paypal)](https://paypal.me/JustArchi) [![PayPal donate](https://img.shields.io/badge/PayPal-donate-00457c.svg?logo=paypal)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=HD2P2P3WGS5Y4) [![Revolut donate](https://img.shields.io/badge/Revolut-donate-0075eb.svg?logo=revolut)](https://pay.revolut.com/justarchi) [![Steam donate](https://img.shields.io/badge/Steam-donate-000000.svg?logo=steam)](https://steamcommunity.com/tradeoffer/new/?partner=46697991&token=0ix2Ruv_)
[![GitHub sponsor](https://img.shields.io/badge/GitHub-sponsor-ea4aaa.svg?logo=github-sponsors)](https://github.com/sponsors/JustArchi) [![PayPal.me donate](https://img.shields.io/badge/PayPal.me-donate-00457c.svg?logo=paypal)](https://paypal.me/JustArchi) [![PayPal donate](https://img.shields.io/badge/PayPal-donate-00457c.svg?logo=paypal)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=HD2P2P3WGS5Y4) [![Revolut donate](https://img.shields.io/badge/Revolut-donate-0075eb.svg?logo=revolut)](https://pay.revolut.com/justarchi) [![Steam donate](https://img.shields.io/badge/Steam-donate-000000.svg?logo=steam)](https://steamcommunity.com/tradeoffer/new/?partner=46697991&token=0ix2Ruv_)
[![BTC donate](https://img.shields.io/badge/BTC-donate-f7931a.svg?logo=bitcoin)](https://www.blockchain.com/explorer/addresses/btc/3HwcgZbtoF5vSxJkNUvThVSJipKi7r5EqU) [![ETH donate](https://img.shields.io/badge/ETH-donate-3c3c3d.svg?logo=ethereum)](https://www.blockchain.com/explorer/addresses/eth/0xA1F7Ba62C5a3A8b93Fe6656936192432F328a366) [![LTC donate](https://img.shields.io/badge/LTC-donate-a6a9aa.svg?logo=litecoin)](https://live.blockcypher.com/ltc/address/MJCeBEZUsNgDhRhqbLFfPiDcf7CSrdvmZ3) [![USDC donate](https://img.shields.io/badge/USDC-donate-2775ca.svg?logo=cashapp)](https://etherscan.io/address/0xCf42D9F53F974CBd7c304eF0243CAe8e029885A8) [![USDT donate](https://img.shields.io/badge/USDT-donate-50af95.svg?logo=tether)](https://etherscan.io/address/0x985FDdD3AD00838A2049B07A33b783104d60f776)

2
.github/SUPPORT.md vendored
View File

@@ -2,6 +2,6 @@
Our **[wiki](https://github.com/JustArchiNET/ArchiSteamFarm/wiki)** is the official online documentation which covers at least a significant majority (if not all) of ASF subjects you could be interested in. We recommend to start with **[setting up](https://github.com/JustArchiNET/ArchiSteamFarm/wiki/Setting-up)**, **[configuration](https://github.com/JustArchiNET/ArchiSteamFarm/wiki/Configuration)** and our **[FAQ](https://github.com/JustArchiNET/ArchiSteamFarm/wiki/FAQ)** which should help you with setting up ASF, configuring it, as well as answering the most common questions that you might have. For more advanced matters, as well as further elaboration, we have other pages available on our **[wiki](https://github.com/JustArchiNET/ArchiSteamFarm/wiki)** that you can visit.
We also have three independent support channels dedicated to our ASF users, in case you couldn't manage to solve the issue yourself. We answer all support and technical matters in our **[GitHub discussions](https://github.com/JustArchiNET/ArchiSteamFarm/discussions/categories/support)**, **[Steam group](https://steamcommunity.com/groups/archiasf/discussions/1)**, and on our **[Discord server](https://discord.gg/hSQgt8j)**. You're free to use the support channel that matches your preferences, although keep in mind that you have a higher chance solving your issue on the GitHub or Steam, where we're doing our best to answer all questions that couldn't be answered by our community itself (as opposed to Discord server where we're not active 24/7 and therefore not always able to answer).
We also have three independent support channels dedicated to our ASF users, in case you couldn't manage to solve the issue yourself. We answer all support and technical matters in our **[GitHub discussions](https://github.com/JustArchiNET/ArchiSteamFarm/discussions/categories/support-english)**, **[Steam group](https://steamcommunity.com/groups/archiasf/discussions/1)**, and on our **[Discord server](https://discord.gg/hSQgt8j)**. You're free to use the support channel that matches your preferences, although keep in mind that you have a higher chance solving your issue on the GitHub or Steam, where we're doing our best to answer all questions that couldn't be answered by our community itself (as opposed to Discord server where we're not active 24/7 and therefore not always able to answer).
GitHub **issues** (unlike discussions), are being used solely for ASF development, especially in regards to bugs and enhancements. We have a very strict policy regarding that, as GitHub issues is **not** a general support channel, it's dedicated exclusively to ASF development and we're not answering common ASF matters there, as we have appropriate support channels (mentioned above) for that. Common matters include not only general questions or issues that are obviously related to program usage, but also users reporting "bugs" that are clearly considered intended behaviour coming for example (and mainly) from misconfiguration or lack of understanding how the program works. If you're not sure whether your matter relates to ASF development or not, especially if you're not sure if it's a bug or intended behaviour, we recommend to use a support channel instead, where we'll answer you in calm atmosphere and forward your matter as GitHub issue if deemed appropriate. Invalid GitHub issues will be closed immediately and won't be answered.

View File

View File

@@ -12,13 +12,5 @@
],
"git-submodules": {
"enabled": true
},
"packageRules": [
{
// TODO: <= 3.1 for Mono support, last failed version 6.12, https://steamcommunity.com/groups/archiasf/discussions/1/2997673517556002529
"allowedVersions": "<= 3.1",
"matchManagers": [ "nuget" ],
"matchPackageNames": [ "Microsoft.Extensions.Configuration.Json", "Microsoft.Extensions.Logging.Configuration" ]
}
]
}
}

View File

@@ -21,7 +21,7 @@ jobs:
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
@@ -39,12 +39,3 @@ jobs:
- name: Run ${{ matrix.configuration }} ArchiSteamFarm.Tests
run: dotnet test ArchiSteamFarm.Tests -c "${{ matrix.configuration }}" -p:ContinuousIntegrationBuild=true -p:UseAppHost=false --nologo
- name: Upload latest strings for translation on Crowdin
if: ${{ github.event_name == 'push' && github.ref == 'refs/heads/main' && matrix.configuration == 'Release' && startsWith(matrix.os, 'ubuntu-') }}
uses: crowdin/github-action@v1.19.0
with:
crowdin_branch_name: main
config: '.github/crowdin.yml'
project_id: ${{ secrets.ASF_CROWDIN_PROJECT_ID }}
token: ${{ secrets.ASF_CROWDIN_API_TOKEN }}

View File

@@ -1,6 +1,7 @@
name: ASF-code-quality
on: [push, pull_request]
on:
- push
env:
DOTNET_CLI_TELEMETRY_OPTOUT: true
@@ -14,32 +15,25 @@ permissions:
jobs:
main:
if: github.event_name == 'push' || github.event.pull_request.head.repo.full_name == github.repository
environment: qa-qodana
runs-on: ubuntu-latest
steps:
- name: Checkout code
if: github.event_name != 'pull_request'
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
- name: Checkout code (for PR)
if: github.event_name == 'pull_request'
uses: actions/checkout@v4.1.1
with:
fetch-depth: 100 # History is required for pull request analysis
ref: ${{ github.event.pull_request.head.sha }} # To check out the actual pull request commit, not the merge commit
show-progress: false
- name: Run Qodana scan
uses: JetBrains/qodana-action@v2023.3.1
uses: JetBrains/qodana-action@v2024.1.8
with:
args: --property=idea.headless.enable.statistics=false
args: --config,.github/qodana.yaml,--property=idea.headless.enable.statistics=false
pr-mode: false
upload-result: true
env:
QODANA_TOKEN: ${{ secrets.QODANA_TOKEN }}
- name: Report Qodana results to GitHub
uses: github/codeql-action/upload-sarif@v3.24.4
uses: github/codeql-action/upload-sarif@v3.25.11
with:
sarif_file: ${{ runner.temp }}/qodana/results/qodana.sarif.json

28
.github/workflows/crowdin-ci.yml vendored Normal file
View File

@@ -0,0 +1,28 @@
name: ASF-crowdin-ci
on:
push:
branches:
- main
permissions: {}
jobs:
upload:
environment: dev-crowdin
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
- name: Upload latest strings for translation on Crowdin
uses: crowdin/github-action@v2.0.0
with:
crowdin_branch_name: main
config: '.github/crowdin.yml'
project_id: ${{ secrets.ASF_CROWDIN_PROJECT_ID }}
token: ${{ secrets.ASF_CROWDIN_API_TOKEN }}

View File

@@ -19,20 +19,20 @@ jobs:
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3.0.0
uses: docker/setup-buildx-action@v3.4.0
- name: Build ${{ matrix.configuration }} Docker image from ${{ matrix.file }}
uses: docker/build-push-action@v5.1.0
uses: docker/build-push-action@v6.3.0
with:
build-args: CONFIGURATION=${{ matrix.configuration }}
context: .
file: ${{ matrix.file }}
platforms: ${{ env.PLATFORMS }}
build-args: |
CONFIGURATION=${{ matrix.configuration }}
STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
provenance: true
sbom: true

View File

@@ -5,7 +5,6 @@ on:
types: [released]
env:
ASF_PRIVATE_SNK: ${{ secrets.ASF_PRIVATE_SNK }}
PLATFORMS: linux/amd64,linux/arm,linux/arm64
TAG: latest
@@ -14,40 +13,32 @@ permissions:
jobs:
main:
environment: release-docker
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3.0.0
uses: docker/setup-buildx-action@v3.4.0
- name: Login to ghcr.io
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Login to DockerHub
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: Prepare private key for signing
shell: sh
run: |
set -eu
if [ -n "${ASF_PRIVATE_SNK-}" ]; then
echo "$ASF_PRIVATE_SNK" | base64 -d > "resources/ArchiSteamFarm.snk"
fi
- name: Prepare environment outputs
shell: sh
run: |
@@ -59,12 +50,16 @@ jobs:
echo "DH_REPOSITORY=$(echo ${{ secrets.DOCKERHUB_USERNAME }}/${{ github.event.repository.name }} | tr '[:upper:]' '[:lower:]')" >> "$GITHUB_ENV"
- name: Build and publish Docker image from Dockerfile.Service
uses: docker/build-push-action@v5.1.0
uses: docker/build-push-action@v6.3.0
with:
context: .
file: Dockerfile.Service
platforms: ${{ env.PLATFORMS }}
build-args: STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
provenance: true
sbom: true
secrets: |
ASF_PRIVATE_SNK=${{ secrets.ASF_PRIVATE_SNK }}
STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
labels: |
org.opencontainers.image.created=${{ env.DATE_ISO8601 }}
org.opencontainers.image.version=${{ env.FIXED_TAG }}

View File

@@ -6,7 +6,6 @@ on:
- main
env:
ASF_PRIVATE_SNK: ${{ secrets.ASF_PRIVATE_SNK }}
PLATFORMS: linux/amd64,linux/arm,linux/arm64
TAG: main
@@ -15,40 +14,32 @@ permissions:
jobs:
main:
environment: release-docker
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3.0.0
uses: docker/setup-buildx-action@v3.4.0
- name: Login to ghcr.io
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Login to DockerHub
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: Prepare private key for signing
shell: sh
run: |
set -eu
if [ -n "${ASF_PRIVATE_SNK-}" ]; then
echo "$ASF_PRIVATE_SNK" | base64 -d > "resources/ArchiSteamFarm.snk"
fi
- name: Prepare environment outputs
shell: sh
run: |
@@ -59,11 +50,15 @@ jobs:
echo "DH_REPOSITORY=$(echo ${{ secrets.DOCKERHUB_USERNAME }}/${{ github.event.repository.name }} | tr '[:upper:]' '[:lower:]')" >> "$GITHUB_ENV"
- name: Build and publish Docker image from Dockerfile
uses: docker/build-push-action@v5.1.0
uses: docker/build-push-action@v6.3.0
with:
context: .
platforms: ${{ env.PLATFORMS }}
build-args: STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
provenance: true
sbom: true
secrets: |
ASF_PRIVATE_SNK=${{ secrets.ASF_PRIVATE_SNK }}
STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
labels: |
org.opencontainers.image.created=${{ env.DATE_ISO8601 }}
org.opencontainers.image.version=${{ github.sha }}
@@ -77,6 +72,6 @@ jobs:
uses: peter-evans/dockerhub-description@v4.0.0
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_PASSWORD }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
repository: ${{ env.DH_REPOSITORY }}
short-description: ${{ github.event.repository.description }}

View File

@@ -6,7 +6,6 @@ on:
- '*'
env:
ASF_PRIVATE_SNK: ${{ secrets.ASF_PRIVATE_SNK }}
PLATFORMS: linux/amd64,linux/arm,linux/arm64
TAG: released
@@ -15,40 +14,32 @@ permissions:
jobs:
main:
environment: release-docker
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3.0.0
uses: docker/setup-buildx-action@v3.4.0
- name: Login to ghcr.io
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Login to DockerHub
uses: docker/login-action@v3.0.0
uses: docker/login-action@v3.2.0
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: Prepare private key for signing
shell: sh
run: |
set -eu
if [ -n "${ASF_PRIVATE_SNK-}" ]; then
echo "$ASF_PRIVATE_SNK" | base64 -d > "resources/ArchiSteamFarm.snk"
fi
- name: Prepare environment outputs
shell: sh
run: |
@@ -60,11 +51,15 @@ jobs:
echo "DH_REPOSITORY=$(echo ${{ secrets.DOCKERHUB_USERNAME }}/${{ github.event.repository.name }} | tr '[:upper:]' '[:lower:]')" >> "$GITHUB_ENV"
- name: Build and publish Docker image from Dockerfile
uses: docker/build-push-action@v5.1.0
uses: docker/build-push-action@v6.3.0
with:
context: .
platforms: ${{ env.PLATFORMS }}
build-args: STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
provenance: true
sbom: true
secrets: |
ASF_PRIVATE_SNK=${{ secrets.ASF_PRIVATE_SNK }}
STEAM_TOKEN_DUMPER_TOKEN=${{ secrets.STEAM_TOKEN_DUMPER_TOKEN }}
labels: |
org.opencontainers.image.created=${{ env.DATE_ISO8601 }}
org.opencontainers.image.version=${{ env.FIXED_TAG }}

View File

@@ -8,7 +8,8 @@ env:
DOTNET_NOLOGO: true
DOTNET_SDK_VERSION: 8.0
NODE_JS_VERSION: 'lts/*'
PLUGINS: ArchiSteamFarm.OfficialPlugins.ItemsMatcher ArchiSteamFarm.OfficialPlugins.MobileAuthenticator ArchiSteamFarm.OfficialPlugins.SteamTokenDumper
PLUGINS_BUNDLED: ArchiSteamFarm.OfficialPlugins.ItemsMatcher ArchiSteamFarm.OfficialPlugins.MobileAuthenticator ArchiSteamFarm.OfficialPlugins.SteamTokenDumper
PLUGINS_INCLUDED: ArchiSteamFarm.OfficialPlugins.Monitoring # Apart from declaring them here, there is certain amount of hardcoding needed below for uploading
permissions: {}
@@ -18,7 +19,7 @@ jobs:
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
@@ -42,8 +43,9 @@ jobs:
run: npm run-script deploy --no-progress --prefix ASF-ui
- name: Upload ASF-ui
uses: actions/upload-artifact@v4.3.1
uses: actions/upload-artifact@v4.3.4
with:
if-no-files-found: error
name: ASF-ui
path: ASF-ui/dist
@@ -71,11 +73,16 @@ jobs:
- os: windows-latest
variant: win-x64
environment: build
runs-on: ${{ matrix.os }}
permissions:
attestations: write
id-token: write
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
@@ -88,7 +95,7 @@ jobs:
run: dotnet --info
- name: Download previously built ASF-ui
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: ASF-ui
path: ASF-ui/dist
@@ -125,35 +132,6 @@ jobs:
}
}
- name: Prepare for publishing on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
shell: bash
run: |
set -euo pipefail
dotnet restore
dotnet build ArchiSteamFarm -c "$CONFIGURATION" -p:ContinuousIntegrationBuild=true -p:TargetLatestRuntimePatch=false -p:UseAppHost=false --nologo
- name: Prepare for publishing on Windows
if: startsWith(matrix.os, 'windows-')
shell: pwsh
run: |
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
$ProgressPreference = 'SilentlyContinue'
dotnet restore
if ($LastExitCode -ne 0) {
throw "Last command failed."
}
dotnet build ArchiSteamFarm -c "$env:CONFIGURATION" -p:ContinuousIntegrationBuild=true -p:TargetLatestRuntimePatch=false -p:UseAppHost=false --nologo
if ($LastExitCode -ne 0) {
throw "Last command failed."
}
- name: Prepare ArchiSteamFarm.OfficialPlugins.SteamTokenDumper on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
env:
@@ -181,69 +159,6 @@ jobs:
(Get-Content "ArchiSteamFarm.OfficialPlugins.SteamTokenDumper\SharedInfo.cs").Replace('STEAM_TOKEN_DUMPER_TOKEN', "$env:STEAM_TOKEN_DUMPER_TOKEN") | Set-Content "ArchiSteamFarm.OfficialPlugins.SteamTokenDumper\SharedInfo.cs"
}
- name: Publish official plugins on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
env:
MAX_JOBS: 4
shell: bash
run: |
set -euo pipefail
publish() {
dotnet publish "$1" -c "$CONFIGURATION" -o "out/${1}" -p:ContinuousIntegrationBuild=true -p:TargetLatestRuntimePatch=false -p:UseAppHost=false --no-restore --nologo
}
for plugin in $PLUGINS; do
while [ "$(jobs -p | wc -l)" -ge "$MAX_JOBS" ]; do
sleep 1
done
publish "$plugin" &
done
wait
- name: Publish official plugins on Windows
if: startsWith(matrix.os, 'windows-')
env:
MAX_JOBS: 4
shell: pwsh
run: |
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
$ProgressPreference = 'SilentlyContinue'
$PublishBlock = {
param($plugin)
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
$ProgressPreference = 'SilentlyContinue'
Set-Location "$env:GITHUB_WORKSPACE"
dotnet publish "$plugin" -c "$env:CONFIGURATION" -o "out\$plugin" -p:ContinuousIntegrationBuild=true -p:TargetLatestRuntimePatch=false -p:UseAppHost=false --no-restore --nologo
if ($LastExitCode -ne 0) {
throw "Last command failed."
}
}
foreach ($plugin in $env:PLUGINS.Split([char[]] $null, [System.StringSplitOptions]::RemoveEmptyEntries)) {
# Limit active jobs in parallel to help with memory usage
$jobs = $(Get-Job -State Running)
while (@($jobs).Count -ge $env:MAX_JOBS) {
Wait-Job -Job $jobs -Any | Out-Null
$jobs = $(Get-Job -State Running)
}
Start-Job -Name "$plugin" $PublishBlock -ArgumentList "$plugin"
}
Get-Job | Receive-Job -Wait
- name: Publish ASF-${{ matrix.variant }} on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
env:
@@ -260,28 +175,12 @@ jobs:
dotnet publish ArchiSteamFarm -c "$CONFIGURATION" -o "out/${VARIANT}" "-p:ASFVariant=${VARIANT}" -p:ContinuousIntegrationBuild=true --nologo $variantArgs
# If we're including official plugins for this framework, copy them to output directory
for plugin in $PLUGINS; do
if [ -d "out/${plugin}" ]; then
mkdir -p "out/${VARIANT}/plugins/${plugin}"
cp -pR "out/${plugin}/"* "out/${VARIANT}/plugins/${plugin}"
fi
done
# Include .ico file for all platforms, since only Windows script can bundle it inside the exe
cp "resources/ASF.ico" "out/${VARIANT}/ArchiSteamFarm.ico"
# By default use fastest compression
seven_zip_args="-mx=1"
zip_args="-1"
# Include extra logic for builds marked for release
case "$GITHUB_REF" in
"refs/tags/"*)
# Tweak compression args for release publishing
seven_zip_args="-mx=9 -mfb=258 -mpass=15"
zip_args="-9"
# Update link in Changelog.html accordingly
if [ -f "out/${VARIANT}/Changelog.html" ]; then
tag="$(echo "$GITHUB_REF" | cut -c 11-)"
@@ -292,37 +191,6 @@ jobs:
;;
esac
# Create the final zip file
case "$(uname -s)" in
"Darwin")
# We prefer to use zip on macOS as 7z implementation on that OS doesn't handle file permissions (chmod +x)
if command -v zip >/dev/null; then
(
cd "${GITHUB_WORKSPACE}/out/${VARIANT}"
zip -q -r $zip_args "../ASF-${VARIANT}.zip" .
)
elif command -v 7z >/dev/null; then
7z a -bd -slp -tzip -mm=Deflate $seven_zip_args "out/ASF-${VARIANT}.zip" "${GITHUB_WORKSPACE}/out/${VARIANT}/*"
else
echo "ERROR: No supported zip tool!"
return 1
fi
;;
*)
if command -v 7z >/dev/null; then
7z a -bd -slp -tzip -mm=Deflate $seven_zip_args "out/ASF-${VARIANT}.zip" "${GITHUB_WORKSPACE}/out/${VARIANT}/*"
elif command -v zip >/dev/null; then
(
cd "${GITHUB_WORKSPACE}/out/${VARIANT}"
zip -q -r $zip_args "../ASF-${VARIANT}.zip" .
)
else
echo "ERROR: No supported zip tool!"
return 1
fi
;;
esac
- name: Publish ASF-${{ matrix.variant }} on Windows
if: startsWith(matrix.os, 'windows-')
env:
@@ -345,30 +213,13 @@ jobs:
throw "Last command failed."
}
# If we're including official plugins for this framework, copy them to output directory
foreach ($plugin in $env:PLUGINS.Split([char[]] $null, [System.StringSplitOptions]::RemoveEmptyEntries)) {
if (Test-Path "out\$plugin" -PathType Container) {
if (!(Test-Path "out\$env:VARIANT\plugins\$plugin" -PathType Container)) {
New-Item -ItemType Directory -Path "out\$env:VARIANT\plugins\$plugin" > $null
}
Copy-Item "out\$plugin\*" "out\$env:VARIANT\plugins\$plugin" -Recurse
}
}
# Icon is available only in .exe Windows builds, we'll bundle the .ico file for other flavours
if (!(Test-Path "out\$env:VARIANT\ArchiSteamFarm.exe" -PathType Leaf)) {
Copy-Item 'resources\ASF.ico' "out\$env:VARIANT\ArchiSteamFarm.ico"
}
# By default use fastest compression
$compressionArgs = '-mx=1'
# Include extra logic for builds marked for release
if ($env:GITHUB_REF -like 'refs/tags/*') {
# Tweak compression args for release publishing
$compressionArgs = '-mx=9', '-mfb=258', '-mpass=15'
# Update link in Changelog.html accordingly
if (Test-Path "out\$env:VARIANT\Changelog.html" -PathType Leaf) {
$tag = $env:GITHUB_REF.Substring(10)
@@ -377,6 +228,111 @@ jobs:
}
}
- name: Publish bundled plugins on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
env:
VARIANT: ${{ matrix.variant }}
shell: bash
run: |
set -euo pipefail
if [ "$VARIANT" = 'generic' ]; then
variantArgs="-p:TargetLatestRuntimePatch=false -p:UseAppHost=false"
else
variantArgs="-r $VARIANT"
fi
for plugin in $PLUGINS_BUNDLED; do
dotnet publish "$plugin" -c "$CONFIGURATION" -o "out/${VARIANT}/plugins/${plugin}" "-p:ASFVariant=${VARIANT}" -p:ContinuousIntegrationBuild=true --nologo $variantArgs
done
- name: Publish bundled plugins on Windows
if: startsWith(matrix.os, 'windows-')
env:
VARIANT: ${{ matrix.variant }}
shell: pwsh
run: |
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
$ProgressPreference = 'SilentlyContinue'
if ($env:VARIANT -like 'generic*') {
$variantArgs = '-p:TargetLatestRuntimePatch=false', '-p:UseAppHost=false'
} else {
$variantArgs = '-r', "$env:VARIANT"
}
foreach ($plugin in $env:PLUGINS_BUNDLED.Split([char[]] $null, [System.StringSplitOptions]::RemoveEmptyEntries)) {
dotnet publish "$plugin" -c "$env:CONFIGURATION" -o "out\$env:VARIANT\plugins\$plugin" "-p:ASFVariant=$env:VARIANT" -p:ContinuousIntegrationBuild=true --nologo $variantArgs
if ($LastExitCode -ne 0) {
throw "Last command failed."
}
}
- name: Zip ASF-${{ matrix.variant }} on Unix
if: startsWith(matrix.os, 'macos-') || startsWith(matrix.os, 'ubuntu-')
env:
VARIANT: ${{ matrix.variant }}
shell: bash
run: |
set -euo pipefail
# By default use fastest compression
seven_zip_args="-mx=1"
zip_args="-1"
# Tweak compression args for release publishing
case "$GITHUB_REF" in
"refs/tags/"*)
seven_zip_args="-mx=9 -mfb=258 -mpass=15"
zip_args="-9"
;;
esac
# Create the final zip file
case "$(uname -s)" in
"Darwin")
# We prefer to use zip on macOS as 7z implementation on that OS doesn't handle file permissions (chmod +x)
if command -v zip >/dev/null; then
(
cd "${GITHUB_WORKSPACE}/out/${VARIANT}"
zip -q -r $zip_args "../ASF-${VARIANT}.zip" .
)
else
7z a -bd -slp -tzip -mm=Deflate $seven_zip_args "out/ASF-${VARIANT}.zip" "${GITHUB_WORKSPACE}/out/${VARIANT}/*"
fi
;;
*)
if command -v 7z >/dev/null; then
7z a -bd -slp -tzip -mm=Deflate $seven_zip_args "out/ASF-${VARIANT}.zip" "${GITHUB_WORKSPACE}/out/${VARIANT}/*"
else
(
cd "${GITHUB_WORKSPACE}/out/${VARIANT}"
zip -q -r $zip_args "../ASF-${VARIANT}.zip" .
)
fi
;;
esac
- name: Zip ASF-${{ matrix.variant }} on Windows
if: startsWith(matrix.os, 'windows-')
env:
VARIANT: ${{ matrix.variant }}
shell: pwsh
run: |
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
$ProgressPreference = 'SilentlyContinue'
# By default use fastest compression
$compressionArgs = '-mx=1'
# Tweak compression args for release publishing
if ($env:GITHUB_REF -like 'refs/tags/*') {
$compressionArgs = '-mx=9', '-mfb=258', '-mpass=15'
}
# Create the final zip file
7z a -bd -slp -tzip -mm=Deflate $compressionArgs "out\ASF-$env:VARIANT.zip" "$env:GITHUB_WORKSPACE\out\$env:VARIANT\*"
@@ -404,74 +360,138 @@ jobs:
}
}
- name: Upload ASF-${{ matrix.variant }}
uses: actions/upload-artifact@v4.3.1
- name: Generate artifact attestation for ASF-${{ matrix.variant }}.zip
if: ${{ github.event_name == 'push' }}
uses: actions/attest-build-provenance@v1.3.2
with:
subject-path: out/ASF-${{ matrix.variant }}.zip
- name: Upload ASF-${{ matrix.variant }}
uses: actions/upload-artifact@v4.3.4
with:
if-no-files-found: error
name: ${{ matrix.os }}_ASF-${{ matrix.variant }}
path: out/ASF-${{ matrix.variant }}.zip
- name: Publish included plugins on Unix
if: ${{ matrix.os == 'ubuntu-latest' && matrix.variant == 'generic' }}
env:
VARIANT: ${{ matrix.variant }}
shell: bash
run: |
set -euo pipefail
# By default use fastest compression
seven_zip_args="-mx=1"
zip_args="-1"
# Tweak compression args for release publishing
case "$GITHUB_REF" in
"refs/tags/"*)
seven_zip_args="-mx=9 -mfb=258 -mpass=15"
zip_args="-9"
;;
esac
for plugin in $PLUGINS_INCLUDED; do
dotnet publish "$plugin" -c "$CONFIGURATION" -o "out/${plugin}" "-p:ASFVariant=${VARIANT}" -p:ContinuousIntegrationBuild=true -p:TargetLatestRuntimePatch=false -p:UseAppHost=false --nologo
# Create the final zip file
if command -v 7z >/dev/null; then
7z a -bd -slp -tzip -mm=Deflate $seven_zip_args "out/${plugin}.zip" "${GITHUB_WORKSPACE}/out/${plugin}/*"
else
(
cd "${GITHUB_WORKSPACE}/out/${plugin}"
zip -q -r $zip_args "../${plugin}.zip" .
)
fi
done
- name: Generate artifact attestation for ArchiSteamFarm.OfficialPlugins.Monitoring
if: ${{ github.event_name == 'push' && matrix.os == 'ubuntu-latest' && matrix.variant == 'generic' }}
uses: actions/attest-build-provenance@v1.3.2
with:
subject-path: out/ArchiSteamFarm.OfficialPlugins.Monitoring.zip
- name: Upload ArchiSteamFarm.OfficialPlugins.Monitoring
if: ${{ matrix.os == 'ubuntu-latest' && matrix.variant == 'generic' }}
uses: actions/upload-artifact@v4.3.4
with:
if-no-files-found: error
name: ArchiSteamFarm.OfficialPlugins.Monitoring
path: out/ArchiSteamFarm.OfficialPlugins.Monitoring.zip
release:
if: ${{ github.event_name == 'push' && startsWith(github.ref, 'refs/tags/') }}
needs: publish-asf
environment: release-github
runs-on: ubuntu-latest
permissions:
attestations: write
contents: write
id-token: write
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
- name: Download ASF-generic artifact from ubuntu-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: ubuntu-latest_ASF-generic
path: out
- name: Download ASF-linux-arm artifact from ubuntu-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: ubuntu-latest_ASF-linux-arm
path: out
- name: Download ASF-linux-arm64 artifact from ubuntu-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: ubuntu-latest_ASF-linux-arm64
path: out
- name: Download ASF-linux-x64 artifact from ubuntu-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: ubuntu-latest_ASF-linux-x64
path: out
- name: Download ASF-osx-arm64 artifact from macos-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: macos-latest_ASF-osx-arm64
path: out
- name: Download ASF-osx-x64 artifact from macos-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: macos-latest_ASF-osx-x64
path: out
- name: Download ASF-win-arm64 artifact from windows-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: windows-latest_ASF-win-arm64
path: out
- name: Download ASF-win-x64 artifact from windows-latest
uses: actions/download-artifact@v4.1.2
uses: actions/download-artifact@v4.1.8
with:
name: windows-latest_ASF-win-x64
path: out
- name: Download ArchiSteamFarm.OfficialPlugins.Monitoring artifact
uses: actions/download-artifact@v4.1.8
with:
name: ArchiSteamFarm.OfficialPlugins.Monitoring
path: out
- name: Import GPG key for signing
uses: crazy-max/ghaction-import-gpg@v6.1.0
with:
@@ -479,34 +499,46 @@ jobs:
- name: Generate SHA-512 checksums and signature
shell: sh
working-directory: out
run: |
set -eu
(
cd "out"
sha512sum *.zip > SHA512SUMS
gpg -a -b -o SHA512SUMS.sign SHA512SUMS
sha512sum *.zip > SHA512SUMS
gpg -a -b -o SHA512SUMS.sign SHA512SUMS
)
- name: Generate artifact attestation for SHA512SUMS
uses: actions/attest-build-provenance@v1.3.2
with:
subject-path: out/SHA512SUMS
- name: Upload SHA512SUMS
uses: actions/upload-artifact@v4.3.1
uses: actions/upload-artifact@v4.3.4
with:
if-no-files-found: error
name: SHA512SUMS
path: out/SHA512SUMS
- name: Upload SHA512SUMS.sign
uses: actions/upload-artifact@v4.3.1
- name: Generate artifact attestation for SHA512SUMS.sign
uses: actions/attest-build-provenance@v1.3.2
with:
subject-path: out/SHA512SUMS.sign
- name: Upload SHA512SUMS.sign
uses: actions/upload-artifact@v4.3.4
with:
if-no-files-found: error
name: SHA512SUMS.sign
path: out/SHA512SUMS.sign
- name: Create ArchiSteamFarm GitHub release
uses: ncipollo/release-action@v1.14.0
with:
allowUpdates: true
artifactErrorsFailBuild: true
artifacts: "out/*"
bodyFile: .github/RELEASE_TEMPLATE.md
makeLatest: false
name: ArchiSteamFarm V${{ github.ref_name }}
prerelease: true
token: ${{ secrets.ARCHIBOT_GITHUB_TOKEN }}
updateOnlyUnreleased: true

View File

@@ -3,17 +3,19 @@ name: ASF-translations
on:
schedule:
- cron: '55 1 * * *'
workflow_dispatch:
permissions:
contents: write
jobs:
update:
environment: dev-crowdin
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4.1.1
uses: actions/checkout@v4.1.7
with:
show-progress: false
submodules: recursive
@@ -21,16 +23,15 @@ jobs:
- name: Reset wiki to follow origin
shell: sh
working-directory: wiki
run: |
set -eu
cd wiki
git fetch --depth=1 origin master
git reset --hard origin/master
- name: Download latest translations from Crowdin
uses: crowdin/github-action@v1.19.0
uses: crowdin/github-action@v2.0.0
with:
upload_sources: false
download_translations: true
@@ -51,11 +52,10 @@ jobs:
- name: Commit the changes to wiki
shell: sh
working-directory: wiki
run: |
set -eu
cd wiki
git add -A "locale"
if ! git diff --cached --quiet; then

2
ASF-ui

Submodule ASF-ui updated: cd1173a0d6...cd60876ac0

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -32,6 +34,7 @@ using ArchiSteamFarm.Core;
using ArchiSteamFarm.Plugins.Interfaces;
using ArchiSteamFarm.Steam;
using ArchiSteamFarm.Steam.Data;
using ArchiSteamFarm.Steam.Exchange;
using SteamKit2;
namespace ArchiSteamFarm.CustomPlugins.ExamplePlugin;
@@ -43,7 +46,7 @@ namespace ArchiSteamFarm.CustomPlugins.ExamplePlugin;
// If you do not want to handle a particular action (e.g. OnBotMessage that is offered in IBotMessage), it's the best idea to not inherit it at all
// This will keep your code compact, efficient and less dependent. You can always add additional interfaces when you'll need them, this example project will inherit quite a bit of them to show you potential usage
[SuppressMessage("ReSharper", "MemberCanBeFileLocal")]
internal sealed class ExamplePlugin : IASF, IBot, IBotCommand2, IBotConnection, IBotFriendRequest, IBotMessage, IBotModules, IBotTradeOffer {
internal sealed class ExamplePlugin : IASF, IBot, IBotCommand2, IBotConnection, IBotFriendRequest, IBotMessage, IBotModules, IBotTradeOffer2 {
// This is used for identification purposes, typically you want to use a friendly name of your plugin here, such as the name of your main class
// Please note that this property can have direct dependencies only on structures that were initialized by the constructor, as it's possible to be called before OnLoaded() takes place
[JsonInclude]
@@ -178,7 +181,7 @@ internal sealed class ExamplePlugin : IASF, IBot, IBotCommand2, IBotConnection,
// It allows you not only to analyze such trades, but generate a response whether ASF should accept it (true), or proceed like usual (false)
// Thanks to that, you can implement custom rules for all trades that aren't handled by ASF, for example cross-set trading on your own custom rules
// You'd implement your own logic here, as an example we'll allow all trades to be accepted if the bot's name starts from "TrashBot"
public Task<bool> OnBotTradeOffer(Bot bot, TradeOffer tradeOffer) => Task.FromResult(bot.BotName.StartsWith("TrashBot", StringComparison.OrdinalIgnoreCase));
public Task<bool> OnBotTradeOffer(Bot bot, TradeOffer tradeOffer, ParseTradeResult.EResult asfResult) => Task.FromResult(bot.BotName.StartsWith("TrashBot", StringComparison.OrdinalIgnoreCase));
// This is the earliest method that will be called, right after loading the plugin, long before any bot initialization takes place
// It's a good place to initialize all potential (non-bot-specific) structures that you will need across lifetime of your plugin, such as global timers, concurrent dictionaries and alike

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -41,7 +43,7 @@ using SteamKit2;
namespace ArchiSteamFarm.OfficialPlugins.ItemsMatcher;
internal static class Backend {
internal static async Task<ObjectResponse<GenericResponse<BackgroundTaskResponse>>?> AnnounceDiffForListing(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<Asset.EType> acceptedMatchableTypes, uint totalInventoryCount, bool matchEverything, string tradeToken, IReadOnlyCollection<AssetForListing> inventoryRemoved, string? previousInventoryChecksum, string? nickname = null, string? avatarHash = null) {
internal static async Task<ObjectResponse<GenericResponse<BackgroundTaskResponse>>?> AnnounceDiffForListing(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<EAssetType> acceptedMatchableTypes, uint totalInventoryCount, bool matchEverything, string tradeToken, IReadOnlyCollection<AssetForListing> inventoryRemoved, string? previousInventoryChecksum, string? nickname = null, string? avatarHash = null) {
ArgumentNullException.ThrowIfNull(webBrowser);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {
@@ -72,7 +74,7 @@ internal static class Backend {
return await webBrowser.UrlPostToJsonObject<GenericResponse<BackgroundTaskResponse>, AnnouncementDiffRequest>(request, data: data, requestOptions: WebBrowser.ERequestOptions.ReturnRedirections | WebBrowser.ERequestOptions.ReturnClientErrors | WebBrowser.ERequestOptions.AllowInvalidBodyOnErrors | WebBrowser.ERequestOptions.CompressRequest).ConfigureAwait(false);
}
internal static async Task<ObjectResponse<GenericResponse<BackgroundTaskResponse>>?> AnnounceForListing(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<Asset.EType> acceptedMatchableTypes, uint totalInventoryCount, bool matchEverything, string tradeToken, string? nickname = null, string? avatarHash = null) {
internal static async Task<ObjectResponse<GenericResponse<BackgroundTaskResponse>>?> AnnounceForListing(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<EAssetType> acceptedMatchableTypes, uint totalInventoryCount, bool matchEverything, string tradeToken, string? nickname = null, string? avatarHash = null) {
ArgumentNullException.ThrowIfNull(webBrowser);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {
@@ -129,7 +131,7 @@ internal static class Backend {
return response?.StatusCode;
}
internal static async Task<(HttpStatusCode StatusCode, ImmutableHashSet<ListedUser> Users)?> GetListedUsersForMatching(Guid licenseID, Bot bot, WebBrowser webBrowser, IReadOnlyCollection<Asset> inventory, IReadOnlyCollection<Asset.EType> acceptedMatchableTypes) {
internal static async Task<(HttpStatusCode StatusCode, ImmutableHashSet<ListedUser> Users)?> GetListedUsersForMatching(Guid licenseID, Bot bot, WebBrowser webBrowser, IReadOnlyCollection<Asset> inventory, IReadOnlyCollection<EAssetType> acceptedMatchableTypes) {
ArgumentOutOfRangeException.ThrowIfEqual(licenseID, Guid.Empty);
ArgumentNullException.ThrowIfNull(bot);
ArgumentNullException.ThrowIfNull(webBrowser);
@@ -156,10 +158,10 @@ internal static class Backend {
return null;
}
return (response.StatusCode, response.Content?.Result ?? ImmutableHashSet<ListedUser>.Empty);
return (response.StatusCode, response.Content?.Result ?? []);
}
internal static async Task<ObjectResponse<GenericResponse<ImmutableHashSet<SetPart>>>?> GetSetParts(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<Asset.EType> matchableTypes, IReadOnlyCollection<uint> realAppIDs, CancellationToken cancellationToken = default) {
internal static async Task<ObjectResponse<GenericResponse<ImmutableHashSet<SetPart>>>?> GetSetParts(WebBrowser webBrowser, ulong steamID, IReadOnlyCollection<EAssetType> matchableTypes, IReadOnlyCollection<uint> realAppIDs, CancellationToken cancellationToken = default) {
ArgumentNullException.ThrowIfNull(webBrowser);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -120,7 +122,7 @@ internal static class Commands {
IList<string?> results = await Utilities.InParallel(bots.Select(bot => Task.Run(() => ResponseMatch(Steam.Interaction.Commands.GetProxyAccess(bot, access, steamID), bot)))).ConfigureAwait(false);
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))];
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))!];
return responses.Count > 0 ? string.Join(Environment.NewLine, responses) : null;
}

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -38,7 +40,7 @@ internal sealed class AnnouncementDiffRequest : AnnouncementRequest {
[JsonRequired]
private string PreviousInventoryChecksum { get; init; }
internal AnnouncementDiffRequest(Guid guid, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<Asset.EType> matchableTypes, uint totalInventoryCount, bool matchEverything, byte maxTradeHoldDuration, string tradeToken, IReadOnlyCollection<AssetForListing> inventoryRemoved, string previousInventoryChecksum, string? nickname = null, string? avatarHash = null) : base(guid, steamID, inventory, inventoryChecksum, matchableTypes, totalInventoryCount, matchEverything, maxTradeHoldDuration, tradeToken, nickname, avatarHash) {
internal AnnouncementDiffRequest(Guid guid, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<EAssetType> matchableTypes, uint totalInventoryCount, bool matchEverything, byte maxTradeHoldDuration, string tradeToken, IReadOnlyCollection<AssetForListing> inventoryRemoved, string previousInventoryChecksum, string? nickname = null, string? avatarHash = null) : base(guid, steamID, inventory, inventoryChecksum, matchableTypes, totalInventoryCount, matchEverything, maxTradeHoldDuration, tradeToken, nickname, avatarHash) {
ArgumentOutOfRangeException.ThrowIfEqual(guid, Guid.Empty);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -48,7 +50,7 @@ internal class AnnouncementRequest {
[JsonInclude]
[JsonRequired]
private ImmutableHashSet<Asset.EType> MatchableTypes { get; init; }
private ImmutableHashSet<EAssetType> MatchableTypes { get; init; }
[JsonInclude]
[JsonRequired]
@@ -73,7 +75,7 @@ internal class AnnouncementRequest {
[JsonRequired]
private string TradeToken { get; init; }
internal AnnouncementRequest(Guid guid, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<Asset.EType> matchableTypes, uint totalInventoryCount, bool matchEverything, byte maxTradeHoldDuration, string tradeToken, string? nickname = null, string? avatarHash = null) {
internal AnnouncementRequest(Guid guid, ulong steamID, IReadOnlyCollection<AssetForListing> inventory, string inventoryChecksum, IReadOnlyCollection<EAssetType> matchableTypes, uint totalInventoryCount, bool matchEverything, byte maxTradeHoldDuration, string tradeToken, string? nickname = null, string? avatarHash = null) {
ArgumentOutOfRangeException.ThrowIfEqual(guid, Guid.Empty);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -39,7 +41,7 @@ internal class AssetForMatching {
[JsonInclude]
[JsonPropertyName("r")]
[JsonRequired]
internal Asset.ERarity Rarity { get; private init; }
internal EAssetRarity Rarity { get; private init; }
[JsonInclude]
[JsonPropertyName("e")]
@@ -54,7 +56,7 @@ internal class AssetForMatching {
[JsonInclude]
[JsonPropertyName("p")]
[JsonRequired]
internal Asset.EType Type { get; private init; }
internal EAssetType Type { get; private init; }
[JsonConstructor]
protected AssetForMatching() { }

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -40,5 +42,5 @@ internal class AssetInInventory : AssetForMatching {
AssetID = asset.AssetID;
}
internal Asset ToAsset() => new(Asset.SteamAppID, Asset.SteamCommunityContextID, ClassID, Amount, tradable: Tradable, assetID: AssetID, realAppID: RealAppID, type: Type, rarity: Rarity);
internal Asset ToAsset() => new(Asset.SteamAppID, Asset.SteamCommunityContextID, ClassID, Amount, new InventoryDescription(Asset.SteamAppID, ClassID, tradable: Tradable, realAppID: RealAppID, type: Type, rarity: Rarity), AssetID);
}

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -40,13 +42,13 @@ internal sealed class InventoriesRequest {
[JsonInclude]
[JsonRequired]
internal ImmutableHashSet<Asset.EType> MatchableTypes { get; private init; }
internal ImmutableHashSet<EAssetType> MatchableTypes { get; private init; }
[JsonInclude]
[JsonRequired]
internal ulong SteamID { get; private init; }
internal InventoriesRequest(Guid guid, ulong steamID, IReadOnlyCollection<Asset> inventory, IReadOnlyCollection<Asset.EType> matchableTypes) {
internal InventoriesRequest(Guid guid, ulong steamID, IReadOnlyCollection<Asset> inventory, IReadOnlyCollection<EAssetType> matchableTypes) {
ArgumentOutOfRangeException.ThrowIfEqual(guid, Guid.Empty);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -31,11 +33,11 @@ namespace ArchiSteamFarm.OfficialPlugins.ItemsMatcher.Data;
internal sealed class ListedUser {
[JsonInclude]
[JsonRequired]
internal ImmutableHashSet<AssetInInventory> Assets { get; private init; } = ImmutableHashSet<AssetInInventory>.Empty;
internal ImmutableHashSet<AssetInInventory> Assets { get; private init; } = [];
[JsonInclude]
[JsonRequired]
internal ImmutableHashSet<Asset.EType> MatchableTypes { get; private init; } = ImmutableHashSet<Asset.EType>.Empty;
internal ImmutableHashSet<EAssetType> MatchableTypes { get; private init; } = [];
[JsonInclude]
[JsonRequired]

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -36,7 +38,7 @@ internal sealed class SetPart {
[JsonInclude]
[JsonPropertyName("r")]
[JsonRequired]
internal Asset.ERarity Rarity { get; private init; }
internal EAssetRarity Rarity { get; private init; }
[JsonInclude]
[JsonPropertyName("e")]
@@ -46,7 +48,7 @@ internal sealed class SetPart {
[JsonInclude]
[JsonPropertyName("p")]
[JsonRequired]
internal Asset.EType Type { get; private init; }
internal EAssetType Type { get; private init; }
[JsonConstructor]
private SetPart() { }

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -35,7 +37,7 @@ internal sealed class SetPartsRequest {
[JsonInclude]
[JsonRequired]
internal ImmutableHashSet<Asset.EType> MatchableTypes { get; private init; }
internal ImmutableHashSet<EAssetType> MatchableTypes { get; private init; }
[JsonInclude]
[JsonRequired]
@@ -45,7 +47,7 @@ internal sealed class SetPartsRequest {
[JsonRequired]
internal ulong SteamID { get; private init; }
internal SetPartsRequest(Guid guid, ulong steamID, IReadOnlyCollection<Asset.EType> matchableTypes, IReadOnlyCollection<uint> realAppIDs) {
internal SetPartsRequest(Guid guid, ulong steamID, IReadOnlyCollection<EAssetType> matchableTypes, IReadOnlyCollection<uint> realAppIDs) {
ArgumentOutOfRangeException.ThrowIfEqual(guid, Guid.Empty);
if ((steamID == 0) || !new SteamID(steamID).IsIndividualAccount) {

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingSomeConfirmationsFailed" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,19 +53,29 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">
<value>{0} sets ont été matché pendant ce round.</value>
<comment>{0} will be replaced by number of sets traded</comment>
</data>
<data name="ListingAnnouncing" xml:space="preserve">
<value>Annonce de {0} ({1}) avec l'inventaire réalisé à partir de {2} au total sur la liste...</value>
<comment>{0} will be replaced by steam ID (number), {1} will be replaced by user's nickname, {2} will be replaced with number of items in the inventory</comment>
</data>
<data name="MatchingFound" xml:space="preserve">
<value>Correspondance totale de {0} éléments avec le bot {1} ({2}), envoi de l'offre d'échange...</value>
<comment>{0} will be replaced by number of items matched, {1} will be replaced by steam ID (number), {2} will be replaced by user's nickname</comment>
</data>
<data name="TradeOfferFailed" xml:space="preserve">
<value>Impossible d'envoyer une offre d'échange au bot {0} ({1}), en cours ...</value>
<comment>{0} will be replaced by steam ID (number), {1} will be replaced by user's nickname'</comment>
</data>
<data name="ActivelyMatchingSomeConfirmationsFailed" xml:space="preserve">
<value>Certaines confirmations ont échoué, environ {0} sur les transactions {1} ont été envoyées avec succès.</value>
<comment>{0} will be replaced by amount of the trade offers that succeeded (number), {1} will be replaced by amount of the trade offers that were supposed to be sent in total (number)</comment>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<data name="ActivelyMatchingItemsRound" xml:space="preserve">

View File

@@ -0,0 +1,191 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
// |
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// |
// http://www.apache.org/licenses/LICENSE-2.0
// |
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
using System;
using System.Collections.Generic;
using System.Linq;
using ArchiSteamFarm.Steam.Data;
namespace ArchiSteamFarm.OfficialPlugins.ItemsMatcher;
internal static class MatchingUtilities {
internal static (Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> FullState, Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> TradableState) GetDividedInventoryState(IReadOnlyCollection<Asset> inventory) {
if ((inventory == null) || (inventory.Count == 0)) {
throw new ArgumentNullException(nameof(inventory));
}
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> fullState = new();
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> tradableState = new();
foreach (Asset item in inventory) {
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (item.RealAppID, item.Type, item.Rarity);
if (fullState.TryGetValue(key, out Dictionary<ulong, uint>? fullSet)) {
fullSet[item.ClassID] = fullSet.GetValueOrDefault(item.ClassID) + item.Amount;
} else {
fullState[key] = new Dictionary<ulong, uint> { { item.ClassID, item.Amount } };
}
if (!item.Tradable) {
continue;
}
if (tradableState.TryGetValue(key, out Dictionary<ulong, uint>? tradableSet)) {
tradableSet[item.ClassID] = tradableSet.GetValueOrDefault(item.ClassID) + item.Amount;
} else {
tradableState[key] = new Dictionary<ulong, uint> { { item.ClassID, item.Amount } };
}
}
return (fullState, tradableState);
}
internal static Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> GetTradableInventoryState(IReadOnlyCollection<Asset> inventory) {
if ((inventory == null) || (inventory.Count == 0)) {
throw new ArgumentNullException(nameof(inventory));
}
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> tradableState = new();
foreach (Asset item in inventory.Where(static item => item.Tradable)) {
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (item.RealAppID, item.Type, item.Rarity);
if (tradableState.TryGetValue(key, out Dictionary<ulong, uint>? tradableSet)) {
tradableSet[item.ClassID] = tradableSet.GetValueOrDefault(item.ClassID) + item.Amount;
} else {
tradableState[key] = new Dictionary<ulong, uint> { { item.ClassID, item.Amount } };
}
}
return tradableState;
}
internal static HashSet<Asset> GetTradableItemsFromInventory(IReadOnlyCollection<Asset> inventory, IReadOnlyDictionary<ulong, uint> classIDs, bool randomize = false) {
if ((inventory == null) || (inventory.Count == 0)) {
throw new ArgumentNullException(nameof(inventory));
}
if ((classIDs == null) || (classIDs.Count == 0)) {
throw new ArgumentNullException(nameof(classIDs));
}
// We need a copy of classIDs passed since we're going to manipulate them
Dictionary<ulong, uint> classIDsState = classIDs.ToDictionary();
HashSet<Asset> result = [];
IEnumerable<Asset> items = inventory.Where(static item => item.Tradable);
// Randomization helps to decrease "items no longer available" in regards to sending offers to other users
if (randomize) {
#pragma warning disable CA5394 // This call isn't used in a security-sensitive manner
items = items.Where(item => classIDsState.ContainsKey(item.ClassID)).OrderBy(static _ => Random.Shared.Next());
#pragma warning restore CA5394 // This call isn't used in a security-sensitive manner
}
foreach (Asset item in items) {
if (!classIDsState.TryGetValue(item.ClassID, out uint amount)) {
continue;
}
if (amount >= item.Amount) {
result.Add(item);
if (amount > item.Amount) {
classIDsState[item.ClassID] = amount - item.Amount;
} else {
classIDsState.Remove(item.ClassID);
if (classIDsState.Count == 0) {
return result;
}
}
} else {
Asset itemToAdd = item.DeepClone();
itemToAdd.Amount = amount;
result.Add(itemToAdd);
classIDsState.Remove(itemToAdd.ClassID);
if (classIDsState.Count == 0) {
return result;
}
}
}
// If we got here it means we still have classIDs to match
throw new InvalidOperationException(nameof(classIDs));
}
internal static bool IsEmptyForMatching(IReadOnlyDictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> fullState, IReadOnlyDictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> tradableState) {
ArgumentNullException.ThrowIfNull(fullState);
ArgumentNullException.ThrowIfNull(tradableState);
foreach (((uint RealAppID, EAssetType Type, EAssetRarity Rarity) set, IReadOnlyDictionary<ulong, uint> state) in tradableState) {
if (!fullState.TryGetValue(set, out Dictionary<ulong, uint>? fullSet) || (fullSet.Count == 0)) {
throw new InvalidOperationException(nameof(fullSet));
}
if (!IsEmptyForMatching(fullSet, state)) {
return false;
}
}
// We didn't find any matchable combinations, so this inventory is empty
return true;
}
internal static bool IsEmptyForMatching(IReadOnlyDictionary<ulong, uint> fullSet, IReadOnlyDictionary<ulong, uint> tradableSet) {
ArgumentNullException.ThrowIfNull(fullSet);
ArgumentNullException.ThrowIfNull(tradableSet);
foreach ((ulong classID, uint amount) in tradableSet) {
switch (amount) {
case 0:
// No tradable items, this should never happen, dictionary should not have this key to begin with
throw new InvalidOperationException(nameof(amount));
case 1:
// Single tradable item, can be matchable or not depending on the rest of the inventory
if (!fullSet.TryGetValue(classID, out uint fullAmount) || (fullAmount == 0)) {
throw new InvalidOperationException(nameof(fullAmount));
}
if (fullAmount > 1) {
// If we have a single tradable item but more than 1 in total, this is matchable
return false;
}
// A single exclusive tradable item is not matchable, continue
continue;
default:
// Any other combination of tradable items is always matchable
return false;
}
}
// We didn't find any matchable combinations, so this inventory is empty
return true;
}
}

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -27,7 +29,6 @@ using System.Globalization;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Text.Json;
using System.Threading;
using System.Threading.Tasks;
@@ -61,11 +62,11 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
private const byte MinimumSteamGuardEnabledDays = 15; // As imposed by Steam limits
private const byte MinPersonaStateTTL = 5; // Minimum amount of minutes we must wait before requesting persona state update
private static readonly FrozenSet<Asset.EType> AcceptedMatchableTypes = new HashSet<Asset.EType>(4) {
Asset.EType.Emoticon,
Asset.EType.FoilTradingCard,
Asset.EType.ProfileBackground,
Asset.EType.TradingCard
private static readonly FrozenSet<EAssetType> AcceptedMatchableTypes = new HashSet<EAssetType>(4) {
EAssetType.Emoticon,
EAssetType.FoilTradingCard,
EAssetType.ProfileBackground,
EAssetType.TradingCard
}.ToFrozenSet();
private readonly Bot Bot;
@@ -229,7 +230,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
return;
}
HashSet<Asset.EType> acceptedMatchableTypes = Bot.BotConfig.MatchableTypes.Where(AcceptedMatchableTypes.Contains).ToHashSet();
HashSet<EAssetType> acceptedMatchableTypes = Bot.BotConfig.MatchableTypes.Where(AcceptedMatchableTypes.Contains).ToHashSet();
if (acceptedMatchableTypes.Count == 0) {
throw new InvalidOperationException(nameof(acceptedMatchableTypes));
@@ -250,8 +251,8 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
List<Asset> inventory;
try {
inventory = await Bot.ArchiWebHandler.GetInventoryAsync().ToListAsync().ConfigureAwait(false);
} catch (HttpRequestException e) {
inventory = await Bot.ArchiHandler.GetMyInventoryAsync().ToListAsync().ConfigureAwait(false);
} catch (TimeoutException e) {
// This is actually a network failure, so we'll stop sending heartbeats but not record it as valid check
ShouldSendHeartBeats = false;
@@ -282,10 +283,10 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
List<AssetForListing> assetsForListing = [];
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), bool> tradableSets = new();
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), bool> tradableSets = new();
foreach (Asset item in inventory) {
if (item is { AssetID: > 0, Amount: > 0, ClassID: > 0, RealAppID: > 0, Type: > Asset.EType.Unknown, Rarity: > Asset.ERarity.Unknown, IsSteamPointsShopItem: false } && acceptedMatchableTypes.Contains(item.Type)) {
if (item is { AssetID: > 0, Amount: > 0, ClassID: > 0, RealAppID: > 0, Type: > EAssetType.Unknown, Rarity: > EAssetRarity.Unknown, IsSteamPointsShopItem: false } && acceptedMatchableTypes.Contains(item.Type)) {
// Only tradable assets matter for MatchEverything bots
if (!matchEverything || item.Tradable) {
assetsForListing.Add(new AssetForListing(item, index, previousAssetID));
@@ -293,7 +294,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
// But even for Fair bots, we should track and skip sets where we don't have any item to trade with
if (!matchEverything) {
(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key = (item.RealAppID, item.Type, item.Rarity);
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (item.RealAppID, item.Type, item.Rarity);
if (tradableSets.TryGetValue(key, out bool tradable)) {
if (!tradable && item.Tradable) {
@@ -375,15 +376,15 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
if (!matchEverything) {
// We should deduplicate our sets before sending them to the server, for doing that we'll use ASFB set parts data
HashSet<uint> realAppIDs = [];
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), Dictionary<ulong, uint>> state = new();
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> state = new();
foreach (AssetForListing asset in assetsForListing) {
realAppIDs.Add(asset.RealAppID);
(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
if (state.TryGetValue(key, out Dictionary<ulong, uint>? set)) {
set[asset.ClassID] = set.TryGetValue(asset.ClassID, out uint amount) ? amount + asset.Amount : asset.Amount;
set[asset.ClassID] = set.GetValueOrDefault(asset.ClassID) + asset.Amount;
} else {
state[key] = new Dictionary<ulong, uint> { { asset.ClassID, asset.Amount } };
}
@@ -446,11 +447,11 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
return;
}
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), HashSet<ulong>> databaseSets = setPartsResponse.Content.Result.GroupBy(static setPart => (setPart.RealAppID, setPart.Type, setPart.Rarity)).ToDictionary(static group => group.Key, static group => group.Select(static setPart => setPart.ClassID).ToHashSet());
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), HashSet<ulong>> databaseSets = setPartsResponse.Content.Result.GroupBy(static setPart => (setPart.RealAppID, setPart.Type, setPart.Rarity)).ToDictionary(static group => group.Key, static group => group.Select(static setPart => setPart.ClassID).ToHashSet());
Dictionary<ulong, uint> setCopy = [];
foreach (((uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key, Dictionary<ulong, uint> set) in state) {
foreach (((uint RealAppID, EAssetType Type, EAssetRarity Rarity) key, Dictionary<ulong, uint> set) in state) {
if (!databaseSets.TryGetValue(key, out HashSet<ulong>? databaseSet)) {
// We have no clue about this set, we can't do any optimization
continue;
@@ -488,7 +489,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
HashSet<AssetForListing> assetsForListingFiltered = [];
foreach (AssetForListing asset in assetsForListing.Where(asset => state.TryGetValue((asset.RealAppID, asset.Type, asset.Rarity), out Dictionary<ulong, uint>? setState) && setState.TryGetValue(asset.ClassID, out uint targetAmount) && (targetAmount > 0)).OrderByDescending(static asset => asset.Tradable).ThenByDescending(static asset => asset.Index)) {
(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
if (!state.TryGetValue(key, out Dictionary<ulong, uint>? setState) || !setState.TryGetValue(asset.ClassID, out uint targetAmount) || (targetAmount == 0)) {
// We're not interested in this combination
@@ -901,7 +902,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
return;
}
HashSet<Asset.EType> acceptedMatchableTypes = Bot.BotConfig.MatchableTypes.Where(AcceptedMatchableTypes.Contains).ToHashSet();
HashSet<EAssetType> acceptedMatchableTypes = Bot.BotConfig.MatchableTypes.Where(AcceptedMatchableTypes.Contains).ToHashSet();
if (acceptedMatchableTypes.Count == 0) {
Bot.ArchiLogger.LogNullError(acceptedMatchableTypes);
@@ -937,8 +938,8 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
HashSet<Asset> assetsForMatching;
try {
assetsForMatching = await Bot.ArchiWebHandler.GetInventoryAsync().Where(item => item is { AssetID: > 0, Amount: > 0, ClassID: > 0, RealAppID: > 0, Type: > Asset.EType.Unknown, Rarity: > Asset.ERarity.Unknown, IsSteamPointsShopItem: false } && acceptedMatchableTypes.Contains(item.Type) && !Bot.BotDatabase.MatchActivelyBlacklistAppIDs.Contains(item.RealAppID)).ToHashSetAsync().ConfigureAwait(false);
} catch (HttpRequestException e) {
assetsForMatching = await Bot.ArchiHandler.GetMyInventoryAsync().Where(item => item is { AssetID: > 0, Amount: > 0, ClassID: > 0, RealAppID: > 0, Type: > EAssetType.Unknown, Rarity: > EAssetRarity.Unknown, IsSteamPointsShopItem: false } && acceptedMatchableTypes.Contains(item.Type) && !Bot.BotDatabase.MatchActivelyBlacklistAppIDs.Contains(item.RealAppID)).ToHashSetAsync().ConfigureAwait(false);
} catch (TimeoutException e) {
Bot.ArchiLogger.LogGenericWarningException(e);
Bot.ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, nameof(assetsForMatching)));
@@ -957,7 +958,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
}
// Remove from our inventory items that can't be possibly matched due to no dupes to offer available
HashSet<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity)> setsToKeep = Trading.GetInventorySets(assetsForMatching).Where(static set => set.Value.Any(static amount => amount > 1)).Select(static set => set.Key).ToHashSet();
HashSet<(uint RealAppID, EAssetType Type, EAssetRarity Rarity)> setsToKeep = Trading.GetInventorySets(assetsForMatching).Where(static set => set.Value.Any(static amount => amount > 1)).Select(static set => set.Key).ToHashSet();
if (assetsForMatching.RemoveWhere(item => !setsToKeep.Contains((item.RealAppID, item.Type, item.Rarity))) > 0) {
if (assetsForMatching.Count == 0) {
@@ -969,15 +970,15 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
// We should deduplicate our sets before sending them to the server, for doing that we'll use ASFB set parts data
HashSet<uint> realAppIDs = [];
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), Dictionary<ulong, uint>> setsState = new();
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> setsState = new();
foreach (Asset asset in assetsForMatching) {
realAppIDs.Add(asset.RealAppID);
(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
if (setsState.TryGetValue(key, out Dictionary<ulong, uint>? set)) {
set[asset.ClassID] = set.TryGetValue(asset.ClassID, out uint amount) ? amount + asset.Amount : asset.Amount;
set[asset.ClassID] = set.GetValueOrDefault(asset.ClassID) + asset.Amount;
} else {
setsState[key] = new Dictionary<ulong, uint> { { asset.ClassID, asset.Amount } };
}
@@ -1031,11 +1032,11 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
return;
}
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), HashSet<ulong>> databaseSets = setPartsResponse.Content.Result.GroupBy(static setPart => (setPart.RealAppID, setPart.Type, setPart.Rarity)).ToDictionary(static group => group.Key, static group => group.Select(static setPart => setPart.ClassID).ToHashSet());
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), HashSet<ulong>> databaseSets = setPartsResponse.Content.Result.GroupBy(static setPart => (setPart.RealAppID, setPart.Type, setPart.Rarity)).ToDictionary(static group => group.Key, static group => group.Select(static setPart => setPart.ClassID).ToHashSet());
Dictionary<ulong, uint> setCopy = [];
foreach (((uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key, Dictionary<ulong, uint> set) in setsState) {
foreach (((uint RealAppID, EAssetType Type, EAssetRarity Rarity) key, Dictionary<ulong, uint> set) in setsState) {
uint minimumAmount = uint.MaxValue;
uint maximumAmount = uint.MinValue;
@@ -1094,7 +1095,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
HashSet<Asset> assetsForMatchingFiltered = [];
foreach (Asset asset in assetsForMatching.Where(asset => setsState.TryGetValue((asset.RealAppID, asset.Type, asset.Rarity), out Dictionary<ulong, uint>? setState) && setState.TryGetValue(asset.ClassID, out uint targetAmount) && (targetAmount > 0)).OrderByDescending(static asset => asset.Tradable)) {
(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
(uint RealAppID, EAssetType Type, EAssetRarity Rarity) key = (asset.RealAppID, asset.Type, asset.Rarity);
if (!setsState.TryGetValue(key, out Dictionary<ulong, uint>? setState) || !setState.TryGetValue(asset.ClassID, out uint targetAmount) || (targetAmount == 0)) {
// We're not interested in this combination
@@ -1148,9 +1149,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
return;
}
#pragma warning disable CA2000 // False positive, we're actually wrapping it in the using clause below exactly for that purpose
using (await Bot.Actions.GetTradingLock().ConfigureAwait(false)) {
#pragma warning restore CA2000 // False positive, we're actually wrapping it in the using clause below exactly for that purpose
tradesSent = await MatchActively(response.Value.Users, assetsForMatching, acceptedMatchableTypes).ConfigureAwait(false);
}
@@ -1165,7 +1164,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
}
}
private async Task<bool> MatchActively(IReadOnlyCollection<ListedUser> listedUsers, IReadOnlyCollection<Asset> ourAssets, IReadOnlyCollection<Asset.EType> acceptedMatchableTypes) {
private async Task<bool> MatchActively(ImmutableHashSet<ListedUser> listedUsers, HashSet<Asset> ourAssets, HashSet<EAssetType> acceptedMatchableTypes) {
if ((listedUsers == null) || (listedUsers.Count == 0)) {
throw new ArgumentNullException(nameof(listedUsers));
}
@@ -1178,9 +1177,9 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
throw new ArgumentNullException(nameof(acceptedMatchableTypes));
}
(Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), Dictionary<ulong, uint>> ourFullState, Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), Dictionary<ulong, uint>> ourTradableState) = Trading.GetDividedInventoryState(ourAssets);
(Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> ourFullState, Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> ourTradableState) = MatchingUtilities.GetDividedInventoryState(ourAssets);
if (Trading.IsEmptyForMatching(ourFullState, ourTradableState)) {
if (MatchingUtilities.IsEmptyForMatching(ourFullState, ourTradableState)) {
// User doesn't have any more dupes in the inventory
Bot.ArchiLogger.LogGenericTrace(string.Format(CultureInfo.CurrentCulture, Strings.ErrorIsEmpty, $"{nameof(ourFullState)} || {nameof(ourTradableState)}"));
@@ -1248,6 +1247,14 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
byte failuresInRow = 0;
uint matchedSets = 0;
HashSet<(uint RealAppID, EAssetType Type, EAssetRarity Rarity)> skippedSetsThisUser = [];
HashSet<(uint RealAppID, EAssetType Type, EAssetRarity Rarity)> skippedSetsThisTrade = [];
Dictionary<ulong, uint> classIDsToGive = new();
Dictionary<ulong, uint> classIDsToReceive = new();
Dictionary<ulong, uint> fairClassIDsToGive = new();
Dictionary<ulong, uint> fairClassIDsToReceive = new();
foreach (ListedUser listedUser in listedUsers.Where(listedUser => (listedUser.SteamID != Bot.SteamID) && acceptedMatchableTypes.Any(listedUser.MatchableTypes.Contains) && !Bot.IsBlacklistedFromTrades(listedUser.SteamID)).OrderByDescending(listedUser => !deprioritizedSteamIDs.Contains(listedUser.SteamID)).ThenByDescending(static listedUser => listedUser.TotalGamesCount > 1).ThenByDescending(static listedUser => listedUser.MatchEverything).ThenBy(static listedUser => listedUser.TotalInventoryCount)) {
if (failuresInRow >= WebBrowser.MaxTries) {
Bot.ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, $"{nameof(failuresInRow)} >= {WebBrowser.MaxTries}"));
@@ -1261,7 +1268,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
break;
}
HashSet<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity)> wantedSets = ourTradableState.Keys.Where(set => listedUser.MatchableTypes.Contains(set.Type)).ToHashSet();
HashSet<(uint RealAppID, EAssetType Type, EAssetRarity Rarity)> wantedSets = ourTradableState.Keys.Where(set => listedUser.MatchableTypes.Contains(set.Type)).ToHashSet();
if (wantedSets.Count == 0) {
continue;
@@ -1282,26 +1289,27 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
continue;
}
HashSet<Asset> theirInventory = listedUser.Assets.Where(item => (!listedUser.MatchEverything || item.Tradable) && wantedSets.Contains((item.RealAppID, item.Type, item.Rarity)) && ((tradeHoldDuration.Value == 0) || !(item.Type is Asset.EType.FoilTradingCard or Asset.EType.TradingCard && CardsFarmer.SalesBlacklist.Contains(item.RealAppID)))).Select(static asset => asset.ToAsset()).ToHashSet();
HashSet<Asset> theirInventory = listedUser.Assets.Where(item => (!listedUser.MatchEverything || item.Tradable) && wantedSets.Contains((item.RealAppID, item.Type, item.Rarity)) && ((tradeHoldDuration.Value == 0) || !(item.Type is EAssetType.FoilTradingCard or EAssetType.TradingCard && CardsFarmer.SalesBlacklist.Contains(item.RealAppID)))).Select(static asset => asset.ToAsset()).ToHashSet();
if (theirInventory.Count == 0) {
continue;
}
HashSet<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity)> skippedSetsThisUser = [];
skippedSetsThisUser.Clear();
Dictionary<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity), Dictionary<ulong, uint>> theirTradableState = Trading.GetTradableInventoryState(theirInventory);
Dictionary<(uint RealAppID, EAssetType Type, EAssetRarity Rarity), Dictionary<ulong, uint>> theirTradableState = MatchingUtilities.GetTradableInventoryState(theirInventory);
for (byte i = 0; i < Trading.MaxTradesPerAccount; i++) {
byte itemsInTrade = 0;
HashSet<(uint RealAppID, Asset.EType Type, Asset.ERarity Rarity)> skippedSetsThisTrade = [];
Dictionary<ulong, uint> classIDsToGive = new();
Dictionary<ulong, uint> classIDsToReceive = new();
Dictionary<ulong, uint> fairClassIDsToGive = new();
Dictionary<ulong, uint> fairClassIDsToReceive = new();
skippedSetsThisTrade.Clear();
foreach (((uint RealAppID, Asset.EType Type, Asset.ERarity Rarity) set, Dictionary<ulong, uint> ourFullItems) in ourFullState.Where(set => !skippedSetsThisUser.Contains(set.Key) && listedUser.MatchableTypes.Contains(set.Key.Type) && set.Value.Values.Any(static count => count > 1))) {
classIDsToGive.Clear();
classIDsToReceive.Clear();
fairClassIDsToGive.Clear();
fairClassIDsToReceive.Clear();
foreach (((uint RealAppID, EAssetType Type, EAssetRarity Rarity) set, Dictionary<ulong, uint> ourFullItems) in ourFullState.Where(set => !skippedSetsThisUser.Contains(set.Key) && listedUser.MatchableTypes.Contains(set.Key.Type) && set.Value.Values.Any(static count => count > 1))) {
if (!ourTradableState.TryGetValue(set, out Dictionary<ulong, uint>? ourTradableItems) || (ourTradableItems.Count == 0)) {
// We may have no more tradable items from this set
continue;
@@ -1312,14 +1320,14 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
continue;
}
if (Trading.IsEmptyForMatching(ourFullItems, ourTradableItems)) {
if (MatchingUtilities.IsEmptyForMatching(ourFullItems, ourTradableItems)) {
// We may have no more matchable items from this set
continue;
}
// Those 2 collections are on user-basis since we can't be sure that the trade passes through (and therefore we need to keep original state in case of a failure)
Dictionary<ulong, uint> ourFullSet = new(ourFullItems);
Dictionary<ulong, uint> ourTradableSet = new(ourTradableItems);
Dictionary<ulong, uint> ourFullSet = ourFullItems.ToDictionary();
Dictionary<ulong, uint> ourTradableSet = ourTradableItems.ToDictionary();
bool match;
@@ -1331,26 +1339,27 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
continue;
}
foreach ((ulong theirItem, uint theirTradableAmount) in theirTradableItems.OrderBy(item => ourFullSet.TryGetValue(item.Key, out uint ourAmountOfTheirItem) ? ourAmountOfTheirItem : 0)) {
foreach ((ulong theirItem, uint theirTradableAmount) in theirTradableItems.OrderBy(item => ourFullSet.GetValueOrDefault(item.Key))) {
if (ourFullSet.TryGetValue(theirItem, out uint ourAmountOfTheirItem) && (ourFullAmount <= ourAmountOfTheirItem + 1)) {
continue;
}
if (!listedUser.MatchEverything) {
// We have a potential match, let's check fairness for them
fairClassIDsToGive.TryGetValue(ourItem, out uint fairGivenAmount);
fairClassIDsToReceive.TryGetValue(theirItem, out uint fairReceivedAmount);
uint fairGivenAmount = fairClassIDsToGive.GetValueOrDefault(ourItem);
uint fairReceivedAmount = fairClassIDsToReceive.GetValueOrDefault(theirItem);
fairClassIDsToGive[ourItem] = ++fairGivenAmount;
fairClassIDsToReceive[theirItem] = ++fairReceivedAmount;
// Filter their inventory for the sets we're trading or have traded with this user
HashSet<Asset> fairFiltered = theirInventory.Where(item => ((item.RealAppID == set.RealAppID) && (item.Type == set.Type) && (item.Rarity == set.Rarity)) || skippedSetsThisTrade.Contains((item.RealAppID, item.Type, item.Rarity))).Select(static item => item.CreateShallowCopy()).ToHashSet();
HashSet<Asset> fairFiltered = theirInventory.Where(item => ((item.RealAppID == set.RealAppID) && (item.Type == set.Type) && (item.Rarity == set.Rarity)) || skippedSetsThisTrade.Contains((item.RealAppID, item.Type, item.Rarity))).ToHashSet();
// Copy list to HashSet<Steam.Asset>
HashSet<Asset> fairItemsToGive = Trading.GetTradableItemsFromInventory(ourInventory.Values.Where(item => ((item.RealAppID == set.RealAppID) && (item.Type == set.Type) && (item.Rarity == set.Rarity)) || skippedSetsThisTrade.Contains((item.RealAppID, item.Type, item.Rarity))).Select(static item => item.CreateShallowCopy()).ToHashSet(), fairClassIDsToGive.ToDictionary(static classID => classID.Key, static classID => classID.Value));
HashSet<Asset> fairItemsToReceive = Trading.GetTradableItemsFromInventory(fairFiltered.Select(static item => item.CreateShallowCopy()).ToHashSet(), fairClassIDsToReceive.ToDictionary(static classID => classID.Key, static classID => classID.Value));
// Get tradable items from our and their inventory
HashSet<Asset> fairItemsToGive = MatchingUtilities.GetTradableItemsFromInventory(ourInventory.Values.Where(item => ((item.RealAppID == set.RealAppID) && (item.Type == set.Type) && (item.Rarity == set.Rarity)) || skippedSetsThisTrade.Contains((item.RealAppID, item.Type, item.Rarity))).ToHashSet(), fairClassIDsToGive);
HashSet<Asset> fairItemsToReceive = MatchingUtilities.GetTradableItemsFromInventory(fairFiltered, fairClassIDsToReceive);
// Actual check
// Actual check, since we do this against remote user, we flip places for items
if (!Trading.IsTradeNeutralOrBetter(fairFiltered, fairItemsToReceive, fairItemsToGive)) {
// Revert the changes
if (fairGivenAmount > 1) {
@@ -1373,11 +1382,11 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
skippedSetsThisTrade.Add(set);
// Update our state based on given items
classIDsToGive[ourItem] = classIDsToGive.TryGetValue(ourItem, out uint ourGivenAmount) ? ourGivenAmount + 1 : 1;
classIDsToGive[ourItem] = classIDsToGive.GetValueOrDefault(ourItem) + 1;
ourFullSet[ourItem] = ourFullAmount - 1; // We don't need to remove anything here because we can guarantee that ourItem.Value is at least 2
// Update our state based on received items
classIDsToReceive[theirItem] = classIDsToReceive.TryGetValue(theirItem, out uint ourReceivedAmount) ? ourReceivedAmount + 1 : 1;
classIDsToReceive[theirItem] = classIDsToReceive.GetValueOrDefault(theirItem) + 1;
ourFullSet[theirItem] = ourAmountOfTheirItem + 1;
if (ourTradableAmount > 1) {
@@ -1418,8 +1427,8 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
}
// Remove the items from inventories
HashSet<Asset> itemsToGive = Trading.GetTradableItemsFromInventory(ourInventory.Values, classIDsToGive);
HashSet<Asset> itemsToReceive = Trading.GetTradableItemsFromInventory(theirInventory, classIDsToReceive, true);
HashSet<Asset> itemsToGive = MatchingUtilities.GetTradableItemsFromInventory(ourInventory.Values, classIDsToGive);
HashSet<Asset> itemsToReceive = MatchingUtilities.GetTradableItemsFromInventory(theirInventory, classIDsToReceive, true);
if ((itemsToGive.Count != itemsToReceive.Count) || !Trading.IsFairExchange(itemsToGive, itemsToReceive)) {
// Failsafe
@@ -1503,10 +1512,14 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
// However, since this is only an assumption, we must mark newly acquired items as untradable so we're sure that they're not considered for trading, only for matching
foreach (Asset itemToReceive in itemsToReceive) {
if (ourInventory.TryGetValue(itemToReceive.AssetID, out Asset? item)) {
item.Tradable = false;
item.Description ??= new InventoryDescription(itemToReceive.AppID, itemToReceive.ClassID, itemToReceive.InstanceID, realAppID: itemToReceive.RealAppID, type: itemToReceive.Type, rarity: itemToReceive.Rarity);
item.Description.Body.tradable = false;
item.Amount += itemToReceive.Amount;
} else {
itemToReceive.Tradable = false;
itemToReceive.Description ??= new InventoryDescription(itemToReceive.AppID, itemToReceive.ClassID, itemToReceive.InstanceID, realAppID: itemToReceive.RealAppID, type: itemToReceive.Type, rarity: itemToReceive.Rarity);
itemToReceive.Description.Body.tradable = false;
ourInventory[itemToReceive.AssetID] = itemToReceive;
}
@@ -1515,11 +1528,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
throw new InvalidOperationException(nameof(fullAmounts));
}
if (!fullAmounts.TryGetValue(itemToReceive.ClassID, out uint fullAmount)) {
fullAmount = 0;
}
fullAmounts[itemToReceive.ClassID] = itemToReceive.Amount + fullAmount;
fullAmounts[itemToReceive.ClassID] = fullAmounts.GetValueOrDefault(itemToReceive.ClassID) + itemToReceive.Amount;
}
skippedSetsThisUser.UnionWith(skippedSetsThisTrade);
@@ -1531,7 +1540,7 @@ internal sealed class RemoteCommunication : IAsyncDisposable, IDisposable {
matchedSets += (uint) skippedSetsThisUser.Count;
if (Trading.IsEmptyForMatching(ourFullState, ourTradableState)) {
if (MatchingUtilities.IsEmptyForMatching(ourFullState, ourTradableState)) {
// User doesn't have any more dupes in the inventory
break;
}

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net

View File

@@ -1,8 +1,10 @@
// ----------------------------------------------------------------------------------------------
// _ _ _ ____ _ _____
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
// ----------------------------------------------------------------------------------------------
// |
// Copyright 2015-2024 Łukasz "JustArchi" Domeradzki
// Contact: JustArchi@JustArchi.net
@@ -36,8 +38,6 @@ using SteamKit2.Internal;
namespace ArchiSteamFarm.OfficialPlugins.MobileAuthenticator;
internal static class Commands {
private const byte MaxFinalizationAttempts = 900 / Steam.Security.MobileAuthenticator.CodeInterval;
internal static async Task<string?> OnBotCommand(Bot bot, EAccess access, string message, string[] args, ulong steamID = 0) {
ArgumentNullException.ThrowIfNull(bot);
@@ -144,43 +144,22 @@ internal static class Commands {
ulong steamTime = await mobileAuthenticator.GetSteamTime().ConfigureAwait(false);
bool successFinalizing = false;
string? code = mobileAuthenticator.GenerateTokenForTime(steamTime);
for (byte i = 0; i < MaxFinalizationAttempts; i++) {
if (i > 0) {
steamTime += Steam.Security.MobileAuthenticator.CodeInterval;
}
string? code = mobileAuthenticator.GenerateTokenForTime(steamTime);
if (string.IsNullOrEmpty(code)) {
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, nameof(mobileAuthenticator.GenerateTokenForTime)));
}
CTwoFactor_FinalizeAddAuthenticator_Response? response = await mobileAuthenticatorHandler.FinalizeAuthenticator(bot.SteamID, activationCode, code, steamTime).ConfigureAwait(false);
if (response == null) {
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, nameof(mobileAuthenticatorHandler.FinalizeAuthenticator)));
}
if (response.want_more) {
// OK, whatever
continue;
}
if (!response.success) {
EResult result = (EResult) response.status;
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, result));
}
successFinalizing = true;
break;
if (string.IsNullOrEmpty(code)) {
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, nameof(mobileAuthenticator.GenerateTokenForTime)));
}
if (!successFinalizing) {
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.ErrorRequestFailedTooManyTimes, MaxFinalizationAttempts));
CTwoFactor_FinalizeAddAuthenticator_Response? response = await mobileAuthenticatorHandler.FinalizeAuthenticator(bot.SteamID, activationCode, code, steamTime).ConfigureAwait(false);
if (response == null) {
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, nameof(mobileAuthenticatorHandler.FinalizeAuthenticator)));
}
if (!response.success) {
EResult result = (EResult) response.status;
return bot.Commands.FormatBotResponse(string.Format(CultureInfo.CurrentCulture, Strings.WarningFailedWithError, result));
}
if (!bot.TryImportAuthenticator(mobileAuthenticator)) {
@@ -220,7 +199,7 @@ internal static class Commands {
IList<string?> results = await Utilities.InParallel(bots.Select(bot => ResponseTwoFactorFinalize(Steam.Interaction.Commands.GetProxyAccess(bot, access, steamID), bot, activationCode))).ConfigureAwait(false);
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))];
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))!];
return responses.Count > 0 ? string.Join(Environment.NewLine, responses) : null;
}
@@ -313,7 +292,7 @@ internal static class Commands {
IList<string?> results = await Utilities.InParallel(bots.Select(bot => ResponseTwoFactorFinalized(Steam.Interaction.Commands.GetProxyAccess(bot, access, steamID), bot, activationCode))).ConfigureAwait(false);
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))];
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))!];
return responses.Count > 0 ? string.Join(Environment.NewLine, responses) : null;
}
@@ -392,7 +371,7 @@ internal static class Commands {
IList<string?> results = await Utilities.InParallel(bots.Select(bot => ResponseTwoFactorInit(Steam.Interaction.Commands.GetProxyAccess(bot, access, steamID), bot))).ConfigureAwait(false);
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))];
List<string> responses = [..results.Where(static result => !string.IsNullOrEmpty(result))!];
return responses.Count > 0 ? string.Join(Environment.NewLine, responses) : null;
}

View File

@@ -9,21 +9,21 @@
namespace ArchiSteamFarm.OfficialPlugins.MobileAuthenticator.Localization {
using System;
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
[System.Diagnostics.DebuggerNonUserCodeAttribute()]
[System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
internal class Strings {
private static System.Resources.ResourceManager resourceMan;
private static System.Globalization.CultureInfo resourceCulture;
[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
internal Strings() {
}
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
internal static System.Resources.ResourceManager ResourceManager {
get {
@@ -34,7 +34,7 @@ namespace ArchiSteamFarm.OfficialPlugins.MobileAuthenticator.Localization {
return resourceMan;
}
}
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
internal static System.Globalization.CultureInfo Culture {
get {

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

View File

@@ -53,13 +53,11 @@
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
</value>
</resheader>
</root>

Some files were not shown because too many files have changed in this diff Show More