@@ -8,7 +8,7 @@ use std::str::{self, FromStr};
8
8
use crate :: AlreadyPrintedError ;
9
9
use anyhow:: { anyhow, bail, Context as _} ;
10
10
use cargo_platform:: Platform ;
11
- use cargo_util:: paths;
11
+ use cargo_util:: paths:: { self , normalize_path } ;
12
12
use cargo_util_schemas:: manifest:: { self , TomlManifest } ;
13
13
use cargo_util_schemas:: manifest:: { RustVersion , StringOrBool } ;
14
14
use itertools:: Itertools ;
@@ -2336,6 +2336,14 @@ fn prepare_toml_for_publish(
2336
2336
2337
2337
let mut package = me. package ( ) . unwrap ( ) . clone ( ) ;
2338
2338
package. workspace = None ;
2339
+ if let Some ( StringOrBool :: String ( path) ) = & package. build {
2340
+ let path = paths:: normalize_path ( Path :: new ( path) ) ;
2341
+ let path = path
2342
+ . into_os_string ( )
2343
+ . into_string ( )
2344
+ . map_err ( |_err| anyhow:: format_err!( "non-UTF8 `package.build`" ) ) ?;
2345
+ package. build = Some ( StringOrBool :: String ( normalize_path_string_sep ( path) ) ) ;
2346
+ }
2339
2347
let current_resolver = package
2340
2348
. resolver
2341
2349
. as_ref ( )
@@ -2362,7 +2370,16 @@ fn prepare_toml_for_publish(
2362
2370
. context ( "license file should have been resolved before `prepare_for_publish()`" ) ?;
2363
2371
let license_path = Path :: new ( & license_file) ;
2364
2372
let abs_license_path = paths:: normalize_path ( & package_root. join ( license_path) ) ;
2365
- if abs_license_path. strip_prefix ( package_root) . is_err ( ) {
2373
+ if let Ok ( license_file) = abs_license_path. strip_prefix ( package_root) {
2374
+ package. license_file = Some ( manifest:: InheritableField :: Value (
2375
+ normalize_path_string_sep (
2376
+ license_file
2377
+ . to_str ( )
2378
+ . ok_or_else ( || anyhow:: format_err!( "non-UTF8 `package.license-file`" ) ) ?
2379
+ . to_owned ( ) ,
2380
+ ) ,
2381
+ ) ) ;
2382
+ } else {
2366
2383
// This path points outside of the package root. `cargo package`
2367
2384
// will copy it into the root, so adjust the path to this location.
2368
2385
package. license_file = Some ( manifest:: InheritableField :: Value (
@@ -2384,7 +2401,18 @@ fn prepare_toml_for_publish(
2384
2401
manifest:: StringOrBool :: String ( readme) => {
2385
2402
let readme_path = Path :: new ( & readme) ;
2386
2403
let abs_readme_path = paths:: normalize_path ( & package_root. join ( readme_path) ) ;
2387
- if abs_readme_path. strip_prefix ( package_root) . is_err ( ) {
2404
+ if let Ok ( readme_path) = abs_readme_path. strip_prefix ( package_root) {
2405
+ package. readme = Some ( manifest:: InheritableField :: Value ( StringOrBool :: String (
2406
+ normalize_path_string_sep (
2407
+ readme_path
2408
+ . to_str ( )
2409
+ . ok_or_else ( || {
2410
+ anyhow:: format_err!( "non-UTF8 `package.license-file`" )
2411
+ } ) ?
2412
+ . to_owned ( ) ,
2413
+ ) ,
2414
+ ) ) ) ;
2415
+ } else {
2388
2416
// This path points outside of the package root. `cargo package`
2389
2417
// will copy it into the root, so adjust the path to this location.
2390
2418
package. readme = Some ( manifest:: InheritableField :: Value (
@@ -2402,16 +2430,27 @@ fn prepare_toml_for_publish(
2402
2430
manifest:: StringOrBool :: Bool ( _) => { }
2403
2431
}
2404
2432
}
2433
+
2434
+ let lib = if let Some ( target) = & me. lib {
2435
+ Some ( prepare_target_for_publish ( target, "library" ) ?)
2436
+ } else {
2437
+ None
2438
+ } ;
2439
+ let bin = prepare_targets_for_publish ( me. bin . as_ref ( ) , "binary" ) ?;
2440
+ let example = prepare_targets_for_publish ( me. example . as_ref ( ) , "example" ) ?;
2441
+ let test = prepare_targets_for_publish ( me. test . as_ref ( ) , "test" ) ?;
2442
+ let bench = prepare_targets_for_publish ( me. bench . as_ref ( ) , "benchmark" ) ?;
2443
+
2405
2444
let all = |_d : & manifest:: TomlDependency | true ;
2406
2445
let mut manifest = manifest:: TomlManifest {
2407
2446
package : Some ( package) ,
2408
2447
project : None ,
2409
2448
profile : me. profile . clone ( ) ,
2410
- lib : me . lib . clone ( ) ,
2411
- bin : me . bin . clone ( ) ,
2412
- example : me . example . clone ( ) ,
2413
- test : me . test . clone ( ) ,
2414
- bench : me . bench . clone ( ) ,
2449
+ lib,
2450
+ bin,
2451
+ example,
2452
+ test,
2453
+ bench,
2415
2454
dependencies : map_deps ( gctx, me. dependencies . as_ref ( ) , all) ?,
2416
2455
dev_dependencies : map_deps (
2417
2456
gctx,
@@ -2555,3 +2594,49 @@ fn prepare_toml_for_publish(
2555
2594
. map ( manifest:: InheritableDependency :: Value )
2556
2595
}
2557
2596
}
2597
+
2598
+ fn prepare_targets_for_publish (
2599
+ targets : Option < & Vec < manifest:: TomlTarget > > ,
2600
+ context : & str ,
2601
+ ) -> CargoResult < Option < Vec < manifest:: TomlTarget > > > {
2602
+ let Some ( targets) = targets else {
2603
+ return Ok ( None ) ;
2604
+ } ;
2605
+
2606
+ let mut prepared = Vec :: with_capacity ( targets. len ( ) ) ;
2607
+ for target in targets {
2608
+ let target = prepare_target_for_publish ( target, context) ?;
2609
+ prepared. push ( target) ;
2610
+ }
2611
+
2612
+ Ok ( Some ( prepared) )
2613
+ }
2614
+
2615
+ fn prepare_target_for_publish (
2616
+ target : & manifest:: TomlTarget ,
2617
+ context : & str ,
2618
+ ) -> CargoResult < manifest:: TomlTarget > {
2619
+ let mut target = target. clone ( ) ;
2620
+ if let Some ( path) = target. path {
2621
+ let path = normalize_path ( & path. 0 ) ;
2622
+ target. path = Some ( manifest:: PathValue ( normalize_path_sep ( path, context) ?) ) ;
2623
+ }
2624
+ Ok ( target)
2625
+ }
2626
+
2627
+ fn normalize_path_sep ( path : PathBuf , context : & str ) -> CargoResult < PathBuf > {
2628
+ let path = path
2629
+ . into_os_string ( )
2630
+ . into_string ( )
2631
+ . map_err ( |_err| anyhow:: format_err!( "non-UTF8 path for {context}" ) ) ?;
2632
+ let path = normalize_path_string_sep ( path) ;
2633
+ Ok ( path. into ( ) )
2634
+ }
2635
+
2636
+ fn normalize_path_string_sep ( path : String ) -> String {
2637
+ if std:: path:: MAIN_SEPARATOR != '/' {
2638
+ path. replace ( std:: path:: MAIN_SEPARATOR , "/" )
2639
+ } else {
2640
+ path
2641
+ }
2642
+ }
0 commit comments