一、创建 SSMVCAnnoDemo 项目

点击菜单,选择“File -> New Project” 创建新项目。选择使用 archetype 中的 maven-quickstart 模版创建。

输入对应的项目坐标GroupId 和 ArtifactId

之后在项目名称中填入项目名称,这里我填的 ProjectName 和上文的 ArtifactId 相同,都是 SuperDemo。

点击确定后,等待 Maven 帮我们构建好项目的目录结构。当控制台显示 BUILD SUCCESS 就表示初始化完成了。

完成初始化之后,我们分别创建 model、interface、provider、consumer 模块,它们的作用分别是:

model:存放 POJO 文件的模块

interface:存放接口文件的模块

provider:提供服务的模块

consumer:调用服务的模块

二、配置 model 模块

在 SuperDemo 模块的 pom.xml 文件添加 JUnit、Log4J 等公共依赖:

<!-- 单元测试 JUnit -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
<scope>provided</scope>
</dependency>
<!-- 日志记录 Log4j -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.6</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.6</version>
</dependency>
<!-- JSON 包 -->
<dependency>
<groupId>net.sf.json-lib</groupId>
<artifactId>json-lib</artifactId>
<version>2.4</version>
<classifier>jdk15</classifier>
</dependency>

修改后的 pom.xml 为:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion> <groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>SuperDemo</artifactId>
<version>1.0-SNAPSHOT</version>
<modules>
<module>interface</module>
<module>model</module>
<module>provider</module>
<module>consumer</module>
</modules>
<packaging>pom</packaging> <name>SuperDemo</name>
<url>http://maven.apache.org</url> <properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<junit.version>3.8.1</junit.version>
</properties> <dependencies>
<!-- 单元测试 JUnit -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
<scope>provided</scope>
</dependency>
<!-- 日志记录 Log4j -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.6</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.6</version>
</dependency>
<!-- JSON 包 -->
<dependency>
<groupId>net.sf.json-lib</groupId>
<artifactId>json-lib</artifactId>
<version>2.4</version>
<classifier>jdk15</classifier>
</dependency>
</dependencies>
</project>

pom.xml

下载 MBGGenerator(密码:c1dy),这是MyBatis 官方的 MyBatis Generator,我们使用它将数据库表转化成 model、mapper 以及 SqlProvider 文件。

下载文件解压放到 provider 模块的 resources 目录下。进入 resources/mbg 目录,双击运行 generate.bat,程序自动将配置文件 resources/mbgconfig.xml 中配置的表格映射成相对应的文件。

将上面生成后的 com.chanshuyi.model.User 类拷贝至 model 模块的 com.chanshuyi.model 包。

三、配置 interface 模块

打开 interface 模块的 pom.xml 模块,加入对于 SuperDemo 下 model 模块的依赖:

<dependency>
<groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>model</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>

创建 com.chanshuyi.dao.IUserDao 接口

package com.chanshuyi.dao;

import com.chanshuyi.model.User;

import java.util.List;
import java.util.Map; /**
* Created by chanshuyi on 2015/12/26.
*/
public interface IUserDao {
User getUserById(int userId); /**
*
* @param param Map中的key要与数据库表中的字段名相同
* @return
*/
User getUserByMapSql(Map<String, String> param); List<User> getUserListByMapSql(Map<String, String> param);
}

创建 com.chanshuyi.service.IUserService 接口

package com.chanshuyi.service;

import com.chanshuyi.model.User;

import java.util.List;
import java.util.Map; /**
* Created by chanshuyi on 2015/12/26.
*/
public interface IUserService {
User getUserById(int userId); /**
*
* @param param Map中的key要与数据库表中的字段名相同
* @return
*/
User getUserByMapSql(Map<String, String> param); List<User> getUserListByMapSql(Map<String, String> param);
}

四、配置 provider 模块

打开 provider 模块的 pom.xml 文件,加入全局属性声明

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<springframework.version>4.1.6.RELEASE</springframework.version>
<commonsLogging.version>1.2</commonsLogging.version>
</properties>

导入 Spring、MyBatis 等依赖

