Compare commits

...

22 Commits

Author SHA1 Message Date
10a50948fc Merge pull request 'asset tool v0.4.12 update rbx-dom' () from staging into master
Reviewed-on: 
2025-05-01 00:26:28 +00:00
9eabb0197c
asset-tool v0.4.12 update rbx-dom 2025-04-30 17:23:36 -07:00
fa9d42fc1f
update deps 2025-04-30 17:13:02 -07:00
8f754f0bca
update rbx-dom 2025-04-30 17:12:49 -07:00
2987a6b321 Merge pull request 'v0.4.4 api tweaks' () from staging into master
Reviewed-on: 
2025-04-11 01:29:34 +00:00
450b6a0829
update deps 2025-04-10 17:26:47 -07:00
091a2a92f1
rbx_asset: v0.4.4 parse string ints + save intermediate allocation 2025-04-10 17:24:49 -07:00
31aae80cc5
rbx_asset: change api to save intermediate allocation 2025-04-10 17:24:49 -07:00
041cc75015
rbx_asset: move code into util, types 2025-04-10 17:24:49 -07:00
d77312309f
rbx_asset: helpers for integers within a string 2025-04-10 17:24:49 -07:00
50145460b9
rbx_asset: simplify gzip logic 2025-04-10 00:25:34 -07:00
ad8e1865f3 Merge pull request 'rbx_asset: cloud: implement new asset-delivery-api' () from staging into master
Reviewed-on: 
2025-04-06 22:23:12 +00:00
27deef3dd6 Merge pull request 'UploadResponse.AssetVersion + add continue to DownloadUserInventoryJson' () from staging into master
Reviewed-on: 
2025-04-04 20:56:56 +00:00
89a478eaac Merge pull request 'asset-tool: add AssetDetails + DownloadVersionV2' () from staging into master
Reviewed-on: 
2025-04-03 22:54:41 +00:00
d6adc1da45 Merge pull request 'v0.4.9 roblox error in body' () from staging into master
Reviewed-on: 
2025-02-11 21:54:11 +00:00
e89edf287f Merge pull request 'v0.4.8 better errors' () from staging into master
Reviewed-on: 
2025-01-17 10:59:21 +00:00
4ffeaa5784 Merge pull request 'v0.4.7 user inventory + git fix' () from staging into master
Reviewed-on: 
2024-10-01 20:10:30 +00:00
607f964928 Merge pull request 'add documentation, update dependencies' () from staging into master
Reviewed-on: 
2024-09-17 04:44:30 +00:00
8dc7c96f2d Merge pull request 'Create multiple assets concurrently' () from staging into master
Reviewed-on: 
2024-08-17 18:00:27 +00:00
68d751f81f Merge pull request 'use old api for download, error on http status' () from staging into master
Reviewed-on: 
2024-07-16 18:21:06 +00:00
c2052be036 Merge pull request 'use old api for compile-upload-asset' () from staging into master
Reviewed-on: 
2024-07-10 17:18:05 +00:00
2e9485dea6 Merge pull request 'add old asset upload api' () from staging into master
Reviewed-on: 
2024-07-10 16:45:17 +00:00
11 changed files with 399 additions and 203 deletions

278
Cargo.lock generated

