InternalModuleServiceCallImpl.java
001 /* This file is part of the project "Hilbert II" - http://www.qedeq.org
002  *
003  * Copyright 2000-2014,  Michael Meyling <mime@qedeq.org>.
004  *
005  * "Hilbert II" is free software; you can redistribute
006  * it and/or modify it under the terms of the GNU General Public
007  * License as published by the Free Software Foundation; either
008  * version 2 of the License, or (at your option) any later version.
009  *
010  * This program is distributed in the hope that it will be useful,
011  * but WITHOUT ANY WARRANTY; without even the implied warranty of
012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
013  * GNU General Public License for more details.
014  */
015 
016 package org.qedeq.kernel.bo.job;
017 
018 import org.qedeq.base.io.Parameters;
019 import org.qedeq.kernel.bo.common.ModuleServiceCall;
020 import org.qedeq.kernel.bo.common.ModuleServiceResult;
021 import org.qedeq.kernel.bo.common.QedeqBo;
022 import org.qedeq.kernel.bo.common.ServiceJob;
023 import org.qedeq.kernel.bo.module.InternalModuleServiceCall;
024 import org.qedeq.kernel.bo.module.InternalServiceJob;
025 import org.qedeq.kernel.se.common.Service;
026 import org.qedeq.kernel.se.common.ServiceCompleteness;
027 
028 /**
029  * Single call for a service.
030  *
031  @author  Michael Meyling
032  */
033 public class InternalModuleServiceCallImpl implements InternalModuleServiceCall {
034 
035     /** Counter for each service call. */
036     private static volatile long globalCounter;
037 
038     /** The service the thread works for. */
039     private final Service service;
040 
041     /** QEDEQ module the process is working on. */
042     private final QedeqBo qedeq;
043 
044     /** Current global config parameters for the service. */
045     private final Parameters config;
046 
047     /** Call specific parameters for this service call. */
048     private final Parameters parameters;
049 
050     /** Begin time for service call. */
051     private long begin;
052 
053     /** End time for service call. */
054     private long end;
055 
056     /** Last time we started. */
057     private long start;
058 
059     /** Call duration time without being blocked. */
060     private long duration;
061 
062     /** Is this process paused? */
063     private boolean paused;
064 
065     /** Is this process running (even if its paused)? */
066     private boolean running;
067 
068     /** Percentage of currently running service execution. */
069     private double executionPercentage;
070 
071     /** Currently taken action. */
072     private String action = "not yet started";
073 
074     /** Service process. */
075     private final InternalServiceJob process;
076 
077     /** Parent service call. Might be <code>null</code>. */
078     private final ModuleServiceCall parent;
079 
080     /** Call id. */
081     private final long id;
082 
083     /** Result of service call. */
084     private ModuleServiceResult result;
085 
086     /** Was the module newly blocked by this call. Otherwise a previous service call might have locked the module
087      * for the process already. */
088     private boolean newlyBlockedModule;
089 
090     /** Answers completeness questions if not <code>null</code>. */
091     private ServiceCompleteness completeness;
092 
093     /**
094      * A new service process within the current thread.
095      *
096      @param   service     This service is executed.
097      @param   qedeq       Module we work on.
098      @param   config      Current global config parameters for this call.
099      @param   parameters  Call specific parameters..
100      @param   process     Service process we run within.
101      @param   parent      Parent service call if any.
102      */
103     public InternalModuleServiceCallImpl(final Service service, final QedeqBo qedeq,
104             final Parameters config, final Parameters parameters, final InternalServiceJob process,
105             final ModuleServiceCall parent) {
106         this.id = inc();
107         this.qedeq = qedeq;
108         this.service = service;
109         this.config = config;
110         this.parameters = parameters;
111         this.process = process;
112         this.parent = parent;
113         running = false;
114         begin();
115     }
116 
117     private synchronized long inc() {
118         return globalCounter++;
119     }
120 
121     public Service getService() {
122         return service;
123     }
124 
125     public QedeqBo getQedeq() {
126         return qedeq;
127     }
128 
129     public synchronized Parameters getConfigParameters() {
130         return config;
131     }
132 
133     public String getConfigParametersString() {
134         return config.getParameterString();
135     }
136 
137     public synchronized Parameters getParameters() {
138         return parameters;
139     }
140 
141     public String getParametersString() {
142         return parameters.getParameterString();
143     }
144 
145     public long getBeginTime() {
146         return begin;
147     }
148 
149     public synchronized long getEndTime() {
150         return end;
151     }
152 
153     public synchronized long getDuration() {
154         return duration;
155     }
156 
157     private synchronized void begin() {
158         begin = System.currentTimeMillis();
159         start = begin;
160         action = "started";
161         running = true;
162     }
163 
164     public synchronized boolean isPaused() {
165         return paused;
166     }
167 
168     public synchronized void pause() {
169         duration += System.currentTimeMillis() - start;
170         paused = true;
171     }
172 
173     public synchronized void resume() {
174         paused = false;
175         start = System.currentTimeMillis();
176     }
177 
178     private synchronized void end() {
179         end = System.currentTimeMillis();
180         duration += end - start;
181         paused = false;
182         running = false;
183     }
184 
185     public void setNewlyBlockedModule(final boolean newlyBlockedModule) {
186         this.newlyBlockedModule = newlyBlockedModule;
187     }
188 
189     public boolean getNewlyBlockedModule() {
190         return this.newlyBlockedModule;
191     }
192 
193     public synchronized void finishOk() {
194         finish(ServiceResultImpl.SUCCESSFUL);
195     }
196 
197     public synchronized void finishError(final String errorMessage) {
198         finish(new ServiceResultImpl(errorMessage));
199     }
200 
201     public synchronized void finish(final ModuleServiceResult result) {
202         if (running) {
203             action = "finished";
204             executionPercentage = 100;
205             completeness = null;
206             this.result = result;
207             end();
208         }
209     }
210 
211     public synchronized void halt(final ModuleServiceResult result) {
212         if (running) {
213             this.result = result;
214             if (completeness != null) {
215                 executionPercentage = completeness.getVisitPercentage();
216             else {
217                 completeness = null;
218             }
219             end();
220         }
221     }
222 
223     public synchronized void halt(final String errorMessage) {
224         halt(new ServiceResultImpl(errorMessage));
225     }
226 
227     public synchronized void interrupt() {
228         if (running) {
229             this.result = ServiceResultImpl.INTERRUPTED;
230             if (completeness != null) {
231                 executionPercentage = completeness.getVisitPercentage();
232             else {
233                 completeness = null;
234             }
235             process.setInterruptedState();
236             end();
237         }
238     }
239 
240     public synchronized boolean isRunning() {
241         return running;
242     }
243 
244     public synchronized ServiceJob getServiceProcess() {
245         return process;
246     }
247 
248     public synchronized double getExecutionPercentage() {
249         if (completeness != null) {
250             executionPercentage = completeness.getVisitPercentage();
251         }
252         return executionPercentage;
253     }
254 
255     public synchronized void setExecutionPercentage(final double percentage) {
256         this.executionPercentage = percentage;
257     }
258 
259     public synchronized String getAction() {
260         return action;
261     }
262 
263     public synchronized String getLocation() {
264         if (completeness != null) {
265             return completeness.getLocationDescription();
266         }
267         return action;
268     }
269 
270     public synchronized void setAction(final String action) {
271         this.action = action;
272     }
273 
274     public long getId() {
275         return id;
276     }
277 
278     public int hashCode() {
279         return (intid;
280     }
281 
282     public boolean equals(final Object obj) {
283         return == compareTo(obj);
284     }
285 
286     public int compareTo(final Object o) {
287         if (!(instanceof ModuleServiceCall)) {
288             return -1;
289         }
290         final ModuleServiceCall s = (ModuleServiceCallo;
291         return (getId() < s.getId() ? -(getId() == s.getId() 1));
292     }
293 
294     public ModuleServiceCall getParentServiceCall() {
295         return parent;
296     }
297 
298     public synchronized ModuleServiceResult getServiceResult() {
299         return result;
300     }
301 
302     public InternalServiceJob getInternalServiceProcess() {
303         return process;
304     }
305 
306     public synchronized void setServiceCompleteness(final ServiceCompleteness completeness) {
307         this.completeness = completeness;
308     }
309 
310 }