<dependencies>
<!-- ********************** MyBatis ********************** -->
<!-- MyBatis 核心包 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.1.1</version>
</dependency>
<!-- 添加mybatis与Spring整合的核心包 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>1.1.1</version>
</dependency> <!-- ********************** Spring ********************** -->
<!-- 添加Spring-core包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-tx包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- Spring ORM 相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-jdbc包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>${springframework.version}</version>
</dependency>
<!--添加spring-web包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-context包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>${commonsLogging.version}</version>
</dependency>
<!--添加aspectjweaver包 -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.5</version>
</dependency> <!-- ********************** JDBC ********************** -->
<!-- MySQL -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.21</version>
</dependency>
<!-- Druid -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.0.6</version>
</dependency> <!-- ********************** DUBBO ********************** -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.5.3</version>
<exclusions>
<exclusion>
<groupId>org.springframework</groupId>
<artifactId>spring</artifactId>
</exclusion>
</exclusions>
</dependency> <!-- ********************** Zookeeper ********************** -->
<!-- zookeeper -->
<dependency>
<groupId>com.github.sgroschupf</groupId>
<artifactId>zkclient</artifactId>
<version>0.1</version>
</dependency>
<dependency>
<groupId>org.apache.zookeeper</groupId>
<artifactId>zookeeper</artifactId>
<version>3.3.3</version>
<exclusions>
<exclusion>
<groupId>com.sun.jmx</groupId>
<artifactId>jmxri</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jdmk</groupId>
<artifactId>jmxtools</artifactId>
</exclusion>
<exclusion>
<groupId>javax.jms</groupId>
<artifactId>jms</artifactId>
</exclusion>
</exclusions>
</dependency> <!-- ********************** 其他 ********************** -->
<!-- 核心接口 -->
<dependency>
<groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>

在 resources 目录下创建 applicationContext.xml

<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx" xmlns:jdbc="http://www.springframework.org/schema/jdbc"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:task="http://www.springframework.org/schema/task"
xsi:schemaLocation="
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task-3.0.xsd"> <!-- ================================== import sub-config file ================================== -->
<import resource="spring-mybatis.xml" />
<!-- ================================== /import sub-config file ================================== -->
</beans>

创建 MyBatis 配置文件 spring-mybatis.xml

 <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <!-- 引入外部properties文件 -->
<context:property-placeholder location="classpath:jdbc.properties" /> <!-- ====================================================== Add MyBatis Support Start ====================================================== -->
<!-- 配置写数据源 -->
<bean id="dataSourceWrite" class="com.alibaba.druid.pool.DruidDataSource" init-method="init" destroy-method="close">
<!-- 基本属性 url、user、password -->
<property name="url" value="${jdbc.master.url}" />
<property name="username" value="${jdbc.master.username}" />
<property name="password" value="${jdbc.master.password}" />
<!-- 配置初始化大小、最小、最大 -->
<property name="initialSize" value="${jdbc.master.initialSize}" />
<property name="minIdle" value="${jdbc.master.minIdle}" />
<property name="maxActive" value="${jdbc.master.maxActive}" />
<!-- 配置获取连接等待超时的时间 -->
<property name="maxWait" value="60000" />
<!-- 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒 -->
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<!-- 配置一个连接在池中最小生存的时间,单位是毫秒 -->
<property name="minEvictableIdleTimeMillis" value="300000" />
<property name="validationQuery" value="SELECT '1'" />
<property name="testWhileIdle" value="true" />
<property name="testOnBorrow" value="true" />
<property name="testOnReturn" value="false" />
<!-- 打开PSCache,并且指定每个连接上PSCache的大小 mysql false -->
<property name="poolPreparedStatements" value="false" />
<property name="maxPoolPreparedStatementPerConnectionSize" value="20" />
<!-- 配置监控统计拦截的filters -->
<property name="filters" value="config,stat,log4j,wall" />
<property name="connectionProperties" value="config.decrypt=false" />
</bean>
<!-- 配置读数据源 -->
<bean id="dataSourceRead" class="com.alibaba.druid.pool.DruidDataSource" init-method="init" destroy-method="close">
<!-- 基本属性 url、user、password -->
<property name="url" value="${jdbc.slave.url}" />
<property name="username" value="${jdbc.slave.username}" />
<property name="password" value="${jdbc.slave.password}" />
<!-- 配置初始化大小、最小、最大 -->
<property name="initialSize" value="${jdbc.slave.initialSize}" />
<property name="minIdle" value="${jdbc.slave.minIdle}" />
<property name="maxActive" value="${jdbc.slave.maxActive}" />
<!-- 配置获取连接等待超时的时间 -->
<property name="maxWait" value="60000" />
<!-- 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒 -->
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<!-- 配置一个连接在池中最小生存的时间,单位是毫秒 -->
<property name="minEvictableIdleTimeMillis" value="300000" />
<property name="validationQuery" value="SELECT '1'" />
<property name="testWhileIdle" value="true" />
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<!-- 打开PSCache,并且指定每个连接上PSCache的大小 mysql false -->
<property name="poolPreparedStatements" value="false" />
<property name="maxPoolPreparedStatementPerConnectionSize" value="20" />
<!-- 配置监控统计拦截的filters -->
<property name="filters" value="config,stat,log4j,wall" />
<property name="connectionProperties" value="config.decrypt=false" />
</bean> <!-- 可写的SessionFactory -->
<bean id="sqlWriteSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean" scope="singleton">
<property name="dataSource" ref="dataSourceWrite" />
<property name="configLocation" value="classpath:mybatis-config.xml" />
</bean>
<!-- 只读的SessionFactory -->
<bean id="sqlReadOnlySessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean" scope="singleton">
<property name="dataSource" ref="dataSourceRead" />
<property name="configLocation" value="classpath:mybatis-config.xml" />
</bean> <!-- 可写的Session -->
<bean id="writableSQLSession" class="org.mybatis.spring.SqlSessionTemplate">
<constructor-arg index="0" ref="sqlWriteSessionFactory" />
</bean>
<!-- 只读的Session -->
<bean id="readonlySQLSession" class="org.mybatis.spring.SqlSessionTemplate">
<constructor-arg index="0" ref="sqlReadOnlySessionFactory" />
</bean>
<!-- ====================================================== Add MyBatis Support End ====================================================== -->
</beans>

