This is an automated email from the ASF dual-hosted git repository.

paulk pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/groovy.git


The following commit(s) were added to refs/heads/master by this push:
     new 77919a1  documentation for records (cont'd) plus minor 
refactoring/cleanup
77919a1 is described below

commit 77919a1502280df0986772cd1f3b925292e11512
Author: Paul King <[email protected]>
AuthorDate: Sat Oct 30 10:39:08 2021 +1000

    documentation for records (cont'd) plus minor refactoring/cleanup
---
 .../groovy/transform/ImmutableASTTransformation.java |  5 +++--
 .../transform/RecordTypeASTTransformation.java       |  2 +-
 src/spec/doc/_records.adoc                           | 20 ++++++++++++++------
 src/spec/test/RecordSpecificationTest.groovy         | 11 +++++++++++
 4 files changed, 29 insertions(+), 9 deletions(-)

diff --git 
a/src/main/java/org/codehaus/groovy/transform/ImmutableASTTransformation.java 
b/src/main/java/org/codehaus/groovy/transform/ImmutableASTTransformation.java
index 0f2f760..695d551 100644
--- 
a/src/main/java/org/codehaus/groovy/transform/ImmutableASTTransformation.java
+++ 
b/src/main/java/org/codehaus/groovy/transform/ImmutableASTTransformation.java
@@ -31,6 +31,7 @@ import org.codehaus.groovy.ast.AnnotationNode;
 import org.codehaus.groovy.ast.ClassHelper;
 import org.codehaus.groovy.ast.ClassNode;
 import org.codehaus.groovy.ast.FieldNode;
+import org.codehaus.groovy.ast.MethodNode;
 import org.codehaus.groovy.ast.Parameter;
 import org.codehaus.groovy.ast.PropertyNode;
 import org.codehaus.groovy.ast.VariableScope;
@@ -287,7 +288,7 @@ public class ImmutableASTTransformation extends 
AbstractASTTransformation implem
         );
     }
 
-    static void createCopyWith(final ClassNode cNode, final List<PropertyNode> 
pList) {
+    static MethodNode createCopyWith(final ClassNode cNode, final 
List<PropertyNode> pList) {
         BlockStatement body = new BlockStatement();
         body.addStatement(ifS(
                 orX(
@@ -311,7 +312,7 @@ public class ImmutableASTTransformation extends 
AbstractASTTransformation implem
 
         final ClassNode clonedNode = cNode.getPlainNodeReference();
 
-        addGeneratedMethod(cNode, "copyWith",
+        return addGeneratedMethod(cNode, "copyWith",
                 ACC_PUBLIC | ACC_FINAL,
                 clonedNode,
                 params(new Parameter(new ClassNode(Map.class), "map")),
diff --git 
a/src/main/java/org/codehaus/groovy/transform/RecordTypeASTTransformation.java 
b/src/main/java/org/codehaus/groovy/transform/RecordTypeASTTransformation.java
index bfb8f95..ba62ec7 100644
--- 
a/src/main/java/org/codehaus/groovy/transform/RecordTypeASTTransformation.java
+++ 
b/src/main/java/org/codehaus/groovy/transform/RecordTypeASTTransformation.java
@@ -185,7 +185,7 @@ public class RecordTypeASTTransformation extends 
AbstractASTTransformation imple
             if (unsupportedTupleAttribute(tupleCons, "callSuper")) return;
         }
 
-        if (!pList.isEmpty() && memberHasValue(node, "copyWith", Boolean.TRUE) 
&& !hasDeclaredMethod(cNode, "copyWith", 1)) {
+        if (!pList.isEmpty() && !memberHasValue(node, "copyWith", 
Boolean.FALSE) && !hasDeclaredMethod(cNode, "copyWith", 1)) {
             ImmutableASTTransformation.createCopyWith(cNode, pList);
         }
     }
diff --git a/src/spec/doc/_records.adoc b/src/spec/doc/_records.adoc
index 235ce47..0ca5c30 100644
--- a/src/spec/doc/_records.adoc
+++ b/src/spec/doc/_records.adoc
@@ -57,7 +57,9 @@ 
include::../test/RecordSpecificationTest.groovy[tags=record_message_equivalent,i
 ----
 
 Note the special naming convention for record getters. They are the same name 
as the field
-(rather than the otherwise common JavaBean convention of capitalized with a 
"get" prefix).
+(rather than the often common JavaBean convention of capitalized with a "get" 
prefix).
+Rather than refering to a records fields or properties, the term _component_
+is typicaly used for records. So our `Message` record has `from`, `to`, and 
`body` components.
 
 Like in Java, you can override the normally implicitly supplied methods
 by writing your own:
@@ -148,16 +150,22 @@ 
include::../test/RecordSpecificationTest.groovy[tags=record_point2d_tostring_ann
 
 We can see here that without the package name it would have the same toString 
as our previous example.
 
-=== CopyWith
+=== Copying
 
-For a record with many fields, it can be useful to make a copy with one or 
more fields changes.
-This can be enabled by setting the `copyWith` annotation attribute to `true`:
+It can be useful to make a copy of a record with some components changed.
+This can be done using a provided `copyWith` method which takes named 
arguments.
+Record components are set from the supplied arguments.
+For components not mentioned, a (shallow) copy of the original record 
commponent is used.
+Here is how you might use `copyWith` for the `Fruit` record:
 
 [source,groovy]
 ----
 include::../test/RecordSpecificationTest.groovy[tags=record_copywith,indent=0]
 ----
 
+The `copyWith` functionality can be disabled by setting the
+`RecordBase#copyWith` annotation attribute to `false`.
+
 === Deep immutability
 
 As with Java, records by default offer shallow immutability.
@@ -173,8 +181,8 @@ These examples illustrates the principal behind
 Groovy's record feature offering three levels of convenience:
 
 * Using the `record` keyword for maximum succinctness
-* Support low-ceremony customization using declarative annotations
-* Provide normal method implementations when full control is required
+* Supporting low-ceremony customization using declarative annotations
+* Allowing normal method implementations when full control is required
 
 == Other differences to Java
 
diff --git a/src/spec/test/RecordSpecificationTest.groovy 
b/src/spec/test/RecordSpecificationTest.groovy
index 13ff0ae..e8fe883 100644
--- a/src/spec/test/RecordSpecificationTest.groovy
+++ b/src/spec/test/RecordSpecificationTest.groovy
@@ -110,6 +110,17 @@ def orange = apple.copyWith(name: 'Orange')
 assert orange.toString() == 'Fruit[name=Orange, price=11.6]'
 // end::record_copywith[]
 '''
+        assertScript '''
+import groovy.transform.RecordBase
+import static groovy.test.GroovyAssert.shouldFail
+
+@RecordBase(copyWith=false)
+record Fruit(String name, double price) {}
+def apple = new Fruit('Apple', 11.6)
+shouldFail(MissingMethodException) {
+    apple.copyWith(name: 'Orange')
+}
+'''
     }
 
     void testImmutable() {

Reply via email to