Skip to content

Releases: mapstruct/mapstruct

1.6.0.Beta2

11 May 07:10
Compare
Choose a tag to compare
1.6.0.Beta2 Pre-release
Pre-release

Features

  • Support conditional mapping for source parameters (#2610, #3459, #3270)
  • Add @SourcePropertyName to handle a property name of the source object (#3323) - Currently only applicable for @Condition methods

Enhancements

  • Improve error message for mapping to target = "." using expression (#3485)
  • Improve error messages for auto generated mappings (#2788)
  • Remove unnecessary casts to long (#3400)

Bugs

  • @Condition cannot be used only with @Context parameters (#3561)
  • @Condition treated as ambiguous mapping for methods returning Boolean/boolean (#3565)
  • Subclass mapping warns about unmapped property that is mapped in referenced mapper (#3360)
  • Interface inherited build method is not found (#3463)
  • Bean with getter returning Stream is treating the Stream as an alternative setter (#3462)
  • Using Mapping#expression and Mapping#conditionalQualifiedBy(Name) should lead to compile error (#3413)
  • Defined mappings for subclass mappings with runtime exception subclass exhaustive strategy not working if result type is abstract class (#3331)

Documentation

  • Clarify that Mapping#ignoreByDefault is inherited in nested mappings in documentation (#3577)

Build

  • Improve tests to show that Lombok @SuperBuilder is supported (#3524)
  • Add Java 21 CI matrix build (#3473)

1.6.0.Beta1

04 Nov 22:28
Compare
Choose a tag to compare
1.6.0.Beta1 Pre-release
Pre-release

Features

  • Access to target property name (#2688) - @TargetPropertyName can be used to access the target property name to conditional and mapping methods
  • Support passing annotations to generated code (#1574, #2773, #2895, #2983) - Using @AnnotateWith. If a method is annotated with @Deprecated it is automatically copied into the generated code.
  • Support for globally defining nullValueIterableMappingStrategy and nullValueMapMappingStrategy (#2953) - The different strategies can be configured using mapstruct.nullValueIterableMappingStrategy and mapstruct.nullValueMapMappingStrategy respectively
  • Support qualifiers for SubclassMapping annotated methods (#3119)
  • Support defining custom processor options for custom SPI (#3071) - There is also AdditionalSupportedOptionsProvider that can be used to defined the supported options for a custom SPI. The additional options cannot start with mapstruct.
  • Support for defining Javadoc on the generated mapper (#2987) - Using @Javadoc

Enhancements

  • Support for converting between Enum and Integer (#2963)
  • Support for converting between Locale and String (#3172)
  • Support for implicit conversion between java.time.LocalDate and java.time.LocalDateTime (#3199)
  • Support custom name in Spring annotations (#1427) - Can be done using @AnnotateWith(value = Service.class, elements = @AnnotateWith.Element(strings = "cakeMapperV2"))
  • Support meta annotations for @ValueMapping (#3037)
  • Ambiguous mapping method but there is a more specific mapping (#1216)
  • Do not treat getter as an alternative write accessor when using CollectionMappingStrategy#TARGET_IMMUTABLE (#2952)
  • Improve line location report for invalid qualifier for SubclassMapping (#3202)
  • Support @InheritConfiguration for @SubclassMapping in methods with identical signature (#3125)
  • Do not require subclassExhaustiveStrategy when source is a sealed class and all subtypes are specified (#3054)
  • Add validation of String type for @TargetPropertyName (#2863)
  • Support for all lifecycle methods on type being build with builders (#1454)
    • @BeforeMapping with @TargetType the type being build
    • @AfterMapping with @TargetType the type being build
    • @AfterMapping with @MappingTarget the type being build
  • Redundant null checks for nested properties (#3245)
  • @Default on Java Record's constructor isn't respected (#3231)
  • Add InjectionStrategy.SETTER (#3229)
  • Add BeanMapping#unmappedSourcePolicy (#3309)
  • Improve support for Map attributes for immutables (#3089)
  • Support mapping Iterable to Collection (#3376)

Bugs

  • Breaking change: Mapping from Map to Bean (#3144)
  • Condition with @TargetType on Collection fails to compile (#2901)
  • Annotations are automatically passed in forged methods (#3015)
  • Mapping Composition does not work for @SubclassMapping (#3174)
  • Mapping control disabling conversions does not disable them in 2 step mappings (#3186)
  • @BeanMapping(ignoreByDefault = true) does not work for constructor properties (#3158)
  • @ValueMapping strips spaces from source (#3153)
  • defaultExpression does not work when mapping a collection of custom types (#3159)
  • Arrays cannot be mapped to collection / iterable using an adder method (#3165)
  • Unmapped source properties error when source is mapped to a nested field of the target object (#2781)
  • NullPointerException when ignoring target '.' (#3238) - There is now a compilation error instead of an error in the processor
  • NullValuePropertyMappingStrategy.IGNORE does not ignore target collection even when source one is null (only when collectionMappingStrategy = CollectionMappingStrategy.TARGET_IMMUTABLE) (#3104)
  • @SubclassMapping not working with @Mapping nested properties and target all (#3126)
  • Compile error when using default and static methods in @MapperConfig (#3296)
  • Generic class with adder method and CollectionMappingStrategy.ADDER_PREFERRED fails (#3310)
  • MapStruct can not map only primitives (#3317)
  • 2-step mapping with generics does not work correctly (#2663)
  • MapStruct no longer handles generic mapping methods (in conjunction with immutables) after upgrading from 1.4.x to version 1.5.x (#3163)
  • Ignored mappings when using @InheritConfiguration (#3361)

Documentation

  • Use GitHub new Issue Form Templates (#3008)
  • Mapping composition is no longer experimental (#3239)
  • Improve Lombok integration documentation (#3374)

Build / Refactoring

  • Try to stabilise some date conversion tests (#2806)
  • Avoid unnecessary unboxing of Boolean (#3003)
  • Update FreeMarker to 2.3.32
  • Refactor method selection and use a context to be able to more easily access information (#3280)
  • Update tarLongFileMode to use POSIX (#3340)
  • Simplified some expressions, redundant expressions removed (#3292)
  • Refactor to use presence check for mapping methods (#3347) - Still only internal and custom presence checks methods are not supported for source parameters (see #2610 for that)
  • Update github actions (#3397)
    • Add Java 21 to test matrix
    • Add Java EA to test matrix
    • Removing java 13 and 18 from test matrict

Breaking Changes

Map to Bean

In 1.5 we added support for mapping a map to a bean by implicitly mapping all the properties from the target bean by accessing them from the map. However, this lead to some problems in multi mapping methods. Therefore, in this release we tightened up a bit and in multi source mapping methods the Map will not be considered when doing implicit mappings.

e.g.

@Mapper
public interface CarMapper {

    // This method is going to implicitly map all the target properties from the map
    Target map(Map<String, Object> map);
    
    // This method is not going to use the map for implicit mappings.
    //  Only the name will be mapped from the map (since it has been defined like that
    @Mapping(target = "name", source = "map.name")
    Target map(Source source, Map<String, Object> map)

}

@BeanMapping inheritance

All, except resultType and ignoredUnmappedSourceProperties attributes of @BeanMapping have been made to consistently be passed down to the generated nested methods. This means that if you were relying on some buggy behavior it might no longer work.

e.g. BeanMapping#ignoreByDefault was not being passed down properly, i.e. implicit mapping was being done for nested properties. This has been fixed. If you want to implicitly map nested mappings then you'll have to define your own mapper appropriatelly.

@Mapper
interface MyMapper {
  @BeanMapping( ignoreByDefault = true )
  @Mapping( source = "sub", target = "target" )
  Target map( Source source );
}

needs to be replaced with

@Mapper
interface MyMapper {
  @BeanMapping( ignoreByDefault = true )
  @Mapping( source = "sub", target = "target" )
  Target map( Source source );
  
  // this is the mapping `source = "sub"` and `target = "target"` 
  // redefined to get rid of the `ignoreByDefault=true`, because this property is inherited
  SubTarget subSourceToSubTarget( SubSource subSource );
}

Sponsoring

After the request from the community we have enabled sponsoring for the project. See #2340 for how you can sponsor us if you want to.

Contributors

1.5.5.Final

23 Apr 20:18
Compare
Choose a tag to compare

Enhancements

  • Add support for Jakarta XML Binding (#2730)

Bugs

  • BeanMappingOptions#ignoreUnmappedSourceProperties are not inherited via @InheritConfiguration (#3248) - Regression from 1.5.3

Documentation

  • jakarta-cdi component model not in docs (#3236)
  • Polish links in docs (#3214)

1.5.4.Final

13 Apr 21:56
Compare
Choose a tag to compare

Enhancements

  • Support for Jakarta @ApplicationScoped is missing (#2950)

Bugs

  • Exceptions declared to be thrown by a mapping method, are not declared in generated mapping methods for nested types (#3142)
  • DeepClone mapping control not generating third tier functions to clone (#3135)
  • missing throws clauses when mapping enum with checked exceptions (#3110)
  • Version 1.5.3 doesn't consider Mapping annotations for nested objects (worked with 1.5.2) (#3057)
  • Cannot use only BeanMapping#mappingControl (#3040)

Documentation

  • Document <THROW_EXCEPTION> in the reference guide (#3112)

1.5.3.Final

07 Oct 18:42
Compare
Choose a tag to compare

Bugs

  • Generic @AfterMapping does not consider @MappingTarget properly in 1.5 (#3036)
  • Method annotated with @AfterMapping is not called (#2955)
  • Ignored unknown source property error, but property exist (#2743)
  • SubclassMapping doesn't honour mappingControl (#3018)
  • Upgrade from 1.4.1 to 1.5.2 broke primitive to wrapper classes mapping (#2921)
  • Conversion of BigDecimal to primitive double wrong with 1.5.2 (#2913)
  • Ambiguous mapping methods when upgrading to MapStruct 1.5.0.RC1 (#2840)
  • SubclassMapping stackoverflow exception (#2825)
  • Optional wrapping pattern broken in 1.5.2.Final (#2925)
  • Missing import in generated mapper when referencing a nested enum from an unrelated class (#2945)
  • Unused import warning of nested classes (#2907)
  • Compilation error in generated code for @Conditional and collection (#2937)
  • Missing import of nested class (#2897)
  • Ignoring unmapped source properties in inverse inheritance (#2949)
  • Compilation error when mapping fields with the same type due to not wrapping in a try-catch block (#2839)
  • Using @TargetType as a parameter for @Condition causes NPE during compiling (#2882)
  • Cannot map from a covariant (extends) generic type (#2677)

Documentation

  • Add IntelliJ and Eclipse plugin to the documentation (#2928)
  • Fix typos in documentation (#2974, #2982, #2989)
  • Update Typos in javadoc (#2958)
  • Polish comments, javadoc and documentation (#3026)
  • Improve documentation for BeanMapping#ignoreByDefault (#2929)

Build

  • Build fails when running mvn test on an M1 Mac (#2922)

1.5.2.Final

18 Jun 17:14
Compare
Choose a tag to compare

Enhancements

  • Add support for Java Text Blocks in expressions (#2837)

Bugs

  • Generated code does not include enclosing class when referring to nested class (#2880)
  • SubclassExhaustiveStrategy.RUNTIME_EXCEPTION option does not work if the superclass has a non-empty constructor #2891

Build

  • Codecov no longer publishes information for commits (#2870)

1.5.1.Final

05 Jun 06:54
Compare
Choose a tag to compare

Bugs

  • NullPointerException when reporting errors for non Mappers (#2867)

1.5.0.Final

02 Jun 21:31
Compare
Choose a tag to compare

Bugs

  • Compilation error due to missing import with nested classes (#2797)
  • MapStruct 1.5.0 generates invalid code when using @Condition on a presence check for a generic wrapper (#2795)
  • No compile error when conditionExpression and expression are used together (#2794)
  • No import is added to generated class when using @BeforeMapping on a used mapper (#2807)

Documentation

  • Error in the readme ( what is MapStruct paragraph ) (#2851)
  • Enhance documentation around SPI usage (#2739)

Build

  • Update jacoco maven plugin to compile on Java 17 (#2835)

Previous Release Notes

1.5.0.RC1

21 Mar 07:24
Compare
Choose a tag to compare
1.5.0.RC1 Pre-release
Pre-release

Enhancement

  • Add compiler check for unimplemented methods for lifecycle @BeforeMapping / @AfterMapping methods (#2674)
  • Opt-out of using builders via a processor option (#1661)
  • @DecoratedWith does not work with incremental compilation in Gradle 7.3 (#2682)
  • Add support for Jakarta Dependency Injection API (#2567)
  • Allow @InheritInverseConfiguration with @SubclassMapping(s) (#2696)
  • MapStruct 1.4 regression: issue combining qualifiedByName, uses and method chaining (#2538) - In 1.4 we strengthened the check for qualified methods and reported an error if there was no applicable qualifier. This strengthening led to 2-step mappings not to work properly when only one of the steps is qualified. With this issue it is now possible to use 2-step mappings with only one of the steps being qualified.

Bugs

  • Fail to import nested enum when an enum constant is referenced (#2704)
  • Added support for collections and maps with a no-args constructor (#2668)
  • MapStruct does not always use builders in target-object (#1997)
  • Cannot map from a covariant (extends) generic type (#2677)
  • Detecting javax.annotation.processing.Generated in modular Java does not seem to work (#2629)
  • Using MappingTarget inside a Condition causes a FreeMarker template error (#2758)
  • Illegal start of type when using a static method of a generic type (#2755)
  • Mapping embedded map keys that contain characters that aren't valid for Java method names (#2748)

Documentation

  • @Condition docs out of sync (#2689)
  • Add documentation about the new NullValueMappingStrategy for collections and maps (#2687)
  • Add documentation about when mappers are injected (#2686)
  • Clarify documentation about builders and lifecycle @AfterMapping / @BeforeMapping methods (#2719)
  • Correct description for example demonstrating default expression (#2709)
  • Clarify documentation about Condition for update mappings (#2715)

Build

  • Update tools gem for tests to run properly on Java 18+ (#2725)
  • Support defining which test dependencies should be available during testing (#2728)
  • Run CDI integration tests on Java 16+ (#2468)

Contributors

We'd like to thank all the contributors who worked on this release!

1.5.0.Beta2

12 Dec 12:15
Compare
Choose a tag to compare
1.5.0.Beta2 Pre-release
Pre-release

Features

  • Support for Type-Refinement mapping (or Downcast Mapping) (#131, #366, #2438)
  • NullValueMappingStrategy option to map collections/maps, but not beans (#2351)

Enhancement

  • Diagnostics show up on non-Mapper types (#598)
  • Generate imports only for top level classes (#1386)
  • MapStruct should return the target object(which marking with @MappingTarget) when the source object is null (#1752) - See Behaviour Changes
  • Getting incorrect "iterable type to non-iterable type" error (#2005)
  • Expose suppressTimestampInGenerated in @Mapper annotation (#2225)
  • Provide available case transformation when unknown is used in CaseEnumTransformationStrategy (#2525)
  • Add built in conversion between URL and String (#2552)
  • Add unmappedSourcePolicy annotation processor argument (#2555)

Bugs

  • Import handling in TypeFactory should deal with inner types bug (#148)
  • Ambiguous constructors error message does not contain the ambiguous constructors (#2515)
  • MapStruct 1.5.0.Beta1 ZonedDateTime field mapping regression (#2530)
  • Issue with unmappedSourcePolicy and implicit source mapping (#2537)
  • TYPE_USE annotations on method parameters cause them not to match when using errorprone (#2541)
  • ReverseConversion should maintain RequiredHelperMethods (#2544)
  • New mapping feature not support property paths (#2553)
  • Mapping List in Record causes warning (#2554)
  • BeanMapping#ignoreByDefault interaction with unmappedSourcePolicy (#2560)
  • Allow use of mapstruct in default package with nested classes (#2593)
  • Record with "is" prefixed Boolean field causes unmapped source property report (#2596)
  • FQN used when mapping Stream to Array (#2614)
  • Cannot map nested target when mapping from Map to Bean (#2624)
  • Warning about unmapped not existing property (#2635)
  • @Condition not working when the source in the Mapping is the source parameter (#2666)
  • Optional "wrapping" pattern broken with 1.5.0.Beta (#2673)

Documentation

  • Document usage of qualifiers used together with defaultValue (#2636)

Build

  • Add JDK 18 to build matrix (#2591)
  • Move tycho-compiler-jdt as test dependency (#2611)

Codebase Enhancements

  • Refactor Accessors and remove not needed AccessorType(s) (#2680)

Behaviour Changes

Update mappings with a return type

Prior to this release update mappings with a return type returned null when the source parameter was null. However, this is not what a user expects (see #1752).

With this release methods like

Car updateCar(CarDto source, @MappingTarget Car car);

will always return the @MappingTarget method, irregardless of what the source is.