配置 MyBatis 注解扫描路径,创建 mybatis-config.xml 配置文件:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<mappers>
<!-- 配置扫描的Mapper类 -->
<package name="com.chanshuyi.dao.mapper"/>
</mappers>
</configuration>

创建数据库配置文件 jdbc.properties

############################  MySQL/Oracle/SQLServer Database Configuratioin Info ###############################
# MySQL Master DB Info
jdbc.master.dialet=org.hibernate.dialect.MySQLDialect
jdbc.master.driverClassName=com.mysql.jdbc.Driver
jdbc.master.url=jdbc:mysql://127.0.0.1:3306/superdemo
jdbc.master.username=root
jdbc.master.password=sa # MySQL Slave DB Info
jdbc.slave.dialet=org.hibernate.dialect.MySQLDialect
jdbc.slave.driverClassName=com.mysql.jdbc.Driver
jdbc.slave.url=jdbc:mysql://localhost:3306/superdemo
jdbc.slave.username=root
jdbc.slave.password=sa ############################## Connection Pool Configuration Info ##############################################
# MySQL Master DB Setting
jdbc.master.initialSize = 10
jdbc.master.minIdle = 0
jdbc.master.maxActive = 30 # MySQL Slave DB Setting
jdbc.slave.initialSize = 10
jdbc.slave.minIdle = 0
jdbc.slave.maxActive = 30

创建 resources/log4j.properties 文件,提供日志记录。

#Console Log
log4j.rootLogger=info, console, file # Write to Console
log4j.appender.console=org.apache.log4j.ConsoleAppender
log4j.appender.console.Threshold=INFO
log4j.appender.console.layout=org.apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=%5p %d{MM-dd HH:mm:ss}(%F:%L): %m%n # Write to File
log4j.appender.file=org.apache.log4j.DailyRollingFileAppender
log4j.appender.file.File=${catalina.home}app/log/log.log
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%5p %d{MM-dd HH:mm:ss}(%F:%L): %m%n

在 com.chanshuyi.dao.mapper.UserMapper 类中增加 getUserListByMapSql 接口:

/**
* 根据参数构造SQL进行查询
* @param param
* @return
*/
@SelectProvider(type = UserSqlProvider.class, method = "getUserListByMapSql")
List<User> getUserListByMapSql(@Param("param") Map<String, String> param);

在 UserSqlProvider 类增加对上面接口 SQL 的实现:

/**
* 获取查询SQL
* @param param
* @return
*/
public String getUserListByMapSql(Map<String, Object> param) {
StringBuilder builder = new StringBuilder();
Map<String, String> realParam = (Map<String, String>)param.get("param"); //add select part
builder.append(" select * from user where 1 = 1 "); //add condition part
String conditionStr = "";
if(!StringUtil.isNullOrEmpty(realParam)){
conditionStr = getQueryCondition(realParam);
if(!StringUtil.isNullOrEmpty(conditionStr)){
builder.append(conditionStr);
}
} return new String(builder);
} public String getQueryCondition(Map<String, String> param){
StringBuilder builder = new StringBuilder(); //if param is null or empty, return empty String
if(param == null || param.size() <){
return "";
} for(String key : param.keySet()){
String value = param.get(key);
if(value != null && !value.isEmpty()){
builder.append(" and " + key + " = '" + value + "'");
}
} return new String(builder);
}

上面用到了 StringUtil.java,我们在 com.chanshuyi.util 中导入它:

package com.mszz.util;

import java.util.Collection;
import java.util.Map; /**
* 字符串工具类
* @author chenxinquan
*
*/
public class StringUtil {
/**
* 判断对象或对象数组中每一个对象是否为空: 对象为null,字符序列长度为0,集合类、Map为empty
* @author zl
* @param obj
* @return
*/
public static boolean isNullOrEmpty(Object obj) {
if (obj == null)
return true; if (obj instanceof CharSequence)
return ((CharSequence) obj).length() == 0; if (obj instanceof Collection)
return ((Collection) obj).isEmpty(); if (obj instanceof Map)
return ((Map) obj).isEmpty(); if (obj instanceof Object[]) {
Object[] object = (Object[]) obj;
if (object.length == 0) {
return true;
}
boolean empty = true;
for (int i = 0; i < object.length; i++) {
if (!isNullOrEmpty(object[i])) {
empty = false;
break;
}
}
return empty;
}
return false;
}
} StringUtil.java

