This is an automated email from the ASF dual-hosted git repository. borinquenkid pushed a commit to branch chore/8.1.x-datamapping-core-timestamp in repository https://gitbox.apache.org/repos/asf/grails-core.git
commit a4218ff51355e605c1f4e64ec23e155a5dc024b2 Author: Walter Duque de Estrada <[email protected]> AuthorDate: Tue Aug 18 10:59:05 2026 -0500 Add spec coverage for AggregateTimestampProvider AggregateTimestampProvider was the only class in the timestamp package without test coverage. Also replaces iterator().next() with getFirst() per SequencedCollection (JDK 21). Co-Authored-By: Claude Sonnet 5 <[email protected]> --- .../gorm/timestamp/AggregateTimestampProvider.java | 2 +- .../gorm/timestamp/DefaultTimestampProvider.java | 2 - .../AggregateTimestampProviderSpec.groovy | 126 +++++++++++++++++++++ 3 files changed, 127 insertions(+), 3 deletions(-) diff --git a/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProvider.java b/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProvider.java index 7fb0f360f3..d8e0855056 100644 --- a/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProvider.java +++ b/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProvider.java @@ -49,7 +49,7 @@ public class AggregateTimestampProvider implements TimestampProvider { } } } else { - return createTimestamp(timestampProviders.iterator().next(), dateTimeClass); + return createTimestamp(timestampProviders.getFirst(), dateTimeClass); } throw new IllegalArgumentException("dateTimeClass given as parameter isn't supported by any TimestampProvider. You should call supportsCreating first."); } diff --git a/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/DefaultTimestampProvider.java b/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/DefaultTimestampProvider.java index 471345b4c0..5d44a8dc08 100644 --- a/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/DefaultTimestampProvider.java +++ b/grails-datamapping-core/src/main/groovy/org/grails/datastore/gorm/timestamp/DefaultTimestampProvider.java @@ -26,9 +26,7 @@ import org.springframework.util.ClassUtils; /** * Default implementation of TimestampProvider - * * supports creating timestamps for any class that supports a constructor that accepts a Long or long value. - * * "currentTimeMillis" can be overrided in subclasses (useful for testing purposes) * */ diff --git a/grails-datamapping-core/src/test/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProviderSpec.groovy b/grails-datamapping-core/src/test/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProviderSpec.groovy new file mode 100644 index 0000000000..d29cbff92c --- /dev/null +++ b/grails-datamapping-core/src/test/groovy/org/grails/datastore/gorm/timestamp/AggregateTimestampProviderSpec.groovy @@ -0,0 +1,126 @@ +/* + * 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 + * + * https://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 org.grails.datastore.gorm.timestamp + +import spock.lang.Specification + +class AggregateTimestampProviderSpec extends Specification { + + AggregateTimestampProvider aggregateTimestampProvider = new AggregateTimestampProvider() + + void "getTimestampProviders defaults to an empty list"() { + expect: + aggregateTimestampProvider.timestampProviders == [] + } + + void "setTimestampProviders stores the given providers"() { + given: + TimestampProvider dateProvider = Stub(TimestampProvider) + TimestampProvider stringProvider = Stub(TimestampProvider) + + when: + aggregateTimestampProvider.timestampProviders = [dateProvider, stringProvider] + + then: + aggregateTimestampProvider.timestampProviders == [dateProvider, stringProvider] + } + + void "supportsCreating returns true when any delegate provider supports the class"() { + given: + TimestampProvider dateProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> false + } + TimestampProvider stringProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> true + } + aggregateTimestampProvider.timestampProviders = [dateProvider, stringProvider] + + expect: + aggregateTimestampProvider.supportsCreating(Date) + } + + void "supportsCreating returns false when no delegate provider supports the class"() { + given: + TimestampProvider dateProvider = Stub(TimestampProvider) { + supportsCreating(_) >> false + } + aggregateTimestampProvider.timestampProviders = [dateProvider] + + expect: + !aggregateTimestampProvider.supportsCreating(Date) + } + + void "supportsCreating returns false when there are no delegate providers"() { + expect: + !aggregateTimestampProvider.supportsCreating(Date) + } + + void "createTimestamp delegates directly to the single registered provider"() { + given: + Date timestamp = new Date() + TimestampProvider onlyProvider = Stub(TimestampProvider) { + createTimestamp(Date) >> timestamp + } + aggregateTimestampProvider.timestampProviders = [onlyProvider] + + expect: + aggregateTimestampProvider.createTimestamp(Date) == timestamp + } + + void "createTimestamp with multiple providers delegates to the first provider that supports the class"() { + given: + Date timestamp = new Date() + TimestampProvider unsupportingProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> false + } + TimestampProvider supportingProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> true + createTimestamp(Date) >> timestamp + } + aggregateTimestampProvider.timestampProviders = [unsupportingProvider, supportingProvider] + + expect: + aggregateTimestampProvider.createTimestamp(Date) == timestamp + } + + void "createTimestamp with multiple providers throws when none support the class"() { + given: + TimestampProvider firstProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> false + } + TimestampProvider secondProvider = Stub(TimestampProvider) { + supportsCreating(Date) >> false + } + aggregateTimestampProvider.timestampProviders = [firstProvider, secondProvider] + + when: + aggregateTimestampProvider.createTimestamp(Date) + + then: + thrown(IllegalArgumentException) + } + + void "createTimestamp with no registered providers throws"() { + when: + aggregateTimestampProvider.createTimestamp(Date) + + then: + thrown(NoSuchElementException) + } +}
