1mod adapter;
4mod diagnostic;
5mod outcome;
6mod rule;
7mod target;
8
9pub use adapter::{ConversionError, ExportAdapter, ImportAdapter, ImportResult, InMemoryAdapter, convert};
10pub use diagnostic::{
11 Diagnostic, DiagnosticCode, DiagnosticField, DiagnosticValue, InvalidDiagnosticCode, NativeFinding,
12 NativeFindingLabel, NativeFindingLabelKind, Severity,
13};
14pub use outcome::{ConversionKind, ConversionOutcome, ConversionPlan, ConversionResult, LossPolicy, PlanError};
15pub use rule::{DiagnosticRule, RULES, RuleId, find_rule};
16pub use target::{ParsePlatformVersionError, PlatformVersion, TargetProfile, TargetProfileError, VersionRange};
17
18#[cfg(test)]
19mod integration_tests {
20 use boxferry_model::{Application, Identifier};
21
22 use crate::{
23 ConversionKind, ConversionOutcome, Diagnostic, DiagnosticCode, ImportAdapter, ImportResult, InMemoryAdapter,
24 LossPolicy, PlatformVersion, Severity, TargetProfile, convert,
25 };
26
27 struct LossyImporter {
28 application: Application,
29 }
30
31 impl ImportAdapter for LossyImporter {
32 type Source = ();
33
34 fn import(&self, _source: &Self::Source) -> ImportResult {
35 let code = DiagnosticCode::new("BFE0010").ok();
36 let (outcomes, diagnostics) = code.map_or_else(
37 || (Vec::new(), Vec::new()),
38 |code| {
39 let outcome =
40 ConversionOutcome::loss("services.web.extension", ConversionKind::Unsupported, code.clone())
41 .ok();
42 let outcomes = outcome.into_iter().collect();
43 let diagnostics = vec![Diagnostic::new(code, Severity::Warning, "extension omitted")];
44 (outcomes, diagnostics)
45 },
46 );
47 ImportResult::new(Some(self.application.clone()), outcomes, diagnostics)
48 }
49 }
50
51 #[test]
52 fn import_losses_participate_in_output_authorization() -> Result<(), String> {
53 let application = Application::new(Identifier::new("example").map_err(|error| error.to_string())?);
54 let importer = LossyImporter { application };
55 let exporter = InMemoryAdapter::exact("candidate".to_owned());
56 let target =
57 TargetProfile::new("target", PlatformVersion::new(1, 0, 0), None).map_err(|error| error.to_string())?;
58
59 let strict =
60 convert(&importer, &(), &exporter, &target, LossPolicy::ExactOnly).map_err(|error| error.to_string())?;
61 assert!(strict.is_blocked());
62
63 let partial =
64 convert(&importer, &(), &exporter, &target, LossPolicy::AllowPartial).map_err(|error| error.to_string())?;
65 assert_eq!(partial.output().map(String::as_str), Some("candidate"));
66 assert!(partial.outcomes().iter().any(|outcome| {
67 outcome.kind() == ConversionKind::Unsupported && outcome.subject() == "services.web.extension"
68 }));
69 Ok(())
70 }
71}