创建 com.chanshuyi.dao.impl.BaseDao.java 类,提供基本的数据库读写对象,并用注解方式将 SqlSession 注入。

package com.chanshuyi.dao.impl;

import org.apache.ibatis.session.SqlSession;
import org.springframework.beans.factory.annotation.Autowired; /**
* 所有Service的基类,用来注入sqlSession
*/
public class BaseDao {
/**
* 可写的sqlSession
*/
@Autowired
protected SqlSession writableSQLSession; /**
* 只读的sqlSession
*/
@Autowired
protected SqlSession readonlySQLSession;
}

创建 com.chanshuyi.dao.impl.UserDaoImpl.java 继承 BaseDao.java、实现 IUserDao 接口,并用 @Repository 创建名称为 userDao 的对象。

package com.chanshuyi.dao.impl;

import com.chanshuyi.dao.IUserDao;
import com.chanshuyi.dao.mapper.UserMapper;
import com.chanshuyi.model.User;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.stereotype.Repository; import java.util.List;
import java.util.Map; /**
* Created by Administrator on 2015/12/26.
*/
@Repository("userDao")
public class UserDaoImpl extends BaseDao implements IUserDao { private static Log logger = LogFactory.getLog(UserDaoImpl.class); @Override
public User getUserById(int userId) {
UserMapper mapper = readonlySQLSession.getMapper(UserMapper.class);
return mapper.selectByPrimaryKey(userId);
} /**
*
* @param param
* @return
*/
@Override
public User getUserByMapSql(Map<String, String> param) {
logger.info("getUserByMapSql 根据动态参数查询用户对象");
return getUserListByMapSql(param).size() > 0 ? getUserListByMapSql(param).get(0) : null;
} /**
* get**MapSql()类的方法只能用于各参数的等于查询
* 例如:select * from user where username = 1 and password = 3 (正确)
* select * from user where username in (1,2,3) (错误,无法实现)
* @param param
* @return
*/
@Override
public List<User> getUserListByMapSql(Map<String, String> param) {
logger.info("getUserListByMapSql 根据动态参数查询用户对象列表");
UserMapper mapper = readonlySQLSession.getMapper(UserMapper.class);
return mapper.getUserListByMapSql(param);
}
}

创建 com.chanshuyi.service.impl.UserServiceImpl 类,并添加 @Service 注解创建名称为 userService 的对象,并将 userDao 对象注入。

package com.chanshuyi.service.impl;

import com.chanshuyi.dao.IUserDao;
import com.chanshuyi.model.User;
import com.chanshuyi.service.IUserService;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service; import java.util.List;
import java.util.Map; /**
* Created by Administrator on 2015/6/18.
*/
@Service("userService")
public class UserServiceImpl implements IUserService { private static Log logger = LogFactory.getLog(UserServiceImpl.class); @Autowired
IUserDao userDao; @Override
public User getUserById(int userId) {
return userDao.getUserById(userId);
} @Override
public User getUserByMapSql(Map<String, String> param) {
return userDao.getUserByMapSql(param);
} @Override
public List<User> getUserListByMapSql(Map<String, String> param) {
return userDao.getUserListByMapSql(param);
}
}

DAO 和 SERVICE 层的配置写好之后,需要在 applicationContext.xml 文件中配置扫描路径:

<!-- 开启注解相关处理器 -->
<context:annotation-config/>
<!-- 自动扫描Spring注解(如:autowired) -->
<context:component-scan base-package="com.chanshuyi.dao.impl, com.chanshuyi.service.impl"/>

到这里基本 provider 大部分配置已经结束,下面我们需要启动 provider 模块,让它对外提供服务。

创建 com.chanshuyi.util.SystemDetails 类,用来打印系统的基本信息:

package com.chanshuyi.util;

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.TimeZone; public class SystemDetails {
/**
* 输出系统基本信息
*/
public static void outputDetails() {
timeZone();
currentTime();
os();
} /**
* 输出系统时区
*/
private static void timeZone() {
Calendar cal = Calendar.getInstance();
TimeZone timeZone = cal.getTimeZone();
System.out.println("系统时区:" + timeZone.getDisplayName());
} /**
* 输出系统时间
*/
private static void currentTime() {
String fromFormat = "yyyy-MM-dd HH:mm:ss";
SimpleDateFormat format = new SimpleDateFormat(fromFormat);
Date myDate = new Date();
System.out.println("系统时间:" + format.format(myDate));
} /**
* 输出系统基本配置
*/
private static void os() {
String osName = System.getProperty("os.name"); //操作系统名称
System.out.println("当前系统:" + osName);
String osArch = System.getProperty("os.arch"); //操作系统构架
System.out.println("当前系统架构" + osArch);
String osVersion = System.getProperty("os.version"); //操作系统版本
System.out.println("当前系统版本:" + osVersion);
}
}

