在第一章中我们实现了最基本的Servlet和Android用get进行网络交互功能。在实际开发中基本是需要带参数的,需要处理get/post,head,cookie,parameter等等;还要进行业务处理,访问数据库,组装数据。然后才会下发数据到客户端。
在这里面因为代码的业务越来越复杂,版本迭代等因素造成Servlet的代码也会越来越多,IT人员的高度流动性加剧了代码维护工作量,甚至到后期就是灾难性的。下面我们用MVP来降低代码的耦和型,在Server端因为没有View层可以叫SVP。在这里不在介绍MVP的思想了,直接代码实现
FirstPresenter处理数据解析和业务逻辑调度,代码如下
package servlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class FirstPresenter implements FirstPresenterInterface {
private FirstServletInterface mFirstServletInterface;
public FirstPresenter(FirstServletInterface servletInterface){
mFirstServletInterface = servletInterface;
}
public void parseParameters(HttpServletRequest request,
HttpServletResponse response,int type) {
// TODO Auto-generated method stub
System.out.println("处理请求类型。。。type="+type);
response.setContentType("text/html;charset=utf-8");
String sendMsg = "这是来自FirstServlet的数据";
mFirstServletInterface.sendMSG(response,sendMsg);
}
}
FirstPresenterInterface把FirstPresenter方法暴露给Servlet,Servlet只能访问暴露的方法。代码如下
package servlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public interface FirstPresenterInterface {
public void parseParameters(HttpServletRequest request, HttpServletResponse response,int httpType);
}
FirstServlet接收和下发数据,不在进行任何的业务处理。代码如下
package servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class FirstServlet extends HttpServlet implements FirstServletInterface{
FirstPresenterInterface mPresenter;
/** * Constructor of the object. */
public FirstServlet() {
super();
}
/** * Destruction of the servlet. <br> */
public void destroy() {
super.destroy(); // Just puts "destroy" string in log
// Put your code here
}
@Override
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// TODO Auto-generated method stub
// super.doDelete(req, resp);
System.out.println("处理Get请求。。。");
mPresenter.parseParameters(request, response, HttpType.HTTP_TYPE_GET);
// response.setContentType("text/html;charset=utf-8");
// PrintWriter out = response.getWriter();
//
// out.println("<strong>Hello servlet</strong>");
// out.flush();
// out.close();
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// TODO Auto-generated method stub
// super.doGet(request, response);
System.out.println("处理Post请求。。。");
mPresenter.parseParameters(request, response, HttpType.HTTP_TYPE_POST);
// response.setContentType("text/html;charset=utf-8");
// PrintWriter out = response.getWriter();
//
// out.println("<strong>Hello servlet</strong>");
// out.flush();
// out.close();
}
/** * Initialization of the servlet. <br> * * @throws ServletException if an error occurs */
public void init() throws ServletException {
// Put your code here
mPresenter = new FirstPresenter(this);
}
public void sendMSG(HttpServletResponse response,String msg) {
PrintWriter out;
try {
out = response.getWriter();
out.println(msg);
out.flush();
out.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
FirstServletInterface P层处理完业务逻辑后调度接口定义的方法,这里传递response和P生成的数据msg
package servlet;
import javax.servlet.http.HttpServletResponse;
public interface FirstServletInterface {
public void sendMSG(HttpServletResponse response,String msg);
}
数据模块,因我们的比较简单还没有牵扯到数据库,这里暂时空着。具体实现实在P解析数据以后,根据业务逻辑和module交互,获取资源在传递到S层
HttpType常量定义
package servlet;
public class HttpType {
public static final int HTTP_TYPE_GET = 0;
public static final int HTTP_TYPE_POST = 1;
}
和上面服务端一样,移动的项目因为UI修改、版本迭代、技术更新、人员离职、机型适配等等造成项目也是越来越难维护。如果中间有错误实现,到后期调试会非常的浪费时间。下面是本例子android代码
MainPresenter 不在直接接触UI,当然也不能做Activity里面页面跳转逻辑,仅仅处理业务。
package com.example.zqw.servletdemo;
import android.util.Log;
import com.zhy.http.okhttp.OkHttpUtils;
import com.zhy.http.okhttp.callback.StringCallback;
import okhttp3.Call;
import okhttp3.Request;
/** * Created by zqw on 2016/2/24. */
public class MainPresenter implements PresenterInterface{
MainInterface mInterface;
public MainPresenter(MainInterface mainInterface){
this.mInterface = mainInterface;
}
@Override
public void getInfo() {
String url = "http://172.16.41.113:8080/FirstServletDemo/servlet/HelloServlet";
OkHttpUtils
.get()
.url(url)
.build()
.execute(new MyStringCallback());
}
public class MyStringCallback extends StringCallback {
@Override
public void onBefore(Request request)
{
super.onBefore(request);
// setTitle("loading...");
}
@Override
public void onAfter()
{
super.onAfter();
// setTitle("Sample-okHttp");
}
@Override
public void onError(Call call, Exception e)
{
mInterface.showErrorInfo("您的请求出错啦:"+e.toString());
}
@Override
public void onResponse(String response)
{
mInterface.showErrorInfo("您获取的数据是:"+response);
}
@Override
public void inProgress(float progress)
{
// Log.e(TAG, "inProgress:" + progress);
}
}
}
MainActivity不在处理网络请求,这里只关心view相关工作。继承MainInterface并实现二个方法,显示正常请求数据和请求异常的提示
package com.example.zqw.servletdemo;
import android.os.Bundle;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.Snackbar;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.Toolbar;
import android.util.Log;
import android.view.View;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.TextView;
import android.widget.Toast;
import com.zhy.http.okhttp.OkHttpUtils;
import com.zhy.http.okhttp.callback.StringCallback;
import okhttp3.Call;
import okhttp3.Request;
public class MainActivity extends AppCompatActivity implements MainInterface{
private static final String TAG = "MainActivity";
TextView mTV;
MainPresenter mainPresenter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mTV = (TextView)findViewById(R.id.servletTV);
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
fab.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
.setAction("Action", null).show();
}
});
mainPresenter = new MainPresenter(this);
mainPresenter.getInfo();
}
public void showInfo(String msg) {
mTV.setText(msg);
}
public void showErrorInfo(String msg) {
mTV.setText(msg);
Toast toast = Toast.makeText(this,msg,Toast.LENGTH_LONG);
toast.show();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_main, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
}