]>
Commit | Line | Data |
---|---|---|
83571aee EH |
1 | //! Tests for profiles defined in config files. |
2 | ||
77ee608d | 3 | use cargo_test_support::paths::CargoPathExt; |
61fb34b0 | 4 | use cargo_test_support::{basic_lib_manifest, paths, project}; |
2f7b5225 | 5 | |
0e0d9688 | 6 | #[cargo_test] |
2f7b5225 | 7 | fn profile_config_gated() { |
7fe2fbc8 | 8 | let p = project() |
2f7b5225 EH |
9 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
10 | .file("src/lib.rs", "") | |
11 | .file( | |
12 | ".cargo/config", | |
13 | r#" | |
14 | [profile.dev] | |
15 | debug = 1 | |
16 | "#, | |
fecb7246 AC |
17 | ) |
18 | .build(); | |
2f7b5225 | 19 | |
85984a87 DW |
20 | p.cargo("build -v") |
21 | .with_stderr_contains( | |
22 | "\ | |
77ee608d EH |
23 | [WARNING] config profiles require the `-Z config-profile` command-line option \ |
24 | (found profile `dev` in [..]/foo/.cargo/config) | |
2f7b5225 | 25 | ", |
fecb7246 AC |
26 | ) |
27 | .with_stderr_contains("[..]-C debuginfo=2[..]") | |
85984a87 | 28 | .run(); |
2f7b5225 EH |
29 | } |
30 | ||
77ee608d EH |
31 | #[cargo_test] |
32 | fn named_profile_gated() { | |
33 | // Named profile in config requires enabling in Cargo.toml. | |
34 | let p = project() | |
35 | .file("src/lib.rs", "") | |
36 | .file( | |
37 | ".cargo/config", | |
38 | r#" | |
39 | [profile.foo] | |
40 | inherits = 'dev' | |
41 | opt-level = 1 | |
42 | "#, | |
43 | ) | |
44 | .build(); | |
45 | p.cargo("build --profile foo -Zunstable-options -Zconfig-profile") | |
46 | .masquerade_as_nightly_cargo() | |
47 | .with_stderr( | |
48 | "\ | |
49 | [ERROR] config profile `foo` is not valid (defined in `[..]/foo/.cargo/config`) | |
50 | ||
51 | Caused by: | |
52 | feature `named-profiles` is required | |
53 | ||
54 | consider adding `cargo-features = [\"named-profiles\"]` to the manifest | |
55 | ", | |
56 | ) | |
57 | .with_status(101) | |
58 | .run(); | |
59 | } | |
60 | ||
0e0d9688 | 61 | #[cargo_test] |
2f7b5225 | 62 | fn profile_config_validate_warnings() { |
7fe2fbc8 | 63 | let p = project() |
dda81d31 | 64 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
fecb7246 | 65 | .file("src/lib.rs", "") |
2f7b5225 EH |
66 | .file( |
67 | ".cargo/config", | |
68 | r#" | |
69 | [profile.test] | |
70 | opt-level = 3 | |
71 | ||
72 | [profile.asdf] | |
73 | opt-level = 3 | |
74 | ||
75 | [profile.dev] | |
76 | bad-key = true | |
77 | ||
78 | [profile.dev.build-override] | |
79 | bad-key-bo = true | |
80 | ||
fcfe0b89 | 81 | [profile.dev.package.bar] |
2f7b5225 EH |
82 | bad-key-bar = true |
83 | "#, | |
fecb7246 AC |
84 | ) |
85 | .build(); | |
2f7b5225 | 86 | |
85984a87 DW |
87 | p.cargo("build -Z config-profile") |
88 | .masquerade_as_nightly_cargo() | |
89 | .with_stderr_unordered( | |
84a80d8f | 90 | "\ |
91015d52 EH |
91 | [WARNING] unused config key `profile.dev.bad-key` in `[..].cargo/config` |
92 | [WARNING] unused config key `profile.dev.package.bar.bad-key-bar` in `[..].cargo/config` | |
93 | [WARNING] unused config key `profile.dev.build-override.bad-key-bo` in `[..].cargo/config` | |
84a80d8f EH |
94 | [COMPILING] foo [..] |
95 | [FINISHED] [..] | |
2f7b5225 | 96 | ", |
fecb7246 AC |
97 | ) |
98 | .run(); | |
2f7b5225 EH |
99 | } |
100 | ||
0e0d9688 | 101 | #[cargo_test] |
2f7b5225 | 102 | fn profile_config_error_paths() { |
77ee608d | 103 | // Errors in config show where the error is located. |
7fe2fbc8 | 104 | let p = project() |
2f7b5225 EH |
105 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
106 | .file("src/lib.rs", "") | |
107 | .file( | |
108 | ".cargo/config", | |
109 | r#" | |
110 | [profile.dev] | |
111 | opt-level = 3 | |
112 | "#, | |
fecb7246 AC |
113 | ) |
114 | .file( | |
2f7b5225 EH |
115 | paths::home().join(".cargo/config"), |
116 | r#" | |
117 | [profile.dev] | |
118 | rpath = "foo" | |
119 | "#, | |
fecb7246 AC |
120 | ) |
121 | .build(); | |
2f7b5225 | 122 | |
85984a87 DW |
123 | p.cargo("build -Z config-profile") |
124 | .masquerade_as_nightly_cargo() | |
125 | .with_status(101) | |
126 | .with_stderr( | |
2f7b5225 | 127 | "\ |
77ee608d EH |
128 | [ERROR] error in [..]/foo/.cargo/config: \ |
129 | could not load config key `profile.dev`: \ | |
130 | error in [..]/home/.cargo/config: \ | |
131 | `profile.dev.rpath` expected true/false, but found a string | |
2f7b5225 | 132 | ", |
fecb7246 AC |
133 | ) |
134 | .run(); | |
2f7b5225 EH |
135 | } |
136 | ||
0e0d9688 | 137 | #[cargo_test] |
2f7b5225 | 138 | fn profile_config_validate_errors() { |
7fe2fbc8 | 139 | let p = project() |
dda81d31 | 140 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
fecb7246 | 141 | .file("src/lib.rs", "") |
2f7b5225 EH |
142 | .file( |
143 | ".cargo/config", | |
144 | r#" | |
fcfe0b89 | 145 | [profile.dev.package.foo] |
2f7b5225 EH |
146 | panic = "abort" |
147 | "#, | |
fecb7246 AC |
148 | ) |
149 | .build(); | |
2f7b5225 | 150 | |
85984a87 DW |
151 | p.cargo("build -Z config-profile") |
152 | .masquerade_as_nightly_cargo() | |
153 | .with_status(101) | |
154 | .with_stderr( | |
2f7b5225 | 155 | "\ |
77ee608d | 156 | [ERROR] config profile `dev` is not valid (defined in `[..]/foo/.cargo/config`) |
2f7b5225 EH |
157 | |
158 | Caused by: | |
fcfe0b89 | 159 | `panic` may not be specified in a `package` profile |
2f7b5225 | 160 | ", |
fecb7246 AC |
161 | ) |
162 | .run(); | |
2f7b5225 EH |
163 | } |
164 | ||
0e0d9688 | 165 | #[cargo_test] |
2f7b5225 | 166 | fn profile_config_syntax_errors() { |
7fe2fbc8 | 167 | let p = project() |
2f7b5225 EH |
168 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
169 | .file("src/lib.rs", "") | |
170 | .file( | |
171 | ".cargo/config", | |
172 | r#" | |
173 | [profile.dev] | |
174 | codegen-units = "foo" | |
175 | "#, | |
fecb7246 AC |
176 | ) |
177 | .build(); | |
2f7b5225 | 178 | |
85984a87 DW |
179 | p.cargo("build -Z config-profile") |
180 | .masquerade_as_nightly_cargo() | |
181 | .with_status(101) | |
182 | .with_stderr( | |
2f7b5225 | 183 | "\ |
77ee608d EH |
184 | [ERROR] error in [..]/foo/.cargo/config: \ |
185 | could not load config key `profile.dev`: \ | |
186 | error in [..]/foo/.cargo/config: \ | |
187 | `profile.dev.codegen-units` expected an integer, but found a string | |
2f7b5225 | 188 | ", |
fecb7246 AC |
189 | ) |
190 | .run(); | |
2f7b5225 EH |
191 | } |
192 | ||
0e0d9688 | 193 | #[cargo_test] |
2f7b5225 | 194 | fn profile_config_override_spec_multiple() { |
7fe2fbc8 | 195 | let p = project() |
2f7b5225 EH |
196 | .file( |
197 | "Cargo.toml", | |
198 | r#" | |
2f7b5225 EH |
199 | [package] |
200 | name = "foo" | |
201 | version = "0.0.1" | |
202 | ||
203 | [dependencies] | |
204 | bar = { path = "bar" } | |
205 | "#, | |
fecb7246 AC |
206 | ) |
207 | .file( | |
2f7b5225 EH |
208 | ".cargo/config", |
209 | r#" | |
fcfe0b89 | 210 | [profile.dev.package.bar] |
2f7b5225 EH |
211 | opt-level = 3 |
212 | ||
fcfe0b89 | 213 | [profile.dev.package."bar:0.5.0"] |
2f7b5225 EH |
214 | opt-level = 3 |
215 | "#, | |
fecb7246 AC |
216 | ) |
217 | .file("src/lib.rs", "") | |
dda81d31 | 218 | .file("bar/Cargo.toml", &basic_lib_manifest("bar")) |
fecb7246 | 219 | .file("bar/src/lib.rs", "") |
2f7b5225 EH |
220 | .build(); |
221 | ||
222 | // Unfortunately this doesn't tell you which file, hopefully it's not too | |
223 | // much of a problem. | |
85984a87 DW |
224 | p.cargo("build -v -Z config-profile") |
225 | .masquerade_as_nightly_cargo() | |
226 | .with_status(101) | |
227 | .with_stderr( | |
2f7b5225 | 228 | "\ |
fcfe0b89 EH |
229 | [ERROR] multiple package overrides in profile `dev` match package `bar v0.5.0 ([..])` |
230 | found package specs: bar, bar:0.5.0", | |
fecb7246 AC |
231 | ) |
232 | .run(); | |
2f7b5225 EH |
233 | } |
234 | ||
0e0d9688 | 235 | #[cargo_test] |
2f7b5225 EH |
236 | fn profile_config_all_options() { |
237 | // Ensure all profile options are supported. | |
7fe2fbc8 | 238 | let p = project() |
2b6fd6f0 | 239 | .file("src/main.rs", "fn main() {}") |
2f7b5225 EH |
240 | .file( |
241 | ".cargo/config", | |
242 | r#" | |
243 | [profile.release] | |
244 | opt-level = 1 | |
245 | debug = true | |
246 | debug-assertions = true | |
247 | overflow-checks = false | |
248 | rpath = true | |
249 | lto = true | |
250 | codegen-units = 2 | |
251 | panic = "abort" | |
252 | incremental = true | |
253 | "#, | |
fecb7246 AC |
254 | ) |
255 | .build(); | |
2f7b5225 | 256 | |
85984a87 DW |
257 | p.cargo("build --release -v -Z config-profile") |
258 | .masquerade_as_nightly_cargo() | |
2b6fd6f0 | 259 | .env_remove("CARGO_INCREMENTAL") |
85984a87 | 260 | .with_stderr( |
2f7b5225 EH |
261 | "\ |
262 | [COMPILING] foo [..] | |
263 | [RUNNING] `rustc --crate-name foo [..] \ | |
264 | -C opt-level=1 \ | |
265 | -C panic=abort \ | |
2b6fd6f0 | 266 | -C lto \ |
2f7b5225 EH |
267 | -C codegen-units=2 \ |
268 | -C debuginfo=2 \ | |
269 | -C debug-assertions=on \ | |
270 | -C overflow-checks=off [..]\ | |
2b6fd6f0 EH |
271 | -C rpath [..]\ |
272 | -C incremental=[..] | |
2f7b5225 EH |
273 | [FINISHED] release [optimized + debuginfo] [..] |
274 | ", | |
fecb7246 AC |
275 | ) |
276 | .run(); | |
2f7b5225 EH |
277 | } |
278 | ||
0e0d9688 | 279 | #[cargo_test] |
2f7b5225 EH |
280 | fn profile_config_override_precedence() { |
281 | // Config values take precedence over manifest values. | |
7fe2fbc8 | 282 | let p = project() |
2f7b5225 EH |
283 | .file( |
284 | "Cargo.toml", | |
285 | r#" | |
2f7b5225 EH |
286 | [package] |
287 | name = "foo" | |
288 | version = "0.0.1" | |
289 | ||
290 | [dependencies] | |
291 | bar = {path = "bar"} | |
292 | ||
293 | [profile.dev] | |
294 | codegen-units = 2 | |
295 | ||
fcfe0b89 | 296 | [profile.dev.package.bar] |
2f7b5225 EH |
297 | opt-level = 3 |
298 | "#, | |
fecb7246 AC |
299 | ) |
300 | .file("src/lib.rs", "") | |
dda81d31 | 301 | .file("bar/Cargo.toml", &basic_lib_manifest("bar")) |
fecb7246 | 302 | .file("bar/src/lib.rs", "") |
2f7b5225 EH |
303 | .file( |
304 | ".cargo/config", | |
305 | r#" | |
fcfe0b89 | 306 | [profile.dev.package.bar] |
2f7b5225 EH |
307 | opt-level = 2 |
308 | "#, | |
fecb7246 AC |
309 | ) |
310 | .build(); | |
2f7b5225 | 311 | |
85984a87 DW |
312 | p.cargo("build -v -Z config-profile") |
313 | .masquerade_as_nightly_cargo() | |
314 | .with_stderr( | |
2f7b5225 EH |
315 | "\ |
316 | [COMPILING] bar [..] | |
317 | [RUNNING] `rustc --crate-name bar [..] -C opt-level=2 -C codegen-units=2 [..] | |
318 | [COMPILING] foo [..] | |
319 | [RUNNING] `rustc --crate-name foo [..]-C codegen-units=2 [..] | |
320 | [FINISHED] dev [unoptimized + debuginfo] target(s) in [..]", | |
fecb7246 AC |
321 | ) |
322 | .run(); | |
2f7b5225 EH |
323 | } |
324 | ||
0e0d9688 | 325 | #[cargo_test] |
2f7b5225 | 326 | fn profile_config_no_warn_unknown_override() { |
7fe2fbc8 | 327 | let p = project() |
dda81d31 | 328 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
fecb7246 | 329 | .file("src/lib.rs", "") |
2f7b5225 EH |
330 | .file( |
331 | ".cargo/config", | |
332 | r#" | |
fcfe0b89 | 333 | [profile.dev.package.bar] |
2f7b5225 EH |
334 | codegen-units = 4 |
335 | "#, | |
fecb7246 AC |
336 | ) |
337 | .build(); | |
2f7b5225 | 338 | |
85984a87 DW |
339 | p.cargo("build -Z config-profile") |
340 | .masquerade_as_nightly_cargo() | |
341 | .with_stderr_does_not_contain("[..]warning[..]") | |
342 | .run(); | |
2f7b5225 EH |
343 | } |
344 | ||
0e0d9688 | 345 | #[cargo_test] |
2f7b5225 | 346 | fn profile_config_mixed_types() { |
7fe2fbc8 | 347 | let p = project() |
2f7b5225 EH |
348 | .file("Cargo.toml", &basic_lib_manifest("foo")) |
349 | .file("src/lib.rs", "") | |
350 | .file( | |
351 | ".cargo/config", | |
352 | r#" | |
353 | [profile.dev] | |
354 | opt-level = 3 | |
355 | "#, | |
fecb7246 AC |
356 | ) |
357 | .file( | |
2f7b5225 EH |
358 | paths::home().join(".cargo/config"), |
359 | r#" | |
360 | [profile.dev] | |
361 | opt-level = 's' | |
362 | "#, | |
fecb7246 AC |
363 | ) |
364 | .build(); | |
2f7b5225 | 365 | |
85984a87 DW |
366 | p.cargo("build -v -Z config-profile") |
367 | .masquerade_as_nightly_cargo() | |
368 | .with_stderr_contains("[..]-C opt-level=3 [..]") | |
369 | .run(); | |
2f7b5225 | 370 | } |
77ee608d EH |
371 | |
372 | #[cargo_test] | |
373 | fn named_config_profile() { | |
374 | // Exercises config named profies. | |
375 | // foo -> middle -> bar -> dev | |
376 | // middle exists in Cargo.toml, the others in .cargo/config | |
377 | use super::config::ConfigBuilder; | |
378 | use cargo::core::compiler::CompileMode; | |
379 | use cargo::core::enable_nightly_features; | |
380 | use cargo::core::features::Features; | |
381 | use cargo::core::profiles::{Profiles, UnitFor}; | |
382 | use cargo::core::{InternedString, PackageId}; | |
383 | use cargo::util::toml::TomlProfiles; | |
384 | use std::fs; | |
385 | enable_nightly_features(); | |
386 | paths::root().join(".cargo").mkdir_p(); | |
387 | fs::write( | |
388 | paths::root().join(".cargo/config"), | |
389 | r#" | |
390 | [profile.foo] | |
391 | inherits = "middle" | |
392 | codegen-units = 2 | |
393 | [profile.foo.build-override] | |
394 | codegen-units = 6 | |
395 | [profile.foo.package.dep] | |
396 | codegen-units = 7 | |
397 | ||
398 | [profile.middle] | |
399 | inherits = "bar" | |
400 | codegen-units = 3 | |
401 | ||
402 | [profile.bar] | |
403 | inherits = "dev" | |
404 | codegen-units = 4 | |
405 | debug = 1 | |
406 | "#, | |
407 | ) | |
408 | .unwrap(); | |
409 | let config = ConfigBuilder::new().unstable_flag("config-profile").build(); | |
410 | let mut warnings = Vec::new(); | |
411 | let features = Features::new(&["named-profiles".to_string()], &mut warnings).unwrap(); | |
412 | assert_eq!(warnings.len(), 0); | |
413 | let profile_name = InternedString::new("foo"); | |
414 | let toml = r#" | |
415 | [profile.middle] | |
416 | inherits = "bar" | |
417 | codegen-units = 1 | |
418 | opt-level = 1 | |
419 | [profile.middle.package.dep] | |
420 | overflow-checks = false | |
421 | ||
422 | [profile.foo.build-override] | |
423 | codegen-units = 5 | |
424 | debug-assertions = false | |
425 | [profile.foo.package.dep] | |
426 | codegen-units = 8 | |
427 | "#; | |
428 | #[derive(serde::Deserialize)] | |
429 | struct TomlManifest { | |
430 | profile: Option<TomlProfiles>, | |
431 | } | |
432 | let manifest: TomlManifest = toml::from_str(toml).unwrap(); | |
433 | let profiles = | |
434 | Profiles::new(manifest.profile.as_ref(), &config, profile_name, &features).unwrap(); | |
435 | ||
436 | let crates_io = cargo::core::source::SourceId::crates_io(&config).unwrap(); | |
437 | let a_pkg = PackageId::new("a", "0.1.0", crates_io).unwrap(); | |
438 | let dep_pkg = PackageId::new("dep", "0.1.0", crates_io).unwrap(); | |
439 | ||
440 | // normal package | |
441 | let p = profiles.get_profile(a_pkg, true, UnitFor::new_normal(), CompileMode::Build); | |
442 | assert_eq!(p.name, "foo"); | |
443 | assert_eq!(p.codegen_units, Some(2)); // "foo" from config | |
444 | assert_eq!(p.opt_level, "1"); // "middle" from manifest | |
445 | assert_eq!(p.debuginfo, Some(1)); // "bar" from config | |
446 | assert_eq!(p.debug_assertions, true); // "dev" built-in (ignore build-override) | |
447 | assert_eq!(p.overflow_checks, true); // "dev" built-in (ignore package override) | |
448 | ||
449 | // build-override | |
450 | let bo = profiles.get_profile(a_pkg, true, UnitFor::new_build(), CompileMode::Build); | |
451 | assert_eq!(bo.name, "foo"); | |
452 | assert_eq!(bo.codegen_units, Some(6)); // "foo" build override from config | |
453 | assert_eq!(bo.opt_level, "1"); // SAME as normal | |
454 | assert_eq!(bo.debuginfo, Some(1)); // SAME as normal | |
455 | assert_eq!(bo.debug_assertions, false); // "foo" build override from manifest | |
456 | assert_eq!(bo.overflow_checks, true); // SAME as normal | |
457 | ||
458 | // package overrides | |
459 | let po = profiles.get_profile(dep_pkg, false, UnitFor::new_normal(), CompileMode::Build); | |
460 | assert_eq!(po.name, "foo"); | |
461 | assert_eq!(po.codegen_units, Some(7)); // "foo" package override from config | |
462 | assert_eq!(po.opt_level, "1"); // SAME as normal | |
463 | assert_eq!(po.debuginfo, Some(1)); // SAME as normal | |
464 | assert_eq!(po.debug_assertions, true); // SAME as normal | |
465 | assert_eq!(po.overflow_checks, false); // "middle" package override from manifest | |
466 | } | |
467 | ||
468 | #[cargo_test] | |
469 | fn named_env_profile() { | |
470 | // Environment variables used to define a named profile. | |
471 | let p = project() | |
472 | .file( | |
473 | "Cargo.toml", | |
474 | r#" | |
475 | cargo-features = ["named-profiles"] | |
476 | [package] | |
477 | name = "foo" | |
478 | version = "0.1.0" | |
479 | "#, | |
480 | ) | |
481 | .file("src/lib.rs", "") | |
482 | .build(); | |
483 | ||
484 | p.cargo("build -v -Zconfig-profile -Zunstable-options --profile=other") | |
485 | .masquerade_as_nightly_cargo() | |
486 | .env("CARGO_PROFILE_OTHER_CODEGEN_UNITS", "1") | |
487 | .env("CARGO_PROFILE_OTHER_INHERITS", "dev") | |
488 | .with_stderr_contains("[..]-C codegen-units=1 [..]") | |
489 | .run(); | |
490 | } |