diff --git a/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/BuildableOrderState.java b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/BuildableOrderState.java new file mode 100644 index 0000000000..5bafa33243 --- /dev/null +++ b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/BuildableOrderState.java @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +/** + * The base class for a Sort Order state that can be transformed into a complete + * and well-formed {@link Order}. + */ +public abstract class BuildableOrderState extends OrderState { + + /** + * Construct a new instance. + * + * @param order + */ + protected BuildableOrderState(Order order) { + super(order); + } + + /** + * Build and return the {@link Order}. + * + * @return the built Order + */ + public final Order build() { + order.close(); + return order; + } + +} diff --git a/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Direction.java b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Direction.java new file mode 100644 index 0000000000..a935fde7e4 --- /dev/null +++ b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Direction.java @@ -0,0 +1,60 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +/** + * Sort directions. + * + * @author Jeff Nelson + */ +enum Direction { + + ASCENDING(1), DESCENDING(-1); + + /** + * Return the default {@link Direction}. + * + * @return the default + */ + static Direction $default() { + return Direction.ASCENDING; + } + + /** + * The coefficient is multiplied by the result of a {@link Comparator} to + * sort elements in forward or reverse order. + */ + private final int coefficient; + + /** + * Construct a new instance. + * + * @param coefficient + */ + Direction(int coefficient) { + this.coefficient = coefficient; + } + + /** + * Return the coefficient associated with this {@link Direction}. + * + * @return the coefficient + */ + public int coefficient() { + return coefficient; + } + +} diff --git a/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Order.java b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Order.java new file mode 100644 index 0000000000..cdf1068fac --- /dev/null +++ b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Order.java @@ -0,0 +1,113 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +import java.util.LinkedHashMap; +import java.util.Objects; + +import javax.annotation.Nullable; + +import com.google.common.annotations.VisibleForTesting; +import com.google.common.base.Preconditions; +import com.google.common.collect.Maps; + +/** + * {@link Order} encapsulates the semantics of a result set sorting. Any given + * time, objects of this class can exist in one of two modes: {@code building} + * or {@code built}. When an Order is + * {@code built}, it is guaranteed to represent a fully and well formed sort + * order that can be processed. On the other hand, when a Order is + * {@code building} it is in an incomplete state. + *
+ * This class is the public interface to Order construction. It is meant to + * be used in a chained manner, where the caller initially calls + * {@link Order#by} and continues to construct the Order using the + * options available from each subsequently returned state. + *
+ * + */ +public final class Order { + + /** + * Start building a new {@link Order}. + * + * @return the Order builder + */ + public static OrderByState by(String key) { + Order order = new Order(); + return new OrderByState(order, key, Direction.$default()); + } + + /** + * A mapping from each key to direction ordinal (e.g. 1 for ASC and -1 for + * DESC) in the constructed {@link Order}. + */ + @VisibleForTesting + final LinkedHashMap+ * For the purposes of a builder, an {@link OrderState} typically describes what + * was most recently consumed. + *
+ */ +public abstract class OrderState { + + /** + * A reference to the {@link Order} that is being built. + */ + protected final Order order; + + /** + * Construct a new instance. + * + * @param order + */ + protected OrderState(Order order) { + this.order = order; + } + +} diff --git a/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/OrderThenState.java b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/OrderThenState.java new file mode 100644 index 0000000000..90581383eb --- /dev/null +++ b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/OrderThenState.java @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +/** + * The {@link OrderThenState} is simply a bridge that allows a transition back + * to a {@link OrderByState}. + */ +public class OrderThenState extends OrderState { + + /** + * Construct a new instance. + * + * @param order + */ + OrderThenState(Order order) { + super(order); + } + + public OrderByState by(String key) { + return new OrderByState(order, key, Direction.$default()); + } + +} \ No newline at end of file diff --git a/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Sort.java b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Sort.java new file mode 100644 index 0000000000..fcc3ddf84c --- /dev/null +++ b/concourse-driver-java/src/main/java/com/cinchapi/concourse/lang/sort/Sort.java @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +/** + * Serves as an alias for {@link Order} + */ +public final class Sort { + + /** + * Start building a new {@link Order}. + * + * @return the Order builder + */ + public static OrderByState by(String key) { + return Order.by(key); + } + + private Sort() {/* no-init */} + +} diff --git a/concourse-driver-java/src/test/java/com/cinchapi/concourse/lang/sort/OrderTest.java b/concourse-driver-java/src/test/java/com/cinchapi/concourse/lang/sort/OrderTest.java new file mode 100644 index 0000000000..fabfb2c3dc --- /dev/null +++ b/concourse-driver-java/src/test/java/com/cinchapi/concourse/lang/sort/OrderTest.java @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2013-2019 Cinchapi Inc. + * + * Licensed 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 com.cinchapi.concourse.lang.sort; + +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +import com.google.common.collect.ImmutableMap; + +/** + * Unit tests for the {@link com.cinchapi.concourse.lang.sort.Order} building + * functionality. + */ +public class OrderTest { + + @Test + public void testDefaultSortOrder() { + Map