GROOVY-8065: Map created as org.springframework.http.HttpHeaders is empty in 2.4.8, works fine in 2.4.7 (closes #480)
Project: http://git-wip-us.apache.org/repos/asf/groovy/repo Commit: http://git-wip-us.apache.org/repos/asf/groovy/commit/1358ed58 Tree: http://git-wip-us.apache.org/repos/asf/groovy/tree/1358ed58 Diff: http://git-wip-us.apache.org/repos/asf/groovy/diff/1358ed58 Branch: refs/heads/parrot Commit: 1358ed58af0df10a959924816310f8f1c020aa50 Parents: e96a961 Author: paulk <pa...@asert.com.au> Authored: Thu Jan 26 23:51:32 2017 +1000 Committer: paulk <pa...@asert.com.au> Committed: Sat Jan 28 08:46:13 2017 +1000 ---------------------------------------------------------------------- src/main/groovy/lang/MetaClassImpl.java | 21 ++++++----- src/test/groovy/bugs/Groovy8065Bug.groovy | 48 ++++++++++++++++++++++++++ 2 files changed, 61 insertions(+), 8 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/groovy/blob/1358ed58/src/main/groovy/lang/MetaClassImpl.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/lang/MetaClassImpl.java b/src/main/groovy/lang/MetaClassImpl.java index d7d8d9b..93c013b 100644 --- a/src/main/groovy/lang/MetaClassImpl.java +++ b/src/main/groovy/lang/MetaClassImpl.java @@ -2686,18 +2686,15 @@ public class MetaClassImpl implements MetaClass, MutableMetaClass { } //---------------------------------------------------------------------- - // turn setProperty on a Map to put on the Map itself - //---------------------------------------------------------------------- - if (method == null && !isStatic && this.isMap) { - ((Map) object).put(name, newValue); - return; - } - - //---------------------------------------------------------------------- // field //---------------------------------------------------------------------- if (method == null && field != null) { if (Modifier.isFinal(field.getModifiers())) { + // GROOVY-5985 + if (!isStatic && this.isMap) { + ((Map) object).put(name, newValue); + return; + } throw new ReadOnlyPropertyException(name, theClass); } if(!(this.isMap && isPrivateOrPkgPrivate(field.getModifiers()))) { @@ -2742,6 +2739,14 @@ public class MetaClassImpl implements MetaClass, MutableMetaClass { } //---------------------------------------------------------------------- + // turn setProperty on a Map to put on the Map itself + //---------------------------------------------------------------------- + if (method == null && !isStatic && this.isMap) { + ((Map) object).put(name, newValue); + return; + } + + //---------------------------------------------------------------------- // error due to missing method/field //---------------------------------------------------------------------- if (ambiguousListener) { http://git-wip-us.apache.org/repos/asf/groovy/blob/1358ed58/src/test/groovy/bugs/Groovy8065Bug.groovy ---------------------------------------------------------------------- diff --git a/src/test/groovy/bugs/Groovy8065Bug.groovy b/src/test/groovy/bugs/Groovy8065Bug.groovy new file mode 100644 index 0000000..5c3f018 --- /dev/null +++ b/src/test/groovy/bugs/Groovy8065Bug.groovy @@ -0,0 +1,48 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package groovy.bugs + +class Groovy8065Bug extends GroovyTestCase { + void testMapWithCustomSetDuringAsTypeCast() { + assertScript ''' + class MapWithSet extends LinkedHashMap { + void set(String k, String v) { + put(k.toLowerCase(), v.toUpperCase()) + } + } + def m = [Foo: 'Bar'] as MapWithSet + assert m == [foo: 'BAR'] + ''' + } + + void testMapWithPublicField() { + assertScript ''' + class A extends HashMap { + public foo + } + def a = new A() + a.x = 1 + assert a.x == 1 + a.foo = 2 + assert a.@foo == 2 + assert a.foo == null + assert a == [x:1] + ''' + } +}