@ -17,6 +17,19 @@ version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627"
[[package]]
name = "ahash"
version = "0.8.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e89da841a80418a9b391ebaea17f5c112ffaaa96f621d2c285b5174da76b9011"
dependencies = [
"cfg-if",
"getrandom 0.2.16",
"once_cell",
"version_check",
"zerocopy 0.7.35",
]
[[package]]
name = "aho-corasick"
version = "1.1.3"
@ -93,9 +106,9 @@ dependencies = [
[[package]]
name = "anyhow"
version = "1.0.97"
version = "1.0.98"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dcfed56ad506cb2c684a14971b8861fdc3baaaae314b9e5f9bb532cbe3ba7a4f"
checksum = "e16d2d3311acee920a9eb8d33b8cbc1787ce4a264e85f964c2404b969bdcd487"
[[package]]
name = "arrayref"
@ -111,7 +124,7 @@ checksum = "7c02d123df017efcdfbd739ef81735b36c5ba83ec3c59c80a9d7ecc718f92e50"
[[package]]
name = "asset-tool"
version = "0.4.11"
version = "0.4.12"
dependencies = [
"anyhow",
"clap",
@ -181,9 +194,9 @@ checksum = "5c8214115b7bf84099f1309324e63141d4c5d7cc26862f97a0a857dbefe165bd"
[[package]]
name = "blake3"
version = "1.8.1"
version = "1.8.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "389a099b34312839e16420d499a9cad9650541715937ffbdd40d36f49e77eeb3"
checksum = "3888aaa89e4b2a40fca9848e400f6a658a5a3978de7be858e209cafa8be9a4a0"
dependencies = [
"arrayref",
"arrayvec",
@ -212,9 +225,9 @@ checksum = "d71b6127be86fdcfddb610f7182ac57211d4b18a3e9c82eb2d17662f2227ad6a"
[[package]]
name = "cc"
version = "1.2.17"
version = "1.2.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1fcb57c740ae1daf453ae85f16e37396f672b039e00d9d866e07ddb24e328e3a"
checksum = "04da6a0d40b948dfc4fa8f5bbf402b0fc1a64a28dbf7d12ffd683550f2c1b63a"
dependencies = [
"jobserver",
"libc",
@ -229,9 +242,9 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
[[package]]
name = "chrono"
version = "0.4.40"
version = "0.4.41"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1a7964611d71df112cb1730f2ee67324fcf4d0fc6606acbbe9bfe06df124637c"
checksum = "c469d952047f47f91b68d1cba3f10d63c11d73e4636f24f08daf0278abf01c4d"
dependencies = [
"android-tzdata",
"iana-time-zone",
@ -244,9 +257,9 @@ dependencies = [
[[package]]
name = "clap"
version = "4.5.35"
version = "4.5.37"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d8aa86934b44c19c50f87cc2790e19f54f7a67aedb64101c2e1a2e5ecfb73944"
checksum = "eccb054f56cbd38340b380d4a8e69ef1f02f1af43db2f0cc817a4774d80ae071"
dependencies = [
"clap_builder",
"clap_derive",
@ -254,9 +267,9 @@ dependencies = [
[[package]]
name = "clap_builder"
version = "4.5.35"
version = "4.5.37"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2414dbb2dd0695280da6ea9261e327479e9d37b0630f6b53ba2a11c60c679fd9"
checksum = "efd9466fac8543255d3b1fcad4762c5e116ffe808c8a3043d4263cd4fd4862a2"
dependencies = [
"anstream",
"anstyle",
@ -378,9 +391,9 @@ checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f"
[[package]]
name = "errno"
version = "0.3.10"
version = "0.3.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d"
checksum = "976dd42dc7e85965fe702eb8164f21f450704bdde31faefd6471dba214cb594e"
dependencies = [
"libc",
"windows-sys 0.59.0",
@ -523,9 +536,9 @@ dependencies = [
[[package]]
name = "getrandom"
version = "0.2.15"
version = "0.2.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7"
checksum = "335ff9f135e4384c8150d6f27c6daed433577f86b4750418338c01a1a2528592"
dependencies = [
"cfg-if",
"libc",
@ -567,9 +580,9 @@ dependencies = [
[[package]]
name = "h2"
version = "0.4.8"
version = "0.4.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5017294ff4bb30944501348f6f8e42e6ad28f42c8bbef7a74029aff064a4e3c2"
checksum = "75249d144030531f8dee69fe9cea04d3edf809a017ae445e2abdff6629e86633"
dependencies = [
"atomic-waker",
"bytes",
@ -586,9 +599,9 @@ dependencies = [
[[package]]
name = "hashbrown"
version = "0.15.2"
version = "0.15.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289"
checksum = "84b26c544d002229e640969970a2e74021aadf6e2f96372b9c58eff97de08eb3"
[[package]]
name = "heck"
@ -874,9 +887,9 @@ dependencies = [
[[package]]
name = "indexmap"
version = "2.8.0"
version = "2.9.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3954d50fe15b02142bf25d3b8bdadb634ec3948f103d04ffe3031bc8fe9d7058"
checksum = "cea70ddb795996207ad57735b50c5982d8844f38ba9ee5f1aedcfb708a2aa11e"
dependencies = [
"equivalent",
"hashbrown",
@ -951,9 +964,9 @@ checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe"
[[package]]
name = "libc"
version = "0.2.171"
version = "0.2.172"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c19937216e9d3aa9956d9bb8dfc0b0c8beb6058fc4f7a4dc4d850edf86a237d6"
checksum = "d750af042f7ef4f724306de029d18836c26c1765a54a6a3f094cbd23a7267ffa"
[[package]]
name = "libgit2-sys"
@ -997,9 +1010,9 @@ dependencies = [
[[package]]
name = "linux-raw-sys"
version = "0.9.3"
version = "0.9.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fe7db12097d22ec582439daf8618b8fdd1a7bef6270e9af3b1ebcd30893cf413"
checksum = "cd945864f07fe9f5371a27ad7b52a172b4b499999f1d97574c9fa68373937e12"
[[package]]
name = "litemap"
@ -1007,6 +1020,16 @@ version = "0.7.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "23fb14cb19457329c82206317a5663005a4d404783dc74f4252769b0d5f42856"
[[package]]
name = "lock_api"
version = "0.4.12"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17"
dependencies = [
"autocfg",
"scopeguard",
]
[[package]]
name = "log"
version = "0.4.27"
@ -1056,9 +1079,9 @@ dependencies = [
[[package]]
name = "miniz_oxide"
version = "0.8.6"
version = "0.8.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "29c72f6929239626840b28f919ce8981a317fc5dc63ce25c30d2ab372f94886f"
checksum = "3be647b768db090acb35d5ec5db2b0e1f1de11133ca123b9eacf5137868f892a"
dependencies = [
"adler2",
]
@ -1117,9 +1140,9 @@ checksum = "42f5e15c9953c5e4ccceeb2e7382a716482c34515315f7b03532b8b4e8393d2d"
[[package]]
name = "openssl"
version = "0.10.71"
version = "0.10.72"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5e14130c6a98cd258fdcb0fb6d744152343ff729cbfcb28c656a9d12b999fbcd"
checksum = "fedfea7d58a1f73118430a55da6a286e7b044961736ce96a16a17068ea25e5da"
dependencies = [
"bitflags 2.9.0",
"cfg-if",
@ -1149,9 +1172,9 @@ checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e"
[[package]]
name = "openssl-sys"
version = "0.9.106"
version = "0.9.108"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8bb61ea9811cc39e3c2069f40b8b8e2e70d8569b361f879786cc7ed48b777cdd"
checksum = "e145e1651e858e820e4860f7b9c5e169bc1d8ce1c86043be79fa7b7634821847"
dependencies = [
"cc",
"libc",
@ -1159,6 +1182,29 @@ dependencies = [
"vcpkg",
]
[[package]]
name = "parking_lot"
version = "0.12.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27"
dependencies = [
"lock_api",
"parking_lot_core",
]
[[package]]
name = "parking_lot_core"
version = "0.9.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8"
dependencies = [
"cfg-if",
"libc",
"redox_syscall",
"smallvec",
"windows-targets 0.52.6",
]
[[package]]
name = "paste"
version = "1.0.15"
@ -1195,14 +1241,14 @@ version = "0.2.21"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9"
dependencies = [
"zerocopy",
"zerocopy 0.8.25",
]
[[package]]
name = "proc-macro2"
version = "1.0.94"
version = "1.0.95"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a31971752e70b8b2686d7e46ec17fb38dad4051d94024c88df49b667caea9c84"
checksum = "02b3e5e68a3a1a02aad3ec490a98007cbc13c37cbe84a3cd7b8e406d76e7f778"
dependencies = [
"unicode-ident",
]
@ -1268,7 +1314,7 @@ version = "0.6.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c"
dependencies = [
"getrandom 0.2.15",
"getrandom 0.2.16",
]
[[package]]
@ -1293,8 +1339,9 @@ dependencies = [
[[package]]
name = "rbx_asset"
version = "0.4.3"
version = "0.4.4"
dependencies = [
"bytes",
"chrono",
"flate2",
"reqwest",
@ -1305,10 +1352,11 @@ dependencies = [
[[package]]
name = "rbx_binary"
version = "0.7.7"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7b85057e8ff75a1ce99248200c4b3c7b481a3d52f921f1053ecd67921dcc7930"
checksum = "9573fee5e073d7b303f475c285197fdc8179468de66ca60ee115a58fbac99296"
dependencies = [
"ahash",
"log",
"lz4",
"profiling",
@ -1316,23 +1364,26 @@ dependencies = [
"rbx_reflection",
"rbx_reflection_database",
"thiserror",
"zstd",
]
[[package]]
name = "rbx_dom_weak"
version = "2.9.0"
version = "3.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fcd2a17d09e46af0805f8b311a926402172b97e8d9388745c9adf8f448901841"
checksum = "04425cf6e9376e5486f4fb35906c120d1b1b45618a490318cf563fab1fa230a9"
dependencies = [
"ahash",
"rbx_types",
"serde",
"ustr",
]
[[package]]
name = "rbx_reflection"
version = "4.7.0"
version = "5.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8118ac6021d700e8debe324af6b40ecfd2cef270a00247849dbdfeebb0802677"
checksum = "1b6d0d62baa613556b058a5f94a53b01cf0ccde0ea327ce03056e335b982e77e"
dependencies = [
"rbx_types",
"serde",
@ -1341,9 +1392,9 @@ dependencies = [
[[package]]
name = "rbx_reflection_database"
version = "0.2.12+roblox-638"
version = "1.0.3+roblox-670"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0e29381d675420e841f8c02db5755cbb2545ed3e13f56c539546dc58702b512a"
checksum = "e22c05ef92528c0fb0cc580592a65ca178d3ea9beb07a1d9ca0a2503c4f3721c"
dependencies = [
"lazy_static",
"rbx_reflection",
@ -1353,9 +1404,9 @@ dependencies = [
[[package]]
name = "rbx_types"
version = "1.10.0"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e30f49b2a3bb667e4074ba73c2dfb8ca0873f610b448ccf318a240acfdec6c73"
checksum = "78e4fdde46493def107e5f923d82e813dec9b3eef52c2f75fbad3a716023eda2"
dependencies = [
"base64 0.13.1",
"bitflags 1.3.2",
@ -1368,10 +1419,11 @@ dependencies = [
[[package]]
name = "rbx_xml"
version = "0.13.5"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2b14b3027bc9ccd82e2fc854c8bcd25ed58318e570c355bf2cf63df9cdbd5ba8"
checksum = "bb623833c31cc43bbdaeb32f5e91db8ecd63fc46e438d0d268baf9e61539cf1c"
dependencies = [
"ahash",
"base64 0.13.1",
"log",
"rbx_dom_weak",
@ -1380,6 +1432,15 @@ dependencies = [
"xml-rs",
]
[[package]]
name = "redox_syscall"
version = "0.5.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d2f103c6d277498fbceb16e84d317e2a400f160f46904d5f5410848c829511a3"
dependencies = [
"bitflags 2.9.0",
]
[[package]]
name = "regex"
version = "1.11.1"
@ -1462,7 +1523,7 @@ checksum = "a4689e6c2294d81e88dc6261c768b63bc4fcdb852be6d1352498b114f61383b7"
dependencies = [
"cc",
"cfg-if",
"getrandom 0.2.15",
"getrandom 0.2.16",
"libc",
"untrusted",
"windows-sys 0.52.0",
@ -1510,9 +1571,9 @@ checksum = "719b953e2095829ee67db738b3bfa9fa368c94900df327b3f07fe6e794d2fe1f"
[[package]]
name = "rustix"
version = "1.0.5"
version = "1.0.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d97817398dd4bb2e6da002002db259209759911da105da92bec29ccb12cf58bf"
checksum = "c71e83d6afe7ff64890ec6b71d6a69bb8a610ab78ce364b3352876bb4c801266"
dependencies = [
"bitflags 2.9.0",
"errno",
@ -1523,9 +1584,9 @@ dependencies = [
[[package]]
name = "rustls"
version = "0.23.25"
version = "0.23.26"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "822ee9188ac4ec04a2f0531e55d035fb2de73f18b41a63c70c2712503b6fb13c"
checksum = "df51b5869f3a441595eac5e8ff14d486ff285f7b8c0df8770e49c3b56351f0f0"
dependencies = [
"once_cell",
"rustls-pki-types",
@ -1581,6 +1642,12 @@ dependencies = [
"windows-sys 0.59.0",
]
[[package]]
name = "scopeguard"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
[[package]]
name = "security-framework"
version = "2.11.1"
@ -1665,9 +1732,9 @@ dependencies = [
[[package]]
name = "smallvec"
version = "1.14.0"
version = "1.15.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7fcf8323ef1faaee30a44a340193b1ac6814fd9b7b4e88e9d4519a3e4abe1cfd"
checksum = "8917285742e9f3e1683f0a9c4e6b57960b7314d0b08d30d1ecd426713ee2eee9"
[[package]]
name = "socket2"
@ -1699,9 +1766,9 @@ checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292"
[[package]]
name = "syn"
version = "2.0.100"
version = "2.0.101"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b09a44accad81e1ba1cd74a32461ba89dee89095ba17b32f5d03683b1b1fc2a0"
checksum = "8ce2b7fc941b3a24138a0a7cf8e858bfc6a992e7978a068a5c760deb0ed43caf"
dependencies = [
"proc-macro2",
"quote",
@ -1719,9 +1786,9 @@ dependencies = [
[[package]]
name = "synstructure"
version = "0.13.1"
version = "0.13.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971"
checksum = "728a70f3dbaf5bab7f0c4b1ac8d7ae5ea60a4b5549c8a5914361c99147a709d2"
dependencies = [
"proc-macro2",
"quote",
@ -1794,9 +1861,9 @@ dependencies = [
[[package]]
name = "tokio"
version = "1.44.1"
version = "1.44.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f382da615b842244d4b8738c82ed1275e6c5dd90c459a30941cd07080b06c91a"
checksum = "e6b88822cbe49de4185e3a4cbf8321dd487cf5fe0c5c65695fef6346371e9c48"
dependencies = [
"backtrace",
"bytes",
@ -1841,9 +1908,9 @@ dependencies = [
[[package]]
name = "tokio-util"
version = "0.7.14"
version = "0.7.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6b9590b93e6fcc1739458317cccd391ad3955e2bde8913edf6f95f9e65a8f034"
checksum = "66a539a9ad6d5d281510d5bd368c973d636c02dbf8a67300bfb6b950696ad7df"
dependencies = [
"bytes",
"futures-core",
@ -1933,6 +2000,19 @@ dependencies = [
"percent-encoding",
]
[[package]]
name = "ustr"
version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "18b19e258aa08450f93369cf56dd78063586adf19e92a75b338a800f799a0208"
dependencies = [
"ahash",
"byteorder",
"lazy_static",
"parking_lot",
"serde",
]
[[package]]
name = "utf16_iter"
version = "1.0.5"
@ -1957,6 +2037,12 @@ version = "0.2.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426"
[[package]]
name = "version_check"
version = "0.9.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a"
[[package]]
name = "want"
version = "0.3.1"
@ -2310,9 +2396,9 @@ checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51"
[[package]]
name = "xml-rs"
version = "0.8.25"
version = "0.8.26"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c5b940ebc25896e71dd073bad2dbaa2abfe97b0a391415e22ad1326d9c54e3c4"
checksum = "a62ce76d9b56901b19a74f19431b0d8b3bc7ca4ad685a746dfd78ca8f4fc6bda"
[[package]]
name = "yoke"
@ -2340,18 +2426,38 @@ dependencies = [
[[package]]
name = "zerocopy"
version = "0.8.24"
version = "0.7.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2586fea28e186957ef732a5f8b3be2da217d65c5969d4b1e17f973ebbe876879"
checksum = "1b9b4fd18abc82b8136838da5d50bae7bdea537c574d8dc1a34ed098d6c166f0"
dependencies = [
"zerocopy-derive",
"zerocopy-derive 0.7.35",
]
[[package]]
name = "zerocopy"
version = "0.8.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a1702d9583232ddb9174e01bb7c15a2ab8fb1bc6f227aa1233858c351a3ba0cb"
dependencies = [
"zerocopy-derive 0.8.25",
]
[[package]]
name = "zerocopy-derive"
version = "0.8.24"
version = "0.7.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a996a8f63c5c4448cd959ac1bab0aaa3306ccfd060472f85943ee0750f0169be"
checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "zerocopy-derive"
version = "0.8.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "28a6e20d751156648aa063f3800b706ee209a32c0b4d9f24be3d980b01be55ef"
dependencies = [
"proc-macro2",
"quote",
@ -2406,3 +2512,31 @@ dependencies = [
"quote",
"syn",
]
[[package]]
name = "zstd"
version = "0.13.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e91ee311a569c327171651566e07972200e76fcfe2242a4fa446149a3881c08a"
dependencies = [
"zstd-safe",
]
[[package]]
name = "zstd-safe"
version = "7.2.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f49c4d5f0abb602a93fb8736af2a4f4dd9512e36f7f570d66e65ff867ed3b9d"
dependencies = [
"zstd-sys",
]
[[package]]
name = "zstd-sys"
version = "2.0.15+zstd.1.5.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "eb81183ddd97d0c74cedf1d50d85c8d08c1b8b68ee863bdee9e706eedba1a237"
dependencies = [
"cc",
"pkg-config",
]

@ -1,7 +1,7 @@
workspace = { members = ["rbx_asset", "rox_compiler"] }
[package]
name = "asset-tool"
version = "0.4.11"
version = "0.4.12"
edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
@ -13,10 +13,10 @@ futures = "0.3.30"
git2 = "0.20.0"
lazy-regex = "3.1.0"
rbx_asset = { path = "rbx_asset" }
rbx_binary = "0.7.4"
rbx_dom_weak = "2.7.0"
rbx_reflection_database = "0.2.10"
rbx_xml = "0.13.3"
rbx_binary = "1.0.0"
rbx_dom_weak = "3.0.0"
rbx_reflection_database = "1.0.3"
rbx_xml = "1.0.0"
rox_compiler = { path = "rox_compiler" }
serde_json = "1.0.111"
tokio = { version = "1.35.1", features = ["macros", "rt-multi-thread", "fs"] }

@ -1,6 +1,6 @@
[package]
name = "rbx_asset"
version = "0.4.3"
version = "0.4.4"
edition = "2021"
publish = ["strafesnet"]
repository = "https://git.itzana.me/StrafesNET/asset-tool"
@ -10,9 +10,14 @@ authors = ["Rhys Lloyd <krakow20@gmail.com>"]
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[features]
default = ["gzip"]
gzip = ["dep:flate2"]
[dependencies]
bytes = "1.10.1"
chrono = { version = "0.4.38", features = ["serde"] }
flate2 = "1.0.29"
flate2 = { version = "1.0.29", optional = true }
reqwest = { version = "0.12.4", features = ["json","multipart"] }
serde = { version = "1.0.199", features = ["derive"] }
serde_json = "1.0.111"

@ -1,4 +1,5 @@
use crate::{ResponseError,ReaderType,maybe_gzip_decode,read_readable};
use crate::util::{serialize_u64,deserialize_u64,response_ok};
use crate::types::{ResponseError,MaybeGzippedBytes};
#[derive(Debug,serde::Deserialize,serde::Serialize)]
#[allow(nonstandard_style,dead_code)]
@ -65,8 +66,8 @@ pub struct UpdateAssetRequest{
#[derive(Clone,Debug,serde::Deserialize,serde::Serialize)]
#[allow(nonstandard_style,dead_code)]
pub enum Creator{
userId(String),//u64 string
groupId(String),//u64 string
userId(#[serde(deserialize_with="deserialize_u64",serialize_with="serialize_u64")]u64),
groupId(#[serde(deserialize_with="deserialize_u64",serialize_with="serialize_u64")]u64),
}
#[derive(Debug,serde::Deserialize,serde::Serialize)]
#[allow(nonstandard_style,dead_code)]
@ -146,14 +147,19 @@ pub struct GetAssetLatestRequest{
#[derive(Debug,serde::Deserialize,serde::Serialize)]
#[allow(nonstandard_style,dead_code)]
pub struct AssetResponse{
pub assetId:String,//u64 wrapped in quotes wohoo!!
//u64 wrapped in quotes wohoo!!
#[serde(deserialize_with="deserialize_u64")]
#[serde(serialize_with="serialize_u64")]
pub assetId:u64,
pub assetType:AssetType,
pub creationContext:CreationContext,
pub description:Option<String>,
pub displayName:String,
pub path:String,
pub revisionCreateTime:chrono::DateTime<chrono::Utc>,
pub revisionId:String,//u64
#[serde(deserialize_with="deserialize_u64")]
#[serde(serialize_with="serialize_u64")]
pub revisionId:u64,
pub moderationResult:ModerationResult,
pub icon:Option<String>,
#[serde(default)]
@ -169,7 +175,6 @@ pub enum GetError{
ParseError(url::ParseError),
Response(ResponseError),
Reqwest(reqwest::Error),
IO(std::io::Error)
}
impl std::fmt::Display for GetError{
fn fmt(&self,f:&mut std::fmt::Formatter<'_>)->std::fmt::Result{
@ -375,7 +380,7 @@ impl Context{
.text("request",request_config)
.part("fileContent",part);
let operation=crate::response_ok(
let operation=response_ok(
self.post_form(url,form).await.map_err(CreateError::Reqwest)?
).await.map_err(CreateError::Response)?
.json::<RobloxOperation>().await.map_err(CreateError::Reqwest)?;
@ -394,7 +399,7 @@ impl Context{
.text("request",request_config)
.part("fileContent",reqwest::multipart::Part::bytes(body));
let operation=crate::response_ok(
let operation=response_ok(
self.patch_form(url,form).await.map_err(UpdateError::Reqwest)?
).await.map_err(UpdateError::Response)?
.json::<RobloxOperation>().await.map_err(UpdateError::Reqwest)?;
@ -407,7 +412,7 @@ impl Context{
let raw_url=format!("https://apis.roblox.com/assets/v1/operations/{}",config.operation_id);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json::<RobloxOperation>().await.map_err(GetError::Reqwest)
@ -416,7 +421,7 @@ impl Context{
let raw_url=format!("https://apis.roblox.com/assets/v1/assets/{}",config.asset_id);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json::<AssetResponse>().await.map_err(GetError::Reqwest)
@ -425,7 +430,7 @@ impl Context{
let raw_url=format!("https://apis.roblox.com/assets/v1/assets/{}/versions/{}",config.asset_id,config.version);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json::<AssetResponse>().await.map_err(GetError::Reqwest)
@ -434,7 +439,7 @@ impl Context{
let raw_url=format!("https://apis.roblox.com/asset-delivery-api/v1/assetId/{}",config.asset_id);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json().await.map_err(GetError::Reqwest)
@ -443,30 +448,26 @@ impl Context{
let raw_url=format!("https://apis.roblox.com/asset-delivery-api/v1/assetId/{}/version/{}",config.asset_id,config.version);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json().await.map_err(GetError::Reqwest)
}
pub async fn get_asset(&self,config:&AssetLocation)->Result<Vec<u8>,GetError>{
pub async fn get_asset(&self,config:&AssetLocation)->Result<MaybeGzippedBytes,GetError>{
let url=reqwest::Url::parse(config.location()).map_err(GetError::ParseError)?;
let body=crate::response_ok(
let bytes=response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.bytes().await.map_err(GetError::Reqwest)?;
match maybe_gzip_decode(std::io::Cursor::new(body)){
Ok(ReaderType::GZip(readable))=>read_readable(readable),
Ok(ReaderType::Raw(readable))=>read_readable(readable),
Err(e)=>Err(e),
}.map_err(GetError::IO)
Ok(MaybeGzippedBytes::new(bytes))
}
pub async fn get_asset_versions(&self,config:AssetVersionsRequest)->Result<AssetVersionsResponse,AssetVersionsError>{
let raw_url=format!("https://apis.roblox.com/assets/v1/assets/{}/versions",config.asset_id);
let url=reqwest::Url::parse(raw_url.as_str()).map_err(AssetVersionsError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(AssetVersionsError::Reqwest)?
).await.map_err(AssetVersionsError::Response)?
.json::<AssetVersionsResponse>().await.map_err(AssetVersionsError::Reqwest)
@ -481,7 +482,7 @@ impl Context{
}
}
crate::response_ok(
response_ok(
self.get(url).await.map_err(InventoryPageError::Reqwest)?
).await.map_err(InventoryPageError::Response)?
.json::<InventoryPageResponse>().await.map_err(InventoryPageError::Reqwest)
@ -495,7 +496,7 @@ impl Context{
query.append_pair("versionType","Published");
}
crate::response_ok(
response_ok(
self.post(url,body).await.map_err(UpdateError::Reqwest)?
).await.map_err(UpdateError::Response)?
.json::<UpdatePlaceResponse>().await.map_err(UpdateError::Reqwest)

@ -1,4 +1,5 @@
use crate::{ResponseError,ReaderType,maybe_gzip_decode,read_readable};
use crate::util::response_ok;
use crate::types::{ResponseError,MaybeGzippedBytes};
#[derive(Debug)]
pub enum PostError{
@ -91,7 +92,6 @@ pub enum GetError{
ParseError(url::ParseError),
Response(ResponseError),
Reqwest(reqwest::Error),
IO(std::io::Error)
}
impl std::fmt::Display for GetError{
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
@ -371,7 +371,7 @@ impl Context{
query.append_pair("groupId",group_id.to_string().as_str());
}
}
let response=crate::response_ok(
let response=response_ok(
self.post(url,body).await.map_err(CreateError::PostError)?
).await.map_err(CreateError::Response)?;
@ -423,7 +423,7 @@ impl Context{
query.append_pair("groupId",group_id.to_string().as_str());
}
}
let response=crate::response_ok(
let response=response_ok(
self.post(url,body).await.map_err(UploadError::PostError)?
).await.map_err(UploadError::Response)?;
@ -449,7 +449,7 @@ impl Context{
})
}
}
pub async fn get_asset(&self,config:GetAssetRequest)->Result<Vec<u8>,GetError>{
pub async fn get_asset(&self,config:GetAssetRequest)->Result<MaybeGzippedBytes,GetError>{
let mut url=reqwest::Url::parse("https://assetdelivery.roblox.com/v1/asset/").map_err(GetError::ParseError)?;
//url borrow scope
{
@ -459,16 +459,13 @@ impl Context{
query.append_pair("version",version.to_string().as_str());
}
}
let body=crate::response_ok(
let bytes=response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.bytes().await.map_err(GetError::Reqwest)?;
match maybe_gzip_decode(std::io::Cursor::new(body)){
Ok(ReaderType::GZip(readable))=>read_readable(readable),
Ok(ReaderType::Raw(readable))=>read_readable(readable),
Err(e)=>Err(e),
}.map_err(GetError::IO)
Ok(MaybeGzippedBytes::new(bytes))
}
pub async fn get_asset_v2(&self,config:GetAssetRequest)->Result<GetAssetV2,GetAssetV2Error>{
let mut url=reqwest::Url::parse("https://assetdelivery.roblox.com/v2/asset").map_err(GetAssetV2Error::ParseError)?;
@ -480,7 +477,7 @@ impl Context{
query.append_pair("version",version.to_string().as_str());
}
}
let response=crate::response_ok(
let response=response_ok(
self.get(url).await.map_err(GetAssetV2Error::Reqwest)?
).await.map_err(GetAssetV2Error::Response)?;
@ -500,23 +497,19 @@ impl Context{
info,
})
}
pub async fn get_asset_v2_download(&self,config:&GetAssetV2Location)->Result<Vec<u8>,GetError>{
pub async fn get_asset_v2_download(&self,config:&GetAssetV2Location)->Result<MaybeGzippedBytes,GetError>{
let url=reqwest::Url::parse(config.location.as_str()).map_err(GetError::ParseError)?;
let body=crate::response_ok(
let bytes=response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.bytes().await.map_err(GetError::Reqwest)?;
match maybe_gzip_decode(std::io::Cursor::new(body)){
Ok(ReaderType::GZip(readable))=>read_readable(readable),
Ok(ReaderType::Raw(readable))=>read_readable(readable),
Err(e)=>Err(e),
}.map_err(GetError::IO)
Ok(MaybeGzippedBytes::new(bytes))
}
pub async fn get_asset_details(&self,config:GetAssetDetailsRequest)->Result<AssetDetails,GetError>{
let url=reqwest::Url::parse(format!("https://economy.roblox.com/v2/assets/{}/details",config.asset_id).as_str()).map_err(GetError::ParseError)?;
crate::response_ok(
response_ok(
self.get(url).await.map_err(GetError::Reqwest)?
).await.map_err(GetError::Response)?
.json().await.map_err(GetError::Reqwest)
@ -533,7 +526,7 @@ impl Context{
query.append_pair("cursor",cursor);
}
}
crate::response_ok(
response_ok(
self.get(url).await.map_err(PageError::Reqwest)?
).await.map_err(PageError::Response)?
.json::<AssetVersionsPageResponse>().await.map_err(PageError::Reqwest)
@ -548,7 +541,7 @@ impl Context{
query.append_pair("cursor",cursor);
}
}
crate::response_ok(
response_ok(
self.get(url).await.map_err(PageError::Reqwest)?
).await.map_err(PageError::Response)?
.json::<CreationsPageResponse>().await.map_err(PageError::Reqwest)
@ -562,7 +555,7 @@ impl Context{
query.append_pair("cursor",cursor);
}
}
crate::response_ok(
response_ok(
self.get(url).await.map_err(PageError::Reqwest)?
).await.map_err(PageError::Response)?
.json::<UserInventoryPageResponse>().await.map_err(PageError::Reqwest)

@ -1,56 +1,4 @@
pub mod cloud;
pub mod cookie;
#[allow(dead_code)]
#[derive(Debug)]
pub struct StatusCodeWithUrlAndBody{
pub status_code:reqwest::StatusCode,
pub url:url::Url,
pub body:String,
}
#[derive(Debug)]
pub enum ResponseError{
Reqwest(reqwest::Error),
StatusCodeWithUrlAndBody(StatusCodeWithUrlAndBody),
}
impl std::fmt::Display for ResponseError{
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f,"{self:?}")
}
}
impl std::error::Error for ResponseError{}
// lazy function to draw out meaningful info from http response on failure
pub(crate) async fn response_ok(response:reqwest::Response)->Result<reqwest::Response,ResponseError>{
let status_code=response.status();
if status_code.is_success(){
Ok(response)
}else{
let url=response.url().to_owned();
let bytes=response.bytes().await.map_err(ResponseError::Reqwest)?;
let body=String::from_utf8_lossy(&bytes).to_string();
Err(ResponseError::StatusCodeWithUrlAndBody(StatusCodeWithUrlAndBody{
status_code,
url,
body,
}))
}
}
//idk how to do this better
pub(crate) enum ReaderType<R:std::io::Read>{
GZip(flate2::read::GzDecoder<std::io::BufReader<R>>),
Raw(std::io::BufReader<R>),
}
pub(crate) fn maybe_gzip_decode<R:std::io::Read>(input:R)->std::io::Result<ReaderType<R>>{
let mut buf=std::io::BufReader::new(input);
let peek=std::io::BufRead::fill_buf(&mut buf)?;
match &peek[0..2]{
b"\x1f\x8b"=>Ok(ReaderType::GZip(flate2::read::GzDecoder::new(buf))),
_=>Ok(ReaderType::Raw(buf)),
}
}
pub(crate) fn read_readable(mut readable:impl std::io::Read)->std::io::Result<Vec<u8>>{
let mut contents=Vec::new();
readable.read_to_end(&mut contents)?;
Ok(contents)
}
pub mod types;
mod util;

68
rbx_asset/src/types.rs Normal file

@ -0,0 +1,68 @@
#[allow(dead_code)]
#[derive(Debug)]
pub struct StatusCodeWithUrlAndBody{
pub status_code:reqwest::StatusCode,
pub url:url::Url,
pub body:String,
}
#[derive(Debug)]
pub enum ResponseError{
Reqwest(reqwest::Error),
StatusCodeWithUrlAndBody(StatusCodeWithUrlAndBody),
}
impl std::fmt::Display for ResponseError{
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f,"{self:?}")
}
}
impl std::error::Error for ResponseError{}
#[cfg(feature="gzip")]
use std::io::Cursor;
#[cfg(feature="gzip")]
use flate2::read::GzDecoder;
/// Some bytes that might be gzipped. Use the read_with or to_vec methods to transparently decode gzip.
pub struct MaybeGzippedBytes{
bytes:bytes::Bytes,
}
impl MaybeGzippedBytes{
pub(crate) fn new(bytes:bytes::Bytes)->Self{
Self{bytes}
}
pub fn into_inner(self)->bytes::Bytes{
self.bytes
}
/// get a reference to the bytes, ignoring gzip decoding
pub fn as_raw_ref(&self)->&[u8]{
self.bytes.as_ref()
}
/// Transparently decode gzip data, if present (intermediate allocation)
#[cfg(feature="gzip")]
pub fn to_vec(&self)->std::io::Result<Vec<u8>>{
use std::io::Read;
match self.bytes.get(0..2){
Some(b"\x1f\x8b")=>{
let mut buf=Vec::new();
GzDecoder::new(Cursor::new(self.bytes.as_ref())).read_to_end(&mut buf)?;
Ok(buf)
},
_=>Ok(self.bytes.to_vec())
}
}
/// Read the bytes with the provided decoders.
/// The idea is to make a function that is generic over std::io::Read
/// and pass the same function to both closures.
/// This two closure hack must be done because of the different concrete types.
#[cfg(feature="gzip")]
pub fn read_with<'a,ReadGzip,ReadRaw,T>(&'a self,read_gzip:ReadGzip,read_raw:ReadRaw)->T
where
ReadGzip:Fn(GzDecoder<Cursor<&'a [u8]>>)->T,
ReadRaw:Fn(Cursor<&'a [u8]>)->T,
{
match self.bytes.get(0..2){
Some(b"\x1f\x8b")=>read_gzip(GzDecoder::new(Cursor::new(self.bytes.as_ref()))),
_=>read_raw(Cursor::new(self.bytes.as_ref()))
}
}
}

40
rbx_asset/src/util.rs Normal file

@ -0,0 +1,40 @@
use crate::types::{ResponseError,StatusCodeWithUrlAndBody};
// lazy function to draw out meaningful info from http response on failure
pub(crate) async fn response_ok(response:reqwest::Response)->Result<reqwest::Response,ResponseError>{
let status_code=response.status();
if status_code.is_success(){
Ok(response)
}else{
let url=response.url().to_owned();
let bytes=response.bytes().await.map_err(ResponseError::Reqwest)?;
let body=String::from_utf8_lossy(&bytes).to_string();
Err(ResponseError::StatusCodeWithUrlAndBody(StatusCodeWithUrlAndBody{
status_code,
url,
body,
}))
}
}
use serde::de::{Error,Unexpected};
use serde::{Deserializer,Serializer};
struct U64StringVisitor;
impl serde::de::Visitor<'_> for U64StringVisitor{
type Value=u64;
fn expecting(&self,formatter:&mut std::fmt::Formatter)->std::fmt::Result{
write!(formatter,"string value with int")
}
fn visit_str<E:Error>(self,v:&str)->Result<Self::Value,E>{
v.parse().map_err(|_|E::invalid_value(Unexpected::Str(v),&"u64"))
}
}
pub(crate) fn deserialize_u64<'de,D:Deserializer<'de>>(deserializer:D)->Result<u64,D::Error>{
deserializer.deserialize_any(U64StringVisitor)
}
pub(crate) fn serialize_u64<S:Serializer>(v:&u64,serializer:S)->Result<S::Ok,S::Error>{
serializer.serialize_str(v.to_string().as_str())
}

@ -12,6 +12,6 @@ authors = ["Rhys Lloyd <krakow20@gmail.com>"]
futures = "0.3.30"
lazy-regex = "3.1.0"
rayon = "1.8.0"
rbx_dom_weak = "2.7.0"
rbx_xml = "0.13.3"
rbx_dom_weak = "3.0.0"
rbx_xml = "1.0.0"
tokio = { version = "1.35.1", features = ["fs"] }

@ -1,4 +1,5 @@
use std::path::PathBuf;
use rbx_dom_weak::ustr;
use rbx_dom_weak::types::Ref;
use crate::common::{sanitize,Style,PropertiesOverride};
@ -90,7 +91,7 @@ fn write_item(dom:&rbx_dom_weak::WeakDom,mut file:PathBuf,node:&TreeNode,node_na
if let Some(item)=dom.get_by_ref(node.referent){
//TODO: delete disabled scripts
if let Some(rbx_dom_weak::types::Variant::String(source))=item.properties.get("Source"){
if let Some(rbx_dom_weak::types::Variant::String(source))=item.properties.get(&ustr("Source")){
if properties.is_some(){
//rox style
let source=properties.to_string()+source.as_str();

@ -563,8 +563,8 @@ async fn main()->AResult<()>{
subcommand.api_key_file,
).await?,
creator:match (subcommand.creator_user_id,subcommand.creator_group_id){
(Some(user_id),None)=>rbx_asset::cloud::Creator::userId(user_id.to_string()),
(None,Some(group_id))=>rbx_asset::cloud::Creator::groupId(group_id.to_string()),
(Some(user_id),None)=>rbx_asset::cloud::Creator::userId(user_id),
(None,Some(group_id))=>rbx_asset::cloud::Creator::groupId(group_id),
other=>Err(anyhow!("Invalid creator {other:?}"))?,
},
input_file:subcommand.input_file,
@ -585,8 +585,8 @@ async fn main()->AResult<()>{
subcommand.cookie_file,
).await?,
creator:match (subcommand.creator_user_id,subcommand.creator_group_id){
(Some(user_id),None)=>rbx_asset::cloud::Creator::userId(user_id.to_string()),
(None,Some(group_id))=>rbx_asset::cloud::Creator::groupId(group_id.to_string()),
(Some(user_id),None)=>rbx_asset::cloud::Creator::userId(user_id),
(None,Some(group_id))=>rbx_asset::cloud::Creator::groupId(group_id),
other=>Err(anyhow!("Invalid creator {other:?}"))?,
},
description:subcommand.description.unwrap_or_else(||String::with_capacity(0)),
@ -839,6 +839,7 @@ enum DownloadDecalError{
NoFirstInstance,
NoTextureProperty,
TexturePropertyInvalid,
TextureContentNotUri,
}
impl std::fmt::Display for DownloadDecalError{
fn fmt(&self,f:&mut std::fmt::Formatter<'_>)->std::fmt::Result{
@ -902,20 +903,25 @@ async fn create_asset_medias(config:CreateAssetMediasConfig)->AResult<()>{
let cookie_context=&cookie_context;
async move{(path,
async move{
use rbx_dom_weak::ustr;
let asset_response=asset_response_result.map_err(DownloadDecalError::PollOperation)?;
let file=cookie_context.get_asset(rbx_asset::cookie::GetAssetRequest{
asset_id:asset_response.assetId.parse().map_err(DownloadDecalError::ParseInt)?,
let maybe_gzip=cookie_context.get_asset(rbx_asset::cookie::GetAssetRequest{
asset_id:asset_response.assetId,
version:None,
}).await.map_err(DownloadDecalError::Get)?;
let dom=load_dom(std::io::Cursor::new(file)).map_err(DownloadDecalError::LoadDom)?;
let dom=maybe_gzip.read_with(load_dom,load_dom).map_err(DownloadDecalError::LoadDom)?;
let instance=dom.get_by_ref(
*dom.root().children().first().ok_or(DownloadDecalError::NoFirstInstance)?
).ok_or(DownloadDecalError::NoFirstInstance)?;
let texture=instance.properties.get("Texture").ok_or(DownloadDecalError::NoTextureProperty)?;
let asset_url=match texture{
rbx_dom_weak::types::Variant::Content(url)=>url.clone().into_string(),
let texture=instance.properties.get(&ustr("TextureContent")).ok_or(DownloadDecalError::NoTextureProperty)?;
let content=match texture{
rbx_dom_weak::types::Variant::Content(content)=>content,
_=>Err(DownloadDecalError::TexturePropertyInvalid)?,
};
let asset_url=match content.value(){
rbx_dom_weak::types::ContentType::Uri(uri)=>uri.clone(),
_=>Err(DownloadDecalError::TextureContentNotUri)?,
};
Ok::<_,DownloadDecalError>((asset_response.displayName,asset_url))
}
.await)}
@ -993,8 +999,8 @@ async fn asset_details(cookie:Cookie,asset_id:AssetID)->AResult<()>{
async fn download_version(cookie:Cookie,asset_id:AssetID,version:Option<u64>,dest:PathBuf)->AResult<()>{
let context=CookieContext::new(cookie);
let data=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id,version}).await?;
tokio::fs::write(dest,data).await?;
let maybe_gzip=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id,version}).await?;
tokio::fs::write(dest,maybe_gzip.to_vec()?).await?;
Ok(())
}
@ -1006,9 +1012,9 @@ async fn download_version_v2(cookie:Cookie,asset_id:AssetID,version:Option<u64>,
println!("version:{}",info.version);
let location=info.info.locations.first().ok_or(anyhow::Error::msg("No locations"))?;
let data=context.get_asset_v2_download(location).await?;
let maybe_gzip=context.get_asset_v2_download(location).await?;
tokio::fs::write(dest,data).await?;
tokio::fs::write(dest,maybe_gzip.to_vec()?).await?;
Ok(())
}
@ -1024,7 +1030,7 @@ async fn download_list(cookie:Cookie,asset_id_file_map:AssetIDFileMap)->AResult<
.buffer_unordered(CONCURRENT_REQUESTS)
.for_each(|b:AResult<_>|async{
match b{
Ok((dest,data))=>if let Err(e)=tokio::fs::write(dest,data).await{
Ok((dest,maybe_gzip))=>if let Err(e)=(async||{tokio::fs::write(dest,maybe_gzip.to_vec()?).await})().await{
eprintln!("fs error: {}",e);
},
Err(e)=>eprintln!("dl error: {}",e),
@ -1228,9 +1234,9 @@ async fn download_history(mut config:DownloadHistoryConfig)->AResult<()>{
let mut path=output_folder.clone();
path.push(format!("{}_v{}.rbxl",config.asset_id,version_number));
join_set.spawn(async move{
let file=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id:config.asset_id,version:Some(version_number)}).await?;
let maybe_gzip=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id:config.asset_id,version:Some(version_number)}).await?;
tokio::fs::write(path,file).await?;
tokio::fs::write(path,maybe_gzip.to_vec()?).await?;
Ok::<_,anyhow::Error>(())
});
@ -1350,9 +1356,9 @@ struct DownloadDecompileConfig{
async fn download_decompile(config:DownloadDecompileConfig)->AResult<()>{
let context=CookieContext::new(config.cookie);
let file=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id:config.asset_id,version:None}).await?;
let maybe_gzip=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id:config.asset_id,version:None}).await?;
let dom=load_dom(std::io::Cursor::new(file))?;
let dom=maybe_gzip.read_with(load_dom,load_dom)?;
let context=rox_compiler::DecompiledContext::from_dom(dom);
context.write_files(rox_compiler::WriteConfig{
@ -1532,8 +1538,8 @@ async fn download_and_decompile_history_into_git(config:DownloadAndDecompileHist
.map(|asset_version|{
let context=context.clone();
tokio::task::spawn(async move{
let file=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id,version:Some(asset_version.assetVersionNumber)}).await?;
let dom=load_dom(std::io::Cursor::new(file))?;
let maybe_gzip=context.get_asset(rbx_asset::cookie::GetAssetRequest{asset_id,version:Some(asset_version.assetVersionNumber)}).await?;
let dom=maybe_gzip.read_with(load_dom,load_dom)?;
Ok::<_,anyhow::Error>((asset_version,rox_compiler::DecompiledContext::from_dom(dom)))
})
}))