创建 com.chanshuyi.util.BeanFactoryUtil,用于加载 Spring 配置文件:

package com.chanshuyi.util;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext; public class BeanFactoryUtil {
private static ApplicationContext ctx_producer = null; public final static String ApplicationContextRoot = "";
public final static String ApplicationContextPath = ApplicationContextRoot + "applicationContext.xml"; public static void init() {
if (ctx_producer == null) {
synchronized (BeanFactoryUtil.class) {
if(ctx_producer == null){
String[] configLocations = new String[]{ApplicationContextPath};
ctx_producer = new ClassPathXmlApplicationContext(configLocations);
}
}
}
} public static ApplicationContext getContext() {
if (ctx_producer == null) {
init();
}
return ctx_producer;
}
}

创建 com.chanshuyi.Launcher 类,用于启动 provider 服务,加载 Spring 配置文件,对外提供服务:

package com.chanshuyi;

import com.chanshuyi.util.BeanFactoryUtil;
import com.chanshuyi.util.SystemDetails;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory; public class Launcher { private static Log logger = LogFactory.getLog(Launcher.class); /**
* @param args
*/
public static void main(String[] args) {
System.out.println("=======================");
System.out.println(" Core包启动 ");
SystemDetails.outputDetails();
System.out.println("======================="); getLocalip();
// 初始化spring
logger.info("开始初始化core服务");
BeanFactoryUtil.init(); try{
System.in.read();
} catch (Exception e) {
e.printStackTrace();
}
} /**
* 取得本机ip地址 注意:Spring RmiServiceExporter取得本机ip的方法:InetAddress.getLocalHost()
*/
private static void getLocalip() {
try {
System.out.println("服务暴露的ip: "
+ java.net.InetAddress.getLocalHost().getHostAddress());
} catch (Exception e) {
System.out.println(e.getMessage());
}
}
}

我们还要创建一个 spring-provider.xml 文件,告诉 dubbo 我们的基本信息以及对外提供的服务:

<?xml version="1.0" encoding="UTF-8"?>
<!-- 添加 DUBBO SCHEMA -->
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd http://code.alibabatech.com/schema/dubbo
http://code.alibabatech.com/schema/dubbo/dubbo.xsd"> <!-- 应用名 -->
<!-- 需要用到多个注册中心,因此在 dubbo.properties 中声明 -->
<dubbo:application name="superdemo_provider"/>
<!-- 连接到哪个本地注册中心 -->
<dubbo:registry id="superdemo_zk" address="zookeeper://localhost:2181"/>
<!-- 用dubbo协议在20880端口暴露服务 -->
<dubbo:protocol name="dubbo" port="28080"/>
<!-- 声明需要暴露的服务接口 -->
<dubbo:service registry="superdemo_zk" timeout="3000" interface="com.chanshuyi.service.IUserService" ref="userService"/>
</beans>

记得在 applicationContext.xml 文件中将 spring-provider.xml 文件导入进去:

<import resource="spring-provider.xml" />

五、配置 consumer 模块

打开 pom.xml 文件,导入全局配置变量以及所需的 SpringMVC、Dubbo、Zookeeper、com.chanshuyi.SuperDemo.interface 依赖:

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<springframework.version>4.1.6.RELEASE</springframework.version>
<commonsLogging.version>1.2</commonsLogging.version>
</properties> <dependencies>
<!-- ********************** Spring ********************** -->
<!-- Spring MVC 依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加Spring-core包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-tx包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- Spring ORM 相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-jdbc包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>${springframework.version}</version>
</dependency>
<!--添加spring-web包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-context包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>${commonsLogging.version}</version>
</dependency>
<!--添加aspectjweaver包 -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.5</version>
</dependency> <!-- ********************** DUBBO ********************** -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.5.3</version>
<exclusions>
<exclusion>
<groupId>org.springframework</groupId>
<artifactId>spring</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.apache.zookeeper</groupId>
<artifactId>zookeeper</artifactId>
<version>3.3.3</version>
<exclusions>
<exclusion>
<groupId>com.sun.jmx</groupId>
<artifactId>jmxri</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jdmk</groupId>
<artifactId>jmxtools</artifactId>
</exclusion>
<exclusion>
<groupId>javax.jms</groupId>
<artifactId>jms</artifactId>
</exclusion>
</exclusions>
</dependency> <!-- ********************** Zookeeper ********************** -->
<!-- zookeeper -->
<dependency>
<groupId>com.github.sgroschupf</groupId>
<artifactId>zkclient</artifactId>
<version>0.1</version>
</dependency> <!-- ********************** interface 接口 ********************** -->
<dependency>
<groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
</dependencies>

