All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.ejlchina.http.internal.AsyncHttpTask Maven / Gradle / Ivy

Go to download

Http工具包,封装 OkHttp,链式用法、支持异步同步、响应JSON自动解析,回调线程切换、配置灵活、支持URL占位符、支持BaseUrl、外部依赖少、适用 JavaWeb 和 Android,教程全面、简单易用

There is a newer version: 2.3.0
Show newest version
package com.ejlchina.http.internal;

import java.io.IOException;

import com.ejlchina.http.HttpCall;
import com.ejlchina.http.HttpResult;
import com.ejlchina.http.HttpResult.State;
import com.ejlchina.http.HttpTask;
import com.ejlchina.http.OnCallback;

import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.Response;


/**
 * 异步 Http 请求任务
 *  
 * @author Troy.Zhou
 * 
 */
public class AsyncHttpTask extends HttpTask {

	
    private OnCallback onResponse;
    private OnCallback onException;
    private OnCallback onComplete;

	public AsyncHttpTask(HttpClient client, String url) {
		super(client, url);
	}


	/**
	 * 设置请求执行异常后的回调函数,设置后,相关异常将不再向上抛出
	 * @param onException 请求异常回调
	 * @return HttpTask 实例
	 */
    public AsyncHttpTask setOnException(OnCallback onException) {
        this.onException = onException;
        return this;
    }

	/**
	 * 设置请求执行完成后的回调函数,无论成功|失败|异常 都会被执行
	 * @param onComplete 请求完成回调
	 * @return HttpTask 实例
	 */
    public AsyncHttpTask setOnComplete(OnCallback onComplete) {
        this.onComplete = onComplete;
        return this;
    }
    
	/**
	 * 设置请求得到响应后的回调函数
	 * @param onResponse 请求响应回调
	 * @return HttpTask 实例
	 */
    public AsyncHttpTask setOnResponse(OnCallback onResponse) {
        this.onResponse = onResponse;
        return this;
    }
    
    /**
     * 发起 GET 请求
     * @return HttpCall
     */
    public HttpCall get() {
        return request("GET");
    }

    /**
     * 发起 POST 请求
     * @return HttpCall
     */
    public HttpCall post() {
        return request("POST");
    }

    /**
     * 发起 PUT 请求
     * @return HttpCall
     */
    public HttpCall put() {
        return request("PUT");
    }

    /**
     * 发起 DELETE 请求
     * @return HttpCall
     */
    public HttpCall delete() {
        return request("DELETE");
    }
    
    private HttpCall request(String method) {
    	PreHttpCall call = new PreHttpCall();
    	httpClient.preprocess(this, () -> {
    		synchronized (call) {
    			if (!call.isCanceled()) {
    				call.setCall(executeCall(prepareCall(method)));
        		}
			}
    	});
    	if (tag != null) {
    		httpClient.addTagCall(tag, call, this);
    	}
    	return call;
    }
    
    
    class PreHttpCall implements HttpCall {

    	private boolean canceled = false;
    	private HttpCall call;
    	
		@Override
		public boolean cancel() {
			boolean res = true;
			synchronized (this) {
				if (call != null) {
					res = call.cancel();
				} else {
					canceled = true;
				}
				notify();
			}
			if (tag != null && call == null) {
	    		httpClient.removeTagCall(AsyncHttpTask.this);
	    	}
			return res;
		}

		@Override
		public boolean isDone() {
			if (call != null) {
				return call.isDone();
			}
			return canceled;
		}

		@Override
		public boolean isCanceled() {
			if (call != null) {
				return call.isCanceled();
			}
			return canceled;
		}

		public void setCall(HttpCall call) {
			this.call = call;
			notify();
		}

		@Override
		public synchronized HttpResult getResult() {
			if (canceled) {
				return new RealHttpResult(State.CANCELED);
			}
			if (call == null) {
				try {
					wait();
				} catch (InterruptedException e) {
					throw new HttpException(e.getMessage(), e);
				}
			}
			if (call != null) {
				return call.getResult();
			}
			return new RealHttpResult(State.CANCELED);
		}

    }
    
    class OkHttpCall implements HttpCall {

    	private Call call;
    	private HttpResult result;
    	
		public OkHttpCall(Call call) {
			this.call = call;
		}

		@Override
		public boolean cancel() {
			if (result == null) {
				call.cancel();
				return true;
			}
			return false;
		}

		@Override
		public boolean isDone() {
			return result != null;
		}

		@Override
		public boolean isCanceled() {
			return call.isCanceled();
		}

		@Override
		public synchronized HttpResult getResult() {
			if (result == null) {
				try {
					wait();
				} catch (InterruptedException e) {
					throw new HttpException(e.getMessage(), e);
				}
			}
			return result;
		}

		public void setResult(HttpResult result) {
			synchronized (this) {
				this.result = result;
				notify();
			}
			if (tag != null) {
	    		httpClient.removeTagCall(AsyncHttpTask.this);
	    	}
		}

    }
	
    private HttpCall executeCall(Call call) {
        OkHttpCall httpCall = new OkHttpCall(call);
        call.enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
            	State state = toState(e);
            	doOnException(state, e);
            	if (state == State.CANCELED) {
            		httpCall.setResult(new RealHttpResult(state));
            	} else {
            		httpCall.setResult(new RealHttpResult(state, e));
            	}
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
            	HttpResult result = new RealHttpResult(response, httpClient.getCallbackExecutor());
            	doOnResponse(result);
            	httpCall.setResult(result);
            }
			
        });
		return httpCall;
    }
    

	private void doOnResponse(HttpResult result) {
		httpClient.getCallbackExecutor().execute(() -> {
			if (onComplete != null) {
			    onComplete.on(State.RESPONSED);
			}
			if (onResponse != null) {
				onResponse.on(result);
			}
		});
	}
	
	private void doOnException(State state, Exception e) {
		httpClient.getCallbackExecutor().execute(() -> {
			if (onComplete != null) {
	            onComplete.on(state);
	        }
			// 请求取消不作为一种异常来处理
			if (state != State.CANCELED) {
				if (onException != null) {
				    onException.on(e);
				} else if (!nothrow) {
					throw new HttpException(e.getMessage(), e);
				}
			}
		});
	}
	
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy