在很多产业中,移动服务器配合android系统来实现小型服务器构架越来越成为我们的议题,尤其是物联网的发展,IPV6的推出。智能家居对移动服务器的需要更是千丝万缕,毕竟一台成熟的服务器价格还是不菲的,不适合广泛的每个家庭来安装。所以我提出了移动服务器的议题,来解决我们小访问量的服务器构架。
小型服务器的构架原理是什么,框架结构又如何,通信机制是什么,实现办法该怎样,都是我们遇上的问题。这里我会一一记录我构架的服务器的过程,供大家参考。
服务器的框架:采用apache技术,通信采用http的GET方法,POST方法我没有搞通。
1.效果演示
效果为:
未打开wifi获取的效果
打开wifi获取的IP地址
浏览器通过get方式请求服务器获取的内容。
2.程序讲解
2.1 主线程开启service服务
@Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); initViews(); intent = new Intent(this, WebService.class); Log.i(TAG, "------->>>"+"初始化完毕"+intent.toString()); } private void initViews() { toggleBtn = (ToggleButton) findViewById(R.id.togbtnOpen); toggleBtn.setOnCheckedChangeListener(this); urlText = (TextView) findViewById(R.id.txtUrl); }
处理toggleButton改变触发
@Override public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { if (isChecked) { String ip = getLocalIpAddress(); if (ip == null) { urlText.setText(""); } else { startService(intent); Log.i(TAG, "------->>>"+"WebService起动"); urlText.setText("http://" + ip + ":" + WebService.PORT + "/"); } } else { stopService(intent); Log.i(TAG, "------->>>"+"WebService关闭"+intent.toString()); urlText.setText(""); } }
获取当前IP地址
public String getLocalIpAddress(){ WifiManager wifimanager = (WifiManager)this.getSystemService(Context.WIFI_SERVICE); WifiInfo wifiinfo = (WifiInfo)wifimanager.getConnectionInfo(); try { int i = wifiinfo.getIpAddress(); //返回IP 地址 return (i&0xff)+"."+((i>>8)&0xff)+"."+((i>>16)&0xff)+"."+((i>>24)&0xff); } catch (Exception ex) { ex.printStackTrace(); } return null; }
2.在service任务中加入server处理
public class WebService extends Service { public static final int PORT = 7766; public static final String TAG = "WebService"; private WebServer webServer; @Override public IBinder onBind(Intent intent) { // TODO Auto-generated method stub return null; } @Override public void onCreate() { super.onCreate(); webServer = new WebServer(PORT); } @Override public int onStartCommand(Intent intent, int flags, int startId) { webServer.setDaemon(true); webServer.start(); return super.onStartCommand(intent, flags, startId); } @Override public void onDestroy() { webServer.close(); super.onDestroy(); } }
3.做WebServer处理程序
public class WebServer extends Thread { public static final String TAG = "WebService"; private int port; private boolean isLoop = false; public WebServer(int port) { super(); this.port = port; } @Override public void run() { ServerSocket serverSocket = null; try { Log.i(TAG, "coming in!!"); // 创建服务器套接字 serverSocket = new ServerSocket(port); // 创建HTTP协议处理器 BasicHttpProcessor httpproc = new BasicHttpProcessor(); // 增加HTTP协议拦截器 httpproc.addInterceptor(new ResponseDate()); httpproc.addInterceptor(new ResponseServer()); httpproc.addInterceptor(new ResponseContent()); httpproc.addInterceptor(new ResponseConnControl()); // 创建HTTP服务 HttpService httpService = new HttpService(httpproc, new DefaultConnectionReuseStrategy(), new DefaultHttpResponseFactory()); // 创建HTTP参数 HttpParams params = new BasicHttpParams(); params.setIntParameter(CoreConnectionPNames.SO_TIMEOUT, 5000) .setIntParameter(CoreConnectionPNames.SOCKET_BUFFER_SIZE,8 * 1024) .setBooleanParameter(CoreConnectionPNames.STALE_CONNECTION_CHECK, false) .setBooleanParameter(CoreConnectionPNames.TCP_NODELAY, true) .setParameter(CoreProtocolPNames.ORIGIN_SERVER,"WebServer/1.1"); // 设置HTTP参数 httpService.setParams(params); // 创建HTTP请求执行器注册表 HttpRequestHandlerRegistry reqistry = new HttpRequestHandlerRegistry(); reqistry.register("*"+"AfangCtrl", new AfangCtrl()); reqistry.register("*"+"CameraCtrl", new CameraCtrl()); reqistry.register("*"+"LightCtrl", new LightCtrl()); reqistry.register("*"+"TvCtrl", new TvCtrl()); // 设置HTTP请求执行器 httpService.setHandlerResolver(reqistry); /* 循环接收各客户端 */ isLoop = true; while (isLoop && !Thread.interrupted()) { // 接收客户端套接字 Socket socket = serverSocket.accept(); // 绑定至服务器端HTTP连接 DefaultHttpServerConnection conn = new DefaultHttpServerConnection(); conn.bind(socket, params); // 派送至WorkerThread处理请求 Thread t = new WorkerThread(httpService, conn); t.setDaemon(true); // 设为守护线程 t.start(); } } catch (IOException e) { isLoop = false; e.printStackTrace(); } finally { try { if (serverSocket != null) { serverSocket.close(); } } catch (IOException e) { } } } public void close() { isLoop = false; } }
4.对LightCtrl进行简单描述
当前类要继承HttpRequestHandler类,做handler实现请求的处理
public class LightCtrl implements HttpRequestHandler { private static final String TAG = "HttpJsonlogin"; public LightCtrl(){ } @Override public void handle(HttpRequest request, HttpResponse response, HttpContext context) throws HttpException, IOException { RequestLine requestLine = request.getRequestLine(); String method=requestLine.getMethod(); if("GET".equals(method)){ doGet(request, response); }else{ Log.i(TAG, "method is error:"+method.toString()); } } /**************************************************************** * urlCmd格式:http://loaclhost:port/DEVICE?device=num&operation=open(close)&clientId=phone * @param request * @param response */ public void doGet(HttpRequest request, HttpResponse response){ response.setStatusCode(HttpStatus.SC_OK);//响应成功 response.setHeader("Content-Type", "text/json"); response.setHeader("Content-Type", "charset=gbk"); JSONObject json = new JSONObject(); //************解析参数************************************* String urlCmd = request.getRequestLine().getUri(); int a = urlCmd.indexOf("device"); a=a+7; int b = urlCmd.indexOf("&",a); String device = urlCmd.substring(a, b); a = urlCmd.indexOf("operation"); a=a+10; b = urlCmd.indexOf("&",a); String operation = urlCmd.substring(a, b); a = urlCmd.indexOf("clientId"); a=a+9; b = urlCmd.length(); String clientId = urlCmd.substring(a, b); Log.i(TAG, "请求命令为:"+device+operation+clientId); //根据命令做出响应 StringEntity entity = null; try { json.put("device", device); json.put("operation", operation); json.put("clientId", clientId); json.put("result", "ok"); Log.i(TAG,"响应JSON数据为:"+json.toString()); entity = new StringEntity(json.toString(),"UTF-8"); } catch (JSONException e) { e.printStackTrace(); } catch (UnsupportedEncodingException e) { // TODO Auto-generated catch block e.printStackTrace(); } response.setEntity(entity); } }