之后导入 Tomcat 启动插件,我们将通过 Maven 方式启动 Tomcat,这样就不必在本地配置一个 Tomcat 服务器。

<!--  Maven的Tomcat插件(支持Maven以"tomcat7:run"方式启动web项目)  -->
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.1</version>
<configuration>
<port>5050</port>
<path>/</path>
<uriEncoding>UTF-8</uriEncoding>
<finalName>mgr</finalName>
<server>tomcat7</server>
</configuration>
</plugin>

配置完成后的 pom.xml 文件是这样的:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<parent>
<artifactId>SuperDemo</artifactId>
<groupId>com.chanshuyi.SuperDemo</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>app</artifactId>
<packaging>war</packaging>
<name>app Maven Webapp</name>
<url>http://maven.apache.org</url> <properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<springframework.version>4.1.6.RELEASE</springframework.version>
<commonsLogging.version>1.2</commonsLogging.version>
</properties> <dependencies>
<!-- ********************** Spring ********************** -->
<!-- Spring MVC 依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加Spring-core包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-tx包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- Spring ORM 相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-jdbc包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>${springframework.version}</version>
</dependency>
<!--添加spring-web包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${springframework.version}</version>
</dependency>
<!-- 添加spring-context包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>${commonsLogging.version}</version>
</dependency>
<!--添加aspectjweaver包 -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.5</version>
</dependency> <!-- ********************** DUBBO ********************** -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.5.3</version>
<exclusions>
<exclusion>
<groupId>org.springframework</groupId>
<artifactId>spring</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.apache.zookeeper</groupId>
<artifactId>zookeeper</artifactId>
<version>3.3.3</version>
<exclusions>
<exclusion>
<groupId>com.sun.jmx</groupId>
<artifactId>jmxri</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jdmk</groupId>
<artifactId>jmxtools</artifactId>
</exclusion>
<exclusion>
<groupId>javax.jms</groupId>
<artifactId>jms</artifactId>
</exclusion>
</exclusions>
</dependency> <!-- ********************** Zookeeper ********************** -->
<!-- zookeeper -->
<dependency>
<groupId>com.github.sgroschupf</groupId>
<artifactId>zkclient</artifactId>
<version>0.1</version>
</dependency> <!-- ********************** interface 接口 ********************** -->
<dependency>
<groupId>com.chanshuyi.SuperDemo</groupId>
<artifactId>interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
</dependencies> <build>
<finalName>consumer</finalName>
<!-- Maven的Tomcat插件(支持Maven以"tomcat7:run"方式启动web项目) -->
<plugins>
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.1</version>
<configuration>
<port>5050</port>
<path>/</path>
<uriEncoding>UTF-8</uriEncoding>
<finalName>mgr</finalName>
<server>tomcat7</server>
</configuration>
</plugin>
</plugins>
</build>
</project>

之后在 main 目录下创建 java 目录,并设置为 Java Source(源码目录):

之后创建 com.chanshuyi.controller.UserController 类:

package com.chanshuyi.controller;

import com.chanshuyi.service.IUserService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam; import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.Map; /**
* Created by Administrator on 2015/6/18.
*/
@Controller("userAction")
@RequestMapping(value="/login")
public class UserController{ private static Logger logger = LoggerFactory.getLogger(UserController.class); private String message; private String username; private String password; @Autowired
private IUserService userService; @Autowired
private HttpServletRequest request; @RequestMapping("")
public String login(@RequestParam(value = "username", required = false) String username,
@RequestParam(value = "password", required = false) String password){
try{
Map<String, String> param = new HashMap<String, String>();
param.put("username", username);
param.put("password", password);
if(userService.getUserByMapSql(param) != null){
message = "登录成功!";
logger.info(message);
}else{
message = "登录失败!";
logger.info(message);
}
}catch(Exception e){
logger.warn(e.getMessage());
e.printStackTrace();
}
request.setAttribute("message", message);
return "index"; // 转到webapp/index.jsp页面
} /******** set/get ********/
public String getMessage() {
return message;
} public void setMessage(String message) {
this.message = message;
} public String getUsername() {
return username;
} public void setUsername(String username) {
this.username = username;
} public String getPassword() {
return password;
} public void setPassword(String password) {
this.password = password;
}
}

创建 dubbo 配置文件 spring-consumer.xml,这个文件告诉 dubbo 本模块的基本信息以及请求的服务:

