http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/SpreadListEvaluatingException.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/SpreadListEvaluatingException.java b/src/main/groovy/groovy/lang/SpreadListEvaluatingException.java new file mode 100644 index 0000000..b6de965 --- /dev/null +++ b/src/main/groovy/groovy/lang/SpreadListEvaluatingException.java @@ -0,0 +1,25 @@ +/* + * 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.lang; + +public class SpreadListEvaluatingException extends GroovyRuntimeException { + public SpreadListEvaluatingException(String message) { + super(message); + } +}
http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/SpreadMap.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/SpreadMap.java b/src/main/groovy/groovy/lang/SpreadMap.java new file mode 100644 index 0000000..7ba9e4f --- /dev/null +++ b/src/main/groovy/groovy/lang/SpreadMap.java @@ -0,0 +1,120 @@ +/* + * 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.lang; + +import org.codehaus.groovy.runtime.typehandling.DefaultTypeTransformation; + +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +/** + * Helper to turn a list with an even number of elements into a Map. + * + * @author Pilho Kim + * @author Tim Tiemens + */ +public class SpreadMap extends HashMap { + private int hashCode; + + public SpreadMap(Object[] values) { + int i = 0; + while (i < values.length) { + super.put(values[i++], values[i++]); + } + } + + public SpreadMap(Map map) { + super(map); + } + + /** + * @since 1.8.0 + * @param list the list to make spreadable + */ + public SpreadMap(List list) { + this(list.toArray()); + } + + public Object put(Object key, Object value) { + throw new RuntimeException("SpreadMap: " + this + " is an immutable map, and so (" + + key + ": " + value + ") cannot be added."); + } + + public Object remove(Object key) { + throw new RuntimeException("SpreadMap: " + this + " is an immutable map, and so the key (" + + key + ") cannot be deleted."); + } + + public void putAll(Map t) { + throw new RuntimeException("SpreadMap: " + this + " is an immutable map, and so the map (" + + t + ") cannot be put in this spreadMap."); + } + + public boolean equals(Object that) { + if (that instanceof SpreadMap) { + return equals((SpreadMap) that); + } + return false; + } + + public boolean equals(SpreadMap that) { + if (that == null) return false; + + if (size() == that.size()) { + for (Object key : keySet()) { + if (!DefaultTypeTransformation.compareEqual(get(key), that.get(key))) { + return false; + } + } + return true; + } + return false; + } + + public int hashCode() { + if (hashCode == 0) { + for (Object key : keySet()) { + int hash = (key != null) ? key.hashCode() : 0xbabe; + hashCode ^= hash; + } + } + return hashCode; + } + + /** + * @return the string expression of <code>this</code> + */ + public String toString() { + if (isEmpty()) { + return "*:[:]"; + } + StringBuilder sb = new StringBuilder("*:["); + Iterator iter = keySet().iterator(); + while (iter.hasNext()) { + Object key = iter.next(); + sb.append(key).append(":").append(get(key)); + if (iter.hasNext()) + sb.append(", "); + } + sb.append("]"); + return sb.toString(); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/SpreadMapEvaluatingException.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/SpreadMapEvaluatingException.java b/src/main/groovy/groovy/lang/SpreadMapEvaluatingException.java new file mode 100644 index 0000000..408a223 --- /dev/null +++ b/src/main/groovy/groovy/lang/SpreadMapEvaluatingException.java @@ -0,0 +1,25 @@ +/* + * 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.lang; + +public class SpreadMapEvaluatingException extends GroovyRuntimeException { + public SpreadMapEvaluatingException(String message) { + super(message); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/StringWriterIOException.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/StringWriterIOException.java b/src/main/groovy/groovy/lang/StringWriterIOException.java new file mode 100644 index 0000000..0372399 --- /dev/null +++ b/src/main/groovy/groovy/lang/StringWriterIOException.java @@ -0,0 +1,37 @@ +/* + * 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.lang; + +import java.io.IOException; + +/** + * An IO exception occurred trying to append to a StringWriter which should never happen. + * + * @author <a href="mailto:[email protected]">James Strachan</a> + */ +public class StringWriterIOException extends RuntimeException { + + public StringWriterIOException(IOException e) { + super(e); + } + + public IOException getIOException() { + return (IOException) getCause(); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/TracingInterceptor.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/TracingInterceptor.java b/src/main/groovy/groovy/lang/TracingInterceptor.java new file mode 100644 index 0000000..f67de11 --- /dev/null +++ b/src/main/groovy/groovy/lang/TracingInterceptor.java @@ -0,0 +1,120 @@ +/* + * 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.lang; + +import java.io.IOException; +import java.io.PrintWriter; +import java.io.Writer; + +/* + * This {@link Interceptor} traces method calls on the proxied object to a log. + * By default, the log is simply <pre>System.out</pre>; however, that can be + * changed with the <pre>setWriter(Writer)</pre> method. + * <p> + * A message will be written to output before a method is invoked and after a method + * is invoked. If methods are nested, and invoke one another, then indentation + * of two spaces is written. + * <p> + * Here is an example usage on the ArrayList object: <br> + * <pre class="groovyTestCase"> + * def proxy = ProxyMetaClass.getInstance(ArrayList.class) + * proxy.interceptor = new TracingInterceptor() + * proxy.use { + * def list = [1, 2, 3] + * assert 3 == list.size() + * assert list.contains(1) + * } + * </pre> + * Running this code produces this output: + * <pre> + * before java.util.ArrayList.size() + * after java.util.ArrayList.size() + * before java.util.ArrayList.contains(java.lang.Integer) + * after java.util.ArrayList.contains(java.lang.Integer) + * </pre> + */ +public class TracingInterceptor implements Interceptor { + + protected Writer writer = new PrintWriter(System.out); + private int indent = 0; + + /** + * Returns the writer associated with this interceptor. + */ + public Writer getWriter() { + return writer; + } + + /** + * Changes the writer associated with this interceptor. + */ + public void setWriter(Writer writer) { + this.writer = writer; + } + + public Object beforeInvoke(Object object, String methodName, Object[] arguments) { + write(object, methodName, arguments, "before"); + indent++ ; + return null; + } + + public Object afterInvoke(Object object, String methodName, Object[] arguments, Object result) { + indent--; + write(object, methodName, arguments, "after "); + return result; + } + + public boolean doInvoke() { + return true; + } + private String indent(){ + StringBuilder result = new StringBuilder(); + for (int i=0; i<indent;i++){ + result.append(" "); + } + return result.toString(); + } + + protected void write(Object object, String methodName, Object[] arguments, final String origin) { + try { + writer.write(indent()); + writer.write(origin); + writer.write(" "); + Class theClass = object instanceof Class ? (Class) object: object.getClass(); + writeInfo(theClass, methodName, arguments); + writer.write("\n"); + writer.flush(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + protected void writeInfo(final Class aClass, String methodName, Object[] arguments) throws IOException { + writer.write(aClass.getName()); + writer.write("."); + writer.write(methodName); + writer.write("("); + for (int i = 0; i < arguments.length; i++) { + if (i > 0) writer.write(", "); + Object argument = arguments[i]; + writer.write(argument.getClass().getName()); + } + writer.write(")"); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/TrampolineClosure.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/TrampolineClosure.java b/src/main/groovy/groovy/lang/TrampolineClosure.java new file mode 100644 index 0000000..ed68f00 --- /dev/null +++ b/src/main/groovy/groovy/lang/TrampolineClosure.java @@ -0,0 +1,111 @@ +/* + * 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.lang; + +/** + * A TrampolineClosure wraps a closure that needs to be executed on a functional trampoline. + * Upon calling, a TrampolineClosure will call the original closure waiting for its result. + * If the outcome of the call is another instance of a TrampolineClosure, created perhaps as a result to a call to the TrampolineClosure.trampoline() + * method, the TrampolineClosure will again be invoked. This repetitive invocation of returned TrampolineClosure instances will continue + * until a value other than TrampolineClosure is returned. + * That value will become the final result of the trampoline. + * + * @author Vaclav Pech + */ +final class TrampolineClosure<V> extends Closure<V> { + + private final Closure<V> original; + + TrampolineClosure(final Closure<V> original) { + super(original.getOwner(), original.getDelegate()); + this.original = original; + } + + /** + * Delegates to the wrapped closure + */ + @Override + public int getMaximumNumberOfParameters() { + return original.maximumNumberOfParameters; + } + + /** + * Delegates to the wrapped closure + */ + @Override + public Class[] getParameterTypes() { + return original.parameterTypes; + } + + /** + * Starts the trampoline loop and calls the wrapped closure as the first step. + * @return The final result of the trampoline + */ + @Override + public V call() { + return loop(original.call()); + } + + /** + * Starts the trampoline loop and calls the wrapped closure as the first step. + * @return The final result of the trampoline + */ + @Override + public V call(final Object arguments) { + return loop(original.call(arguments)); + } + + /** + * Starts the trampoline loop and calls the wrapped closure as the first step. + * @return The final result of the trampoline + */ + @Override + public V call(final Object... args) { + return loop(original.call(args)); + } + + private V loop(final Object lastResult) { + Object result = lastResult; + + for (;;) { + if (result instanceof TrampolineClosure) { + result = ((TrampolineClosure)result).original.call(); + } else return (V) result; + } + } + + /** + * Builds a trampolined variant of the current closure. + * @param args Parameters to curry to the underlying closure. + * @return An instance of TrampolineClosure wrapping the original closure after currying. + */ + @Override + public Closure<V> trampoline(final Object... args) { + return new TrampolineClosure<V>(original.curry(args)); + } + + /** + * Returns itself, since it is a good enough trampolined variant of the current closure. + * @return An instance of TrampolineClosure wrapping the original closure. + */ + @Override + public Closure<V> trampoline() { + return this; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple.java b/src/main/groovy/groovy/lang/Tuple.java new file mode 100644 index 0000000..036d13e --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple.java @@ -0,0 +1,85 @@ +/* + * 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.lang; + +import org.codehaus.groovy.runtime.typehandling.DefaultTypeTransformation; + +import java.io.Serializable; +import java.util.AbstractList; +import java.util.List; +import java.util.Objects; + +/** + * Represents a list of Objects. + * + * @author <a href="mailto:[email protected]">James Strachan</a> + */ +public class Tuple<E> extends AbstractList<E> implements Serializable { + private static final long serialVersionUID = -6707770506387821031L; + private final E[] contents; + + public Tuple(E... contents) { + if (contents == null) throw new NullPointerException(); + this.contents = contents; + } + + @Override + public E get(int index) { + return contents[index]; + } + + @Override + public int size() { + return contents.length; + } + + @SuppressWarnings("unchecked") + @Override + public List<E> subList(int fromIndex, int toIndex) { + int size = toIndex - fromIndex; + E[] newContent = (E[]) new Object[size]; + System.arraycopy(contents, fromIndex, newContent, 0, size); + return new Tuple<>(newContent); + } + + public Tuple<E> subTuple(int fromIndex, int toIndex) { + return (Tuple<E>) subList(fromIndex, toIndex); + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || !(o instanceof Tuple)) return false; + + Tuple that = (Tuple) o; + int size = size(); + if (size != that.size()) return false; + for (int i = 0; i < size; i++) { + if (!DefaultTypeTransformation.compareEqual(get(i), that.get(i))) { + return false; + } + } + return true; + } + + @Override + public int hashCode() { + return Objects.hash(contents); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple1.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple1.java b/src/main/groovy/groovy/lang/Tuple1.java new file mode 100644 index 0000000..9b8d6bd --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple1.java @@ -0,0 +1,54 @@ +/* + * 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.lang; + +/** + * Represents a list of 1 typed Object. + * + * @since 2.5.0 + */ +public class Tuple1<T1> extends Tuple { + private static final long serialVersionUID = -4647790147461409603L; + private final T1 first; + + public Tuple1(T1 first) { + super(first); + + this.first = first; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 1; + } + + public T1 getFirst() { + return first; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple2.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple2.java b/src/main/groovy/groovy/lang/Tuple2.java new file mode 100644 index 0000000..b096aee --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple2.java @@ -0,0 +1,60 @@ +/* + * 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.lang; + +/** + * Represents a list of 2 typed Objects. + */ +public class Tuple2<T1, T2> extends Tuple { + private static final long serialVersionUID = 9006144674906325597L; + private final T1 first; + private final T2 second; + + public Tuple2(T1 first, T2 second) { + super(first, second); + + this.first = first; + this.second = second; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 2; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple3.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple3.java b/src/main/groovy/groovy/lang/Tuple3.java new file mode 100644 index 0000000..b5fe7d9 --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple3.java @@ -0,0 +1,71 @@ +/* + * 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.lang; + +/** + * Represents a list of 3 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple3<T1, T2, T3> extends Tuple { + private static final long serialVersionUID = 8469774237154310687L; + private final T1 first; + private final T2 second; + private final T3 third; + + public Tuple3(T1 first, T2 second, T3 third) { + super(first, second, third); + + this.first = first; + this.second = second; + this.third = third; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 3; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple4.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple4.java b/src/main/groovy/groovy/lang/Tuple4.java new file mode 100644 index 0000000..04f414e --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple4.java @@ -0,0 +1,79 @@ +/* + * 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.lang; + +/** + * Represents a list of 4 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple4<T1, T2, T3, T4> extends Tuple { + private static final long serialVersionUID = -7788878731471377207L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + + public Tuple4(T1 first, T2 second, T3 third, T4 fourth) { + super(first, second, third, fourth); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 4; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple5.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple5.java b/src/main/groovy/groovy/lang/Tuple5.java new file mode 100644 index 0000000..ee9c802 --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple5.java @@ -0,0 +1,87 @@ +/* + * 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.lang; + +/** + * Represents a list of 5 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple5<T1, T2, T3, T4, T5> extends Tuple { + private static final long serialVersionUID = 6722094358774027115L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + private final T5 fifth; + + public Tuple5(T1 first, T2 second, T3 third, T4 fourth, T5 fifth) { + super(first, second, third, fourth, fifth); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + this.fifth = fifth; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + case 4: + return fifth; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 5; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } + + public T5 getFifth() { + return fifth; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple6.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple6.java b/src/main/groovy/groovy/lang/Tuple6.java new file mode 100644 index 0000000..76d12ca --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple6.java @@ -0,0 +1,95 @@ +/* + * 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.lang; + +/** + * Represents a list of 6 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple6<T1, T2, T3, T4, T5, T6> extends Tuple { + private static final long serialVersionUID = -7848588473093102288L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + private final T5 fifth; + private final T6 sixth; + + public Tuple6(T1 first, T2 second, T3 third, T4 fourth, T5 fifth, T6 sixth) { + super(first, second, third, fourth, fifth, sixth); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + this.fifth = fifth; + this.sixth = sixth; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + case 4: + return fifth; + case 5: + return sixth; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 6; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } + + public T5 getFifth() { + return fifth; + } + + public T6 getSixth() { + return sixth; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple7.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple7.java b/src/main/groovy/groovy/lang/Tuple7.java new file mode 100644 index 0000000..05046e7 --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple7.java @@ -0,0 +1,103 @@ +/* + * 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.lang; + +/** + * Represents a list of 7 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple7<T1, T2, T3, T4, T5, T6, T7> extends Tuple { + private static final long serialVersionUID = 4226144828786865766L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + private final T5 fifth; + private final T6 sixth; + private final T7 seventh; + + public Tuple7(T1 first, T2 second, T3 third, T4 fourth, T5 fifth, T6 sixth, T7 seventh) { + super(first, second, third, fourth, fifth, sixth, seventh); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + this.fifth = fifth; + this.sixth = sixth; + this.seventh = seventh; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + case 4: + return fifth; + case 5: + return sixth; + case 6: + return seventh; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 7; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } + + public T5 getFifth() { + return fifth; + } + + public T6 getSixth() { + return sixth; + } + + public T7 getSeventh() { + return seventh; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple8.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple8.java b/src/main/groovy/groovy/lang/Tuple8.java new file mode 100644 index 0000000..1f38ca9 --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple8.java @@ -0,0 +1,111 @@ +/* + * 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.lang; + +/** + * Represents a list of 8 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple8<T1, T2, T3, T4, T5, T6, T7, T8> extends Tuple { + private static final long serialVersionUID = -8895822084644138566L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + private final T5 fifth; + private final T6 sixth; + private final T7 seventh; + private final T8 eighth; + + public Tuple8(T1 first, T2 second, T3 third, T4 fourth, T5 fifth, T6 sixth, T7 seventh, T8 eighth) { + super(first, second, third, fourth, fifth, sixth, seventh, eighth); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + this.fifth = fifth; + this.sixth = sixth; + this.seventh = seventh; + this.eighth = eighth; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + case 4: + return fifth; + case 5: + return sixth; + case 6: + return seventh; + case 7: + return eighth; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 8; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } + + public T5 getFifth() { + return fifth; + } + + public T6 getSixth() { + return sixth; + } + + public T7 getSeventh() { + return seventh; + } + + public T8 getEighth() { + return eighth; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Tuple9.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Tuple9.java b/src/main/groovy/groovy/lang/Tuple9.java new file mode 100644 index 0000000..3189c10 --- /dev/null +++ b/src/main/groovy/groovy/lang/Tuple9.java @@ -0,0 +1,120 @@ +/* + * 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.lang; + +/** + * Represents a list of 9 typed Objects. + * + * @since 2.5.0 + */ +public class Tuple9<T1, T2, T3, T4, T5, T6, T7, T8, T9> extends Tuple { + private static final long serialVersionUID = -5181196675351911769L; + private final T1 first; + private final T2 second; + private final T3 third; + private final T4 fourth; + private final T5 fifth; + private final T6 sixth; + private final T7 seventh; + private final T8 eighth; + private final T9 ninth; + + public Tuple9(T1 first, T2 second, T3 third, T4 fourth, T5 fifth, T6 sixth, T7 seventh, T8 eighth, T9 ninth) { + super(first, second, third, fourth, fifth, sixth, seventh, eighth, ninth); + + this.first = first; + this.second = second; + this.third = third; + this.fourth = fourth; + this.fifth = fifth; + this.sixth = sixth; + this.seventh = seventh; + this.eighth = eighth; + this.ninth = ninth; + } + + @Override + public Object get(int index) { + switch (index) { + case 0: + return first; + case 1: + return second; + case 2: + return third; + case 3: + return fourth; + case 4: + return fifth; + case 5: + return sixth; + case 6: + return seventh; + case 7: + return eighth; + case 8: + return ninth; + default: + throw new IndexOutOfBoundsException("index: " + index); + } + } + + @Override + public int size() { + return 9; + } + + public T1 getFirst() { + return first; + } + + public T2 getSecond() { + return second; + } + + public T3 getThird() { + return third; + } + + public T4 getFourth() { + return fourth; + } + + public T5 getFifth() { + return fifth; + } + + public T6 getSixth() { + return sixth; + } + + public T7 getSeventh() { + return seventh; + } + + public T8 getEighth() { + return eighth; + } + + public T9 getNinth() { + return ninth; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/Writable.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/Writable.java b/src/main/groovy/groovy/lang/Writable.java new file mode 100644 index 0000000..ec135cd --- /dev/null +++ b/src/main/groovy/groovy/lang/Writable.java @@ -0,0 +1,56 @@ +/* + * 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.lang; + +import java.io.IOException; +import java.io.Writer; + + +/** + * Represents an object which is capable of writing itself to a text stream + * in a more efficient format than just creating a toString() representation + * of itself. This mechanism is particularly useful for templates and such like. + * <p> + * It is worth noting that writable implementations often override their + * toString() implementation as well to allow rendering the same result + * directly to a String; however this is not required. + * + * @author <a href="mailto:[email protected]">James Strachan</a> + */ +public interface Writable { + + /** + * Writes this object to the given writer. + * <p> + * This is used to defer content creation until the point when it is + * streamed to the output destination. Oftentimes, content will be defined + * but not necessarily created (as is may be the case with a Closure + * definition.) In that case, the output is then 'deferred' to the point + * when it is serialized to the writer. This class may be used whenever an + * object should be responsible for creating its own textual representation, + * but creating the entire output as a single String would be inefficient + * (such as outputting a multi-gigabyte XML document.) + * + * @param out the Writer to which this Writable should output its data. + * @return the Writer that was passed + * @throws IOException if an error occurred while outputting data to the writer + */ + Writer writeTo(Writer out) throws IOException; + +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/groovydoc/Groovydoc.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/groovydoc/Groovydoc.java b/src/main/groovy/groovy/lang/groovydoc/Groovydoc.java new file mode 100644 index 0000000..d7d4204 --- /dev/null +++ b/src/main/groovy/groovy/lang/groovydoc/Groovydoc.java @@ -0,0 +1,96 @@ +/* + * 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.lang.groovydoc; + +import java.lang.reflect.AnnotatedElement; +import java.util.List; +import java.util.Objects; + +/** + * Represents groovydoc + */ +public class Groovydoc { + private final String content; + private List<GroovydocTag> tagList; + private final GroovydocHolder holder; + + public Groovydoc(String content, GroovydocHolder groovydocHolder) { + this.content = content; + this.holder = groovydocHolder; + } + + public Groovydoc(final String content, final AnnotatedElement annotatedElement) { + this.content = content; + this.holder = new GroovydocHolder<AnnotatedElement>() { + @Override + public Groovydoc getGroovydoc() { + return Groovydoc.this; + } + + @Override + public AnnotatedElement getInstance() { + return annotatedElement; + } + }; + } + + /** + * Get the content of groovydoc + * @return the text content + */ + public String getContent() { + return content; + } + + /** + * TODO Get list of groovydoc tags + * @return a list of tags + */ + public List<GroovydocTag> getTagList() { + throw new UnsupportedOperationException("[TODO]parsing tags will be a new features of the next releases"); +// return tagList; + } + + /** + * Get the holder of the groovydoc + * @return the groovydoc holder + */ + public GroovydocHolder getHolder() { + return holder; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + Groovydoc groovydoc = (Groovydoc) o; + return Objects.equals(content, groovydoc.content) && + Objects.equals(holder, groovydoc.holder); + } + + @Override + public int hashCode() { + return Objects.hash(content, holder); + } + + @Override + public String toString() { + return this.content; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/groovydoc/GroovydocHolder.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/groovydoc/GroovydocHolder.java b/src/main/groovy/groovy/lang/groovydoc/GroovydocHolder.java new file mode 100644 index 0000000..eb41df4 --- /dev/null +++ b/src/main/groovy/groovy/lang/groovydoc/GroovydocHolder.java @@ -0,0 +1,37 @@ +/* + * 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.lang.groovydoc; + +/** + * Represents Groovydoc Holder + */ +public interface GroovydocHolder<T> { + String DOC_COMMENT = "_DOC_COMMENT"; // keys for meta data + /** + * Get the groovydoc + * @return the groovydoc + */ + Groovydoc getGroovydoc(); + + /** + * Get GroovydocHolder instance + * @return GroovydocHolder instance + */ + T getInstance(); +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/groovydoc/GroovydocTag.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/groovydoc/GroovydocTag.java b/src/main/groovy/groovy/lang/groovydoc/GroovydocTag.java new file mode 100644 index 0000000..14e5aaa --- /dev/null +++ b/src/main/groovy/groovy/lang/groovydoc/GroovydocTag.java @@ -0,0 +1,68 @@ +/* + * 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.lang.groovydoc; + +import java.util.Objects; + +/** + * TODO parse groovydoc to get tag content + */ +public class GroovydocTag { + private String name; + private String content; + private Groovydoc groovydoc; + + public GroovydocTag(String name, String content, Groovydoc groovydoc) { + this.name = name; + this.content = content; + this.groovydoc = groovydoc; + } + + public String getName() { + return name; + } + + public String getContent() { + return content; + } + + public Groovydoc getGroovydoc() { + return groovydoc; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + GroovydocTag that = (GroovydocTag) o; + return Objects.equals(name, that.name) && + Objects.equals(content, that.content) && + Objects.equals(groovydoc, that.groovydoc); + } + + @Override + public int hashCode() { + return Objects.hash(name, content, groovydoc); + } + + @Override + public String toString() { + return content; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/lang/package.html ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/lang/package.html b/src/main/groovy/groovy/lang/package.html new file mode 100644 index 0000000..1ea84fc --- /dev/null +++ b/src/main/groovy/groovy/lang/package.html @@ -0,0 +1,28 @@ +<!-- + + 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. + +--> +<html> + <head> + <title>package groovy.lang.*</title> + </head> + <body> + <p>Core Groovy language classes for implementing data structures, closures, metadata and so forth.</p> + </body> +</html> http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/security/GroovyCodeSourcePermission.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/security/GroovyCodeSourcePermission.java b/src/main/groovy/groovy/security/GroovyCodeSourcePermission.java new file mode 100644 index 0000000..e723e0b --- /dev/null +++ b/src/main/groovy/groovy/security/GroovyCodeSourcePermission.java @@ -0,0 +1,40 @@ +/* + * 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.security; + +import java.security.BasicPermission; + +/** + * Permission required to explicitly specify a codebase for a groovy script whose + * codebase cannot be determined. Typically this permission is only + * required by clients that want to associate a code source with a script which + * is a String or an InputStream. + * + * @author Steve Goetze + */ +public final class GroovyCodeSourcePermission extends BasicPermission { + + public GroovyCodeSourcePermission(String name) { + super(name); + } + + public GroovyCodeSourcePermission(String name, String actions) { + super(name, actions); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/security/package.html ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/security/package.html b/src/main/groovy/groovy/security/package.html new file mode 100644 index 0000000..cb094ff --- /dev/null +++ b/src/main/groovy/groovy/security/package.html @@ -0,0 +1,30 @@ +<!-- + + 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. + +--> +<html> + <head> + <title>package groovy.security.*</title> + </head> + <body> + <p> + Security-related classes + </p> + </body> +</html> http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/time/BaseDuration.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/time/BaseDuration.java b/src/main/groovy/groovy/time/BaseDuration.java new file mode 100644 index 0000000..e2cc023 --- /dev/null +++ b/src/main/groovy/groovy/time/BaseDuration.java @@ -0,0 +1,141 @@ +/* + * 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.time; + +import org.codehaus.groovy.runtime.DefaultGroovyMethods; +import org.codehaus.groovy.runtime.StringGroovyMethods; + +import java.util.ArrayList; +import java.util.Calendar; +import java.util.Date; +import java.util.List; + +/** + * Base class for date and time durations. + * + * @author John Wilson [email protected] + * @see Duration + */ +public abstract class BaseDuration implements Comparable<BaseDuration> { + protected final int years; + protected final int months; + protected final int days; + protected final int hours; + protected final int minutes; + protected final int seconds; + protected final int millis; + + protected BaseDuration(final int years, final int months, final int days, final int hours, final int minutes, final int seconds, final int millis) { + this.years = years; + this.months = months; + this.days = days; + this.hours = hours; + this.minutes = minutes; + this.seconds = seconds; + this.millis = millis; + } + + protected BaseDuration(final int days, final int hours, final int minutes, final int seconds, final int millis) { + this(0, 0, days, hours, minutes, seconds, millis); + } + + public int getYears() { + return this.years; + } + + public int getMonths() { + return this.months; + } + + public int getDays() { + return this.days; + } + + public int getHours() { + return this.hours; + } + + public int getMinutes() { + return this.minutes; + } + + public int getSeconds() { + return this.seconds; + } + + public int getMillis() { + return this.millis; + } + + public Date plus(final Date date) { + final Calendar cal = Calendar.getInstance(); + + cal.setTime(date); + cal.add(Calendar.YEAR, this.years); + cal.add(Calendar.MONTH, this.months); + cal.add(Calendar.DAY_OF_YEAR, this.days); + cal.add(Calendar.HOUR_OF_DAY, this.hours); + cal.add(Calendar.MINUTE, this.minutes); + cal.add(Calendar.SECOND, this.seconds); + cal.add(Calendar.MILLISECOND, this.millis); + + return cal.getTime(); + } + + public String toString() { + List buffer = new ArrayList(); + + if (this.years != 0) buffer.add(this.years + " years"); + if (this.months != 0) buffer.add(this.months + " months"); + if (this.days != 0) buffer.add(this.days + " days"); + if (this.hours != 0) buffer.add(this.hours + " hours"); + if (this.minutes != 0) buffer.add(this.minutes + " minutes"); + + if (this.seconds != 0 || this.millis != 0) { + int norm_millis = this.millis % 1000; + int norm_seconds = this.seconds + DefaultGroovyMethods.intdiv(this.millis - norm_millis, 1000).intValue(); + CharSequence millisToPad = "" + Math.abs(norm_millis); + buffer.add((norm_seconds == 0 ? (norm_millis < 0 ? "-0" : "0") : norm_seconds) + "." + StringGroovyMethods.padLeft(millisToPad, 3, "0") + " seconds"); + } + + if (!buffer.isEmpty()) { + return DefaultGroovyMethods.join(buffer.iterator(), ", "); + } else { + return "0"; + } + } + + public abstract long toMilliseconds(); + + public abstract Date getAgo(); + + public abstract From getFrom(); + + public int compareTo(BaseDuration otherDuration) { + return Long.signum(toMilliseconds() - otherDuration.toMilliseconds()); + } + + public abstract static class From { + public abstract Date getNow(); + + public Date getToday() { + return getNow(); + } + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/time/DatumDependentDuration.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/time/DatumDependentDuration.java b/src/main/groovy/groovy/time/DatumDependentDuration.java new file mode 100644 index 0000000..c73d9aa --- /dev/null +++ b/src/main/groovy/groovy/time/DatumDependentDuration.java @@ -0,0 +1,141 @@ +/* + * 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.time; + +import java.util.Calendar; +import java.util.Date; + +/** + * DatumDependentDuration represents durations whose length in milliseconds + * cannot be determined without knowing the datum point. + * <p> + * I don't know how many days in a year unless I know if it's a leap year or not. + * <p> + * I don't know how many days in a month unless I know the name of the month + * (and if it's a leap year if the month is February) + * + * @author John Wilson [email protected] + */ +public class DatumDependentDuration extends BaseDuration { + public DatumDependentDuration(final int years, final int months, final int days, final int hours, final int minutes, final int seconds, final int millis) { + super(years, months, days, hours, minutes, seconds, millis); + } + + public int getMonths() { + return this.months; + } + + public int getYears() { + return this.years; + } + + public DatumDependentDuration plus(final DatumDependentDuration rhs) { + return new DatumDependentDuration(this.getYears() + rhs.getYears(), this.getMonths() + rhs.getMonths(), + this.getDays() + rhs.getDays(), this.getHours() + rhs.getHours(), + this.getMinutes() + rhs.getMinutes(), this.getSeconds() + rhs.getSeconds(), + this.getMillis() + rhs.getMillis()); + } + + public DatumDependentDuration plus(final TimeDatumDependentDuration rhs) { + return rhs.plus(this); + } + + public DatumDependentDuration plus(final Duration rhs) { + return new DatumDependentDuration(this.getYears(), this.getMonths(), + this.getDays() + rhs.getDays(), this.getHours() + rhs.getHours(), + this.getMinutes() + rhs.getMinutes(), this.getSeconds() + rhs.getSeconds(), + this.getMillis() + rhs.getMillis()); + + } + + public DatumDependentDuration plus(final TimeDuration rhs) { + return rhs.plus(this); + + } + + public DatumDependentDuration minus(final DatumDependentDuration rhs) { + return new DatumDependentDuration(this.getYears() - rhs.getYears(), this.getMonths() - rhs.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + + } + + public DatumDependentDuration minus(final Duration rhs) { + return new DatumDependentDuration(this.getYears(), this.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + + } + + /** + * @see groovy.time.BaseDuration#toMilliseconds() + * + * Change the duration into milliseconds, relative to 'now.' Therefore + * things like timezone and time of year will affect how this conversion + * occurs. + */ + public long toMilliseconds() { + final Date now = new Date(); + return TimeCategory.minus(plus(now), now).toMilliseconds(); + } + + public Date getAgo() { + final Calendar cal = Calendar.getInstance(); + + cal.add(Calendar.YEAR, -this.getYears()); + cal.add(Calendar.MONTH, -this.getMonths()); + cal.add(Calendar.DAY_OF_YEAR, -this.getDays()); + cal.add(Calendar.HOUR_OF_DAY, -this.getHours()); + cal.add(Calendar.MINUTE, -this.getMinutes()); + cal.add(Calendar.SECOND, -this.getSeconds()); + cal.add(Calendar.MILLISECOND, -this.getMillis()); + + cal.set(Calendar.HOUR_OF_DAY, 0); + cal.set(Calendar.MINUTE, 0); + cal.set(Calendar.SECOND, 0); + cal.set(Calendar.MILLISECOND, 0); + + return new Date(cal.getTimeInMillis()); + } + + public From getFrom() { + return new From() { + public Date getNow() { + final Calendar cal = Calendar.getInstance(); + + cal.add(Calendar.YEAR, DatumDependentDuration.this.getYears()); + cal.add(Calendar.MONTH, DatumDependentDuration.this.getMonths()); + cal.add(Calendar.DAY_OF_YEAR, DatumDependentDuration.this.getDays()); + cal.add(Calendar.HOUR_OF_DAY, DatumDependentDuration.this.getHours()); + cal.add(Calendar.MINUTE, DatumDependentDuration.this.getMinutes()); + cal.add(Calendar.SECOND, DatumDependentDuration.this.getSeconds()); + cal.add(Calendar.MILLISECOND, DatumDependentDuration.this.getMillis()); + + cal.set(Calendar.HOUR_OF_DAY, 0); + cal.set(Calendar.MINUTE, 0); + cal.set(Calendar.SECOND, 0); + cal.set(Calendar.MILLISECOND, 0); + + return new Date(cal.getTimeInMillis()); + } + }; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/time/Duration.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/time/Duration.java b/src/main/groovy/groovy/time/Duration.java new file mode 100644 index 0000000..e187957 --- /dev/null +++ b/src/main/groovy/groovy/time/Duration.java @@ -0,0 +1,119 @@ +/* + * 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.time; + +import java.util.Calendar; +import java.util.Date; + +/** + * Duration represents time periods which have values independent of the context. + * So, whilst we can't say how long a month is without knowing the year and the name of the month, + * we know how long a day is independent of the date. + * <p> + * This is not 100% true for days. + * Days can actually be 23, 24 or 25 hours long (due to daylight saving adjustments.) + * <p> + * If you ask Duration to convert itself to milliseconds then it will work on the basis of 24 hours + * in a day. If you add or subtract it from a date it will take daylight saving into account. + * + * @author John Wilson [email protected] + */ +public class Duration extends BaseDuration { + public Duration(final int days, final int hours, final int minutes, final int seconds, final int millis) { + super(days, hours, minutes, seconds, millis); + } + + public Duration plus(final Duration rhs) { + return new Duration(this.getDays() + rhs.getDays(), this.getHours() + rhs.getHours(), + this.getMinutes() + rhs.getMinutes(), this.getSeconds() + rhs.getSeconds(), + this.getMillis() + rhs.getMillis()); + } + + public Duration plus(final TimeDuration rhs) { + return rhs.plus(this); + } + + public DatumDependentDuration plus(final DatumDependentDuration rhs) { + return rhs.plus(this); + } + + public Duration minus(final Duration rhs) { + return new Duration(this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public TimeDuration minus(final TimeDuration rhs) { + return new TimeDuration(this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public DatumDependentDuration minus(final DatumDependentDuration rhs) { + return new DatumDependentDuration(-rhs.getYears(), -rhs.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public TimeDatumDependentDuration minus(final TimeDatumDependentDuration rhs) { + return new TimeDatumDependentDuration(-rhs.getYears(), -rhs.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public long toMilliseconds() { + return ((((((long)(this.getDays() * 24 ) + this.getHours()) * 60 + this.getMinutes()) * 60) + this.getSeconds()) * 1000) + this.getMillis(); + } + + public Date getAgo() { + final Calendar cal = Calendar.getInstance(); + + cal.add(Calendar.DAY_OF_YEAR, -this.getDays()); + cal.add(Calendar.HOUR_OF_DAY, -this.getHours()); + cal.add(Calendar.MINUTE, -this.getMinutes()); + cal.add(Calendar.SECOND, -this.getSeconds()); + cal.add(Calendar.MILLISECOND, -this.getMillis()); + + cal.set(Calendar.HOUR_OF_DAY, 0); + cal.set(Calendar.MINUTE, 0); + cal.set(Calendar.SECOND, 0); + cal.set(Calendar.MILLISECOND, 0); + + return new Date(cal.getTimeInMillis()); + } + + public From getFrom() { + return new From() { + public Date getNow() { + final Calendar cal = Calendar.getInstance(); + + cal.add(Calendar.DAY_OF_YEAR, Duration.this.getDays()); + + cal.set(Calendar.HOUR_OF_DAY, 0); + cal.set(Calendar.MINUTE, 0); + cal.set(Calendar.SECOND, 0); + cal.set(Calendar.MILLISECOND, 0); + + return new Date(cal.getTimeInMillis()); + } + }; + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/time/TimeCategory.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/time/TimeCategory.java b/src/main/groovy/groovy/time/TimeCategory.java new file mode 100644 index 0000000..dbc08cd --- /dev/null +++ b/src/main/groovy/groovy/time/TimeCategory.java @@ -0,0 +1,203 @@ +/* + * 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.time; + +import java.util.Calendar; +import java.util.Date; +import java.util.TimeZone; + +/** + * Apply a number of methods to allow convenient Date/Time manipulation,such as: + * <pre class="groovyTestCase"> + * use (groovy.time.TimeCategory) { + * // application on numbers: + * println 1.minute.from.now + * println 10.hours.ago + * + * // application on dates + * def someDate = new Date() + * println someDate - 3.months + * } + * </pre> + * + * @see BaseDuration + */ +public class TimeCategory { + /* + * Methods to allow Date Duration arithmetic + */ + + public static Date plus(final Date date, final BaseDuration duration) { + return duration.plus(date); + } + + public static Date minus(final Date date, final BaseDuration duration) { + final Calendar cal = Calendar.getInstance(); + + cal.setTime(date); + cal.add(Calendar.YEAR, -duration.getYears()); + cal.add(Calendar.MONTH, -duration.getMonths()); + cal.add(Calendar.DAY_OF_YEAR, -duration.getDays()); + cal.add(Calendar.HOUR_OF_DAY, -duration.getHours()); + cal.add(Calendar.MINUTE, -duration.getMinutes()); + cal.add(Calendar.SECOND, -duration.getSeconds()); + cal.add(Calendar.MILLISECOND, -duration.getMillis()); + + return cal.getTime(); + } + + /** + * Retrieves the default TimeZone for a date by using the default Locale + * settings. Recommended that you use {@code TimeZone.getDefault()} instead. + * + * @param self a Date + * @return the TimeZone + */ + @Deprecated + public static TimeZone getTimeZone(Date self) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(self); + return calendar.getTimeZone(); + } + + /** + * Get the DST offset (if any) for the default locale and the given date. + * + * @param self a Date + * @return the DST offset as a Duration. + */ + public static Duration getDaylightSavingsOffset(Date self) { + TimeZone timeZone = getTimeZone(self); + int millis = (timeZone.useDaylightTime() && timeZone.inDaylightTime(self)) + ? timeZone.getDSTSavings() : 0; + return new TimeDuration(0, 0, 0, millis); + } + + public static Duration getDaylightSavingsOffset(BaseDuration self) { + return getDaylightSavingsOffset(new Date(self.toMilliseconds() + 1)); + } + + /** + * Return a Duration representing the DST difference (if any) between two + * dates. i.e. if one date is before the DST changeover, and the other + * date is after, the resulting duration will represent the DST offset. + * + * @param self a Date + * @param other another Date + * @return a Duration + */ + public static Duration getRelativeDaylightSavingsOffset(Date self, Date other) { + Duration d1 = getDaylightSavingsOffset(self); + Duration d2 = getDaylightSavingsOffset(other); + return new TimeDuration(0, 0, 0, (int) (d2.toMilliseconds() - d1.toMilliseconds())); + } + + /** + * Subtract one date from the other. + * + * @param lhs a Date + * @param rhs another Date + * @return a Duration + */ + public static TimeDuration minus(final Date lhs, final Date rhs) { + long milliseconds = lhs.getTime() - rhs.getTime(); + long days = milliseconds / (24 * 60 * 60 * 1000); + milliseconds -= days * 24 * 60 * 60 * 1000; + int hours = (int) (milliseconds / (60 * 60 * 1000)); + milliseconds -= hours * 60 * 60 * 1000; + int minutes = (int) (milliseconds / (60 * 1000)); + milliseconds -= minutes * 60 * 1000; + int seconds = (int) (milliseconds / 1000); + milliseconds -= seconds * 1000; + + return new TimeDuration((int) days, hours, minutes, seconds, (int) milliseconds); + } + + /* + * Methods on Integer to implement 1.month, 4.years etc. + */ + + public static DatumDependentDuration getMonths(final Integer self) { + return new DatumDependentDuration(0, self, 0, 0, 0, 0, 0); + } + + public static DatumDependentDuration getMonth(final Integer self) { + return getMonths(self); + } + + public static DatumDependentDuration getYears(final Integer self) { + return new DatumDependentDuration(self, 0, 0, 0, 0, 0, 0); + } + + public static DatumDependentDuration getYear(final Integer self) { + return getYears(self); + } + + /* + * Methods on Integer to implement 1.week, 4.days etc. + */ + + public static Duration getWeeks(final Integer self) { + return new Duration(self * 7, 0, 0, 0, 0); + } + + public static Duration getWeek(final Integer self) { + return getWeeks(self); + } + + public static Duration getDays(final Integer self) { + return new Duration(self, 0, 0, 0, 0); + } + + public static Duration getDay(final Integer self) { + return getDays(self); + } + + public static TimeDuration getHours(final Integer self) { + return new TimeDuration(0, self, 0, 0, 0); + } + + public static TimeDuration getHour(final Integer self) { + return getHours(self); + } + + public static TimeDuration getMinutes(final Integer self) { + return new TimeDuration(0, 0, self, 0, 0); + } + + public static TimeDuration getMinute(final Integer self) { + return getMinutes(self); + } + + public static TimeDuration getSeconds(final Integer self) { + return new TimeDuration(0, 0, 0, self, 0); + } + + public static TimeDuration getSecond(final Integer self) { + return getSeconds(self); + } + + public static TimeDuration getMilliseconds(final Integer self) { + return new TimeDuration(0, 0, 0, 0, self); + } + + public static TimeDuration getMillisecond(final Integer self) { + return getMilliseconds(self); + } +} http://git-wip-us.apache.org/repos/asf/groovy/blob/d638ca43/src/main/groovy/groovy/time/TimeDatumDependentDuration.java ---------------------------------------------------------------------- diff --git a/src/main/groovy/groovy/time/TimeDatumDependentDuration.java b/src/main/groovy/groovy/time/TimeDatumDependentDuration.java new file mode 100644 index 0000000..eead45a --- /dev/null +++ b/src/main/groovy/groovy/time/TimeDatumDependentDuration.java @@ -0,0 +1,81 @@ +/* + * 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.time; + +import java.util.Calendar; +import java.util.Date; + +/** + * TimeDatumDuration represents a time period which results from an + * arithmetic operation between a TimeDuration object and a DatumDuration object + * + * @author John Wilson [email protected] + */ +public class TimeDatumDependentDuration extends DatumDependentDuration { + public TimeDatumDependentDuration(int years, int months, int days, int hours, int minutes, int seconds, int millis) { + super(years, months, days, hours, minutes, seconds, millis); + } + + public DatumDependentDuration plus(final Duration rhs) { + return new TimeDatumDependentDuration(this.getYears(), this.getMonths(), + this.getDays() + rhs.getDays(), this.getHours() + rhs.getHours(), + this.getMinutes() + rhs.getMinutes(), this.getSeconds() + rhs.getSeconds(), + this.getMillis() + rhs.getMillis()); + } + + public DatumDependentDuration plus(final DatumDependentDuration rhs) { + return new TimeDatumDependentDuration(this.getYears() + rhs.getYears(), this.getMonths() + rhs.getMonths(), + this.getDays() + rhs.getDays(), this.getHours() + rhs.getHours(), + this.getMinutes() + rhs.getMinutes(), this.getSeconds() + rhs.getSeconds(), + this.getMillis() + rhs.getMillis()); + } + + public DatumDependentDuration minus(final Duration rhs) { + return new TimeDatumDependentDuration(this.getYears(), this.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public DatumDependentDuration minus(final DatumDependentDuration rhs) { + return new TimeDatumDependentDuration(this.getYears() - rhs.getYears(), this.getMonths() - rhs.getMonths(), + this.getDays() - rhs.getDays(), this.getHours() - rhs.getHours(), + this.getMinutes() - rhs.getMinutes(), this.getSeconds() - rhs.getSeconds(), + this.getMillis() - rhs.getMillis()); + } + + public From getFrom() { + return new From() { + public Date getNow() { + final Calendar cal = Calendar.getInstance(); + + cal.add(Calendar.YEAR, TimeDatumDependentDuration.this.getYears()); + cal.add(Calendar.MONTH, TimeDatumDependentDuration.this.getMonths()); + cal.add(Calendar.DAY_OF_YEAR, TimeDatumDependentDuration.this.getDays()); + cal.add(Calendar.HOUR_OF_DAY, TimeDatumDependentDuration.this.getHours()); + cal.add(Calendar.MINUTE, TimeDatumDependentDuration.this.getMinutes()); + cal.add(Calendar.SECOND, TimeDatumDependentDuration.this.getSeconds()); + cal.add(Calendar.MILLISECOND, TimeDatumDependentDuration.this.getMillis()); + + return cal.getTime(); + } + }; + } + +}
