Set value to one of the property in Java 15 record

31.4k views Asked by At

I am using Java 15 preview feature record in my code, and defined the record as follow

public record ProductViewModel
        (
                String id,
                String name,
                String description,
                float price
        ) {
}

In the controller level I have the below code

@Put(uri = "/{id}")
public Maybe<HttpResponse> Update(ProductViewModel model, String id) {
        LOG.info(String.format("Controller --> Updating the specified product"));
        return iProductManager.Update(id, model).flatMap(item -> {
            if(item == null)
                return Maybe.just(HttpResponse.notFound());
            else
                return Maybe.just(HttpResponse.accepted());
        });
    }

From the UI in the model the value of id is not passed, however, it is passed as a route parameter. Now I want to set the value in the controller level, something like

model.setid(id) // Old style

How can I set the value to the record particular property

3

There are 3 answers

3
daniel On BEST ANSWER

You can't. Record properties are immutable. What you can do however is add a wither to create a new record with same properties but a new id:

public record ProductViewModel(String id,
                               String name, 
                               String description,
                               float price) {

    public ProductViewModel withId(String id) {
        return new ProductViewModel(id, name(), description(), price());
    }
} 
2
fps On

If you need to mutate an attribute, then you need to use a class instead of a record.

From the JEP:

Enhance the Java programming language with records, which are classes that act as transparent carriers for immutable data. Records can be thought of as nominal tuples.

So, you'd better use a class if you need that behavior.

0
dreamcrash On

You cannot modify them. From the Oracle page:

A record class is a shallowly immutable, transparent carrier for a fixed set of values, called the record components. The Java language provides concise syntax for declaring record classes, whereby the record components are declared in the record header. The list of record components declared in the record header form the record descriptor.

From the Java Language Specification Section 8.10 one can read the following:

A record declaration is implicitly final. It is permitted for the declaration of a record class to redundantly specify the final

and

8.10.3 Record Members

A record class has for each record component appearing in the record component list an implicitly declared field with the same name as the record component and the same type as the declared type of the record component. This field is declared private and final. The field is annotated with the annotations, if any, that appear on the corresponding record component and whose annotation types are applicable in the field declaration context, or in type contexts, or both.