<?xml version="1.0" encoding="UTF-8"?>
<!-- 添加 DUBBO SCHEMA -->
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd http://code.alibabatech.com/schema/dubbo
http://code.alibabatech.com/schema/dubbo/dubbo.xsd"> <!-- 应用名 -->
<!-- 需要用到多个注册中心,因此在 dubbo.properties 中声明 -->
<dubbo:application name="superdemo_consumer"/>
<!-- 连接到哪个本地注册中心 -->
<dubbo:registry id="superdemo_zk" address="zookeeper://localhost:2181"/>
<!-- 用dubbo协议在20880端口暴露服务 -->
<dubbo:protocol name="dubbo" port="28080"/>
<!-- 声明需要引用的服务接口 -->
<dubbo:reference registry="superdemo_zk" id="userService" interface="com.chanshuyi.service.IUserService" check="false"/> </beans>

别忘了在 applicationContext.xml 中将 spring-consumer.xml 加入进去

<import resource="spring-consumer.xml" />

创建 webapp/index.jsp 文件

<%@page language="java" pageEncoding="UTF-8"%>
<%@ page contentType="text/html;charset=utf-8" %>
<%@ page isELIgnored="false"%>
<html>
<head>
<meta charset="utf-8">
</head>
<body>
<h2>Hello World!</h2>
<%-- 通过Struts传递参数,数据传递方式必须选择post,否则编码错误! --%>
<form action="login" method="post" >
<p id="message">${message}</p>
<b>Username:</b><input type="text" id="name" name="username" /><br>
<b>Password:</b><input type="password" id="password" name="password"/><br>
<input type="submit" value="Login"/>
</form>
</body>
</html>

修改 web.xml 文件,加载 SpringMVC 处理器

<!DOCTYPE web-app PUBLIC
"-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd" > <web-app>
<display-name>Archetype Created Web Application</display-name> <!-- 字符集过滤器 -->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping> <!-- spring MVC的核心就是DispatcherServlet,使用springMVC的第一步就是将下面的servlet放入web.xml
servlet-name属性非常重要,默认情况下,DispatchServlet会加载这个名字-servlet.xml的文件,如下,就会加载
dispather-servlet.xml,也是在WEN-INF目录下。-->
<servlet>
<servlet-name>spring</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:/spring-servlet.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<!-- 设置dispatchservlet的匹配模式,通过把dispatchservlet映射到/,默认servlet会处理所有的请求,包括静态资源 -->
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>

创建 SprngMVC 配置文件 spring-servlet.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd"
default-lazy-init="true"> <!-- 通过mvc:resources设置静态资源,这样servlet就会处理这些静态资源,而不通过控制器 -->
<!-- 设置不过滤内容,比如:css,jquery,img 等资源文件 -->
<!--<mvc:resources location="/*.html" mapping="/**.html" />-->
<!--<mvc:resources location="/css/*" mapping="/css/**" />-->
<!--<mvc:resources location="/js/*" mapping="/js/**" />-->
<!--<mvc:resources location="/images/*" mapping="/images/**" />--> <!-- 添加注解驱动 -->
<mvc:annotation-driven />
<!-- 默认扫描的包路径 -->
<context:component-scan base-package="com.chanshuyi.controller" /> <!-- mvc:view-controller可以在不需要Controller处理request的情况,转向到设置的View -->
<!-- 像下面这样设置,如果请求为/,则不通过controller,而直接解析为/index.jsp -->
<!--<mvc:view-controller path="/" view-name="index" />-->
<!-- 配置 SpringMVC Controller 转发JSP页面的路径 -->
<bean class="org.springframework.web.servlet.view.UrlBasedViewResolver">
<property name="viewClass" value="org.springframework.web.servlet.view.JstlView"></property>
<!-- 配置jsp路径前缀 -->
<property name="prefix" value="/"></property>
<!-- 配置URl后缀 -->
<property name="suffix" value=".jsp"></property>
</bean>
</beans>

配置好之后将整个项目编译一次,为整个项目配置 Maven 命令:

六、启动 provider 模块和 consumer 模块测试

启动 provider 模块

先启动 zookeeper,再打开 Launcher.java 运行 main() 方法就可以了。看看控制台和 zookeeper 输出,如果没有报错,那就是启动成功了。

启动 consumer 模块

为 consumer 模块配置 Maven 启动命令:"tomcat7:run"

点击启动项目

测试联通

打开浏览器输入:http://localhost:5050/index.jsp

输入 admin/password,点击 Login 按钮

提示登录成功,说明项目已经成功部署好。

链接:http://pan.baidu.com/s/1pKamdib 密码:vutw

