Backend Development 10 min read

Using MapStruct for Efficient Bean Copying in Java

This article explains why manual property copying in layered Java applications is inefficient, compares runtime copiers like BeanUtils and BeanCopier, and demonstrates how MapStruct provides compile‑time, type‑safe, high‑performance bean mapping with support for deep copy, collection mapping, field ignoring, and Lombok integration.

Architect's Tech Stack
Architect's Tech Stack
Architect's Tech Stack
Using MapStruct for Efficient Bean Copying in Java

In layered Java applications, copying properties between objects such as User and UserVO is common but manual assignment is inefficient.

Traditional approaches like Apache BeanUtils (reflection‑based) and Spring BeanUtils improve speed slightly, while cglib BeanCopier generates bytecode for near‑native performance.

MapStruct, a compile‑time annotation processor, generates type‑safe, high‑performance mappers without reflection, supporting shallow and deep copy, collection mapping, field ignoring, and custom type‑conversion policies.

BeanUtils.copyProperties(source, target);
BeanCopier beanCopier = BeanCopier.create(SourceData.class, TargetData.class, false);
beanCopier.copy(source, target, null);

A typical MapStruct mapper is defined as an interface annotated with @Mapper , and the implementation is generated during compilation.

@Mapper
public interface BeanMapper {
    BeanMapper INSTANCE = Mappers.getMapper(BeanMapper.class);
    TargetData map(SourceData source);
}

Configuration examples include adding the MapStruct dependency and annotation‑processor paths in Maven, enabling Lombok support, and using @Mapping to ignore fields or apply DeepClone for deep copying.

@Mapping(target = "id", ignore = true)
@Mapping(target = "data", mappingControl = DeepClone.class)
TargetData map(SourceData source);

MapStruct also provides compile‑time type‑conversion checks; setting typeConversionPolicy = ReportingPolicy.ERROR forces explicit mappings for mismatched types.

Overall, MapStruct offers a performant, type‑safe alternative to runtime copiers, especially when many object mappings are required, while its drawbacks are the added dependency and limited usefulness for very few mappings.

Javacode generationBackend DevelopmentMapStructBean Mapping
Architect's Tech Stack
Written by

Architect's Tech Stack

Java backend, microservices, distributed systems, containerized programming, and more.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.