use super::test_method::render_test_method;
use crate::core::config::ResolvedCrateConfig;
use crate::core::ir::{EnumDef, EnumVariant, FieldDef, FunctionDef, TypeDef, TypeRef};
use crate::e2e::config::{CallConfig, E2eConfig};
use crate::e2e::fixture::{Assertion, Fixture};
fn stage_status_enum() -> EnumDef {
EnumDef {
name: "StageStatus".to_string(),
variants: vec![
EnumVariant {
name: "Queued".to_string(),
..EnumVariant::default()
},
EnumVariant {
name: "Complete".to_string(),
..EnumVariant::default()
},
],
..EnumDef::default()
}
}
fn stage_output_enum() -> EnumDef {
EnumDef {
name: "StageOutput".to_string(),
variants: vec![EnumVariant {
name: "Text".to_string(),
fields: vec![FieldDef {
name: "0".to_string(),
ty: TypeRef::String,
..FieldDef::default()
}],
is_tuple: true,
..EnumVariant::default()
}],
serde_untagged: true,
..EnumDef::default()
}
}
fn table_ir() -> (Vec<TypeDef>, Vec<EnumDef>, Vec<FunctionDef>) {
let type_defs = vec![
TypeDef {
name: "StatusResult".to_string(),
fields: vec![FieldDef {
name: "status".to_string(),
ty: TypeRef::Named("StageStatus".to_string()),
..FieldDef::default()
}],
..TypeDef::default()
},
TypeDef {
name: "OutputResult".to_string(),
fields: vec![FieldDef {
name: "summary".to_string(),
ty: TypeRef::Optional(Box::new(TypeRef::Named("StageOutput".to_string()))),
optional: true,
..FieldDef::default()
}],
..TypeDef::default()
},
];
let enums = vec![stage_status_enum(), stage_output_enum()];
let functions = vec![
FunctionDef {
name: "read_status".to_string(),
return_type: TypeRef::Named("StatusResult".to_string()),
..FunctionDef::default()
},
FunctionDef {
name: "read_summary".to_string(),
return_type: TypeRef::Named("OutputResult".to_string()),
..FunctionDef::default()
},
];
(type_defs, enums, functions)
}
fn equals_fixture(id: &str, field: &str, value: &str) -> Fixture {
Fixture {
docs: None,
requirements: Vec::new(),
id: id.to_string(),
category: None,
description: "test".to_string(),
tags: vec![],
skip: None,
env: None,
setup: Vec::new(),
call: None,
input: serde_json::Value::Null,
mock_response: None,
source: String::new(),
http: None,
asyncapi: None,
websocket: None,
preserve_input_urls: false,
assertions: vec![Assertion {
assertion_type: "equals".to_string(),
field: Some(field.to_string()),
value: Some(serde_json::Value::String(value.to_string())),
..Assertion::default()
}],
visitor: None,
args: vec![],
assertion_recipes: vec![],
}
}
fn render(
fixture: &Fixture,
function: &str,
type_defs: &[TypeDef],
enums: &[EnumDef],
functions: &[FunctionDef],
fields_display_as_text: &[&str],
) -> String {
let call = CallConfig {
function: function.to_string(),
result_var: "result".to_string(),
..CallConfig::default()
};
let e2e_config = E2eConfig {
call,
fields_display_as_text: fields_display_as_text.iter().map(|s| s.to_string()).collect(),
..Default::default()
};
let config = ResolvedCrateConfig::default();
let mut out = String::new();
render_test_method(
&mut out,
fixture,
"SampleClass",
"",
"",
&[],
None,
false,
&e2e_config,
&std::collections::HashMap::new(),
false,
&[],
&config,
type_defs,
enums,
functions,
&[],
);
out
}
#[test]
fn a_fieldless_enum_field_still_renders_through_get_value() {
let (type_defs, enums, functions) = table_ir();
let fixture = equals_fixture("status_smoke", "status", "Queued");
let out = render(&fixture, "read_status", &type_defs, &enums, &functions, &[]);
assert!(
out.contains(".getValue()"),
"expected the fieldless enum field to render through .getValue(), got:\n{out}"
);
}
#[test]
fn a_data_carrying_union_enum_field_renders_through_the_wrapper_text_accessor_not_get_value() {
let (type_defs, enums, functions) = table_ir();
let fixture = equals_fixture("summary_smoke", "summary", "hello");
let out = render(&fixture, "read_summary", &type_defs, &enums, &functions, &["summary"]);
assert!(
!out.contains(".getValue()"),
"a data-carrying union enum field must never render through .getValue() (the Java \
binding backend's wrapper class for this shape declares no such method), got:\n{out}"
);
assert!(
out.contains(".map(v -> v.text()).orElse(\"\")"),
"expected the union wrapper's .text() accessor, got:\n{out}"
);
}
#[test]
fn a_data_carrying_union_enum_field_never_renders_get_value_even_without_display_as_text_config() {
let (type_defs, enums, functions) = table_ir();
let fixture = equals_fixture("summary_smoke_bare", "summary", "hello");
let out = render(&fixture, "read_summary", &type_defs, &enums, &functions, &[]);
assert!(
!out.contains(".getValue()"),
"a data-carrying union enum field must never render through .getValue(), got:\n{out}"
);
}
#[test]
fn an_unrelated_fieldless_enum_field_is_unaffected() {
let (type_defs, enums, functions) = table_ir();
let fixture = equals_fixture("status_smoke_2", "status", "Complete");
let out = render(&fixture, "read_status", &type_defs, &enums, &functions, &[]);
assert!(
out.contains(".getValue()"),
"expected the fieldless enum field to render through .getValue(), got:\n{out}"
);
}