玩转 SSH(七):使用 dubbo + zookeeper 实现服务模块化的更多相关文章

  1. 关于dubbo+zookeeper微服务的一些认识记录

    借鉴架构示意图: 实例介绍: 公司某项目架构 服务器A:nginx 服务器BC:tomcat1.tomcat2 服务器D:Dubbo+zookeeper 服务器EF:db1+zookeeper.db2 ...

  2. 分布式应用开发 | SpringBoot+dubbo+zookeeper实现服务注册发现 | 远程服务调用

    前言 通过新建两个独立服务--提供者.消费者,模拟两个独立分布的应用,通过使用dubbo+zookeeper来实现远程服务调用. 目录 项目搭建 provider-server consumer-se ...

  3. springboot多模块开发以及整合dubbo\zookeeper进行服务管理

    之前研究了springboot单工程的使用,参考git地址:https://github.com/qiao-zhi/springboot-ssm 下面研究springboot多模块开发的过程. 1.模 ...

  4. springboot+dubbo+zookeeper微服务实践demo

    微服务化越来越火,实际上是应互联网时代而生的,微服务化带来的不仅是性能上的提升,更带来了研发组织的更加便利,协作更加轻松,团队效能更高. 当然不能为了技术而技术,我们需要切合实际的对业务进行划分,降低 ...

  5. Java学习之Dubbo+ZooKeeper分布式服务Demo

    背景:在之前的一个<Java学习之SpringBoot整合SSM Demo>分享中说到搭建ZooKeeper和Dubbo分布式框架中遇到了一些技术问题没能成功,只分享了其中的一个中间产物, ...

  6. dubbo+zookeeper注册服务报错问题:No service registed on zookeeper

    2019-04-04 11:23:40,372 ERROR [tomcat-threads--1] (com.bill99.dolphin.controller.ExceptionController ...

  7. 玩转 SSH 目录

    在做一个新的项目的时候,需要重新搭建一个项目. 于是趁着这个机会把之前学的几个框架的搭建都写一写,整理一下,同时也可以给大家一些参考.何乐而不为叻. 在这个系列中, 我将使用 IntelJ IDEA ...

  8. 玩转Spring Boot 集成Dubbo

    玩转Spring Boot 集成Dubbo 使用Spring Boot 与Dubbo集成,这里我之前尝试了使用注解的方式,简单的使用注解注册服务其实是没有问题的,但是当你涉及到使用注解的时候在服务里面 ...

  9. 微服务的一种开源实现方式——dubbo+zookeeper

    转自: http://blog.csdn.NET/zhdd99/article/details/52263609 微服务架构成了当下的技术热点,实现微服务是要付出很大成本的,但也许是因为微服务的优点太 ...

随机推荐

  1. 随机生成并排序 C,去同,有序数组合并排序

    #include<iostream> #include<stdlib.h> #include<time.h> using namespace std; int ma ...

  2. VMware上安装MS-DOS 6.22之一:基本系统的安装

    在网上看了一遍,发现关于在VMware上安装DOS的教程比较少,并且还有很多人发问怎么在VMware上安装DOS.为了方便大家,我便把我实际安装DOS的步骤讲出来分享一下,当然这其中也参考了一些网上资 ...

  3. PHP学习1 — PHP文件处理

    PHP 中 include 与 require  Php include (或 require)语句会获取指定文件中存在的所有文本/代码/标记,并复制到使用 include 语句的文件中. 这意味着您 ...

  4. HTML移动端开发常见的兼容性总结

    1.安卓浏览器看背景图片,有些设备会模糊.用同等比例的图片在PC机上很清楚,但是手机上很模糊,原因是什么呢?经过研究,是devicePixelRatio作怪,因为手机分辨率太小,如果按照分辨率来显示网 ...

  5. Java中byte与16进制字符串的互换原理

    我们都知道Java中的byte是由8个bit组成的,而16进制即16中状态,它是由4个bit来表示的,因为24=16.所以我们可以把一个byte转换成两个用16进制字符,即把高4位和低4位转换成相应的 ...

  6. BUG,带给我的思考

    今天打开EverNote时,翻到了四年前在anjuke时做的一些bug分析总结.现在回过头看看也是有些价值所在,挑选出部分bug分享,希望能有所启发. 一. iOS新房APP4.4由于在91市场进行试 ...

  7. 入坑系列之HAProxy负载均衡

    在大型系统设计中用代理在负载均衡是最常见的一种方式,而相对靠谱的解决方案中Nginx.HAProxy.LVS.F5在各大场中用得比较普遍,各有各的优势和使用场景,由于本次要使用到TCP,因此Nginx ...

  8. 3314: [Usaco2013 Nov]Crowded Cows

    3314: [Usaco2013 Nov]Crowded Cows Time Limit: 1 Sec  Memory Limit: 128 MBSubmit: 111  Solved: 79[Sub ...

  9. 1619: [Usaco2008 Nov]Guarding the Farm 保卫牧场

    1619: [Usaco2008 Nov]Guarding the Farm 保卫牧场 Time Limit: 5 Sec  Memory Limit: 64 MBSubmit: 498  Solve ...

  10. ajax上传图片

    选择文件后 ajax上传图片到后台,后台执行保存操作,返回上传的图片路径,显示到页面 需要引入ajaxfileupload.js js代码 <script type="text/jav ...