View Javadoc
1   /*
2    * Copyright 2013 The Netty Project
3    *
4    * The Netty Project licenses this file to you under the Apache License,
5    * version 2.0 (the "License"); you may not use this file except in compliance
6    * with the License. You may obtain a copy of the License at:
7    *
8    *   http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13   * License for the specific language governing permissions and limitations
14   * under the License.
15   */
16  package io.netty.util.concurrent;
17  
18  import io.netty.util.internal.logging.InternalLogger;
19  import io.netty.util.internal.logging.InternalLoggerFactory;
20  
21  import java.util.Collection;
22  import java.util.Collections;
23  import java.util.Iterator;
24  import java.util.List;
25  import java.util.concurrent.AbstractExecutorService;
26  import java.util.concurrent.Callable;
27  import java.util.concurrent.RunnableFuture;
28  import java.util.concurrent.TimeUnit;
29  
30  /**
31   * Abstract base class for {@link EventExecutor} implementations.
32   */
33  public abstract class AbstractEventExecutor extends AbstractExecutorService implements EventExecutor {
34      private static final InternalLogger logger = InternalLoggerFactory.getInstance(AbstractEventExecutor.class);
35  
36      static final long DEFAULT_SHUTDOWN_QUIET_PERIOD = 2;
37      static final long DEFAULT_SHUTDOWN_TIMEOUT = 15;
38  
39      private final EventExecutorGroup parent;
40      private final Collection<EventExecutor> selfCollection = Collections.<EventExecutor>singleton(this);
41  
42      protected AbstractEventExecutor() {
43          this(null);
44      }
45  
46      protected AbstractEventExecutor(EventExecutorGroup parent) {
47          this.parent = parent;
48      }
49  
50      @Override
51      public EventExecutorGroup parent() {
52          return parent;
53      }
54  
55      @Override
56      public EventExecutor next() {
57          return this;
58      }
59  
60      @Override
61      public boolean inEventLoop() {
62          return inEventLoop(Thread.currentThread());
63      }
64  
65      @Override
66      public Iterator<EventExecutor> iterator() {
67          return selfCollection.iterator();
68      }
69  
70      @Override
71      public Future<?> shutdownGracefully() {
72          return shutdownGracefully(DEFAULT_SHUTDOWN_QUIET_PERIOD, DEFAULT_SHUTDOWN_TIMEOUT, TimeUnit.SECONDS);
73      }
74  
75      /**
76       * @deprecated {@link #shutdownGracefully(long, long, TimeUnit)} or {@link #shutdownGracefully()} instead.
77       */
78      @Override
79      @Deprecated
80      public abstract void shutdown();
81  
82      /**
83       * @deprecated {@link #shutdownGracefully(long, long, TimeUnit)} or {@link #shutdownGracefully()} instead.
84       */
85      @Override
86      @Deprecated
87      public List<Runnable> shutdownNow() {
88          shutdown();
89          return Collections.emptyList();
90      }
91  
92      @Override
93      public <V> Promise<V> newPromise() {
94          return new DefaultPromise<V>(this);
95      }
96  
97      @Override
98      public <V> ProgressivePromise<V> newProgressivePromise() {
99          return new DefaultProgressivePromise<V>(this);
100     }
101 
102     @Override
103     public <V> Future<V> newSucceededFuture(V result) {
104         return new SucceededFuture<V>(this, result);
105     }
106 
107     @Override
108     public <V> Future<V> newFailedFuture(Throwable cause) {
109         return new FailedFuture<V>(this, cause);
110     }
111 
112     @Override
113     public Future<?> submit(Runnable task) {
114         return (Future<?>) super.submit(task);
115     }
116 
117     @Override
118     public <T> Future<T> submit(Runnable task, T result) {
119         return (Future<T>) super.submit(task, result);
120     }
121 
122     @Override
123     public <T> Future<T> submit(Callable<T> task) {
124         return (Future<T>) super.submit(task);
125     }
126 
127     @Override
128     protected final <T> RunnableFuture<T> newTaskFor(Runnable runnable, T value) {
129         return new PromiseTask<T>(this, runnable, value);
130     }
131 
132     @Override
133     protected final <T> RunnableFuture<T> newTaskFor(Callable<T> callable) {
134         return new PromiseTask<T>(this, callable);
135     }
136 
137     @Override
138     public ScheduledFuture<?> schedule(Runnable command, long delay,
139                                        TimeUnit unit) {
140         throw new UnsupportedOperationException();
141     }
142 
143     @Override
144     public <V> ScheduledFuture<V> schedule(Callable<V> callable, long delay, TimeUnit unit) {
145         throw new UnsupportedOperationException();
146     }
147 
148     @Override
149     public ScheduledFuture<?> scheduleAtFixedRate(Runnable command, long initialDelay, long period, TimeUnit unit) {
150         throw new UnsupportedOperationException();
151     }
152 
153     @Override
154     public ScheduledFuture<?> scheduleWithFixedDelay(Runnable command, long initialDelay, long delay, TimeUnit unit) {
155         throw new UnsupportedOperationException();
156     }
157 
158     /**
159      * Try to execute the given {@link Runnable} and just log if it throws a {@link Throwable}.
160      */
161     protected static void safeExecute(Runnable task) {
162         try {
163             task.run();
164         } catch (Throwable t) {
165             logger.warn("A task raised an exception. Task: {}", task, t);
166         }
167     }
168 }