ivaneeo's blog

自由的力量,自由的生活。

  BlogJava :: 首页 :: 联系 :: 聚合  :: 管理
  669 Posts :: 0 Stories :: 64 Comments :: 0 Trackbacks

2011年6月9日 #

curl -s https://packagecloud.io/install/repositories/rabbitmq/rabbitmq-server/script.rpm.sh | sudo bash

rabbitmq.config 

[{rabbit, [{cluster_partition_handling, autoheal},{loopback_users, []}]}].

posted @ 2015-07-03 20:25 ivaneeo 阅读(1957) | 评论 (0)编辑 收藏

#!/bin/sh

#

# Startup script for ovirt-agent

#

# chkconfig: 2345 85 20

# description: ovirt-agent

# processname: ovirt-agent

# pidfile: /var/run/tomcat.pid # config:# Source function library.

. /etc/rc.d/init.d/functions

# Source networking configuration.

. /etc/sysconfig/network

# Check that networking is up.

export OVIRT_AGENT_HOME=/opt/ovirt-agent

[ -f $OVIRT_AGENT_HOME/bin/startServer.sh ] ||?exit 0 [ -f $OVIRT_AGENT_HOME/bin/stopServer.sh ] ||?exit 0

# See how we were called.

case "$1" in

start)

# Start daemon.

        echo ?"Starting OVirt-agent: "

        $OVIRT_AGENT_HOME/bin/startServer.sh $OVIRT_AGENT_HOME/conf/ovirt-agent.xml

        touch /var/lock/subsys/ovirt-agent

;;

stop)

# Stop daemons.

        echo ?"Shutting down OVirt-agent: "

        $OVIRT_AGENT_HOME/bin/stopServer.sh

        rm -f /var/lock/subsys/ovirt-agent

;;

restart)

        $0 stop

        $0 start

;;

status)

status ovirt-agent

;;

*)

echo "Usage: $0 {start|stop|restart|status}"

exit 1

esac

exit 0

posted @ 2015-07-03 20:06 ivaneeo 阅读(1889) | 评论 (0)编辑 收藏

docker run -d --name="srdesktop1" -p 80:80 -p 8888:8888 -p 8000:8000 -p 8009:8009 -p 8081:8081 -p 3306:3306 -p 19:22 -v /opt/html:/var/www -v /opt/ssdb-master:/opt/ssdb-master -v /opt/apache-tomcat-7.0.53:/opt/apache-tomcat-7.0.53 -v /opt/mule-standalone-3.5.0:/opt/mule-standalone-3.5.0 -v /opt/mysql/data:/var/lib/mysql --privileged=true srdesktop/ubuntu /bin/bash  -exec 'echo -e "192.168.1.93 ovirt-manage\n192.168.1.243 www.engin.org\n127.0.0.1 localhost" >> /etc/hosts && service mysql start  && /etc/init.d/guaca start && rm /opt/ssdb-master/var/ssdb.pid && /opt/ssdb-master/ssdb-server  -d /opt/ssdb-master/ssdb.conf && export JAVA_HOME=/opt/jdk1.7.0_51 && export PATH=$JAVA_HOME/bin:$PATH && /opt/apache-tomcat-7.0.53/bin/startup.sh && service apache2 start && /opt/mule-standalone-3.5.0/bin/mule'


pptpsetup --create myvpn --server www.yanlingyi.com --username vpn --password mincloud --encrypt --start


docker run -d --name="rabbitmq_master" -p 200:22 -p 25672:25672 -p 15672:15672 -p 5672:5672 -p 4369:4369 -p 10051:10050 rabbitmq/ubuntu /bin/bash -exec 'echo -e "172.20.20.10 rabbitmq-master\n127.0.0.1 localhost" > /etc/hosts && /etc/init.d/rabbitmq-server start && /usr/sbin/sshd -D'


# Generated by ovirt-engine installer
#filtering rules
*filter
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
-A INPUT -i lo -j ACCEPT
-A INPUT -p icmp -m icmp --icmp-type any -j ACCEPT
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
#drop all rule
COMMIT

posted @ 2015-06-13 15:09 ivaneeo 阅读(1113) | 评论 (0)编辑 收藏

http://www.cocoachina.com/ios/20150417/11595.html
posted @ 2015-05-02 01:29 ivaneeo 阅读(948) | 评论 (0)编辑 收藏

https://www.igreenjsq.info/user-xianlu.html
posted @ 2015-04-29 19:12 ivaneeo 阅读(1315) | 评论 (0)编辑 收藏

http://www.csdn.net/article/2014-01-02/2817984-13-tools-let-hadoop-fly
好用的数据工具
http://blog.itpub.net/7816530/viewspace-1119924/
posted @ 2015-04-25 14:08 ivaneeo 阅读(946) | 评论 (0)编辑 收藏

netsh interface ipv4 show subinterfaces

netsh interface ipv4 set subinterface "本地连接" mtu=1480 store=persistent
posted @ 2015-04-25 13:01 ivaneeo 阅读(830) | 评论 (0)编辑 收藏

http://www.ovirt.org/Java-sdk
posted @ 2015-04-21 17:23 ivaneeo 阅读(829) | 评论 (0)编辑 收藏

http://m.blog.csdn.net/blog/ebay/43529401
posted @ 2015-04-15 04:49 ivaneeo 阅读(913) | 评论 (0)编辑 收藏

So now you have:

  • The elapsed wall clock time (this period's time, minus last period's time) Call this X
  • The elapsed process cpu time (this period's time, minus last period's time) Call this Y
  • The number of CPUs. Call this C

The percent utilization will be Y / (X x C) * 100

import java.lang.management.*;
import java.util.concurrent.*;

osx = ManagementFactory.getOperatingSystemMXBean();
cores = osx.getAvailableProcessors(); // Factorial to keep the process busy so we can see some actual activity
factorial = { n -> int fact = 1; int i = 1; while(i <= n) { i++; fact *= i; } return fact; }
long elapsedTime = -1, startTime = -1; long elapsedCpu = -1, startCpu = -1;;
for(i in 0..20) { startTime = System.nanoTime(); startCpu = osx.getProcessCpuTime(); CountDownLatch latch = new CountDownLatch(cores); for(x in 1..cores) { Thread.startDaemon() { factorial(1000000); latch.countDown(); } } latch.await(); elapsedTime = System.nanoTime()-startTime; elapsedCpu = osx.getProcessCpuTime()-startCpu; percUsage = (elapsedCpu / (elapsedTime* cores)) *100; println "Percent Usage:$percUsage %"; }
posted @ 2015-04-06 15:44 ivaneeo 阅读(1379) | 评论 (0)编辑 收藏

http://www.linuxidc.com/Linux/2014-08/105422.htm
posted @ 2015-04-03 04:47 ivaneeo 阅读(596) | 评论 (0)编辑 收藏

http://www.tuicool.com/articles/amQNvuq
posted @ 2015-04-03 04:34 ivaneeo 阅读(684) | 评论 (0)编辑 收藏

http://www.ibm.com/developerworks/cn/java/j-quartz/index.html
posted @ 2015-04-03 04:28 ivaneeo 阅读(487) | 评论 (0)编辑 收藏

运行yum makecache生成缓存

eple源:

rpm -Uvh http://ftp.sjtu.edu.cn/fedora/epel/6/i386/epel-release-6-8.noarch.rpm

docker 安装:

You will need RHEL 6.5 or higher, with a RHEL 6 kernel version 2.6.32-431 or higher as this has specific kernel fixes to allow Docker to work.

CentOS 6.5已经是2.6.32-431内核了,所以最好安装这个版本。

yum -y install docker-io
升级:
yum -y update docker-io

手动升级:

wget https://get.docker.io/builds/Linux/x86_64/docker-latest -O docker mv -f docker /usr/bin/docker 

升级完成

启动:

service docker start

开机启动:

chkconfig docker on
posted @ 2015-04-02 12:41 ivaneeo 阅读(492) | 评论 (0)编辑 收藏

http://blog.fens.me/vpn-pptp-client-ubuntu/

 ip route add 192.168.20.0/24 via 192.168.20.1 dev ppp0

http://blog.163.com/monk...popo/blog/static/208680220111014101233949/
posted @ 2015-03-28 17:48 ivaneeo 阅读(406) | 评论 (0)编辑 收藏

http://docs.docker.com/articles/host_integration/
posted @ 2015-03-28 10:31 ivaneeo 阅读(528) | 评论 (0)编辑 收藏

172.20.20.8 mysql-mm1
172.20.20.11 mysql-mm2
172.20.20.10 mysql-data1
172.20.20.9 mysql-data2
172.20.20.10 mysql-sql1
172.20.20.9 mysql-sql2


mysql-mm1:
  docker run -d --name="mysql_mm1" --net=host -v /opt/mysql:/usr/local/mysql mysql_mm/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && ndb_mgmd -f /usr/local/mysql/data/mysql-cluster/config.ini && /usr/sbin/sshd -D'
mysql-mm2:
  docker run -d --name="mysql_mm2" --net=host -v /opt/mysql:/usr/local/mysql mysql_mm/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && ndb_mgmd -f /usr/local/mysql/data/mysql-cluster/config.ini && zabbix_agentd && /usr/sbin/sshd -D'
mysql-data1:
  docker run -d --name="mysql_data1" --net=host -v /opt/mysql:/usr/local/mysql mysql_data/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && /usr/local/mysql/bin/ndbd && zabbix_agentd && /usr/sbin/sshd -D'
mysql-data2:
  docker run -d --name="mysql_data2" --net=host -v /opt/mysql:/usr/local/mysql mysql_data/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && /usr/local/mysql/bin/ndbd && zabbix_agentd && /usr/sbin/sshd -D'
mysql-sql1:
  docker run -d --name="mysql_sql1" --net=host -v /opt/mysql:/usr/local/mysql mysql_sql/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && /usr/local/mysql/bin/mysqld_safe --user=mysql'
mysql-sql2:
  docker run -d --name="mysql_sql2" --net=host -v /opt/mysql:/usr/local/mysql mysql_sql/ubuntu /bin/bash -exec 'echo -e "172.20.20.7 mysql-mm1\n172.20.20.10 mysql-mm2\n172.20.20.8 mysql-data1\n172.20.20.9 mysql-data2\n172.20.20.8 mysql-sql1\n172.20.20.9 mysql-sql2\n127.0.0.1 localhost" > /etc/hosts && /usr/local/mysql/bin/mysqld_safe --user=mysql'
haproxy && nginx: 
  docker run -d --name="loadbalancer_master" -p 8888:8888 -p 6080:6080 -p 8089:8089 -p 8774:8774 -p 9696:9696 -p 9292:9292 -p 8776:8776 -p 5000:5000 -p 8777:8777 -p 11211:11211 -p 11222:11222 -p 5672:5672 -p 35357:35357 -p 8181:2181 -p 10389:10389 -p 2222:22 -p 80:80 -p 1936:1936 -p 3306:3306 -p 10052:10052 -p 10051:10051 -p 8080:8080 -v /opt/etc/nginx/conf:/usr/local/nginx-1.0.6/conf -v /opt/etc/haproxy:/etc/haproxy loadbalancer/ubuntu /bin/bash -exec 'echo -e "127.0.0.1 localhost" > /etc/hosts && service haproxy start && /usr/local/nginx-1.0.6/sbin/nginx && zabbix_agentd && /usr/sbin/sshd -D'
redis_master:  
  docker run -d --name="redis_master" -p 18:22 -p 6379:6379 -p 6380:6380 redis_master/ubuntu /bin/bash -exec '/usr/local/webserver/redis/start.sh && /usr/sbin/sshd -D'
redis_slave: 
  docker run -d --name="redis_slave1" -p 18:22 -p 6379:6379 -p 6380:6380 redis_slave/ubuntu /bin/bash -exec 'echo -e "172.20.20.10 redis-master\n127.0.0.1 localhost" > /etc/hosts && /usr/local/webserver/redis/start.sh && /usr/sbin/sshd -D' 

rabbitmq:        
  docker run -d --name="rabbitmq_master" -p 2222:22 -p 25672:25672 -p 15672:15672 -p 5672:5672 -p 4369:4369 -p 10051:10050 rabbitmq/ubuntu /bin/bash -exec 'echo -e "172.20.20.10 rabbitmq-master\n127.0.0.1 localhost" > /etc/hosts && /etc/init.d/rabbitmq-server start && /usr/sbin/sshd -D'
 
mule:
  docker run -d --name="mule1" -p 5005:5005 -p 2222:22 -p 9999:9999 -p 9003:9003 -p 9000:9000 -p 9001:9001 -p 9004:9004 -v /opt/mule:/opt/mule-standalone-3.5.0_cloud mule/ubuntu /bin/bash -exec 'echo -e "192.168.1.180 lb-master\n192.168.1.180 controller-node\n127.0.0.1 localhost" >> /etc/hosts && /usr/sbin/sshd && export JAVA_HOME=/opt/jdk1.7.0_51 && export PATH=$JAVA_HOME/bin:$PATH && /opt/mule-standalone-3.5.0_cloud/bin/mule'


zentao:

  docker run -d --name="zentao" -p 22222:22 -p 10008:80 -v /opt/www/html/zentaopms:/opt/zentao --privileged=true zentao/ubuntu /bin/bash -exec 'service apache2 start && /usr/sbin/sshd -D'

websocket-tomcat:
  docker run -d --name="websocket_tomcat1" -p 8888:8080 -p 2222:22 -v /opt/apache-tomcat-8.0.15:/opt/apache-tomcat websocket-tomcat/ubuntu /bin/bash -exec 'echo -e "192.168.1.180 lb-master\n127.0.0.1 localhost" > /etc/hosts && export JAVA_HOME=/opt/jdk1.7.0_51 && /opt/apache-tomcat/bin/startup.sh && /usr/sbin/sshd -D'

 docker run -d --name="guacamole1" -p 8088:8088 -p 38:22 -v /opt/apache-tomcat-7.0.53:/opt/apache-tomcat guacamole/ubuntu /bin/bash -exec 'echo -e "192.168.1.150 lb-master\n127.0.0.1 localhost" > /etc/hosts && /etc/init.d/guacd start && /opt/apache-tomcat/bin/start-tomcat.sh && /usr/sbin/sshd -D'
posted @ 2015-03-27 18:48 ivaneeo 阅读(896) | 评论 (0)编辑 收藏

http://www.docin.com/p-558099649.html
posted @ 2015-03-27 16:43 ivaneeo 阅读(423) | 评论 (0)编辑 收藏

ステップ1 /etc/yum.repos.d/virt7-testing.repo というファイルを作ります。

/etc/yum.repos.d/virt7-testing.repo
[virt7-testing] name=virt7-testing baseurl=http://cbs.centos.org/repos/virt7-testing/x86_64/os/ enabled=0  gpgcheck=0 

ステップ2 インストールします。

sudo yum --enablerepo=virt7-testing install docker 

確認します。

$ docker --version Docker version 1.5.0, build a8a31ef/1.5.0 

やったーー!!

※ご利用は自己責任でお願いします。

http://billpaxtonwasright.com/installing-docker-1-5-0-on-centos-7/

posted @ 2015-03-26 23:32 ivaneeo 阅读(670) | 评论 (0)编辑 收藏

在虚拟机的配置文件中增加:

<input type=’tablet’ bus=’usb’/>
(该句位于<devices>配置中)


Linux:


在终端中输入:

xset -m 0

 

Windows:

进入控制面板 -> 鼠标 -> 指针选项,去掉“提高指针精确度”前面的勾。

posted @ 2015-03-23 20:49 ivaneeo 阅读(758) | 评论 (0)编辑 收藏

http://docs.openstack.org/image-guide/content/virt-install.html
posted @ 2015-03-22 23:16 ivaneeo 阅读(450) | 评论 (0)编辑 收藏

http://blog.csdn.net/hackerain/article/details/38172941
posted @ 2015-03-17 18:13 ivaneeo 阅读(459) | 评论 (0)编辑 收藏

http://blog.csdn.net/anhuidelinger/article/details/9818693
posted @ 2015-03-13 19:32 ivaneeo 阅读(440) | 评论 (0)编辑 收藏

https://docs.docker.com/installation/ubuntulinux/#ubuntu-trusty-1404-lts-64-bit
posted @ 2015-03-02 16:21 ivaneeo 阅读(673) | 评论 (0)编辑 收藏

http://www.mimaku5.com/
posted @ 2015-02-27 16:33 ivaneeo 阅读(4308) | 评论 (0)编辑 收藏

http://my.oschina.net/guol/blog/271416
posted @ 2015-02-14 14:29 ivaneeo 阅读(731) | 评论 (0)编辑 收藏

http://www.tuicool.com/articles/RrmAru
posted @ 2015-02-07 03:37 ivaneeo 阅读(690) | 评论 (0)编辑 收藏

http://www.elesos.com/index.php?title=Nginx%E6%90%AD%E5%BB%BAHTTPS%E6%9C%8D%E5%8A%A1%E5%99%A8
posted @ 2015-02-06 14:54 ivaneeo 阅读(683) | 评论 (0)编辑 收藏

<?xml version="1.0" encoding="UTF-8"?>
<mule xmlns:amqp="http://www.mulesoft.org/schema/mule/amqp" xmlns="http://www.mulesoft.org/schema/mule/core" xmlns:doc="http://www.mulesoft.org/schema/mule/documentation"
xmlns:spring="http://www.springframework.org/schema/beans" version="EE-3.5.2"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-current.xsd
http://www.mulesoft.org/schema/mule/core http://www.mulesoft.org/schema/mule/core/current/mule.xsd
http://www.mulesoft.org/schema/mule/amqp http://www.mulesoft.org/schema/mule/amqp/current/mule-amqp.xsd">
    <amqp:connector name="AMQP_Connector" validateConnections="true" host="192.168.199.21" doc:name="AMQP Connector"/>
    <amqp:endpoint exchangeName="test" queueName="test_queue" exchangeType="direct" name="AMQP" responseTimeout="10000" doc:name="AMQP" queueDurable="true"/>
    <flow name="testFlow1" doc:name="testFlow1">
        <amqp:inbound-endpoint responseTimeout="10000" exchange-pattern="request-response" connector-ref="AMQP_Connector" ref="AMQP" doc:name="AMQP"/>
       <byte-array-to-string-transformer doc:name="Transform bytearray message to String"/>
        <logger message="I recived a direct message from AMQP: #[payload]" level="INFO" doc:name="Logger"/>
    </flow>
</mule>
posted @ 2015-02-03 02:20 ivaneeo 阅读(960) | 评论 (0)编辑 收藏

[{rabbit, [{cluster_partition_handling, autoheal},{loopback_users, []}]}].

posted @ 2015-01-16 18:24 ivaneeo 阅读(5076) | 评论 (0)编辑 收藏

http://rhomobi.com/topics/49

nginx为了实现反向代理的需求而增加了一个ngx_http_proxy_module模块。其中proxy_set_header指令就是该模块需要读取的配置文件。在这里,所有设置的值的含义和http请求同中的含义完全相同,除了Host外还有X-Forward-For。
Host的含义是表明请求的主机名,因为nginx作为反向代理使用,而如果后端真是的服务器设置有类似防盗链或者根据http请求头中的host字段来进行路由或判断功能的话,如果反向代理层的nginx不重写请求头中的host字段,将会导致请求失败【默认反向代理服务器会向后端真实服务器发送请求,并且请求头中的host字段应为proxy_pass指令设置的服务器】。
同理,X_Forward_For字段表示该条http请求是有谁发起的?如果反向代理服务器不重写该请求头的话,那么后端真实服务器在处理时会认为所有的请求都来在反向代理服务器,如果后端有防攻击策略的话,那么机器就被封掉了。因此,在配置用作反向代理的nginx中一般会增加两条配置,修改http的请求头:
proxy_set_header Host $http_host;
proxy_set_header X-Forward-For $remote_addr;

这里的$http_host和$remote_addr都是nginx的导出变量,可以再配置文件中直接使用。如果Host请求头部没有出现在请求头中,则$http_host值为空,但是$host值为主域名。因此,一般而言,会用$host代替$http_host变量,从而避免http请求中丢失Host头部的情况下Host不被重写的失误。
posted @ 2015-01-06 22:24 ivaneeo 阅读(760) | 评论 (0)编辑 收藏

http://jasig.github.io/cas/4.0.x/protocol/OAuth-Protocol.html

http://www.tuicool.com/articles/VrERzy

http://www.tuicool.com/articles/Ar2EBz
posted @ 2015-01-05 02:06 ivaneeo 阅读(727) | 评论 (0)编辑 收藏

http://www.mulesoft.org/documentation/display/current/Creating+an+OAuth+2.0a+Web+Service+Provider
posted @ 2015-01-04 22:29 ivaneeo 阅读(626) | 评论 (0)编辑 收藏

http://zh.wikipedia.org/wiki/%E9%A2%84%E5%86%99%E5%BC%8F%E6%97%A5%E5%BF%97
http://zookeeper.apache.org/doc/r3.3.6/bookkeeperStarted.html
http://zookeeper.apache.org/bookkeeper/docs/r4.0.0/bookkeeperProgrammer.html
http://zookeeper.apache.org/bookkeeper/docs/r4.0.0/apidocs/index.html?org/apache/bookkeeper/client/BookKeeper.html
posted @ 2014-12-31 23:38 ivaneeo 阅读(667) | 评论 (0)编辑 收藏

http://nileader.blog.51cto.com/1381108/932156
posted @ 2014-12-31 22:27 ivaneeo 阅读(864) | 评论 (0)编辑 收藏

http://ssdb.io/docs/ssdb-cli.html
posted @ 2014-12-30 22:49 ivaneeo 阅读(5517) | 评论 (0)编辑 收藏

对于防火墙的选择:
  http://blog.sina.com.cn/s/blog_92dc41ea0101j5l1.html
  http://www.lupaworld.com/article-218506-1.html

 openvpn:
  http://grantcurell.com/2014/07/22/setting-up-a-vpn-server-on-ubuntu-14-04/

pfsense防火墙:
  http://www.docin.com/p-88103814.html

ssl vpn:openvpn

ipsec:sprongswan

代理服务器:squid

stunnel:tcp加密


Panabit流控引擎
http://www.panabit.com/html/product/std/2014/0924/86.html
Panabit标准版是目前国内开放度最高、免费、专业的应用层流量管理系统,特别针对P2P应用的识别与控制,截止2009年03月25日,已经支持实际主流应用240种以上,并以两周更新一次特征库的速度持续更新(包括已支持协议和新增协议两方面的更新,Panabit支持协议列表请关注Panabit网站首页"支持协议")。Panabit在精确识别协议即对应用分类的基础上,根据用户自定义策略,提供灵活方便的流量管理机制:带宽限速、带宽保证、带宽预留,并可基于协议/协议组、IP/IP组进行参数化的策略设置。Panabit采用创新的"节点跟踪"技术与"加密协议深度识别"技术提高识别效率和准确度,如对使用加密协议的eMule、Skype等精确识别。Panabit区别于一些同类设备,在不能精确识别协议的情况下,限制客户端并发连接数非科学的做法,易造成误判或影响正常用户。Panabit是一款真正的应用层流控系统,能做限速控制;如果是疑似识别、不能准确定位具体应用的系统,是不敢做限速控制,起不到实际应用层流控效果。
posted @ 2014-12-28 00:30 ivaneeo 阅读(4588) | 评论 (0)编辑 收藏

root@proxzone-project-4:/usr/local/mysql/bin# ndb_mgm -e show

Connected to Management Server at: localhost:1186

Cluster Configuration

---------------------

[ndbd(NDB)] 2 node(s)

id=3 @172.21.21.108  (mysql-5.6.21 ndb-7.3.7, Nodegroup: 0)

id=4 @172.21.21.109  (mysql-5.6.21 ndb-7.3.7, Nodegroup: 0, *)


[ndb_mgmd(MGM)] 2 node(s)

id=1 @172.21.21.107  (mysql-5.6.21 ndb-7.3.7)

id=2 @172.21.21.110  (mysql-5.6.21 ndb-7.3.7)


[mysqld(API)] 2 node(s)

id=5 @172.21.21.108  (mysql-5.6.21 ndb-7.3.7)

id=6 @172.21.21.109  (mysql-5.6.21 ndb-7.3.7)

posted @ 2014-12-26 18:41 ivaneeo 阅读(4221) | 评论 (0)编辑 收藏

https://github.com/alfss/zabbix-rabbitmq
https://github.com/jasonmcintosh/rabbitmq-zabbix
posted @ 2014-12-25 22:49 ivaneeo 阅读(3653) | 评论 (0)编辑 收藏

#!/bin/bash
#written by lenwood
#mail:ccyhaoran@live.cn
diskarray=(`cat /proc/diskstats |grep -E "\bsd[abcdefg]\b|\bxvd[abcdefg]\b"|grep -i "\b$1\b"|awk '{print $3}'|sort|uniq   2>/dev/null`)
length=${#diskarray[@]}
printf "{\n"
printf  '\t'"\"data\":["
for ((i=0;i<$length;i++))
 do
         printf '\n\t\t{'
         printf "\"{#DISK_NAME}\":\"${diskarray[$i]}\"}"
         if [ $i -lt $[$length-1] ];then
                 printf ','
         fi
 done
printf  "\n\t]\n"
printf "}\n"
posted @ 2014-12-25 22:17 ivaneeo 阅读(3071) | 评论 (0)编辑 收藏

http://dev.mysql.com/doc/refman/5.1/en/create-tablespace.html
http://dev.mysql.com/doc/refman/5.1/en/mysql-cluster-disk-data-objects.html
posted @ 2014-12-23 21:04 ivaneeo 阅读(401) | 评论 (0)编辑 收藏

5.1.37-ndb-7.0.8a-cluster-gpl MySQL Cluster Server (GPL) 

create a table with tablespace set. 

* tablespace creation * 
CREATE TABLESPACE ts_1 ADD DATAFILE '/home/db/mysql-cluster/data/data_1.dat' USE LOGFILE GROUP lg_1 INITIAL_SIZE = 26843545600 ENGINE NDB; 
ALTER TABLESPACE ts_1 ADD DATAFILE '/home/db/mysql-cluster/data/data_2.dat' INITIAL_SIZE 26843545600 ENGINE NDB; 
ALTER TABLESPACE ts_1 ADD DATAFILE '/home/db/mysql-cluster/data/data_3.dat' INITIAL_SIZE 26843545600 ENGINE NDB; 
ALTER TABLESPACE ts_1 ADD DATAFILE '/home/db/mysql-cluster/data/data_4.dat' INITIAL_SIZE 26843545600 ENGINE NDB; 


* table creation * 
CREATE TABLE `TABLE` ( 
`A` date NOT NULL, 
`B` varchar(30) NOT NULL, 
`C` varchar(50) NOT NULL, 
`D` varchar(50) NOT NULL, 
`E` varchar(50) NOT NULL, 
`F` varchar(255) DEFAULT NULL 
) TABLESPACE ts_1 STORAGE DISK ENGINE=ndbcluster DEFAULT CHARSET=utf8 


PK, index generated without the table and insert the data(40G), 
I'm Using logs as the following index numbers are still high. (mgm log) 
The actual number of memory ndb also giving you an upward trend ... Why? 


2009-11-17 16:54:58 [MgmtSrvr] INFO -- Node 8: Index usage is 4%(30707 8K pages of total 655392) 
2009-11-17 16:55:25 [MgmtSrvr] INFO -- Node 8: Data usage is 8%(20603 32K pages of total 229376)
posted @ 2014-12-23 20:57 ivaneeo 阅读(552) | 评论 (0)编辑 收藏

1,不支持创建临时表(temporary tables);

2,创建索引和键的限制:

(1),在列上创建索引长度超过3072bytes会成功,但是只能使用索引的前3072bytes。并且会显示警告信息"specified key was too long,max key lenght is 3072 keys"

 

不支持的特征

1,在NDB创建create table时,一定要指定tablespace.

For NDB tables, beginning with MySQL Cluster NDB 6.2.5 and MySQL Cluster NDB 6.3.2, it is also possible to specify whether the column is stored on disk or in memory by using a STORAGE clause. STORAGE DISK causes the column to be stored on disk, and STORAGE MEMORY causes in-memory storage to be used. The CREATE TABLE statement used must still include a TABLESPACE clause:

mysql> CREATE TABLE t1 (
    ->     c1 INT STORAGE DISK,
    ->     c2 INT STORAGE MEMORY
    -> ) ENGINE NDB;
ERROR 1005 (HY000): Can't create table 'c.t1' (errno: 140)

mysql> CREATE TABLE t1 (
    ->     c1 INT STORAGE DISK,
    ->     c2 INT STORAGE MEMORY
    -> ) TABLESPACE ts_1 ENGINE NDB;
Query OK, 0 rows affected (1.06 sec)

 

//NDB参数解释  ---from 《mysql性能调优和架构设计》

1) [NDBD DEFAULT]中的配置项:
NoOfReplicas:定义在Cluster 环境中相同数据的分数,通俗一点来说就是每一份数据存放NoOfReplicas 份。如果希望能够冗余,那么至少设置为2(一般情况来说此参数值设置为2 就够了),最大只能设置为4。另外,NoOfReplicas 值得大小,实际上也就是nodegroup 大小的定义。NoOfReplicas 参数没有系统默认值,所以必须设定,而且只能设置在[NDBD DEFAULT]中,因为此数值在整个Cluster 集群中一个node group 中所有的NDBD 节点都需要一样。另外NoOfReplicas 的数目对整个Cluster 环境中NDB 节点数量有较大的影响,因为NDB 节点总数量是NoOfReplicas * 2 * node_group_num;DataDir:指定本地的pid 文件,trace 文件,日志文件以及错误日志子等存放的路径,无系统默认地址,所以必须设定;

DataMemory:设定用于存放数据和主键索引的内存段的大小。这个大小限制了能存放的数据的大小,因为ndb 存储引擎需属于内存数据库引擎,需要将所有的数据(包括索引)都load 到内存中。这个参数并不是一定需要设定的,但是默认值非常小(80M),只也就是说如果使用默认值,将只能存放很小的数据。参数设置需要带上单位,如512M,2G 等。另外,DataMemory 里面还会存放UNDO 相关的信息,所以,事务的大小和事务并发量也决定了DataMemory 的使用量,建议尽量使用小事务;


IndexMemory:设定用于存放索引(非主键)数据的内存段大小。和DataMemory类似,这个参数值的大小同样也会限制该节点能存放的数据的大小,因为索引的大小是随着数据量增长而增长的。参数设置也如DataMemory 一样需要单位。IndexMemory 默认大小为18M;实际上,一个NDB 节点能存放的数据量是会受到DataMemory 和IndexMemory 两个参数设置的约束,两者任何一个达到限制数量后,都无法再增加能存储的数据量。如果继续存入数据系统会报错“table is full”。

FileSystemPath:指定redo 日志,undo 日志,数据文件以及meta 数据等的存放位置,默认位置为DataDir 的设置,并且在ndbd 初始化的时候,参数所设定的文件夹必须存在。在第一次启动的时候,ndbd 进程会在所设定的文件夹下建立一个子文件夹叫ndb_id_fs,这里的id 为节点的ID 值,如节点id 为3 则文件夹名称为ndb_3_fs。当然,这个参数也不一定非得设置在[NDBD DEFAULT]参数组里面让所有节点的设置都一样(不过建议这样设置),还可以设置在[NDBD]参数组下为每一个节点单独设置自己的FileSystemPath值;

BackupDataDir:设置备份目录路径,默认为FileSystemPath/BACKUP。接下来的几个参数也是非常重要的,主要都是与并行事务数和其他一些并行限制有关的参数设置。
MaxNoOfConcurrentTransactions:设置在一个节点上面的最大并行事务数目,默认为4096,一般情况下来说是足够了的。这个参数值所有节点必须设置一样,所以一般都是设置在[NDBD DEFAULT]参数组下面;


MaxNoOfConcurrentOperations:设置同时能够被更新(或者锁定)的记录数量。一般来说可以设置为在整个集群中相同时间内可能被更新(或者锁定)的总记录数,除以NDB节点数,所得到的值。

MaxNoOfLocalOperations:此参数默认是MaxNoOfConcurrentOperations * 1.1的大小,也就是说,每个节点一般可以处理超过平均值的10%的操作记录数量。但是一般来说,MySQL 建议单独设置此参数而不要使用默认值,并且将此参数设置得更较大一些;

以下的三个参数主要是在一个事务中执行一条query 的时候临时用到存储(或者内存)的情况下所使用到的,所使用的存储信息会在事务结束(commit 或者rollback)的时候释放资源;

MaxNoOfConcurrentIndexOperations:这个参数和MaxNoOfConcurrentOperations参数比较类似,只不过所针对的是Index 的record 而已。其默认值为8192,对伊一般的系统来说都已经足够了,只有在事务并发非常非常大的系统上才有需要增加这个参数的设置。当然,此参数越大,系统运行时候为此而消耗的内存也会越大;

MaxNoOfFiredTriggers:触发唯一索引(hash index)操作的最大的操作数,这个操作数是影响索引的操作条目数,而不是操作的次数。系统默认值为4000,一般系统来说够用了。当然,如果系统并发事务非常高,而且涉及到索引的操作也非常多,自然也就需要提高这个参数值的设置了;

TransactionBufferMemory:这个buffer 值得设置主要是指定用于跟踪索引操作而使用的。主要是用来存储索引操作中涉及到的索引key 值和column 的实际信息。这这个参数的值一般来说也很少需要调整,因为实际系统中需要的这部分buffer 量非常小,虽然默认值只是1M,但是对于一般应用也已经足够了;

下面要介绍到的参数主要是在系统处理中做table scan 或者range scan 的时候使用的一些buffer 的相关设置,设置的恰当可以既节省内存又达到足够的性能要求。

MaxNoOfConcurrentScans:这个参数主要控制在Cluster 环境中并发的table scan和range scan 的总数量平均分配到每一个节点后的平均值。一般来说,每一个scan 都是通过并行的扫描所有的partition 来完成的,每一个partition 的扫描都会在该partition所在的节点上面使用一个scan record。所以,这个参数值得大小应该是“scan record”数目* 节点数目。参数默认大小为256,最大只能设置为500;


MaxNoOfLocalScans:和上面的这个参数相对应,只不过设置的是在本节点上面的并发table scan 和range scan 数量。如果在系统中有大量的并发而且一般都不使用并行的话,需要注意此参数的设置。默认为MaxNoOfConcurrentScans * node 数目;


BatchSizePerLocalScan:该参用于计算在Localscan(并发)过程中被锁住的记录数,文档上说明默认为64;

LongMessageBuffer:这个参数定义的是消息传递时候的buffer 大小,而这里的消息传递主要是内部信息传递以及节点与节点之间的信息传递。这个参数一般很少需要调整,默认大小为1MB 大小;

下面介绍一下与LOG 相关的参数配置说明,包括LOG level。这里的LOG level 有多种,从0 到15,也就是共16 种。如果设定为0,则表示不记录任何LOG。如果设置为最高level,也就是15,则表示所有的信息都会通过标准输出来记录LOG.由于这里的所有信息实际上都会传递到管理节点的cluster LOG 中,所以,一般来说,除了启动时候的LOG级别需要设置为1 之外,其他所有的LOG level 都只需要设置为0 就可以了。

NoOfFragmentLogFiles:这个参数实际上和Oracle 的redo LOG 的group 一样的。其实就是ndb 的redo LOG group 数目,这些redo LOG 用于存放ndb 引擎所做的所有需要变更数据的事情,以及各种checkpoint 信息等。默认值为8;


MaxNoOfSavedMessages:这个参数设定了可以保留的trace 文件(在节点crash的时候参数)的最大个数,文档上面说此参数默认值为25。

LogLevelStartup:设定启动ndb 节点时候需要记录的信息的级别(不同级别所记录的信息的详细程度不一样),默认级别为1;

LogLevelShutdown:设定关闭ndb 节点时候记录日志的信息的级别,默认为0;

LogLevelStatistic:这个参数是针对于统计相关的日志的,就像更新数量,插入数量,buffer 使用情况,主键数量等等统计信息。默认日志级别为0;

LogLevelCheckpoint:checkpoint 日志记录级别(包括local 和global 的),默认为0;


LogLevelNodeRestart:ndb 节点重启过程日志级别,默认为0;

LogLevelConnection:各节点之间连接相关日志记录的级别,默认0;


LogLevelError:在整个Cluster 中错误或者警告信息的日志记录级别,默认0;

LogLevelInfo:普通信息的日志记录级别,默认为0。这里再介绍几个用来作为LOG 记录时候需要用到的Buffer 相关参数,这些参数对于性能都有一定的影响。当然,如果节点运行在无盘模式下的话,则影响不大。


UndoIndexBuffer:undo index buffer 主要是用于存储主键hash 索引在变更之后产生的undo 信息的缓冲区。默认值为2M 大小,最小可以设置为1M,对于大多数应用来说,2M 的默认值是够的.当然,在更新非常频繁的应用里面,适当的调大此参数值对性能还是有一定帮助的。如果此参数太小,会报出677 错误:Index UNDO buffers overloaded;


UndoDataBuffer:和undo index buffer 类似,undo data buffer 主要是在数据发生变更的时候所需要的undo 信息的缓冲区。默认大小为16M,最小同样为1M。当这个参数值太小的时候,系统会报出如下的错误:Data UNDO buffers overloaded,错误号为891;



RedoBuffer:Redo buffer 是用redo LOG 信息的缓冲区,默认大小为8M,最小为1M。如果此buffer 太小,会报1221 错误:REDO LOG buffers overloaded.


此外,NDB 节点还有一些和metadata 以及内部控制相关的参数,但大部分参数都基本上不需要任何调整,所以就不做进一步介绍。如果有兴趣希望详细了解,可以根据MySQL官方的相关参考手册,手册上面都有较为详细的介绍。

3、SQL 节点相关配置说明
1) 和其他节点一样,先介绍一些适用于所有节点的[MySQLD DEFAULT]参数ArbitrationRank:这个参数在介绍管理节点的参数时候已经介绍过了,用于设定节点级别(主要是在多个节点在处理相关操作时候出现分歧时候设定裁定者)的。一般来说,所有的SQL 节点都应该设定为2;

ArbitrationDelay:默认为0,裁定者在开始裁定之前需要被delay 多久,单位为毫秒。一般不需要更改默认值。

BatchByteSize:在做全表扫描或者索引范围扫描的时候,每一次fatch 的数据量,默认为32KB;

BatchSize:类似BatchByteSize 参数,只不过BatchSize 所设定的是每一次fetch的record 数量,而不是物理总量,默认为64,最大为992(暂时还不知道这个值是基于什么理论而设定的)。在实际运行query 的过程中,fetch 的量受到BatchByteSize 和BatchSize两个参数的共同制约,二者取最小值;


MaxScanBatchSize:在Cluster 环境中,进行并行处理的情况下,所有节点的BatchSize 总和的最大值。默认值为256KB,最大值为16MB。

2) 每个节点独有的[MySQLD]参数组,仅有id 和hostname 参数需要配置,在之前各类节点均有介绍了,这里就不再累述。


转自http://www.cnblogs.com/alang85/archive/2011/11/18/2253900.html

posted @ 2014-12-23 20:09 ivaneeo 阅读(685) | 评论 (0)编辑 收藏

  • 一、循环插入数据时出现
      table is full

    二、在mgm>all report memoryusage 查看

    Node 2: Data usage is 22%(2305 32K pages of total 10240)

    使用率到最后98%以上这时出现啦table is full

    基于以上两种情况,其实是一种情况的我的解决方法是:

    根据硬件配置必须根据硬件配置修改my.cnf文件和config.ini文件

    1.config.ini
    [ndbd default]
    NoOfReplicas=2 
    MaxNoOfConcurrentOperations=10000
    DataMemory=320M
    IndexMemory=96M
    TimeBetweenWatchDogCheck=30000
    MaxNoOfOrderedIndexes=512

    2.my.cnf
    [mysqld]
    ndbcluster
    ndb-connectstring=124.95.137.12
    optimizer_switch=engine_condition_pushdown=off

    问题得以解决
    来源:http://www.greensoftcode.net/

posted @ 2014-12-23 20:07 ivaneeo 阅读(1338) | 评论 (0)编辑 收藏

http://www.blogjava.net/yongboy/archive/2013/12/12/407498.html

docker-registry:

http://www.cnblogs.com/xguo/p/3829329.html


ubuntu 14.04
http://www.tuicool.com/articles/b63uei

centos 6.5
http://blog.yourtion.com/ubuntu-install-docker.html
posted @ 2014-12-19 00:57 ivaneeo 阅读(2659) | 评论 (0)编辑 收藏

/etc/sysctl.conf

> > net.bridge.bridge-nf-call-iptables = 1 > 
> net.bridge.bridge-nf-call-ip6tables = 0 > 
> net.bridge.bridge-nf-call-arptables = 1

xe-switch-network-backend bridge

REBOOT
posted @ 2014-12-17 14:54 ivaneeo 阅读(2350) | 评论 (0)编辑 收藏

http://www.chenshake.com/install-on-ubuntu-12-04-open-vswitch/

http://docs.cloudstack.apache.org/projects/cloudstack-installation/en/latest/hypervisor/kvm.html#install-and-configure-the-agent

tip:

添加网桥

使用openvswitch建立网桥,kvm使用,命令如下:

建立网桥br

#ovs-vsctl add-br br0

把eth0(物理机上网的网卡)添加到br0

#ovs-vsctl add-port br0 eth0

如果不出意外的话现在机器就不能上网了,可以按照以下方法解决

删除eth0的配置

#ifconfig eth0 0

为br0分配ip

#dhclient br0

因为我使用的是dhcp获取ip的,所以执行了此命令,如果你的ip是自己手动配置的,请把eth0的配置写到br0上。

posted @ 2014-12-16 00:01 ivaneeo 阅读(387) | 评论 (0)编辑 收藏

https://joshuarogers.net/installing-cloudstack-43-ubuntu-1404

iso:
http://www.tuicool.com/articles/FnYFF32
posted @ 2014-12-15 19:00 ivaneeo 阅读(438) | 评论 (0)编辑 收藏

  MD5Digest dig = new 

MD5Digest(); 

byte[] bytes = "111111".getBytes(); 

dig.update(bytes, 0, bytes.length); 

byte[] md5 = new byte[dig.getDigestSize()]; 

dig.doFinal(md5, 0);

System.out.println(new String(Base64.encode(md5)));

posted @ 2014-12-08 11:08 ivaneeo 阅读(274) | 评论 (0)编辑 收藏

http://www.jolokia.org/download.html

tomcat jmx http://blog.csdn.net/diy8187/article/details/4369137

统计  http://blog.csdn.net/blog4j/article/details/17122061
http://www.myexception.cn/software-architecture-design/410583.html
posted @ 2014-12-06 00:53 ivaneeo 阅读(2087) | 评论 (0)编辑 收藏

http://ma.ttias.be/advanced-monitoring-haproxy-with-zabbix-agent/
posted @ 2014-12-04 23:17 ivaneeo 阅读(1942) | 评论 (0)编辑 收藏

https://www.zabbix.org/wiki/File:Template_JMX_Tomcat-2.2.0.xml
http://blog.chinaunix.net/uid-29179844-id-4093754.html
posted @ 2014-12-04 21:32 ivaneeo 阅读(334) | 评论 (0)编辑 收藏

http://blog.sina.com.cn/s/blog_62079f6201019itr.html
posted @ 2014-12-03 23:25 ivaneeo 阅读(1964) | 评论 (0)编辑 收藏

location / {     proxy_pass http://127.0.0.1:9999;     proxy_connect_timeout 60;     proxy_set_header Host $host;     proxy_set_header X-Real-IP $remote_addr;     proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;     proxy_set_header X-NginX-Proxy true;      # 下面是关键     proxy_http_version 1.1;     proxy_set_header Upgrade $http_upgrade;     proxy_set_header Connection "upgrade";     # 这是配置webpysessoin丢失的问题     fastcgi_param  SCRIPT_NAME        ""; }
http://nginx.org/en/docs/http/websocket.html

posted @ 2014-11-24 21:19 ivaneeo 阅读(1356) | 评论 (0)编辑 收藏

------------------------------------lic-------------------------------------

*u3-7QAAAAIAAAABAAAAAgAKcHVibGljY2VydAAAAUjuvYiDAAVYLjUwOQAAAzQwggMwMIIC7qAD

AgECAgQnLAd6MAsGByqGSM44BAMFADBqMQswCQYDVQQGEwJDTjEQMA4GA1UECBMHYmVpamluZzEQ

MA4GA1UEBxMHYmVpamluZzERMA8GA1UEChMIcHJveHpvbmUxETAPBgNVBAsTCHByb3h6b25lMREw

DwYDVQQDEwhwcm94em9uZTAeFw0xNDEwMDgwNzUxMTFaFw0yNDEwMDUwNzUxMTFaMGoxCzAJBgNV

BAYTAkNOMRAwDgYDVQQIEwdiZWlqaW5nMRAwDgYDVQQHEwdiZWlqaW5nMREwDwYDVQQKEwhwcm94

em9uZTERMA8GA1UECxMIcHJveHpvbmUxETAPBgNVBAMTCHByb3h6b25lMIIBtzCCASwGByqGSM44

BAEwggEfAoGBAP1*U4EddRIpUt9KnC7s5Of2EbdSPO9EAMMeP4C2USZpRV1AIlH7WT2NWPq*xfW6

MPbLm1Vs14E7gB00b*JmYLdrmVClpJ-f6AR7ECLCT7up1*63xhv4O1fnxqimFQ8E-4P208UewwI1

VBNaFpEy9nXzrith1yrv8iIDGZ3RSAHHAhUAl2BQjxUjC8yykrmCouuEC*BYHPUCgYEA9-Gghdab

Pd7LvKtcNrhXuXmUr7v6OuqC-VdMCz0HgmdRWVeOutRZT-ZxBxCBgLRJFnEj6EwoFhO3zwkyjMim

4TwWeotUfI0o4KOuHiuzpnWRbqN*C*ohNWLx-2J6ASQ7zKTxvqhRkImog9*hWuWfBpKLZl6Ae1Ul

ZAFMO*7PSSoDgYQAAoGAR-WVUpxcibqSXpi4VHPXIEoiBCu9Ik8AHItVuevHmPqsOLB5ZXbC2qbN

oIVaJyhLntmeCS6M3ZOPWzHdNqcYdA1Rt9nNYQNpHgaMdHJo-w-ueUCDoo7-L2ho6c59P604f7IA

qmjfSnSWdB5OZlQebi23d96awCLTS0bQkN1k0w2jITAfMB0GA1UdDgQWBBS4wsh7wxLuDzvl1gxL

2oA9AevomTALBgcqhkjOOAQDBQADLwAwLAIUSGuB1IXVBwg0VcHn2iBzAjdMUxQCFCUNoYiFqGE7

Qbx9r-jA9BpDOyuDq5iw6uBl83BChP5kQrBpVLJxZbs=

----------------------------------------------------------------------------

GgYqeio1TiUuLqb1kOvqbpAyOV-CXGt7KCibUH*icgfcehQjhsIHNgisDDDt7AZAeZptrTYf56ky

xrzMEkPdoMMoFQGV*9kEXoab6awrAXP-GDcUAwOK7KS*q8-3O-UY7yjOaSMjR2QHszAgkLrFUuxt

onkCQa6EAriSiWdYu*7FGbTlQNAmiUTXilsnnWSCXyw7Hl6xP08kNbovUY4e31D-boaCdW-hQPQw

0XbDZJdT5ndCo4Mh-R4vu6gSmt*t3QJhp7pyeQeOR6VxpIJRFMUCwz2Ddrn0D160nQJ2fx2vchE-

Cz*vDkgQbCkFb7m9aBxKWztEZnATDwyYjyQmOXlcwO1ef4rdpxrBqpib9H5K1ddcQy6xkQdQXdvP

b-Jvq1Dmh*IKrayoqWQY09fdgEKAjmadF7xYKnEVL5nDwI9ZhtIlOrYktQ6q8NqCLd4wKolMTx8q

uOGWe-259-SGrSUNOp*-kgJXkWnqnRVs3do02XSWAsysixFJVSHNItePltdmBGimexVa1G8rV2dz

rSmPyCDlzF12SZKKYePDQOmaYM4EYiUL9Et271D9tv5SsvEzMZhwFiolb33peKztzz2tZ4lOZbXf

c-9sEPqhiOLYkDGqzxfnNyTjtTI4vz9WYqNjOe4SwOxsnHPkltb2evP4hyXru1CZNsm3w9dt1cHu

i6QMYgYz1ivHKoyZ0iAh8N*NtN7o0OAxptyaDv9v-SsqXljN4af0BdJOzwMzSS65B8f47poUH3X-

sKJIp797A5PTviXrCIwP126YWqPgUUHQ5LrsrsxKoQf6nTn7d*QAEQY5FIEoBtbmpq90KBVFVuZg

OKSawSAuJh7Vv2EK3QWS0lk31eRSXymI85ERboNNGbNmMwek*k02KCtlLP4kO2CNs5WF74Dwo732

wVAcdz3VXKt1bmk-

----------------------------------------------------------------------------

Z29kMzU3MXByb3h6b25lIQ==

posted @ 2014-11-22 23:21 ivaneeo 阅读(1174) | 评论 (0)编辑 收藏

Anypoint Connectors Update Site - http://repository.mulesoft.org/connectors/releases/3.5.0
Anypoint Addons Update Site - http://studio.mulesoft.org/r3/addons/beta
Anypoint Studio Update Site - http://studio.mulesoft.org/r3/updates
APIkit Update Site - http://studio.mulesoft.org/r3/apikit
mule - http://studio.mulesoft.org/3.5/plugin
Mule ESB Runtimes for Anypoint Studio - http://studio.mulesoft.org/r3/studio-runtimes/
mulesoft - http://www.mulesoft.org/documentation/display/current/Studio+Update+Sites
posted @ 2014-11-22 20:47 ivaneeo 阅读(1052) | 评论 (0)编辑 收藏

首先把我看到的有用的资料留下:

1、官方文档-基本用户手册:http://directory.apache.org/apacheds/basic-user-guide.html 主要介绍了安装以及基本操作、登录等。

2、官方文档-高级用户手册:http://directory.apache.org/apacheds/advanced-user-guide.html 介绍了代码编译、系统结构、服务配置以及服务权限管理,这里吐槽一下,真的很难懂,并且各种TODO;

3、看起来像官方的文档:http://joacim.breiler.com/apacheds/book.html 介绍得很详尽,例子也很丰富。

4、访问控制实例 FR20_ApacheDS_Access_Control_Administration_The_X.500_Way.pdf  

=============================================================================================================

常用的名词解析:

DIT  Directory Information Tree
AA administrative areas
AP administrative points

AAA autonomous administrative area 有自治权的管理区域,所有的实体均统一管理
SAA specific administrative area 特定管理区域
IAA  inner administrative area  内部管理区域

SAP specific administrative point
ACI Access Control Information

Usually an entry is selected as the administrative point and marked with an operational attribute. The attributeType of the operational attribute is 'administrativeRole'. 
通过添加一个可选属性来使一个实体成为管理点

ACSA access control specific area

=================================================================================================================

实战演练

需求:

1、LDAP超级管理员,管理LDAP上的所有数据;

2、匿名用户可以查看用户信息;

3、用户分为开发、测试和运维三组;

4、通过用户组授权

操作指南:

1、安装ApacheDS服务端;

  下载地址:apacheds-2.0.0-M15-64bit.bin 下载到目录/home/apacheds/

  1. chmod +x *.bin  
  1. /etc/init.d/apacheds-2.0.0-M15-default start  
这样就完成了ApacheDS的安装与启动

2、安装Apache Directory Studio

本次使用Eclipse插件,详见 http://directory.apache.org/studio/installation-in-eclipse.html,也支持Eclipse market安装。

3、连接与配置

切换到Eclipse的LDAP视图,新建连接

hostname:199.155.122.90 port:10389 encryption method: nocryption (不同加密算法端口注意)

authentication method: simple user:uid=admin,ou=system passwd:secret (默认的最高权限用户)

OpenConfiguration启用Access Control,禁用匿名登录

重启apacheds服务生效

4、分区设置

系统默认example分区,我们删除之,并新建,本次创建dc=xxx.com


5、新建ou=users,新建ou=groups。

  1. dn: ou=groups,dc=taotaosou.com  
  2. objectClass: organizationalUnit  
  3. objectClass: top  
  4. ou: groups  

  1. dn: ou=users,dc=taotaosou.com  
  2. objectClass: organizationalUnit  
  3. objectClass: top  
  4. ou: users  

6、根目录启用权限控制,添加administrativeRole属性是关键

  1. dn: dc=taotaosou.com  
  2. objectclass: domain  
  3. objectclass: top  
  4. dc: taotaosou.com  
  5. administrativeRole: accessControlSpecificArea  

7、添加匿名读权限

  1. dn: cn=enableAllUsersRead,dc=taotaosou.com  
  2. objectClass: subentry  
  3. objectClass: accessControlSubentry  
  4. objectClass: top  
  5. cn: enableAllUsersRead  
  6. prescriptiveACI: { identificationTag "enableAllUsersRead", precedence 0, aut  
  7.  henticationLevel none, itemOrUserFirst userFirst: { userClasses { allUsers   
  8.  }, userPermissions { { protectedItems { entry, allUserAttributeTypesAndValu  
  9.  es }, grantsAndDenials { grantCompare, grantFilterMatch, grantRead, grantRe  
  10.  turnDN, grantBrowse } } } } }  
  11. subtreeSpecification: { }  

8、添加用户自己修改资料权限

  1. dn: cn=allowSelfAccessAndModification,dc=taotaosou.com  
  2. objectClass: subentry  
  3. objectClass: accessControlSubentry  
  4. objectClass: top  
  5. cn: allowSelfAccessAndModification  
  6. prescriptiveACI: { identificationTag "allowSelfAccessAndModification", prece  
  7.  dence 10, authenticationLevel simple, itemOrUserFirst userFirst: { userClas  
  8.  ses { thisEntry }, userPermissions { { protectedItems { entry, allUserAttri  
  9.  buteTypesAndValues }, grantsAndDenials { grantRemove, grantExport, grantCom  
  10.  pare, grantImport, grantRead, grantFilterMatch, grantModify, grantInvoke, g  
  11.  rantDiscloseOnError, grantRename, grantReturnDN, grantBrowse, grantAdd } }   
  12.  } } }  
  13. subtreeSpecification: { }  

9、添加管理员权限

  1. dn: cn=enableAdminSuper,dc=taotaosou.com  
  2. objectClass: subentry  
  3. objectClass: accessControlSubentry  
  4. objectClass: top  
  5. cn: enableAdminSuper  
  6. prescriptiveACI: { identificationTag "enableAdminSuper", precedence 0, authe  
  7.  nticationLevel strong, itemOrUserFirst userFirst: { userClasses { userGroup  
  8.   { "cn=administrator,ou=gourp,dc=taotaosou.com" } }, userPermissions { { pr  
  9.  otectedItems { entry, allUserAttributeTypesAndValues }, grantsAndDenials {   
  10.  grantRemove, grantExport, grantCompare, grantImport, grantRead, grantFilter  
  11.  Match, grantModify, grantInvoke, grantDiscloseOnError, grantRename, grantRe  
  12.  turnDN, grantBrowse, grantAdd } } } } }  
  13. subtreeSpecification: { }  


    http://blog.csdn.net/lansine2005/article/details/19978411
posted @ 2014-11-22 00:00 ivaneeo 阅读(1636) | 评论 (0)编辑 收藏

http://www.ahcit.com/?p=1703
posted @ 2014-11-19 20:47 ivaneeo 阅读(721) | 评论 (0)编辑 收藏

http://redminecrm.com/pages/vmware_image
posted @ 2014-11-18 18:23 ivaneeo 阅读(1126) | 评论 (0)编辑 收藏

可重用性是Jakarta Commons项目的灵魂所在。这些包在设计阶段就已经考虑了可重用性问题。其中一些包,例如Commons里面用来记录日志的Logging包,最初是为其他项目设计的,例如Jakarta Struts项目,当人们发现这些包对于其他项目也非常有用,能够极大地帮助其他项目的开发,他们决定为这些包构造一个"公共"的存放位置,这就是Jakarta Commons项目。 

  为了真正提高可重用性,每一个包都必须不依赖于其他大型的框架或项目。因此,Commons项目的包基本上都是独立的,不仅是相对于其他项目的独立,而且相对于Commons内部的大部分其他包独立。虽然存在一些例外的情况,例如Betwixt包要用到XML API,但绝大部分只使用最基本的API,其主要目的就是要能够通过简单的接口方便地调用。 

  不过由于崇尚简洁,许多包的文档变得过于简陋,缺乏维护和支持,甚至有一部分还有错误的链接,文档也少得可怜。大部分的包需要我们自己去找出其用法,甚至有时还需要我们自己去分析其适用场合。本文将逐一介绍这些包,希望能够帮助你迅速掌握这一积累了许多人心血的免费代码库。 

  说明:Jakarta Commons和Apache Commons是不同的,后者是Apache Software Foundation的一个顶层项目,前者则是Jakarta项目的一个子项目,同是也是本文要讨论的主角。本文后面凡是提到Commons的地方都是指Jakarta的Commons。 

  为了便于说明,本文把Commons项目十八个成品级的组件(排除了EL、Latka和Jexl)分成5类,如下表所示 

 


commons分为3部分Commons Proper、Commons Sandbox和Commons Dormant 
Commons Proper:提供了设计良好可重用的java组件,并都经过了广泛、严格的测试。 
Commons Sandbox:处于实验、测试阶段的组件。 
Commons Dormant:处于停滞状态,从Sandbox退出的,不活跃的组件,谨慎使用。 
Commons Proper组件: 

Codec——包含一些通用的编码解码算法。包括一些语音编码器, Hex, Base64, 以及URL encoder。 
BeanUtils——提供对 Java 反射和自省API的包装,处理javabean的工具。 
Betwixt——将JavaBeans与XML相互转换。 
Digester——基于规则的XML文档解析,主要用于XML到Java对象的映射. 
Email——处理e-mail 
FileUpload——web应用中的文件上传组件 
IO——帮助进行IO功能开发 
JXPath——使用XPath语法操作javabean的工具。 
Lang——提供对java.lang包的扩展 


Chain——对Chain of Responsibility(责任链)设计模式的实现。使多个对象都有机会处理请求, 从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递请求,直到有一个对象处理它为止。 
CLI——处理命令行的命令的解析。 
Attributes—— 支持源代码级的元数据。 
Collections——扩展和增加标准的 Java Collection框架。 
Configuration——操作各种格式的配置文件。Properties文件 /XML文件 /JNDI /JDBC 数据源 /System properties /Applet parameters / Servlet parameters 
Daemon——创建类似unix守护线程的java代码,可以安全地执行一些后台操作,线程不被某个应用程序控制,而是由操作系统控制 类似windows的service,可以设置一个服务依赖于另一个服务,一个服务关闭前必须先执行另一个服务。 
DBCP——一个数据库连接池 
DbUtils——一个JDBC的工具类,比如可以将ResultSets生成javabean。 

Discovery——提供工具来定位资源 (包括类) ,通过使用各种模式来映射服务/引用名称和资源名称。 
EL——JSP 2.0引入的表达式 
HttpClient——使用HTTP协议的客户端开发框架 

Jelly——Jelly能够把XML转换成可执行代码,所以Jelly是一个基于XML与Java的脚本和处理引擎。 Jelly借鉴了JSP定指标签,Velocity, Cocoon和Xdoclet中的脚本引擎的许多优点。Jelly可以用在命令行,Ant或者Servlet之中。 
Jexl——Jexl是一个表达式语言,通过借鉴来自于Velocity的经验扩展了JSTL定义的表达式语言。   
Launcher——跨平台的java程序的启动 
Logging——提供的是一个日志(Log)接口(interface),同时兼顾轻量级和不依赖于具体的日志实现工具。 它提供给中间件/日志工具开发者一个简单的日志操作抽象,允许程序开发人员使用不同的具体日志实现工具。用户被假定已熟悉某种日志实现工具的更高级别的细节。JCL提供的接口,对其它一些日志工具,包括Log4J, Avalon LogKit, and JDK 1.4等,进行了简单的包装,此接口更接近于Log4J和LogKit的实现. 
Math——Math 是一个轻量的,自包含的数学和统计组件,解决了许多非常通用但没有及时出现在Java标准语言中的实践问题. 
Modeler—— 支持兼容JMX规范的MBeans开发。 
Net——集合了网络工具和协议工具的实现 
Pool——Commons-Pool 提供了通用对象池接口,一个用于创建模块化对象池的工具包,以及通常的对象池实现。 
Primitives——对java原始类型的支持。 
SCXML——处理SCXML 
Transaction——事务处理,实现了多层次锁、事务集合、事务文件的访问。  
Validator——提供了一个简单的,可扩展的框架来在一个XML文件中定义校验器 (校验方法)和校验规则。支持校验规则的和错误消息的国际化。 
VFS——访问各种文件系统,可以是本地文件、HTTP服务器上的文件、zip中的文件。 
Commons Sandbox组件: 

Compress——处理压缩文件如tar, zip 和 bzip2 格式。 
CSV——处理CSV文件 
Exec——安全地处理外部进程 
Finder——实现类似UNIX find命令的功能 
I18n——处理软件的I18n功能 
Id——生成id号功能 
Javaflow——捕捉程序运行状态 
JCI——java编译接口 
OpenPGP——处理加密方法OpenPGP.  
Pipeline——处理类似工作队列的管道工具 
Proxy——生成动态代理 
--------------------------------org.apache.commons.beanutils.PropertyUtils; 
copyProperties(a,b);//把相同类型b的属性赋值给a 
-------------------------------- 
在org.apache.commons包中提供了的一系列能简化一些编程过程中常见问题的共通函数和类,使程序员能把主要精力集中在 
构架,业务实现和优化而不是具体实现及验证上,一言以蔽之,它能使我们避免重复的发明车轮。 
posted @ 2014-11-17 00:22 ivaneeo 阅读(288) | 评论 (0)编辑 收藏

http://www.2cto.com/os/201309/243840.html
posted @ 2014-11-15 01:07 ivaneeo 阅读(763) | 评论 (0)编辑 收藏

http://www.cnblogs.com/xiaoerlang/p/3345236.html
posted @ 2014-11-14 21:09 ivaneeo 阅读(279) | 评论 (0)编辑 收藏

http://steven-wiki.readthedocs.org/en/latest/security/cas-tomcat/
http://wenku.baidu.com/view/13a57761783e0912a2162a94.html
restful:
http://jasig.github.io/cas/4.0.0/protocol/REST-Protocol.html
http://jasig.275507.n4.nabble.com/Setting-up-the-RESTlet-servlet-on-CAS-3-3-5-td2068602.html

posted @ 2014-11-13 17:45 ivaneeo 阅读(267) | 评论 (0)编辑 收藏

http://blog.e-works.net.cn/626381/articles/526568.html

http://www.oecp.cn/hi/wlo_o/blog/2160
posted @ 2014-10-29 13:07 ivaneeo 阅读(227) | 评论 (0)编辑 收藏

http://packetlife.net/blog/2011/apr/11/extracting-packets-large-captures/
posted @ 2014-10-17 12:24 ivaneeo 阅读(522) | 评论 (0)编辑 收藏

http://stackoverflow.com/questions/18833931/how-to-use-the-muleclient-request-for-async-amqp-rabbitmq-implementation-from-ja?rq=1
posted @ 2014-10-16 00:42 ivaneeo 阅读(531) | 评论 (0)编辑 收藏

http://www.mulesoft.org/documentation/display/current/Using+Spring+Beans+as+Flow+Components
posted @ 2014-09-30 02:52 ivaneeo 阅读(285) | 评论 (0)编辑 收藏

System.out.println("debug:"+Base64.class.getProtectionDomain().getCodeSource().getLocation());

posted @ 2014-09-26 16:38 ivaneeo 阅读(313) | 评论 (0)编辑 收藏

设置默认时区。当然你可以这样检查一下:

 

//--- 

System.out.println(TimeZone.getDefault()); //

输出当前默认时区

 

final TimeZone zone = TimeZone.getTimeZone("GMT+8"); //

获取中国时区

 

TimeZone.setDefault(zone); //

设置时区

 

System.out.println(TimeZone.getDefault()); //

输出验证

 

//--- 

 

除了上面的解决方法外,还可以:

 

TOMCAT

JAVA

运行参数添加

 -Duser.timezone=Asia/Shanghai 

或者,如果有启动的定时器或首次执行的代码,可以使用语句

 

System.setProperty("user.timezone","Asia/Shanghai"); 

来设置

 

但是为解决时区问题,

这样编码实在太烦,

所以你要知道如何从根本上解决问题:

tomcat的catalina.sh:
JAVA_OPTS="$JAVA_OPTS -Duser.timezone=Asia/Shanghai"

posted @ 2014-09-24 17:16 ivaneeo 阅读(3514) | 评论 (0)编辑 收藏

http://virtuallyhyper.com/2013/05/configure-haproxy-to-load-balance-sites-with-ssl/
posted @ 2014-08-17 01:52 ivaneeo 阅读(287) | 评论 (0)编辑 收藏

正常的网络连接中很少会出现多个包丢失的现象,每成功接收或转发100,000个数据包最多只会有几个包丢失(如图1)。在Linux虚拟机中,通过ifconfig命令可以很轻松地监控到这种状态。

  图1. 通常以太网卡是不会丢包的

  当虚拟机的网络在突发大量访问的情况下,可能会发生多个包丢失,这样就需要调整虚拟机的网络设置。首先,确认虚拟机使用了VMXNET3虚拟网 卡驱动。这样,在Linux宿主机的特定情况下,当大数据文件在高带宽的网络上传输时会发生多数据包丢失。关闭接收和转发校验总和可以解决这种情况。因为 校验总和的作用是停止错误包的发送,这样做会增加风险。考虑到以太网卡的错误率通常低于百万分之一,风险的级别并不高。

  使用Linux ethtool工具来关闭VMware网络设置中的接收和转发校验总和,在命令行窗口中以root账户登录ethtool。例如关闭网卡eth0的校验总 和命令如下:readethtool --offload eth0 rx off tx off;

  命令生效后,打开相应网卡的配置文件:

  /etc/sysconfig/network/ifcfg-eth0 ( SUSE) 或 /etc/sysconfig/network-scripts/ifcfg-eth0 (Red Hat )

  同时把ETHTOOL_OPTIONS参数变为ETHTOOL_OPTIONS='--offload eth0 rx off tx off'

  如果依然存在丢包问题,尝试用ethtool工具增加接收队列的缓冲区大小。默认情况下,缓存设为256,可以设置的最大值为4096。重新设置缓存大小为512,使用命令ethtool -G eth0 512。如果结果不理想,尝试更大的值。

  遇到Windows虚拟机的高丢包率就需要调整VMXNET3驱动的网络设置。在Device Manager中右键单击VMXNET3驱动并选择Properties。在Advanced页中有两个参数:Small RX Buffers和RX Ring #1 Size。适当增加这些参数的值然后测试能否有改善。逐步加大该值直到问题解决。

  多数情况下,这些设置可以降低虚拟机的丢包率。如果调整网络参数失败,或许就需要解决虚拟机其它的一些性能相关问题,而不是虚拟机和ESXi平 台之间的VMware网络设置。咨询宿主机OS 的相关专家,应该有很多可以调整性能的相关参数。当心更改了错误的参数可能会对虚拟机带来明显的负面影响。

posted @ 2014-07-15 22:53 ivaneeo 阅读(495) | 评论 (0)编辑 收藏

http://code4app.net/category/cocos2d
http://www.cocos2d-x.org/hub/all?category=5
http://blog.makeapp.co/
posted @ 2014-06-04 17:09 ivaneeo 阅读(288) | 评论 (0)编辑 收藏

http://ricston.com/blog/mule-image-hosting-raml-mulerequester/
posted @ 2014-05-28 23:32 ivaneeo 阅读(329) | 评论 (0)编辑 收藏

什么东西可以监控OpenStack呢?OpenStack对监控的需求起码有以下这些:

 

  • 不仅要能监控物理机,也能监控虚机
  • 监控信息也必须是tenant隔离的
  • 监控项的收集应该是自动地
  • 监控工具应该一般化以监控任何设备
  • 监控工具必须提供API

下面是监控工具的一般架构:

 

zhjk

 

网上搜索了一下,现在主流的监控工具有:Nagios, cacti, Zabbix, Muni, Zenoss。我不是做运维的对这些工具都不熟,以前不熟,现在也不熟。下面是一些理解,不一定准。

Nagios,最老牌了,比较通用的监控工具。特大的特点是报警。图形化功能一般般。一般要安装Agent,配置起来看网上的说法是比较复杂的,没用过,没实际发言权。

cacti,图形化功能不错,所以Nagios一般结合它来使用。

Zabbix,监控和图形化功能都还可以了,尤其有一本电子书 zabbix 1.8 network monitoring

Zenoss, 监控新贵,它使用无Agent的通用技术如SNMP和SSL来监控,部署起来会比较方便。尤其是Zenoss公司有人现在也加入OpenStack社区了,专门开发了一个OpenStack特有的扩展(

https://github.com/zenoss/ZenPacks.zenoss.OpenStack)不幸的是,目前只支持Nova API 1.1,且它只能收集单个tenant的数据,不利于rating和billing。

OpenStack Ceilometer工程主要监控的是tenant下虚机的数据,用来做billing的,物理机的监控支持不大好。

比较来比较去,如果是我,可能会做如下选型决定,不一定正确 :

Nagios 或者 Zenoss (视情况)

 

下面内容来自:http://docs.openstack.org/developer/ceilometer/, 我们看一下Ceilometer工程的现状, 架构如下:

 

zhjk2

 

运行OpenStack各组件的节点上一般有Agent来收集信息,收集后发给MQ,Ceilometer的Collector进程监控到数据之后存储到DB之中。从http://docs.openstack.org/developer/ceilometer/measurements.html 这页显示的监控项来看,目前Ceilometer监控来的数据主要来只是用来做billing的

 

文章来源:http://blog.csdn.net/quqi99/article/details/9400747
文章作者:张华 http://blog.csdn.net/quqi99

posted @ 2014-05-28 01:01 ivaneeo 阅读(434) | 评论 (0)编辑 收藏

使用truelicense实现用于JAVA工程license机制(包括license生成和验,有需要的朋友可以参考下。


开发的软件产品在交付使用的时候,往往会授权一段时间的试用期,这个时候license就派上用场了。不同于在代码中直接加上时间约束,需要重新授权的时候使用license可以避免修改源码,改动部署,授权方直接生成一个新的license发送给使用方替换掉原来的license文件即可。下面将讲述使用truelicense来实现license的生成和使用。Truelicense是一个开源的证书管理引擎,详细介绍见https://truelicense.java.net/

一、首先介绍下license授权机制的原理:

1、 生成密钥对,方法有很多。

2、 授权者保留私钥,使用私钥对包含授权信息(如使用截止日期,MAC地址等)的license进行数字签名。

3、 公钥给使用者(放在验证的代码中使用),用于验证license是否符合使用条件。

接下来是本例制作license的具体步骤:

二、第一步:使用keytool生成密钥对

以下命令在dos命令行执行,注意当前执行目录,最后生成的密钥对即在该目录下:

1、首先要用KeyTool工具来生成私匙库:(-alias别名 –validity 3650表示10年有效)

keytool -genkey -alias privatekey -keystoreprivateKeys.store -validity 3650

2、然后把私匙库内的公匙导出到一个文件当中:

keytool -export -alias privatekey -file certfile.cer -keystore privateKeys.store

3、然后再把这个证书文件导入到公匙库:

keytool -import -alias publiccert -file certfile.cer -keystore publicCerts.store

最后生成文件privateKeys.store、publicCerts.store拷贝出来备用。

三、第二步:生成证书(该部分代码由授权者独立保管执行)

1、 首先LicenseManagerHolder.java类:

package cn.melina.license; import de.schlichtherle.license.LicenseManager; import de.schlichtherle.license.LicenseParam;  /**  * LicenseManager??????  * @author melina  */ public class LicenseManagerHolder { 	 	private static LicenseManager licenseManager;   	public static synchronized LicenseManager getLicenseManager(LicenseParam licenseParams) {     	if (licenseManager == null) {     		licenseManager = new LicenseManager(licenseParams);     	}     	return licenseManager;     } } 

2、 然后是主要生成license的代码CreateLicense.java:

package cn.melina.license;  import java.io.File; import java.io.IOException; import java.io.InputStream; import java.text.DateFormat; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Properties; import java.util.prefs.Preferences; import javax.security.auth.x500.X500Principal; import de.schlichtherle.license.CipherParam; import de.schlichtherle.license.DefaultCipherParam; import de.schlichtherle.license.DefaultKeyStoreParam; import de.schlichtherle.license.DefaultLicenseParam; import de.schlichtherle.license.KeyStoreParam; import de.schlichtherle.license.LicenseContent; import de.schlichtherle.license.LicenseParam; import de.schlichtherle.license.LicenseManager;  /**  * CreateLicense  * @author melina  */ public class CreateLicense { 	//common param 	private static String PRIVATEALIAS = ""; 	private static String KEYPWD = ""; 	private static String STOREPWD = ""; 	private static String SUBJECT = ""; 	private static String licPath = ""; 	private static String priPath = ""; 	//license content 	private static String issuedTime = ""; 	private static String notBefore = ""; 	private static String notAfter = ""; 	private static String consumerType = ""; 	private static int consumerAmount = 0; 	private static String info = ""; 	// 为了方便直接用的API里的例子 	// X500Princal是一个证书文件的固有格式,详见API 	private final static X500Principal DEFAULTHOLDERANDISSUER = new X500Principal( 			"CN=Duke、OU=JavaSoft、O=Sun Microsystems、C=US"); 	 	public void setParam(String propertiesPath) { 		// 获取参数 		Properties prop = new Properties(); 		InputStream in = getClass().getResourceAsStream(propertiesPath); 		try { 			prop.load(in); 		} catch (IOException e) { 			// TODO Auto-generated catch block 			e.printStackTrace(); 		} 		PRIVATEALIAS = prop.getProperty("PRIVATEALIAS"); 		KEYPWD = prop.getProperty("KEYPWD"); 		STOREPWD = prop.getProperty("STOREPWD"); 		SUBJECT = prop.getProperty("SUBJECT"); 		KEYPWD = prop.getProperty("KEYPWD"); 		licPath = prop.getProperty("licPath"); 		priPath = prop.getProperty("priPath"); 		//license content 		issuedTime = prop.getProperty("issuedTime"); 		notBefore = prop.getProperty("notBefore"); 		notAfter = prop.getProperty("notAfter"); 		consumerType = prop.getProperty("consumerType"); 		consumerAmount = Integer.valueOf(prop.getProperty("consumerAmount")); 		info = prop.getProperty("info"); 		 	}  	public boolean create() {		 		try { 			/************** 证书发布者端执行 ******************/ 			LicenseManager licenseManager = LicenseManagerHolder 					.getLicenseManager(initLicenseParams0()); 			licenseManager.store((createLicenseContent()), new File(licPath));	 		} catch (Exception e) { 			e.printStackTrace(); 			System.out.println("客户端证书生成失败!"); 			return false; 		} 		System.out.println("服务器端生成证书成功!"); 		return true; 	}  	// 返回生成证书时需要的参数 	private static LicenseParam initLicenseParams0() { 		Preferences preference = Preferences 				.userNodeForPackage(CreateLicense.class); 		// 设置对证书内容加密的对称密码 		CipherParam cipherParam = new DefaultCipherParam(STOREPWD); 		// 参数1,2从哪个Class.getResource()获得密钥库;参数3密钥库的别名;参数4密钥库存储密码;参数5密钥库密码 		KeyStoreParam privateStoreParam = new DefaultKeyStoreParam( 				CreateLicense.class, priPath, PRIVATEALIAS, STOREPWD, KEYPWD); 		LicenseParam licenseParams = new DefaultLicenseParam(SUBJECT, 				preference, privateStoreParam, cipherParam); 		return licenseParams; 	}  	// 从外部表单拿到证书的内容 		public final static LicenseContent createLicenseContent() { 			DateFormat format = new SimpleDateFormat("yyyy-MM-dd"); 			LicenseContent content = null; 			content = new LicenseContent(); 			content.setSubject(SUBJECT); 			content.setHolder(DEFAULTHOLDERANDISSUER); 			content.setIssuer(DEFAULTHOLDERANDISSUER); 			try { 				content.setIssued(format.parse(issuedTime)); 				content.setNotBefore(format.parse(notBefore)); 				content.setNotAfter(format.parse(notAfter)); 			} catch (ParseException e) { 				// TODO Auto-generated catch block 				e.printStackTrace(); 			} 			content.setConsumerType(consumerType); 			content.setConsumerAmount(consumerAmount); 			content.setInfo(info); 			// 扩展 			content.setExtra(new Object()); 			return content; 		} } 

3、 测试程序licenseCreateTest.java:

package cn.melina.license; import cn.melina.license.CreateLicense; public class licenseCreateTest { 	public static void main(String[] args){ 		CreateLicense cLicense = new CreateLicense(); 		//获取参数 		cLicense.setParam("./param.properties"); 		//生成证书 		cLicense.create(); 	} } 

4、 生成时使用到的param.properties文件如下:

##########common parameters########### #alias PRIVATEALIAS=privatekey #key(该密码生成密钥对的密码,需要妥善保管,不能让使用者知道) KEYPWD=bigdata123456 #STOREPWD(该密码是在使用keytool生成密钥对时设置的密钥库的访问密码) STOREPWD=abc123456 #SUBJECT SUBJECT=bigdata #licPath licPath=bigdata.lic #priPath priPath=privateKeys.store ##########license content########### #issuedTime issuedTime=2014-04-01 #notBeforeTime notBefore=2014-04-01 #notAfterTime notAfter=2014-05-01 #consumerType consumerType=user #ConsumerAmount consumerAmount=1 #info info=this is a license 

根据properties文件可以看出,这里只简单设置了使用时间的限制,当然可以自定义添加更多限制。该文件中表示授权者拥有私钥,并且知道生成密钥对的密码。并且设置license的内容。

四、第三步:验证证书(使用证书)(该部分代码结合需要授权的程序使用)

1、 首先LicenseManagerHolder.java类,同上。

2、 然后是主要验证license的代码VerifyLicense.java:

package cn.melina.license;  import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.Properties; import java.util.prefs.Preferences;  import de.schlichtherle.license.CipherParam; import de.schlichtherle.license.DefaultCipherParam; import de.schlichtherle.license.DefaultKeyStoreParam; import de.schlichtherle.license.DefaultLicenseParam; import de.schlichtherle.license.KeyStoreParam; import de.schlichtherle.license.LicenseParam; import de.schlichtherle.license.LicenseManager;  /**  * VerifyLicense  * @author melina  */ public class VerifyLicense { 	//common param 	private static String PUBLICALIAS = ""; 	private static String STOREPWD = ""; 	private static String SUBJECT = ""; 	private static String licPath = ""; 	private static String pubPath = ""; 	 	public void setParam(String propertiesPath) { 		// 获取参数 		Properties prop = new Properties(); 		InputStream in = getClass().getResourceAsStream(propertiesPath); 		try { 			prop.load(in); 		} catch (IOException e) { 			// TODO Auto-generated catch block 			e.printStackTrace(); 		} 		PUBLICALIAS = prop.getProperty("PUBLICALIAS"); 		STOREPWD = prop.getProperty("STOREPWD"); 		SUBJECT = prop.getProperty("SUBJECT"); 		licPath = prop.getProperty("licPath"); 		pubPath = prop.getProperty("pubPath"); 	}  	public boolean verify() {		 		/************** 证书使用者端执行 ******************/  		LicenseManager licenseManager = LicenseManagerHolder 				.getLicenseManager(initLicenseParams()); 		// 安装证书 		try { 			licenseManager.install(new File(licPath)); 			System.out.println("客户端安装证书成功!"); 		} catch (Exception e) { 			e.printStackTrace(); 			System.out.println("客户端证书安装失败!"); 			return false; 		} 		// 验证证书 		try { 			licenseManager.verify(); 			System.out.println("客户端验证证书成功!"); 		} catch (Exception e) { 			e.printStackTrace(); 			System.out.println("客户端证书验证失效!"); 			return false; 		} 		return true; 	}  	// 返回验证证书需要的参数 	private static LicenseParam initLicenseParams() { 		Preferences preference = Preferences 				.userNodeForPackage(VerifyLicense.class); 		CipherParam cipherParam = new DefaultCipherParam(STOREPWD);  		KeyStoreParam privateStoreParam = new DefaultKeyStoreParam( 				VerifyLicense.class, pubPath, PUBLICALIAS, STOREPWD, null); 		LicenseParam licenseParams = new DefaultLicenseParam(SUBJECT, 				preference, privateStoreParam, cipherParam); 		return licenseParams; 	} } 

3、 测试程序licenseVerifyTest.java:

package cn.melina.license;  public class licenseVerifyTest { 	public static void main(String[] args){ 		VerifyLicense vLicense = new VerifyLicense(); 		//获取参数 		vLicense.setParam("./param.properties"); 		//验证证书 		vLicense.verify(); 	} } 

4、 验证时使用到的Properties文件如下:

##########common parameters########### #alias PUBLICALIAS=publiccert #STOREPWD(该密码是在使用keytool生成密钥对时设置的密钥库的访问密码) STOREPWD=abc123456 #SUBJECT SUBJECT=bigdata #licPath licPath=bigdata.lic #pubPath pubPath=publicCerts.store 

根据该验证的properties可以看出,使用者只拥有公钥,没有私钥,并且也只知道访问密钥库的密码,而不能知道生成密钥对的密码。

五、说明:

注意实际操作中,公钥、私钥、证书等文件的存放路径。

以上代码需要用到truelicense的一些包,可以自行网上搜,也可以下载我的完整工程,里面附带了所需的jar包。

以上两个完整工程提供下载:http://download.csdn.net/detail/luckymelina/7141131

GOOD LUCK!小伙伴们加油!欢迎与我交流。

posted @ 2014-04-30 03:32 ivaneeo 阅读(6573) | 评论 (0)编辑 收藏

     摘要: 之前做了一个web项目的时候,好好的网站第二天总是会提示using the Connector/J connection property 'autoReconnect=true' to avoid this problem.  这样的错误1com.mysql.jdbc.CommunicationsException: The last packet successfully recei...  阅读全文
posted @ 2014-04-28 13:32 ivaneeo 阅读(478) | 评论 (0)编辑 收藏

/etc/rabbitmq.conf:

[
    {rabbit, [{loopback_users, []}]}
].
posted @ 2014-04-04 21:28 ivaneeo 阅读(1652) | 评论 (0)编辑 收藏

http://outofmemory.cn/code-snippet/4079/java-usage-Xuggler-get-video-shichang-fen-bianlv-high-kuan-kind-information
posted @ 2014-04-01 00:44 ivaneeo 阅读(1223) | 评论 (0)编辑 收藏

Canvas里的globalCompositeOperation是个很少用到的函数,不太熟悉程序绘图的同学们估计压根都不知道这玩意是干什么的.

简单来说,Composite(组合),就是对你在绘图中,后绘制的图形与先绘制的图形之间的组合显示效果,比如在国画中,你先画一笔红色,再来一笔绿色,相交的部分是一种混色,而在油画中,绿色就会覆盖掉相交部分的红色,这在程序绘图中的处理就是Composite,Canvas API中对应的函数就是globalCompositeOperation,跟globalAlpha一样,这个属性是全局的,所以在使用的时候要注意save和restore.

我在练习这个函数的时候,用的是chrome浏览器,但是测试结果却跟实际应该出现的结果不太一致,开始我以为是写错了,检查数遍却没有问题,疑惑之下换了各种浏览器来测试,真是囧啊,每个浏览器居然都不一样,连同核心的chrome和safari都不一样...下面是测试结果.


chrome


firefox


opera


safari


firefox官方网站给的实际效果图

下面是每一个选项的说明(我表达的可能不太明白,看图吧):

source-over 默认,相交部分由后绘制图形的填充(颜色,渐变,纹理)覆盖,全部浏览器通过

source-in 只绘制相交部分,由后绘制图形的填充覆盖,其余部分透明,webkit两兄弟没有通过

source-out 只绘制后绘制图形不相交的部分,由后绘制图形的填充覆盖,其余部分透明,webkit两兄弟没有通过

source-atop 后绘制图形不相交的部分透明,相交部分由后绘制图形的填充覆盖,全部浏览器通过

destination-over 相交部分由先绘制图形的填充(颜色,渐变,纹理)覆盖,全部浏览器通过

destination-in 只绘制相交部分,由先绘制图形的填充覆盖,其余部分透明,webkit两兄弟没有通过

destination-out 只绘制先绘制图形不相交的部分,由先绘制图形的填充覆盖,其余部分透明,全部浏览器通过

destination-atop 先绘制图形不相交的部分透明,相交部分由先绘制图形的填充覆盖,webkit两兄弟没有通过

lighter 相交部分由根据先后图形填充来增加亮度,全部浏览器通过

darker 相交部分由根据先后图形填充来降低亮度,chrome通过,firefox官方说Firefox 3.6 / Thunderbird 3.1 / Fennec 1.0以后版本移除这个效果-0-,why?safari看似可以,但是无论你什么颜色,它都给填充成黑色,opera无效果

copy 只绘制后绘制图形,只有opera通过

xor 相交部分透明,全部浏览器通过

结果太令人无语了,特别是firefox那个新版本移除,我靠,为嘛啊?chrome和safari难兄难弟,成绩一塌糊涂,难道是webkit核心的问题?safari那个填充黑色很有IE6-中png透明问题的风范...opera表现很抢眼,只有一个效果未实现,继续努力!

评分及浏览器版本:
Chrome dev 7.0.503.0 : 7/12
Firefox 3.6.6 : 10/12
Opera 10.53 : 11/12
Safari 4.0.3(531.9.1) : 6/12
posted @ 2014-03-28 15:48 ivaneeo 阅读(278) | 评论 (0)编辑 收藏

 Logging In to Guacamole

You can access the web login screen for Guacamole from the server at http://127.0.0.1:8080/guacamole

The default user is "guacadmin", with the default password of "guacadmin". You can change your password by editing your own user in the administration screen.

With everything configured correctly you should be able to access the web login screen through Amahi at http://guacamole.yourhdaname.com:8080/guacamole/

posted @ 2014-03-25 18:36 ivaneeo 阅读(609) | 评论 (0)编辑 收藏

Using HAProxy to make SSH and SSL available on the same port

Certain places firewall TCP ports other than the most common ports. There are many techniques for bypassing such restrictions. One simple approach is to run a SSH daemon on port 443, however a downside of this is you need to dedicate an IP address to this SSH service.

There is quite a neat technique for making SSH and SSL share a port; in the SSL protocol clients should write first, whereas in SSH the server should write first; therefore by waiting to see if the client writes data it is possible to make a guess as to if the client is an SSL client or a SSH client.

I'm not the first person to think this up, Net::Proxy has a script called sslh and confusingly there is also a C implementation also called sslh.

I recently switched my web server to use HAProxy to allow me some more flexiblity in how I configure things (especially now the development version has keepalive support). While reading the (incredibly detailed) documentation I noticed it should be able to do the sslh technique.

Doing this needs the (currently) in development HAProxy 1.4 (support was added for content switching TCP as well as HTTP in this commit -- thanks to Cyril Bonté on the mailing list for confirming that).

The configuration looks something like the following (global section omitted, you'll want to run it as a user other than root and chroot it if you actually use this).

defaults

  timeout connect 5s

  timeout client 50s

  timeout server 20s


listen ssl :443

  tcp-request inspect-delay 2s

  acl is_ssl req_ssl_ver 2:3.1

  tcp-request content accept if is_ssl

  use_backend ssh if !is_ssl

  server www-ssl :444

  timeout client 2h


backend ssh

  mode tcp

  server ssh :22

  timeout server 2h



This listens on port 443, forwards it to port 444 (where the actual SSL web server is listening) unless it is not SSLv2, SSLv3 or TLSv1 traffic, in which case it forwards it to the ssh backend listening on port 22.

Obviously as I said earlier this is only a guess that is subject to network conditions such as packet loss. I'm not recommending you use this technique on a production site, but for a low traffic machine where you want to run both protocols it is very useful. (By increasing the timeout for SSH you increase the chances of a correct result, but also add a potentially annoying delay).

Sometimes layer 7 filtering techniques are in use and just listening on port 443 is not enough. In this case you can use SSH inside SSL.

posted @ 2014-03-19 01:53 ivaneeo 阅读(1297) | 评论 (0)编辑 收藏

http://blog.sina.com.cn/s/blog_6b8fc5470101fi4b.html
posted @ 2014-03-14 00:31 ivaneeo 阅读(252) | 评论 (0)编辑 收藏

dpkg-deb: error: subprocess paste was killed by signal (Broken pipe)


已解决: cd/var/lib/dpkg
sudo mv info info.bak
sudo mkdir info
posted @ 2014-03-12 19:00 ivaneeo 阅读(1839) | 评论 (0)编辑 收藏

# this config needs haproxy-1.1.28 or haproxy-1.2.1
global
        log 127.0.0.1   local0
        log 127.0.0.1   local1 notice
        #log loghost    local0 info
        maxconn 4096
        tune.bufsize 20480
        tune.maxrewrite 2048
        #chroot /usr/share/haproxy
        user haproxy
        group haproxy
        daemon
        #debug
        #quiet
defaults
    log global
    mode tcp
    option tcplog
    option dontlognull
    option tcp-smart-accept
    option tcp-smart-connect
    #option dontlog-normal
    retries 3
    option redispatch
    timeout connect 1h
    timeout client  1h  
    timeout server  1h
    maxconn 40000
    option redispatch
listen rabbitmq_cluster 0.0.0.0:5672
       mode tcp
       maxconn 2000
       balance roundrobin
       server   rabbit1 172.20.21.1:5672 check inter 2000 rise 2 fall 3
       server   rabbit2 172.20.21.2:5672 check inter 2000 rise 2 fall 3
       server   rabbit3 172.20.21.3:5672 check inter 2000 rise 2 fall 3
listen  mariadb_cluster
        bind 0.0.0.0:3306
        mode tcp       
#option tcpka
        option mysql-check user haproxy #mysql....  root.mysql.....
        #balance leastconn           #....
        balance roundrobin
        server mysql1 172.20.21.1:3306 weight 1 check  inter 1s rise 2 fall 2
        server mysql2 172.20.21.2:3306 weight 1 check  inter 1s rise 2 fall 2
        server mysql3 172.20.21.3:3306 weight 1 check  inter 1s rise 2 fall 2
listen ssdb_cluster 0.0.0.0:8888
       mode tcp
       maxconn 2000
       balance roundrobin
       server   ssdb1 172.20.21.1:8888 check inter 2000 rise 2 fall 3
       server   ssdb2 172.20.21.2:8888 check inter 2000 rise 2 fall 3
listen 49 0.0.0.0:3389
       mode tcp
       maxconn 2000
       balance source
       option tcpka
       server   49 172.20.0.49:3389 check inter 2000 rise 2 fall 3
listen stats :1936
    mode http
    stats enable
    stats hide-version
    stats realm Haproxy\ Statistics
    stats uri /
    stats auth admin:admin
posted @ 2014-03-11 15:22 ivaneeo 阅读(308) | 评论 (0)编辑 收藏

https://github.com/foursquare/heapaudit
posted @ 2014-03-11 14:45 ivaneeo 阅读(347) | 评论 (0)编辑 收藏

     摘要: Install MariaDB Galera Cluster in Ubuntuby SECAGUY on 2 JULY 2013 · LEAVE A COMMENTI am going to show you on how to install MariaDB Cluster (with Galera) in Ubuntu Precis...  阅读全文
posted @ 2014-03-02 00:26 ivaneeo 阅读(526) | 评论 (0)编辑 收藏

http://www.wangzhongyuan.com/archives/351.html
posted @ 2014-02-20 23:02 ivaneeo 阅读(185) | 评论 (0)编辑 收藏

如何杀死僵尸进程呢?

一般僵尸进程很难直接kill掉,不过您可以kill僵尸爸爸。父进程死后,僵尸进程成为”孤儿进程”,过继给1号进程init,init始终会负责清理僵尸进程.它产生的所有僵尸进程也跟着消失。

ps -e -o ppid,stat | grep Z | cut -d” ” -f2 | xargs kill -9

kill -HUP `ps -A -ostat,ppid | grep -e ’^[Zz]‘ | awk ’{print $2}’`

当然您可以自己编写更好的shell脚本,欢迎与大家分享。

另外子进程死后,会发送SIGCHLD信号给父进程,父进程收到此信号后,执行waitpid()函数为子进程收尸。就是基于这样的原理:就算父进 程没有调用wait,内核也会向它发送SIGCHLD消息,而此时,尽管对它的默认处理是忽略,如果想响应这个消息,可以设置一个处理函数。

posted @ 2014-02-20 19:49 ivaneeo 阅读(582) | 评论 (0)编辑 收藏


  Druid DBCP C3P0 JBoss Weblogic BonCP
数据库用户名称 Username Username User user-name    
数据库密码 Password Password Password password    
驱动名称 DriverClassName DriverClassName DriverClass driver-class DriverName  
JDBC连接串 Url Url JdbcUrl connection-url Url  
JDBC连接属性 Properties Properties Properties connection-property Properties  
初始化大小 InitialSize InitialSize InitialPoolSize   Initial Capacity  
连接池最小空闲 MinIdle MinIdle MinPoolSize min-pool-size    
连接池最大空闲 MaxIdle MaxIdle MaxPoolSize max-pool-size    
连接池最大使用连接数量 MaxActive MaxActive     MaximumCapacity  
最小逐出时间 MinEvictableIdleTimeMillis MinEvictableIdleTimeMillis        
最多等待线程 MaxWaitThreadCount MaxWaitThreadCount     HighestNumWaiters  
连接池增长步长     AcquireIncrement   CapacityIncrement  
获取连接时测试是否有效 TestOnBorrow TestOnBorrow TestConnectionOnCheckout      
归还连接时是否测试有效 TestOnReturn TestOnReturn TestConnectionOnCheckin   TestConnectionsOnReserve  
测试有效用的SQL Query ValidationQuery ValidationQuery PreferredTestQuery      
测试有效的超时时间 ValidationQueryTimeout ValidationQueryTimeout        
连接初始化SQL ConnectionInitSqls ConnectionInitSqls     InitSQL  
连接最大存活实现     MaxConnectionAge      
连接泄漏的超时时间 RemoveAbandonedTimeout RemoveAbandonedTimeout UnreturnedConnectionTimeout      
关闭泄漏的连接时打印堆栈信息 LogAbandoned LogAbandoned DebugUnreturnedConnectionStackTraces      
逐出连接的检测时间间隔 TimeBetweenEvictionRunsMillis TimeBetweenEvictionRunsMillis     ShrinkFrequencySeconds  
Statement缓存算法         StatementCacheType  
Statement缓存大小         StatementCacheSize  
          TestTableName  
          SecondsToTrustAnIdlePoolConnection  
          ConnectionCreationRetryFrequencySeconds  
          LoginDelaySeconds  
          Profile Connection Usage  
          Profile Connection Reservation Wait  
          Profile Connection Leak  
          Profile Connection Reservation Failed  
          Profile Statement Cache Entry  
          Profile Statement Usage  
          Profile Connection Last Usage  
          Profile Connection Multithreaded Usage  
          Profile Harvest Frequency Seconds  
连接池扩展 Filters       DriverInterceptor  
          CredentialMappingEnabled  
          InactiveConnectionTimeoutSeconds  
          ConnectionReserveTimeoutSeconds  
  QueryTimeout       StatementTimeout  
连接池关闭时对正在使用连接的处理方式         IgnoreInUseConnectionsEnabled  
把连接放到ThreadLocal中         PinnedToThread  
关闭“赃”连接(调用过getVendorConnection方法)         RemoveInfectedConnections  
posted @ 2013-12-26 16:02 ivaneeo 阅读(1036) | 评论 (0)编辑 收藏

现在网站发展的趋势对网络负载均衡的使用是随着网站规模的提升根据不同的阶段来使用不同的技术:

一种是通过硬件来进行进行,常见的硬件有比较昂贵的NetScaler、F5、Radware和Array等商用的负载均衡器,它的优点就是有专业的维护团队来对这些服务进行维护、缺点就是花销太大,所以对于规模较小的网络服务来说暂时还没有需要使用;另外一种就是类似于LVS/HAProxy、Nginx的基于Linux的开源免费的负载均衡软件策略,这些都是通过软件级别来实现,所以费用非常低廉,所以我个也比较推荐大家采用第二种方案来实施自己网站的负载均衡需求。

近期朋友刘鑫(紫雨荷雪)的项目成功上线了,PV达到了亿级/日的访问量,最前端用的是HAProxy+Keepalived双机作的负载均衡器 /反向代理,整个网站非常稳定;这让我更坚定了以前跟老男孩前辈聊的关于网站架构比较合理设计的架构方案:即Nginx /HAProxy+Keepalived作Web最前端的负载均衡器,后端的MySQL数据库架构采用一主多从,读写分离的方式,采用LVS+Keepalived的方式。

在这里我也有一点要跟大家申明下:很多朋友担心软件级别的负载均衡在高并发流量冲击下的稳定情况,事实是我们通过成功上线的许多网站发现,它们的稳 定性也是非常好的,宕机的可能性微乎其微,所以我现在做的项目,基本上没考虑服务级别的高可用了。相信大家对这些软件级别的负载均衡软件都已经有了很深的 的认识,下面我就它们的特点和适用场合分别说明下。

LVS:使用集群技术和Linux操作系统实现一个高性能、高可用的服务器,它具有很好的可伸缩性(Scalability)、可靠性(Reliability)和可管理性(Manageability),感谢章文嵩博士为我们提供如此强大实用的开源软件。

LVS的特点是:

  1. 抗负载能力强、是工作在网络4层之上仅作分发之用,没有流量的产生,这个特点也决定了它在负载均衡软件里的性能最强的;
  2. 配置性比较低,这是一个缺点也是一个优点,因为没有可太多配置的东西,所以并不需要太多接触,大大减少了人为出错的几率;
  3. 工作稳定,自身有完整的双机热备方案,如LVS+Keepalived和LVS+Heartbeat,不过我们在项目实施中用得最多的还是LVS/DR+Keepalived;
  4. 无流量,保证了均衡器IO的性能不会收到大流量的影响;
  5. 应用范围比较广,可以对所有应用做负载均衡;
  6. 软件本身不支持正则处理,不能做动静分离,这个就比较遗憾了;其实现在许多网站在这方面都有较强的需求,这个是Nginx/HAProxy+Keepalived的优势所在。
  7. 如果是网站应用比较庞大的话,实施LVS/DR+Keepalived起来就比较复杂了,特别后面有Windows Server应用的机器的话,如果实施及配置还有维护过程就比较复杂了,相对而言,Nginx/HAProxy+Keepalived就简单多了。站长教学网 eduyo.com

Nginx的特点是:

  1. 工作在网络的7层之上,可以针对http应用做一些分流的策略,比如针对域名、目录结构,它的正则规则比HAProxy更为强大和灵活,这也是许多朋友喜欢它的原因之一;
  2. Nginx对网络的依赖非常小,理论上能ping通就就能进行负载功能,这个也是它的优势所在;
  3. Nginx安装和配置比较简单,测试起来比较方便;
  4. 也可以承担高的负载压力且稳定,一般能支撑超过几万次的并发量;
  5. Nginx可以通过端口检测到服务器内部的故障,比如根据服务器处理网页返回的状态码、超时等等,并且会把返回错误的请求重新提交到另一个节点,不过其中缺点就是不支持url来检测;
  6. Nginx仅能支持http和Email,这样就在适用范围上面小很多,这个它的弱势;
  7. Nginx不仅仅是一款优秀的负载均衡器/反向代理软件,它同时也是功能强大的Web应用服务器。LNMP现在也是非常流行的web架构,大有和以前最流行的LAMP架构分庭抗争之势,在高流量的环境中也有很好的效果。
  8. Nginx现在作为Web反向加速缓存越来越成熟了,很多朋友都已在生产环境下投入生产了,而且反映效果不错,速度比传统的Squid服务器更快,有兴趣的朋友可以考虑用其作为反向代理加速器。

HAProxy的特点是:

  1. HAProxy是支持虚拟主机的,以前有朋友说这个不支持虚拟主机,我这里特此更正一下。
  2. 能够补充Nginx的一些缺点比如Session的保持,Cookie的引导等工作
  3. 支持url检测后端的服务器出问题的检测会有很好的帮助。
  4. 它跟LVS一样,本身仅仅就只是一款负载均衡软件;单纯从效率上来讲HAProxy更会比Nginx有更出色的负载均衡速度,在并发处理上也是优于Nginx的。
  5. HAProxy可以对Mysql读进行负载均衡,对后端的MySQL节点进行检测和负载均衡,不过在后端的MySQL slaves数量超过10台时性能不如LVS,所以我向大家推荐LVS+Keepalived。
  6. HAProxy的算法现在也越来越多了,具体有如下8种:
    ① roundrobin,表示简单的轮询,这个不多说,这个是负载均衡基本都具备的;
    ② static-rr,表示根据权重,建议关注;
    ③ leastconn,表示最少连接者先处理,建议关注;
    ④ source,表示根据请求源IP,这个跟Nginx的IP_hash机制类似,我们用其作为解决session问题的一种方法,建议关注;
    ⑤ ri,表示根据请求的URI;
    ⑥ rl_param,表示根据请求的URl参数'balance url_param' requires an URL parameter name;
    ⑦ hdr(name),表示根据HTTP请求头来锁定每一次HTTP请求;
    ⑧ rdp-cookie(name),表示根据据cookie(name)来锁定并哈希每一次TCP请求。

 

 

Nginx和LVS作对比的结果

1、Nginx工作在网络的7层,所以它可以针对http应用本身来做分流策略,比如针对域名、目录结构等,相比之下LVS并不具备这样的功能,所 以 Nginx单凭这点可利用的场合就远多于LVS了;但Nginx有用的这些功能使其可调整度要高于LVS,所以经常要去触碰触碰,由LVS的第2条优点 看,触碰多了,人为出问题的几率也就会大。
2、Nginx对网络的依赖较小,理论上只要ping得通,网页访问正常,Nginx就能连得通,Nginx同时还能区分内外网,如果是同时拥有内外网的 节点,就相当于单机拥有了备份线路;LVS就比较依赖于网络环境,目前来看服务器在同一网段内并且LVS使用direct方式分流,效果较能得到保证。另 外注意,LVS需要向托管商至少申请多一个ip来做Visual IP,貌似是不能用本身的IP来做VIP的。要做好LVS管理员,确实得跟进学习很多有关网络通信方面的知识,就不再是一个HTTP那么简单了。站长教学网 eduyo.com
3、Nginx安装和配置比较简单,测试起来也很方便,因为它基本能把错误用日志打印出来。LVS的安装和配置、测试就要花比较长的时间了,因为同上所述,LVS对网络依赖比较大,很多时候不能配置成功都是因为网络问题而不是配置问题,出了问题要解决也相应的会麻烦得多。
4、Nginx也同样能承受很高负载且稳定,但负载度和稳定度差LVS还有几个等级:Nginx处理所有流量所以受限于机器IO和配置;本身的bug也还是难以避免的;Nginx没有现成的双机热备方案,所以跑在单机上还是风险较大,单机上的事情全都很难说。
5、Nginx可以检测到服务器内部的故障,比如根据服务器处理网页返回的状态码、超时等等,并且会把返回错误的请求重新提交到另一个节点。目前LVS中 ldirectd也能支持针对服务器内部的情况来监控,但LVS的原理使其不能重发请求。重发请求这点,譬如用户正在上传一个文件,而处理该上传的节点刚 好在上传过程中出现故障,Nginx会把上传切到另一台服务器重新处理,而LVS就直接断掉了,如果是上传一个很大的文件或者很重要的文件的话,用户可能 会因此而恼火。
6、Nginx对请求的异步处理可以帮助节点服务器减轻负载,假如使用apache直接对外服务,那么出现很多的窄带链接时apache服务器将会占用大 量内存而不能释放,使用多一个Nginx做apache代理的话,这些窄带链接会被Nginx挡住,apache上就不会堆积过多的请求,这样就减少了相 当多的内存占用。这点使用squid也有相同的作用,即使squid本身配置为不缓存,对apache还是有很大帮助的。LVS没有这些功能,也就无法能 比较。
7、Nginx能支持http和email(email的功能估计比较少人用),LVS所支持的应用在这点上会比Nginx更多。在使用上,一般最前端所 采取的策略应是LVS,也就是DNS的指向应为LVS均衡器,LVS的优点令它非常适合做这个任务。重要的ip地址,最好交由LVS托管,比如数据库的 ip、webservice服务器的ip等等,这些ip地址随着时间推移,使用面会越来越大,如果更换ip则故障会接踵而至。所以将这些重要ip交给 LVS托管是最为稳妥的,这样做的唯一缺点是需要的VIP数量会比较多。Nginx可作为LVS节点机器使用,一是可以利用Nginx的功能,二是可以利 用Nginx的性能。当然这一层面也可以直接使用squid,squid的功能方面就比Nginx弱不少了,性能上也有所逊色于Nginx。Nginx也 可作为中层代理使用,这一层面Nginx基本上无对手,唯一可以撼动Nginx的就只有lighttpd了,不过lighttpd目前还没有能做到 Nginx完全的功能,配置也不那么清晰易读。另外,中层代理的IP也是重要的,所以中层代理也拥有一个VIP和LVS是最完美的方案了。具体的应用还得 具体分析,如果是比较小的网站(日PV<1000万),用Nginx就完全可以了,如果机器也不少,可以用DNS轮询,LVS所耗费的机器还是比较 多的;大型网站或者重要的服务,机器不发愁的时候,要多多考虑利用LVS

posted @ 2013-12-25 12:34 ivaneeo 阅读(6561) | 评论 (0)编辑 收藏

roundrobin  Each server is used in turns, according to their weights.
                 This is the smoothest and fairest algorithm when the server's
                 processing time remains equally distributed. This algorithm
                 is dynamic, which means that server weights may be adjusted
                 on the fly for slow starts for instance. It is limited by
                 design to 4128 active servers per backend. Note that in some
                 large farms, when a server becomes up after having been down
                 for a very short time, it may sometimes take a few hundreds
                 requests for it to be re-integrated into the farm and start
                 receiving traffic. This is normal, though very rare. It is
                 indicated here in case you would have the chance to observe
                 it, so that you don't worry.

                 roundrobin:每个server根据权重依次被轮询,

这个算法是动态的,意味着
                 server的权重可以实时地被调整。对于每个haproxy的backend servers的数目
                 而言被限制在4128个活跃数目之内。


     static-rr   Each server is used in turns, according to their weights.
                 This algorithm is as similar to roundrobin except that it is
                 static, which means that changing a server's weight on the
                 fly will have no effect. On the other hand, it has no design
                 limitation on the number of servers, and when a server goes
                 up, it is always immediately reintroduced into the farm, once
                 the full map is recomputed. It also uses slightly less CPU to
                 run (around -1%).
                 静态roundrobin(static-rr):跟roundrobin类似,唯一的区别是不可以动态实时
                 server权重和backend 的server数目没有上限。

     leastconn   The server with the lowest number of connections receives the
                 connection. Round-robin is performed within groups of servers
                 of the same load to ensure that all servers will be used. Use
                 of this algorithm is recommended where very long sessions are
                 expected, such as LDAP, SQL, TSE, etc... but is not very well
                 suited for protocols using short sessions such as HTTP. This
                 algorithm is dynamic, which means that server weights may be
                 adjusted on the fly for slow starts for instance.
                 最小连接数目负载均衡策略(leastconn):round-robin适合于各个server负载相同的情况。
                 最小连接数目算法适合于长时间会话,如LDAP,SQL,TSE,但是并不适合于HTTP短连接的协议。

     source      The source IP address is hashed and divided by the total
                 weight of the running servers to designate which server will
                 receive the request. This ensures that the same client IP
                 address will always reach the same server as long as no
                 server goes down or up. If the hash result changes due to the
                 number of running servers changing, many clients will be
                 directed to a different server. This algorithm is generally
                 used in TCP mode where no cookie may be inserted. It may also
                 be used on the Internet to provide a best-effort stickiness
                 to clients which refuse session cookies. This algorithm is
                 static by default, which means that changing a server's
                 weight on the fly will have no effect, but this can be
                 changed using "hash-type".
                 源IP hash散列调度:将源ip地址进行hash,再根据hasn求模或者一致性hash定位到
                 hash表中的server上。相同的ip地址的请求被分发到同一个server上。但当server的数量变化时,
                 来自于同一client的请求可能会被分发到不同的server上。这个算法通常用在没有cookie的tcp模式下。

     uri         The left part of the URI (before the question mark) is hashed
                 and divided by the total weight of the running servers. The
                 result designates which server will receive the request. This
                 ensures that a same URI will always be directed to the same
                 server as long as no server goes up or down. This is used
                 with proxy caches and anti-virus proxies in order to maximize
                 the cache hit rate. Note that this algorithm may only be used
                 in an HTTP backend. This algorithm is static by default,
                 which means that changing a server's weight on the fly will
                 have no effect, but this can be changed using "hash-type".

                 This algorithm support two optional parameters "len" and
                 "depth", both followed by a positive integer number. These
                 options may be helpful when it is needed to balance servers
                 based on the beginning of the URI only. The "len" parameter
                 indicates that the algorithm should only consider that many
                 characters at the beginning of the URI to compute the hash.
                 Note that having "len" set to 1 rarely makes sense since most
                 URIs start with a leading "/".

                 The "depth" parameter indicates the maximum directory depth
                 to be used to compute the hash. One level is counted for each
                 slash in the request. If both parameters are specified, the
                 evaluation stops when either is reached.

     url_param   The URL parameter specified in argument will be looked up in
                 the query string of each HTTP GET request.

                 If the modifier "check_post" is used, then an HTTP POST
                 request entity will be searched for the parameter argument,
                 when it is not found in a query string after a question mark
                 ('?') in the URL. Optionally, specify a number of octets to
                 wait for before attempting to search the message body. If the
                 entity can not be searched, then round robin is used for each
                 request. For instance, if your clients always send the LB
                 parameter in the first 128 bytes, then specify that. The
                 default is 48. The entity data will not be scanned until the
                 required number of octets have arrived at the gateway, this
                 is the minimum of: (default/max_wait, Content-Length or first
                 chunk length). If Content-Length is missing or zero, it does
                 not need to wait for more data than the client promised to
                 send. When Content-Length is present and larger than
                 <max_wait>, then waiting is limited to <max_wait> and it is
                 assumed that this will be enough data to search for the
                 presence of the parameter. In the unlikely event that
                 Transfer-Encoding: chunked is used, only the first chunk is
                 scanned. Parameter values separated by a chunk boundary, may
                 be randomly balanced if at all.

                 If the parameter is found followed by an equal sign ('=') and
                 a value, then the value is hashed and divided by the total
                 weight of the running servers. The result designates which
                 server will receive the request.

                 This is used to track user identifiers in requests and ensure
                 that a same user ID will always be sent to the same server as
                 long as no server goes up or down. If no value is found or if
                 the parameter is not found, then a round robin algorithm is
                 applied. Note that this algorithm may only be used in an HTTP
                 backend. This algorithm is static by default, which means
                 that changing a server's weight on the fly will have no
                 effect, but this can be changed using "hash-type".

     hdr(name)   The HTTP header <name> will be looked up in each HTTP request.
                 Just as with the equivalent ACL 'hdr()' function, the header
                 name in parenthesis is not case sensitive. If the header is
                 absent or if it does not contain any value, the roundrobin
                 algorithm is applied instead.

                 An optional 'use_domain_only' parameter is available, for
                 reducing the hash algorithm to the main domain part with some
                 specific headers such as 'Host'. For instance, in the Host
                 value "haproxy.1wt.eu ", only "1wt" will be considered.

                 This algorithm is static by default, which means that
                 changing a server's weight on the fly will have no effect,
                 but this can be changed using "hash-type".

     rdp-cookie
     rdp-cookie(name)
                 The RDP cookie <name> (or "mstshash" if omitted) will be
                 looked up and hashed for each incoming TCP request. Just as
                 with the equivalent ACL 'req_rdp_cookie()' function, the name
                 is not case-sensitive. This mechanism is useful as a degraded
                 persistence mode, as it makes it possible to always send the
                 same user (or the same session ID) to the same server. If the
                 cookie is not found, the normal roundrobin algorithm is
                 used instead.

                 Note that for this to work, the frontend must ensure that an
                 RDP cookie is already present in the request buffer. For this
                 you must use 'tcp-request content accept' rule combined with
                 a 'req_rdp_cookie_cnt' ACL.

                 This algorithm is static by default, which means that
                 changing a server's weight on the fly will have no effect,
                 but this can be changed us
posted @ 2013-12-25 12:32 ivaneeo 阅读(532) | 评论 (0)编辑 收藏

1.安装mariadb on ubuntu
http://blog.secaserver.com/2013/07/install-mariadb-galera-cluster-ubuntu/

3 在服务器上用mysql -h 192.168.0.1 -u root -p mysql命令登录mysql数据库

然后用grant命令下放权限。

GRANT ALL PRIVILEGES ON *.* TO root@localhost IDENTIFIED BY 'root-password' WITH GRANT OPTION;

GRANT ALL PRIVILEGES ON *.* TO root@127.0.0.1 IDENTIFIED BY 'root-password' WITH GRANT OPTION;

GRANT ALL PRIVILEGES ON *.* TO root@'%' IDENTIFIED BY 'root-password' WITH GRANT OPTION;

例如:
GRANT   ALL   PRIVILEGES   ON   *.*   TO   root@'%'   identified   by   '123456'  

注意:自己根据情况修改以上命令中的 “用户”“ip地址”“密码”。 

2 安装和配置haproxy
option mysql-check [ user <username> ]   
USE mysql; INSERT INTO user (Host,User) values ('<ip_of_haproxy>','<username>'); FLUSH PRIVILEGESheck

only consists in parsing the Mysql Handshake Initialisation packet or Error packet, we don't send anything in this mode. It was reported that it can generate lockout if check is too frequent and/or if there is not enough traffic. In fact, you need in this case to check MySQL "max_connect_errors" value as if a connection is established successfully within fewer than MySQL "max_connect_errors" attempts after a previous connection was interrupted, the error count for the host is cleared to zero. If HAProxy's server get blocked, the "FLUSH HOSTS" statement is the only way to unblock it.

配置:
# this config needs haproxy-1.1.28 or haproxy-1.2.1 global
log 127.0.0.1
local0 info
#日志相关
log 127.0.0.1
local1 notice
maxconn 4096
daemon
#debug
#quiet defaults
log global mode http #option httplog option dontlognull retries 3 option redispatch maxconn 2000 contimeout 5000 clitimeout 50000 srvtimeout 50000 listen mysql bind 0.0.0.0:3333 #代理端口 mode tcp #模式 TCP option mysql-check user haproxy #mysql健康检查 root为mysql登录用户名 balance roundrobin #调度算法 server mysql1 172.20.21.1:3306 weight 1 check inter 1s rise 2 fall 2 server mysql2 172.20.21.2:3306 weight 1 check inter 1s rise 2 fall 2 server mysql3 172.20.21.3:3306 weight 1 check inter 1s rise 2 fall 2 listen stats :1936 mode http stats enable stats hide-version stats realm Haproxy\ Statistics stats uri / stats auth admin:admin
posted @ 2013-12-22 02:57 ivaneeo 阅读(1252) | 评论 (0)编辑 收藏

如何安裝RabbitMQ Cluster


建立測試環境與測試系統總是最花時間的,趁著今天重新安裝一組RabbitMQ 的測試環境,把所有的步驟和順序都整理起來吧。

安裝RabbitMQ

Our APT repository

To use our APT repository:

  1. Add the following line to your /etc/apt/sources.list:
    deb http://www.rabbitmq.com/debian/ testing main
    (Please note that the word testing in this line refers to the state of our release of RabbitMQ, not any particular Debian distribution. You can use it with Debian stable, testing or unstable, as well as with Ubuntu. We describe the release as "testing" to emphasise that we release somewhat frequently.)
  2. (optional) To avoid warnings about unsigned packages, add our public key to your trusted key list using apt-key(8):
    wget http://www.rabbitmq.com/rabbitmq-signing-key-public.asc sudo apt-key add rabbitmq-signing-key-public.asc
  3. Run apt-get update.
  4. Install packages as usual; for instance,
    sudo apt-get install rabbitmq-server


設定Cluster


最簡易的方法就是先啟動,cluster master node產生 /var/lib/rabbitmq/.erlang.cookie 這份文件,然後再把這份文件copy 到 每一個cluster node鄉對應的目錄下面去,接下來就參考RabbitMQ - create cluster這份文件,範例事先建立3台的cluster。
 
1. 啟動每台rabbitMQ
# rabbit1$ rabbitmq-server -detached
# rabbit2$ rabbitmq-server -detached
# rabbit3$ rabbitmq-server -detached

2. 確認每一台rabbitmq 是否是standalone狀態

# rabbit1$ rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit1 ...
[{nodes,[{disc,[rabbit@rabbit1]}]},{running_nodes,[rabbit@rabbit1]}]
...done.
# rabbit2$ rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit2 ...
[{nodes,[{disc,[rabbit@rabbit2]}]},{running_nodes,[rabbit@rabbit2]}]
...done.
# rabbit3$ rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit3 ...
[{nodes,[{disc,[rabbit@rabbit3]}]},{running_nodes,[rabbit@rabbit3]}]
...done.

3. 依序加入cluster

rabbit2$ rabbitmqctl stop_app
Stopping node rabbit@rabbit2 ...done.
rabbit2$ rabbitmqctl reset
Resetting node rabbit@rabbit2 ...done.
rabbit2$ rabbitmqctl cluster rabbit@rabbit1
Clustering node rabbit@rabbit2 with [rabbit@rabbit1] ...done.
rabbit2$ rabbitmqctl start_app
Starting node rabbit@rabbit2 ...done. 


4. 確認cluster status是否正確加入

rabbit1$ rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit1 ...
[{nodes,[{disc,[rabbit@rabbit1]},{ram,[rabbit@rabbit2]}]},
{running_nodes,[rabbit@rabbit2,rabbit@rabbit1]}]
...done.
rabbit2$ rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit2 ...
[{nodes,[{disc,[rabbit@rabbit1]},{ram,[rabbit@rabbit2]}]},
{running_nodes,[rabbit@rabbit1,rabbit@rabbit2]}]
...done.


設定Web Management Plugin


參考 rabbitmq - Management Plugin,重點是要在Cluster node的每一台都要安裝這個plugin
# rabbitmq-plugins enable rabbitmq_management 
安裝好以後,要記得重啟服務
# service rabbitmq-server restart

設定好就可以連到http://server-name:55672/#/ 看看web 介面有沒有起來,預設的帳號密碼都是guest,如果是內部測試那還沒關係,如果是要連到外面,一定記得要改帳號密碼和permission。


設定帳號


最後我們可以設定一個vhost 以及這個vhost的帳號密碼和權限

#rabbitmqctl add_vhost /demo
#rabbitmqctl add_user demo mypass
#rabbitmqctl set_permissions -p /demo demo ".*" ".*" ".*"

启动HAProxy
/etc/default/haproxy
# Set ENABLED to 1 if you want the init script to start haproxy.
ENABLED=1

启动日志
/etc/rsyslog.d

添加文件haproxy.conf:
$ModLoad imudp
$UDPServerRun 514

local0.*                        -/var/log/haproxy-0.log
local1.*                        -/var/log/haproxy-1.log

HAProxy配置
# this config needs haproxy-1.1.28 or haproxy-1.2.1

global
        log 127.0.0.1   local0
        log 127.0.0.1   local1 notice
        #log loghost    local0 info
        maxconn 4096
        #chroot /usr/share/haproxy
        user haproxy
        group haproxy
        daemon
        #debug
        #quiet

defaults
        log     global
        mode    tcp
        option  tcplog
        option  dontlognull
        retries 3
        option redispatch
        maxconn 2000
        contimeout      5000
        clitimeout      50000
        srvtimeout      50000

listen rabbitmq_cluster 0.0.0.0:5678
       mode tcp
       balance roundrobin
       server   rabbit65 192.168.1.200:5672 check inter 2000 rise 2 fall 3
       server   rabbit66 192.168.1.201:5672 check inter 2000 rise 2 fall 3
listen stats :1936
    mode http
    stats enable
    stats hide-version
    stats realm Haproxy\ Statistics
    stats uri /
    stats auth admin:admin
posted @ 2013-12-16 19:11 ivaneeo 阅读(551) | 评论 (0)编辑 收藏

 Linux下高并发socket最大连接数所受的限制问题

  1、修改用户进程可打开文件数限制

  在Linux平台上,无论编写客户端程序还是服务端程序,在进行高并发TCP连接处理时,最高的并发数量都要受到系统对用户单一进程同时可打开文件数量的限制(这是因为系统为每个TCP连接都要创建一个socket句柄,每个socket句柄同时也是一个文件句柄)。可使用ulimit命令查看系统允许当前用户进程打开的文件数限制:

  [speng@as4 ~]$ ulimit -n

  1024

  这表示当前用户的每个进程最多允许同时打开1024个文件,这1024个文件中还得除去每个进程必然打开的标准输入,标准输出,标准错误,服务器监听 socket,进程间通讯的unix域socket等文件,那么剩下的可用于客户端socket连接的文件数就只有大概1024-10=1014个左右。也就是说缺省情况下,基于Linux的通讯程序最多允许同时1014个TCP并发连接。

  对于想支持更高数量的TCP并发连接的通讯处理程序,就必须修改Linux对当前用户的进程同时打开的文件数量的软限制(soft limit)和硬限制(hardlimit)。其中软限制是指Linux在当前系统能够承受的范围内进一步限制用户同时打开的文件数;硬限制则是根据系统硬件资源状况(主要是系统内存)计算出来的系统最多可同时打开的文件数量。通常软限制小于或等于硬限制。

  修改上述限制的最简单的办法就是使用ulimit命令:

  [speng@as4 ~]$ ulimit -n

  上述命令中,在中指定要设置的单一进程允许打开的最大文件数。如果系统回显类似于"Operation notpermitted"之类的话,说明上述限制修改失败,实际上是因为在中指定的数值超过了Linux系统对该用户打开文件数的软限制或硬限制。因此,就需要修改Linux系统对用户的关于打开文件数的软限制和硬限制。

  第一步,修改/etc/security/limits.conf文件,在文件中添加如下行:

  speng soft nofile 10240

  speng hard nofile 10240

  其中speng指定了要修改哪个用户的打开文件数限制,可用'*'号表示修改所有用户的限制;

  soft或hard指定要修改软限制还是硬限制;10240则指定了想要修改的新的限制值,即最大打开文件数(请注意软限制值要小于或等于硬限制)。修改完后保存文件。

  第二步,修改/etc/pam.d/login文件,在文件中添加如下行:

  session required /lib/security/pam_limits.so 这是告诉Linux在用户完成系统登录后,应该调用pam_limits.so模块来设置系统对该用户可使用的各种资源数量的最大限制(包括用户可打开的最大文件数限制),而pam_limits.so模块就会从/etc/security/limits.conf文件中读取配置来设置这些限制值。修改完后保存此文件。

  第三步,查看Linux系统级的最大打开文件数限制,使用如下命令:

  [speng@as4 ~]$ cat /proc/sys/fs/file-max

  12158

  这表明这台Linux系统最多允许同时打开(即包含所有用户打开文件数总和)12158个文件,是Linux系统级硬限制,所有用户级的打开文件数限制都不应超过这个数值。通常这个系统级硬限制是Linux系统在启动时根据系统硬件资源状况计算出来的最佳的最大同时打开文件数限制,如果没有特殊需要,不应该修改此限制,除非想为用户级打开文件数限制设置超过此限制的值。

  修改此硬限制的方法是修改/etc/rc.local脚本,在脚本中添加如下行:

  echo 22158 > /proc/sys/fs/file-max

  这是让Linux在启动完成后强行将系统级打开文件数硬限制设置为22158.修改完后保存此文件。

  完成上述步骤后重启系统,一般情况下就可以将Linux系统对指定用户的单一进程允许同时打开的最大文件数限制设为指定的数值。如果重启后用 ulimit-n命令查看用户可打开文件数限制仍然低于上述步骤中设置的最大值,这可能是因为在用户登录脚本/etc/profile中使用ulimit -n命令已经将用户可同时打开的文件数做了限制。由于通过ulimit-n修改系统对用户可同时打开文件的最大数限制时,新修改的值只能小于或等于上次 ulimit-n设置的值,因此想用此命令增大这个限制值是不可能的。

  所以,如果有上述问题存在,就只能去打开/etc/profile脚本文件,在文件中查找是否使用了ulimit-n限制了用户可同时打开的最大文件数量,如果找到,则删除这行命令,或者将其设置的值改为合适的值,然后保存文件,用户退出并重新登录系统即可。 通过上述步骤,就为支持高并发TCP连接处理的通讯处理程序解除关于打开文件数量方面的系统限制。

  2、修改网络内核对TCP连接的有关限制

  在Linux上编写支持高并发TCP连接的客户端通讯处理程序时,有时会发现尽管已经解除了系统对用户同时打开文件数的限制,但仍会出现并发TCP连接数增加到一定数量时,再也无法成功建立新的TCP连接的现象。出现这种现在的原因有多种。

  第一种原因可能是因为Linux网络内核对本地端口号范围有限制。此时,进一步分析为什么无法建立TCP连接,会发现问题出在connect()调用返回失败,查看系统错误提示消息是"Can't assign requestedaddress".同时,如果在此时用tcpdump工具监视网络,会发现根本没有TCP连接时客户端发SYN包的网络流量。这些情况说明问题在于本地Linux系统内核中有限制。

  其实,问题的根本原因在于Linux内核的TCP/IP协议实现模块对系统中所有的客户端TCP连接对应的本地端口号的范围进行了限制(例如,内核限制本地端口号的范围为1024~32768之间)。当系统中某一时刻同时存在太多的TCP客户端连接时,由于每个TCP客户端连接都要占用一个唯一的本地端口号(此端口号在系统的本地端口号范围限制中),如果现有的TCP客户端连接已将所有的本地端口号占满,则此时就无法为新的TCP客户端连接分配一个本地端口号了,因此系统会在这种情况下在connect()调用中返回失败,并将错误提示消息设为"Can't assignrequested address".

  有关这些控制逻辑可以查看Linux内核源代码,以linux2.6内核为例,可以查看tcp_ipv4.c文件中如下函数:

  static int tcp_v4_hash_connect(struct sock *sk)

  请注意上述函数中对变量sysctl_local_port_range的访问控制。变量sysctl_local_port_range的初始化则是在tcp.c文件中的如下函数中设置:

  void __init tcp_init(void)

  内核编译时默认设置的本地端口号范围可能太小,因此需要修改此本地端口范围限制。

  第一步,修改/etc/sysctl.conf文件,在文件中添加如下行:

  net.ipv4.ip_local_port_range = 1024 65000

  这表明将系统对本地端口范围限制设置为1024~65000之间。请注意,本地端口范围的最小值必须大于或等于1024;而端口范围的最大值则应小于或等于65535.修改完后保存此文件。

  第二步,执行sysctl命令:

  [speng@as4 ~]$ sysctl -p

  如果系统没有错误提示,就表明新的本地端口范围设置成功。如果按上述端口范围进行设置,则理论上单独一个进程最多可以同时建立60000多个TCP客户端连接。

  第二种无法建立TCP连接的原因可能是因为Linux网络内核的IP_TABLE防火墙对最大跟踪的TCP连接数有限制。此时程序会表现为在 connect()调用中阻塞,如同死机,如果用tcpdump工具监视网络,也会发现根本没有TCP连接时客户端发SYN包的网络流量。由于 IP_TABLE防火墙在内核中会对每个TCP连接的状态进行跟踪,跟踪信息将会放在位于内核内存中的conntrackdatabase中,这个数据库的大小有限,当系统中存在过多的TCP连接时,数据库容量不足,IP_TABLE无法为新的TCP连接建立跟踪信息,于是表现为在connect()调用中阻塞。此时就必须修改内核对最大跟踪的TCP连接数的限制,方法同修改内核对本地端口号范围的限制是类似的:

  第一步,修改/etc/sysctl.conf文件,在文件中添加如下行:

  net.ipv4.ip_conntrack_max = 10240

  这表明将系统对最大跟踪的TCP连接数限制设置为10240.请注意,此限制值要尽量小,以节省对内核内存的占用。

  第二步,执行sysctl命令:

  [speng@as4 ~]$ sysctl -p

  如果系统没有错误提示,就表明系统对新的最大跟踪的TCP连接数限制修改成功。如果按上述参数进行设置,则理论上单独一个进程最多可以同时建立10000多个TCP客户端连接。

  3、使用支持高并发网络I/O的编程技术在Linux上编写高并发TCP连接应用程序时,必须使用合适的网络I/O技术和I/O事件分派机制。可用的I/O技术有同步I/O,非阻塞式同步I/O(也称反应式I/O),以及异步I/O.在高TCP并发的情形下,如果使用同步I/O,这会严重阻塞程序的运转,除非为每个TCP连接的I/O创建一个线程。

  但是,过多的线程又会因系统对线程的调度造成巨大开销。因此,在高TCP并发的情形下使用同步 I/O是不可取的,这时可以考虑使用非阻塞式同步I/O或异步I/O.非阻塞式同步I/O的技术包括使用select(),poll(),epoll等机制。异步I/O的技术就是使用AIO.

  从I/O事件分派机制来看,使用select()是不合适的,因为它所支持的并发连接数有限(通常在1024个以内)。如果考虑性能,poll()也是不合适的,尽管它可以支持的较高的TCP并发数,但是由于其采用"轮询"机制,当并发数较高时,其运行效率相当低,并可能存在I/O事件分派不均,导致部分TCP连接上的I/O出现"饥饿"现象。而如果使用epoll或AIO,则没有上述问题(早期Linux内核的AIO技术实现是通过在内核中为每个 I/O请求创建一个线程来实现的,这种实现机制在高并发TCP连接的情形下使用其实也有严重的性能问题。但在最新的Linux内核中,AIO的实现已经得到改进)。

  综上所述,在开发支持高并发TCP连接的Linux应用程序时,应尽量使用epoll或AIO技术来实现并发的TCP连接上的I/O控制,这将为提升程序对高并发TCP连接的支持提供有效的I/O保证。

  内核参数sysctl.conf的优化

  /etc/sysctl.conf 是用来控制linux网络的配置文件,对于依赖网络的程序(如web服务器和cache服务器)非常重要,RHEL默认提供的最好调整。

  推荐配置(把原/etc/sysctl.conf内容清掉,把下面内容复制进去):

  net.ipv4.ip_local_port_range = 1024 65536

  net.core.rmem_max=16777216

  net.core.wmem_max=16777216

  net.ipv4.tcp_rmem=4096 87380 16777216

  net.ipv4.tcp_wmem=4096 65536 16777216

  net.ipv4.tcp_fin_timeout = 10

  net.ipv4.tcp_tw_recycle = 1

  net.ipv4.tcp_timestamps = 0

  net.ipv4.tcp_window_scaling = 0

  net.ipv4.tcp_sack = 0

  net.core.netdev_max_backlog = 30000

  net.ipv4.tcp_no_metrics_save=1

  net.core.somaxconn = 262144

  net.ipv4.tcp_syncookies = 0

  net.ipv4.tcp_max_orphans = 262144

  net.ipv4.tcp_max_syn_backlog = 262144

  net.ipv4.tcp_synack_retries = 2

  net.ipv4.tcp_syn_retries = 2

  这个配置参考于cache服务器varnish的推荐配置和SunOne 服务器系统优化的推荐配置。

  varnish调优推荐配置的地址为:http://varnish.projects.linpro.no/wiki/Performance

  不过varnish推荐的配置是有问题的,实际运行表明"net.ipv4.tcp_fin_timeout = 3"的配置会导致页面经常打不开;并且当网友使用的是IE6浏览器时,访问网站一段时间后,所有网页都会

  打不开,重启浏览器后正常。可能是国外的网速快吧,我们国情决定需要调整"net.ipv4.tcp_fin_timeout = 10",在10s的情况下,一切正常(实际运行结论)。

  修改完毕后,执行:

  /sbin/sysctl -p /etc/sysctl.conf

  /sbin/sysctl -w net.ipv4.route.flush=1

  命令生效。为了保险起见,也可以reboot系统。

  调整文件数:

  linux系统优化完网络必须调高系统允许打开的文件数才能支持大的并发,默认1024是远远不够的。

  执行命令:

  Shell代码

  echo ulimit -HSn 65536 》 /etc/rc.local

  echo ulimit -HSn 65536 》/root/.bash_profile

  ulimit -HSn 65536

posted @ 2013-11-15 20:00 ivaneeo 阅读(511) | 评论 (0)编辑 收藏

如何设置呢,官方是这样的:

第一步:配置/etc/security/limits.conf

sudo vim /etc/security/limits.conf 文件尾追加  * hard nofile 40960 * soft nofile 40960
4096可以自己设置,四列参数的设置见英文,简单讲一下:

第一列,可以是用户,也可以是组,要用@group这样的语法,也可以是通配符如*%

第二列,两个值:hard,硬限制,soft,软件限制,一般来说soft要比hard小,hard是底线,决对不能超过,超过soft报警,直到hard数

第三列,见列表,打开文件数是nofile

第四列,数量,这个也不能设置太大


第二步:/etc/pam.d/su(官方)或/etc/pam.d/common-session(网络)

sudo vim /etc/pam.d/su 将 pam_limits.so 这一行注释去掉  重起系统
sudo vim /etc/pam.d/common-session 加上以下一行 session required pam_limits.so 

打开/etc/pam.d/su,发现是包含/etc/pam.d/common-session这个文件的,所以修改哪个文件都应该是可以的

我的修改是在/etc/pam.d/common-session文件中进行的。


官方只到第二步,就重启系统了,没有第三步,好象不行,感觉是不是全是第三步的作用?!

第三步:配置/etc/profile

最后一行加上

ulimit -SHn 40960

重启,ulimit -n 验证,显示40960就没问题了


注意以上三步均是要使用root权限进行修改。

posted @ 2013-11-15 19:58 ivaneeo 阅读(3600) | 评论 (0)编辑 收藏

/etc/sysctl.conf

net.core.rmem_default = 25696000
net.core.rmem_max = 25696000
net.core.wmem_default = 25696000
net.core.wmem_max = 25696000
net.ipv4.tcp_timestamps = 0
net.ipv4.tcp_sack =1
net.ipv4.tcp_window_scaling = 1

hotrod方式:
nohup ./bin/startServer.sh -r hotrod -l 172.20.21.1 -c ./etc/config-samples/distributed-udp.xml -p 11222 &
posted @ 2013-11-14 17:56 ivaneeo 阅读(445) | 评论 (0)编辑 收藏

From a convenience perspective, I want to authenticate as infrequently as possible. However, security requirements suggest that I should be authenticated for all sorts of services. This means that Single Sign On and forwardable authentication credentials would be useful.

Within an individual organisation at least, it is useful and fairly straightforward to have centralised control for authentication services. More and more authorisation and applications services are able to use centralised authentication services such as Kerberos.

This document will demonstrate how to configure a machine running OpenSSH server to use GSSAPI so that users can log in if they have authorised kerberos tickets. This is not the place for extensive explanations about tickets or how to set up the Key Distribution Center(KDC) in the first place or how to build or install the necessary software on various different unixlike systems. Likely, your distribution's package management system can provide you with what you need.

Kerberos

All destination machines should have /etc/krb5.conf modified to allow forwardable tickets:

[libdefaults]     default_realm = ALLGOODBITS.ORG     forwardable = TRUE [realms]     ALLGOODBITS.ORG = {                     kdc = kerberos.allgoodbits.org                     } 

Using kadmin, create a principal for a user:

kadmin> ank <username>@<REALM> 

Here the process differs depending upon whether you're using MIT Kerberos (probably) or Heimdal.

MIT

Create a principal for the host:

kadmin> ank -randkey host/<FQDN>@<REALM> 

Extract the key for the host principal to a keytab file and locate it correctly on the ssh server:

kadmin> ktadd -k /tmp/<FQDN>.keytab host/<FQDN> 

Heimdal

Create a principal for the host:

kadmin> ank -r host/<FQDN>@<REALM> 

Extract the key for the host principal to a keytab file and locate it correctly on the ssh server:

kadmin> ext -k /tmp/<FQDN>.keytab host/<FQDN>@<REALM> 

SSH

Then we need to take the keytab file into which you extracted the key for the host principal and copy it to the location on the ssh server where sshd will look for it, probably /etc/krb5.keytab.

We need to configure sshd_config(5). The important options start with GSSAPI, not to be confused with the Kerberos options which are merely for KDC-validated password authentication; the GSSAPI method allows authentication and login based upon existing tickets. In other words, the "Kerberos" method requires you to enter your password (again), GSSAPI will allow login based on upon the tickets you already have.

sshd_config:

GSSAPIAuthentication yes GSSAPICleanupCredentials yes PermitRootLogin without-password 

ssh_config:

GSSAPIAuthentication yes GSSAPIDelegateCredentials yes 

PAM

Linux Pluggable Authentication Modules(PAM) provide a common framework for authentication/authorisation for applications.

/etc/pam.d/common-account:

account sufficient      pam_krb5.so     use_first_pass 

/etc/pam.d/common-auth:

auth    sufficient      pam_krb5.so     use_first_pass 

/etc/pam.d/common-password:

password        sufficient      pam_krb5.so 

/etc/pam.d/common-session:

session optional      pam_krb5.so 

This is sufficient to allow OpenAFS based home directories because although AFS uses Kerberosv4, MIT Kerberos does 5 to 4 ticket conversion on the fly.

Troubleshooting

  • As with anything concerned with kerberos, make sure you have NTP and DNS working properly before you even start.
  • ssh -v can give you a lot of valuable information.
  • read your logs.
posted @ 2013-10-12 18:12 ivaneeo 阅读(318) | 评论 (0)编辑 收藏

nohup ./bin/startServer.sh -r hotrod -l 172.20.21.3 -c ./etc/config-samples/distributed-udp.xml -p 11222 &
posted @ 2013-10-08 10:49 ivaneeo 阅读(450) | 评论 (0)编辑 收藏

https://github.com/sksamuel/elasticsearch-river-hazelcast
posted @ 2013-10-08 00:57 ivaneeo 阅读(414) | 评论 (0)编辑 收藏

ElasticSearch是一个基于Lucene构建的开源,分布式,RESTful搜索引擎。设计用于云计算中,能够达到实时搜索,稳定,可靠,快速,安装使用方便。支持通过HTTP使用JSON进行数据索引。 

  我们建立一个网站或应用程序,并要添加搜索功能,令我们受打击的是:搜索工作是很难的。我们希望我们的搜索解决方案要快,我们希望 有一个零配置和一个完全免费的搜索模式,我们希望能够简单地使用JSON通过HTTP的索引数据,我们希望我们的搜索服务器始终可用,我们希望能够一台开 始并扩展到数百,我们要实时搜索,我们要简单的多租户,我们希望建立一个云的解决方案。Elasticsearch旨在解决所有这些问题和更多的。

安装

  以windows操作系统和ES0.19.7版本为例:

 

  ①下载elasticsearch-0.19.7.zip

 

  ②直接解压至某目录,设置该目录为ES_HOME环境变量

 

  ③安装JDK,并设置JAVA_HOME环境变量

 

  ④在windows下,运行 %ES_HOME%\bin\elasticsearch.bat即可运行

分布式搜索elasticsearch单机与服务器环境搭建

      先到http://www.elasticsearch.org/download/下 载最新版的elasticsearch运行包,本文写时最新的是0.19.1,作者是个很勤快的人,es的更新很频繁,bug修复得很快。下载完解开有三 个包:bin是运行的脚本,config是设置文件,lib是放依赖的包。如果你要装插件的话就要多新建一个plugins的文件夹,把插件放到这个文件 夹中。

1.单机环境:

单机版的elasticsearch运行很简单,linux下直接 bin/elasticsearch就运行了,windows运行bin/elasticsearch.bat。如果是在局域网中运行elasticsearch集群也是很简单的,只要cluster.name设置一致,并且机器在同一网段下,启动的es会自动发现对方,组成集群。

2.服务器环境:

如果是在服务器上就可以使用elasticsearch-servicewrapper这个es插件,它支持通过参数,指定是在后台或前台运行es,并且支持启动,停止,重启es服务(默认es脚本只能通过ctrl+c关闭es)。使用方法是到https://github.com/elasticsearch/elasticsearch-servicewrapper下载service文件夹,放到es的bin目录下。下面是命令集合:
bin/service/elasticsearch +
console 在前台运行es
start 在后台运行es
stop 停止es
install 使es作为服务在服务器启动时自动启动
remove 取消启动时自动启动

在service目录下有个elasticsearch.conf配置文件,主要是设置一些java运行环境参数,其中比较重要的是下面的

参数:

#es的home路径,不用用默认值就可以
set.default.ES_HOME=<Path to ElasticSearch Home>

#分配给es的最小内存
set.default.ES_MIN_MEM=256

#分配给es的最大内存
set.default.ES_MAX_MEM=1024


# 启动等待超时时间(以秒为单位)
wrapper.startup.timeout=300

# 关闭等待超时时间(以秒为单位)

wrapper.shutdown.timeout=300

# ping超时时间(以秒为单位)

wrapper.ping.timeout=300

安装插件

  以head插件为例:

 

  联网时,直接运行%ES_HOME%\bin\plugin -install mobz/elasticsearch-head

 

  不联网时,下载elasticsearch-head的zipball的master包,把内容解压到%ES_HOME%\plugin\head\_site目录下,[该插件为site类型插件]

 

  安装完成,重启服务,在浏览器打开 http://localhost:9200/_plugin/head/ 即可

ES概念

  cluster

 

  代表一个集群,集群中有多个节点,其中有一个为主节点,这个主节点是可以通过选举产生的,主从节点是对于集群内部来说 的。es的一个概念就是去中心化,字面上理解就是无中心节点,这是对于集群外部来说的,因为从外部来看es集群,在逻辑上是个整体,你与任何一个节点的通 信和与整个es集群通信是等价的。

 

  shards

 

  代表索引分片,es可以把一个完整的索引分成多个分片,这样的好处是可以把一个大的索引拆分成多个,分布到不同的节点上。构成分布式搜索。分片的数量只能在索引创建前指定,并且索引创建后不能更改。

 

  replicas

 

  代表索引副本,es可以设置多个索引的副本,副本的作用一是提高系统的容错性,当个某个节点某个分片损坏或丢失时可以从副本中恢复。二是提高es的查询效率,es会自动对搜索请求进行负载均衡。

 

  recovery

 

  代表数据恢复或叫数据重新分布,es在有节点加入或退出时会根据机器的负载对索引分片进行重新分配,挂掉的节点重新启动时也会进行数据恢复。

 

  river

 

  代表es的一个数据源,也是其它存储方式(如:数据库)同步数据到es的一个方法。它是以插件方式存在的一个es服 务,通过读取river中的数据并把它索引到es中,官方的river有couchDB的,RabbitMQ的,Twitter的,Wikipedia 的。

 

  gateway

 

  代表es索引的持久化存储方式,es默认是先把索引存放到内存中,当内存满了时再持久化到硬盘。当这个es集群关闭再 重新启动时就会从gateway中读取索引数据。es支持多种类型的gateway,有本地文件系统(默认),分布式文件系统,Hadoop的HDFS和 amazon的s3云存储服务。

 

  discovery.zen

 

  代表es的自动发现节点机制,es是一个基于p2p的系统,它先通过广播寻找存在的节点,再通过多播协议来进行节点之间的通信,同时也支持点对点的交互。

 

  Transport

 

  代表es内部节点或集群与客户端的交互方式,默认内部是使用tcp协议进行交互,同时它支持http协议(json格式)、thrift、servlet、memcached、zeroMQ等的传输协议(通过插件方式集成)。

分布式搜索elasticsearch中文分词集成

elasticsearch官方只提供smartcn这个中文分词插件,效果不是很好,好在国内有medcl大神(国内最早研究es的人之一)写的两个中文分词插件,一个是ik的,一个是mmseg的,下面分别介绍下两者的用法,其实都差不多的,先安装插件,命令行:
安装ik插件:

plugin -install medcl/elasticsearch-analysis-ik/1.1.0  

下载ik相关配置词典文件到config目录

  1. cd config  
  2. wget http://github.com/downloads/medcl/elasticsearch-analysis-ik/ik.zip --no-check-certificate  
  3. unzip ik.zip  
  4. rm ik.zip  

安装mmseg插件:

  1. bin/plugin -install medcl/elasticsearch-analysis-mmseg/1.1.0  

下载相关配置词典文件到config目录

  1. cd config  
  2. wget http://github.com/downloads/medcl/elasticsearch-analysis-mmseg/mmseg.zip --no-check-certificate  
  3. unzip mmseg.zip  
  4. rm mmseg.zip  

分词配置

ik分词配置,在elasticsearch.yml文件中加上

  1. index:  
  2.   analysis:                     
  3.     analyzer:        
  4.       ik:  
  5.           alias: [ik_analyzer]  
  6.           type: org.elasticsearch.index.analysis.IkAnalyzerProvider  

  1. index.analysis.analyzer.ik.type : “ik”  

这两句的意义相同
mmseg分词配置,也是在在elasticsearch.yml文件中

  1. index:  
  2.   analysis:  
  3.     analyzer:  
  4.       mmseg:  
  5.           alias: [news_analyzer, mmseg_analyzer]  
  6.           type: org.elasticsearch.index.analysis.MMsegAnalyzerProvider  

  1. index.analysis.analyzer.default.type : "mmseg"  

mmseg分词还有些更加个性化的参数设置如下

  1. index:  
  2.   analysis:  
  3.     tokenizer:  
  4.       mmseg_maxword:  
  5.           type: mmseg  
  6.           seg_type: "max_word"  
  7.       mmseg_complex:  
  8.           type: mmseg  
  9.           seg_type: "complex"  
  10.       mmseg_simple:  
  11.           type: mmseg  
  12.           seg_type: "simple"  

这样配置完后插件安装完成,启动es就会加载插件。

定义mapping

在添加索引的mapping时就可以这样定义分词器

  1. {  
  2.    "page":{  
  3.       "properties":{  
  4.          "title":{  
  5.             "type":"string",  
  6.             "indexAnalyzer":"ik",  
  7.             "searchAnalyzer":"ik"  
  8.          },  
  9.          "content":{  
  10.             "type":"string",  
  11.             "indexAnalyzer":"ik",  
  12.             "searchAnalyzer":"ik"  
  13.          }  
  14.       }  
  15.    }  
  16. }  

indexAnalyzer为索引时使用的分词器,searchAnalyzer为搜索时使用的分词器。

java mapping代码如下:

  1. XContentBuilder content = XContentFactory.jsonBuilder().startObject()  
  2.         .startObject("page")  
  3.           .startObject("properties")         
  4.             .startObject("title")  
  5.               .field("type", "string")             
  6.               .field("indexAnalyzer", "ik")  
  7.               .field("searchAnalyzer", "ik")  
  8.             .endObject()   
  9.             .startObject("code")  
  10.               .field("type", "string")           
  11.               .field("indexAnalyzer", "ik")  
  12.               .field("searchAnalyzer", "ik")  
  13.             .endObject()       
  14.           .endObject()  
  15.          .endObject()  
  16.        .endObject()  

定义完后操作索引就会以指定的分词器来进行分词。

 附:

ik分词插件项目地址:https://github.com/medcl/elasticsearch-analysis-ik

mmseg分词插件项目地址:https://github.com/medcl/elasticsearch-analysis-mmseg

如果觉得配置麻烦,也可以下载个配置好的es版本,地址如下:https://github.com/medcl/elasticsearch-rtf

 

elasticsearch的基本用法


最大的特点: 
1. 数据库的 database, 就是  index 
2. 数据库的 table,  就是 tag 
3. 不要使用browser, 使用curl来进行客户端操作.  否则会出现 java heap ooxx... 

curl:  -X 后面跟 RESTful :  GET, POST ... 
-d 后面跟数据。 (d = data to send) 

1. create:  

指定 ID 来建立新记录。 (貌似PUT, POST都可以) 
$ curl -XPOST localhost:9200/films/md/2 -d ' 
{ "name":"hei yi ren", "tag": "good"}' 

使用自动生成的 ID 建立新纪录: 
$ curl -XPOST localhost:9200/films/md -d ' 
{ "name":"ma da jia si jia3", "tag": "good"}' 

2. 查询: 
2.1 查询所有的 index, type: 
$ curl localhost:9200/_search?pretty=true 

2.2 查询某个index下所有的type: 
$ curl localhost:9200/films/_search 

2.3 查询某个index 下, 某个 type下所有的记录: 
$ curl localhost:9200/films/md/_search?pretty=true 

2.4 带有参数的查询:  
$ curl localhost:9200/films/md/_search?q=tag:good 
{"took":7,"timed_out":false,"_shards":{"total":5,"successful":5,"failed":0},"hits":{"total":2,"max_score":1.0,"hits":[{"_index":"film","_type":"md","_id":"2","_score":1.0, "_source" : 
{ "name":"hei yi ren", "tag": "good"}},{"_index":"film","_type":"md","_id":"1","_score":0.30685282, "_source" : 
{ "name":"ma da jia si jia", "tag": "good"}}]}} 

2.5 使用JSON参数的查询: (注意 query 和 term 关键字) 
$ curl localhost:9200/film/_search -d ' 
{"query" : { "term": { "tag":"bad"}}}' 

3. update  
$ curl -XPUT localhost:9200/films/md/1 -d { ...(data)... } 

4. 删除。 删除所有的: 
$ curl -XDELETE localhost:9200/films
posted @ 2013-10-04 02:09 ivaneeo 阅读(16756) | 评论 (0)编辑 收藏

在debian6中,加入开机启动脚本的方法与debian5不同了,直接做符号链接到runlevel已经不起作用了,提示缺少LSB信息,并且用insserv来替代update-rc.d:

root@14:/etc/rc2.d# update-rc.d -n  php_fastcgi.sh  defaults           
update-rc.d: using dependency based boot sequencing
insserv: warning: script 'K02php_fastcgi' missing LSB tags and overrides
insserv: warning: script 'K01php_fastcgi.sh' missing LSB tags and overrides
insserv: warning: script 'php_fastcgi.sh' missing LSB tags and overrides
insserv: warning: current start runlevel(s) (empty) of script `php_fastcgi.sh' overwrites defaults (2 3 4 5).
insserv: warning: current stop runlevel(s) (0) of script `php_fastcgi.sh' overwrites defaults (0 1 6).
insserv: dryrun, not creating .depend.boot, .depend.start, and .depend.stop

# insserv /etc/init.d/php_fastcgi.sh
insserv: warning: script 'K02php_fastcgi' missing LSB tags and overrides
insserv: warning: script 'php_fastcgi.sh' missing LSB tags and overrides

 

debian6中将脚本加入到开机启动的方法:

在脚本中加入LSB描述信息。
root@14:~# more  /etc/init.d/php_fastcgi.sh   
#!/bin/sh
### BEGIN INIT INFO
# Provides:          php_fastcgi.sh
# Required-Start:    $local_fs $remote_fs $network $syslog
# Required-Stop:     $local_fs $remote_fs $network $syslog
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Short-Description: starts the php_fastcgi daemon
# Description:       starts php_fastcgi using start-stop-daemon
### END INIT INFO

安装启动脚本到system init script。
root@14:~# insserv -v -d /etc/init.d/php_fastcgi.sh

重启机器试试吧。

posted @ 2013-09-29 14:45 ivaneeo 阅读(4816) | 评论 (0)编辑 收藏

linux 广播 255.255.255.255

               sendto error: Network is unreachable

              全网广播


场景:

    今天调试linux 网络编程的广播,当向255.255.255.255 的某个端口发送广播包的时候,sendto 返回 -1,错误原因是:

sendto error: Network is unreachable。


2. 指令的解决方法:

oute add -net 255.255.255.255 netmask 255.255.255.255 dev eth0 metric 1

或者

route add -host 255.255.255.255 dev eth0



http://blog.csdn.net/qiaoliang328/article/details/8881474
posted @ 2013-09-10 19:40 ivaneeo 阅读(626) | 评论 (0)编辑 收藏

devcon install c:\windows\inf\netloop.inf *MSLOOP
posted @ 2013-08-17 11:20 ivaneeo 阅读(516) | 评论 (0)编辑 收藏

reg add "HKEY_CURRENT_USER\Software\Microsoft\Windows\ShellNoRoam" /v @ /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Control\ComputerName\ComputerName" /v "ComputerName" /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Control\ComputerName\ActiveComputerName" /v "ComputerName" /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Services\Eventlog" /v "ComputerName" /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Control\ComputerName\ComputerName" /v "ComputerName" /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" /v "NV Hostname" /t REG_SZ /d "%Name%" /f
reg add "HKLM\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" /v "Hostname" /t REG_SZ /d "%Name%" /f
posted @ 2013-08-14 22:38 ivaneeo 阅读(304) | 评论 (0)编辑 收藏

Impala是由Cloudera开发的高性能实时计算工具,相比Hive性能提升了几十、甚至近百倍,基本思想是将计算分发到每个 Datanode所在的节点,依靠内存实现数据的缓存进行快速计算,类似的系统还有Berkeley的Shark。从实际测试来看,Impala效率确实 不错,由于Impala大量使用C++实现,不使用CDH的Image而自己编译安装要费不少功夫,这里记录一下安装配置过程和碰到的一些问题。我在测试 时候使用的是CentOS6.2。
一些基本的安装步骤在这里,但我在安装的时候碰到一些问题,这里再详细说明一下过程。

1.安装所需的依赖lib,这一步没有什么不同

sudo yum install boost-test boost-program-options libevent-devel automake libtool flex bison gcc-c++ openssl-devel make cmake doxygen.x86_64 glib-devel boost-devel python-devel bzip2-devel svn libevent-devel cyrus-sasl-devel wget git unzip

2.安装LLVM,按照流程做即可,注意要在多台机器上编译安装Impala的话,只用在一台机器上执行下面蓝色的部分,再把llvm分发到多台机器上执行后面红色部分的指令就可以了,没必要每个机器都通过svn下载一遍源代码,很费时。

wget http://llvm.org/releases/3.2/llvm-3.2.src.tar.gz
tar xvzf llvm-3.2.src.tar.gz
cd llvm-3.2.src/tools
svn co http://llvm.org/svn/llvm-project/cfe/tags/RELEASE_32/final/ clang
cd ../projects
svn co http://llvm.org/svn/llvm-project/compiler-rt/tags/RELEASE_32/final/ compiler-rt
cd ..
./configure –with-pic
make -j4 REQUIRES_RTTI=1
sudo make install

3.安装Maven,这个没什么好说的,按照步骤,设置一下环境变量即可,Maven是为了后面build impala源代码用的。

wget http://www.fightrice.com/mirrors/apache/maven/maven-3/3.0.4/binaries/apache-maven-3.0.4-bin.tar.gz
tar xvf apache-maven-3.0.4.tar.gz && sudo mv apache-maven-3.0.4 /usr/local

修改~/.bashrc,增加maven环境变量

export M2_HOME=/usr/local/apache-maven-3.0.4
export M2=$M2_HOME/bin
export PATH=$M2:$PATH

更新环境变量,查看mvn版本是否正确

source ~/.bashrc
mvn -version

4.下载Impala源代码

git clone https://github.com/cloudera/impala.git

5.设置Impala环境变量,编译时需要

cd impala
./bin/impala-config.sh

6.下载impala依赖的第三方package

cd thirdparty
./download_thirdparty.sh

注意这里其中一个包cyrus-sasl-2.1.23可能下载失败,可以自行搜索(CSDN里面就有)下载下来然后解压缩到thirdparty 文件夹,最好是在执行完download_thirdparty.sh之后做这一步,因为download_thirdparty.sh会把所有目录下下 载下来的tar.gz给删除掉。

7.理论上现在可以开始build impala了,但是实际build过程中可能会出现问题,我碰到的问题和 Boost相关的(具体错误不记得了),最后发现是由于boost版本太低导致的,CentOS 6.2系统默认yum源中的boost和boost-devel版本是1.41,但是impala编译需要1.44以上的版本,因此需要做的是自己重新编 译boost,我用的是boost 1.46版本。

#删除已安装的boost和boost-devel
yum remove boost
yum remove boost-devel
#下载boost
#可以去(http://www.boost.org/users/history/)下载boost
#下载后解压缩
tar xvzf boost_1_46_0.tar.gz
mv boost_1_46_0 /usr/local/
cd /usr/include
./bootstrap.sh
./bjam
#执行后若打印以下内容,则表示安装成功
# The Boost C++ Libraries were successfully built!
# The following directory should be added to compiler include paths:
# /usr/local/boost_1_46_0
# The following directory should be added to linker library paths:
# /usr/local/boost_1_46_0/stage/lib
#现在还需要设置Boost环境变量和Impala环境变量

export BOOST_ROOT=’/usr/local/boost_1_46_0′
export IMPALA_HOME=’/home/extend/impala’

#注意一下,这里虽然安装了boost,但是我在实际使用的时候,编译还是会报错的,报的错误是找不到这个包:#libboost_filesystem-mt.so,这个包是由boost-devel提供的,所以我的做法是把boost-devel给重新装上
#我没有试过如果之前不删除boost-devel会不会有问题,能确定的是按这里写的流程做是没问题的

yum install boost-devel

8.现在终于可以编译impala了

cd $IMPALA_HOME
./build_public.sh -build_thirdparty
#编译首先会编译C++部分,然后再用mvn编译java部分,整个过程比较慢,我在虚拟机上大概需要1-2个小时。
#Impala编译完后的东西在be/build/debug里面

9.启动impala_shell需要用到的python包

#第一次执行impalad_shell可能会报错,这里需要安装python的两个包:thrift和prettytable,使用easy_install即可
easy_install prettytable
easy_install thrift

10.如果你以为到这里就万事大吉就太天真了,在配置、启动、使用Impala的时候还会有很多奇葩的问题;

问题1:Hive和Hadoop使用的版本
CDH对版本的依赖要求比较高,为了保证Impala正常运行,强烈建议使用Impala里面thirdparty目录中自带的Hadoop(native lib已经编译好的)和Hive版本。
Hadoop的配置文件在$HADOOP_HOME/etc/hadoop中,要注意的是需要启用native lib

#修改hadoop的core-site.xml,除了这个选项之外,其他配置和问题2中的core-site.xml一致
<property>
  <name>hadoop.native.lib</name>
  <value>true</value>
  <description>Should native hadoop libraries, if present, be used.</description>
</property>

问题2:Impala的配置文件位置
Impala默认使用的配置文件路径是在bin/set-classpath.sh中配置的,建议把CLASSPATH部分改成

CLASSPATH=\
$IMPALA_HOME/conf:\
$IMPALA_HOME/fe/target/classes:\
$IMPALA_HOME/fe/target/dependency:\
$IMPALA_HOME/fe/target/test-classes:\
${HIVE_HOME}/lib/datanucleus-core-2.0.3.jar:\
${HIVE_HOME}/lib/datanucleus-enhancer-2.0.3.jar:\
${HIVE_HOME}/lib/datanucleus-rdbms-2.0.3.jar:\
${HIVE_HOME}/lib/datanucleus-connectionpool-2.0.3.jar:

即要求Impala使用其目录下的Conf文件夹作为配置文件,然后创建一下Conf目录,把3样东西拷贝进来:core-site.xml、hdfs-site.xml、hive-site.xml。
core-site.xml的配置,下面几个选项是必须要配置的,

<?xml version="1.0"?>
<?xml-stylesheet type="text/xsl" href="configuration.xsl"?>
<configuration>
<property>
<name>fs.defaultFS</name>
<value>hdfs://10.200.4.11:9000</value>
</property>
<property>
<name>dfs.client.read.shortcircuit</name>
<value>true</value>
</property>
<property>
<name>dfs.client.use.legacy.blockreader.local</name>
<value>false</value>
</property>
<property>
<name>dfs.client.read.shortcircuit.skip.checksum</name>
<value>false</value>
</property>
</configuration>

hdfs-site.xml的配置

<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="configuration.xsl"?>
<configuration>
<property>
<name>dfs.block.local-path-access.user</name>
<value>${your user}</value>
</property>
<property>
<name>dfs.datanode.hdfs-blocks-metadata.enabled</name>
<value>true</value>
</property>
<property>
<name>dfs.datanode.data.dir</name>
<value>${yourdatadir}</value>
</property>
<property>
   <name>dfs.client.use.legacy.blockreader.local</name>
   <value>false</value>
</property>
<property>
   <name>dfs.datanode.data.dir.perm</name>
   <value>750</value>
</property>
<property>
    <name>dfs.client.file-block-storage-locations.timeout</name>
    <value>5000</value>
</property>
<property>
    <name>dfs.domain.socket.path</name>
    <value>/home/extend/cdhhadoop/dn.8075</value>
</property>
</configuration>

最后是hive-site.xml,这个比较简单,指定使用DBMS为元数据存储即可(impala必须和hive共享元数据,因为impala无 法create table);Hive-site.xml使用mysql作为metastore的说明在很多地方都可以查到,配置如下:

<?xml version="1.0"?>
<?xml-stylesheet type="text/xsl" href="configuration.xsl"?>
<configuration>
<property>
  <name>javax.jdo.option.ConnectionURL</name>
  <value>jdbc:mysql://10.28.0.190:3306/impala?createDatabaseIfNotExist=true</value>
  <description>JDBC connect string for a JDBC metastore</description>
</property>
<property>
  <name>javax.jdo.option.ConnectionDriverName</name>
  <value>com.mysql.jdbc.Driver</value>
  <description>Driver class name for a JDBC metastore</description>
</property>

<property>
  <name>javax.jdo.option.ConnectionUserName</name>
  <value>root</value>
  <description>username to use against metastore database</description>
</property>
<property>
  <name>javax.jdo.option.ConnectionPassword</name>
  <value>root</value>
  <description>password to use against metastore database</description>
</property>
</configuration>

记得把mysql-connector的jar包给拷贝到hive的lib里面去,同样也要拷贝给impala ( 拷贝至$IMPALA_HOME/fe/target/dependency)

11.启动Impala。到此,Impala是可以正常启动的。这里说明一下,官方文档没有说很清楚Impala的Service之间是如何互相协调的,按照官方的步骤,最后通过如下方法来在一台机器上启动Impala Service:

#启动单机impala service
${IMPALA_HOME}/bin/start-impalad.sh -use_statestore=false
#启动impala shell
${IMPALA_HOME}/bin/impala-shell.sh

然后impala-shell就可以连接到localhost进行查询了;注意,这里只是单机查询,可以用来验证你的Impala是否正常work 了;如何启动一个Impala集群,跳到第12步。这里继续说一下可能遇到的问题,我遇到的一个比较奇葩的问题是show tables和count(1)没有问题,但是select * from table的时候impala在读取数据的时候就崩溃了(有时报错could not find method close from class org/apache/hadoop/fs/FSDataInputStream with signature ()V ),这里修改了两个地方解决这个问题:

a.修改impala的set-classpath.sh并移除$IMPALA_HOME/fe/target/dependency目录中除了hadoop-auth-2.0.0-*.jar之外所有hadoop-*开头的jar包。

#把impala dependency中和hadoop相关的包给弄出来,只保留auth
mv $IMPALA_HOME/fe/target/dependency/hadoo* $IMPALA_HOME
mv $IMPALA_HOME/hadoop-auth*.jar mv $IMPALA_HOME/fe/target/dependency
#修改bin/set-classpath.sh,将$HADOOP_HOME中的lib给加入,在set-classpath.sh最后一行export CLASSPATH之前#添加
for jar in `ls $HADOOP_HOME/share/hadoop/common/*.jar`; do
CLASSPATH=${CLASSPATH}:$jar
done
for jar in `ls $HADOOP_HOME/share/hadoop/yarn/*.jar`; do
CLASSPATH=${CLASSPATH}:$jar
done
for jar in `ls $HADOOP_HOME/share/hadoop/hdfs/*.jar`; do
CLASSPATH=${CLASSPATH}:$jar
done
for jar in `ls $HADOOP_HOME/share/hadoop/mapreduce/*.jar`; do
CLASSPATH=${CLASSPATH}:$jar
done
for jar in `ls $HADOOP_HOME/share/hadoop/tools/lib/*.jar`; do
CLASSPATH=${CLASSPATH}:$jar
done

b.注意到Impala对待table的时候只能够使用hive的默认列分隔符,如果在hive里面create table的时候使用了自定义的分隔符,Impala servive就会在读数据的时候莫名其妙的崩溃。

12.启动Impala 集群
Impala实际上由两部分组成,一个是StateStore,用来协调各个机器计算,相当于Master,然后就是Impalad,相当于Slave,启动方法如下:

#启动statestore
#方法1,直接利用impala/bin下面的这个python脚本
#这个脚本会启动一个StateStore,同时启动-s个数量的Impala Service在本机
$IMPALA_HOME/bin/start-impala-cluster.py -s 1 –log_dir /home/extend/impala/impalaLogs
#方法2,手动启动StateStore
$IMPALA_HOME/be/build/debug/statestore/statestored -state_store_port=24000

#启动impala service
#在每个编译安装了impala的节点上执行命令
#参数-state_store_host指定启动了stateStore的机器名
#-nn即namenode,指定hadoop的namenode
#-nn_port是namenode的HDFS入口端口号
$IMPALA_HOME/bin/start-impalad.sh -state_store_host=m11 -nn=m11 -nn_port=9000

正常启动之后,访问http://${stateStore_Server}:25010/ 可以看到StateStore的状态,其中的subscribers页面可以看到已经连接上的impala service node;

13.使用Impala客户端
这一步最简单,随便找一个机器启动

$IMPALA_HOME/bin/impala-shell.sh
#启动之后可以随便连接一个impala service
connect m12
#连接上之后就可以执行show tables之类的操作了
#需要注意的是,如果hive创建表或更新了表结构,impala的节点是不知道的
#必须通过客户端连接各个impala service并执行refresh来刷新metadata
#或者重启所有impala service
posted @ 2013-06-29 17:12 ivaneeo 阅读(1731) | 评论 (1)编辑 收藏

nohup ./bin/startServer.sh -r hotrod -l 172.20.21.1 -c ./etc/config-samples/distributed-udp.xml -p 11222 &
posted @ 2013-06-07 19:32 ivaneeo 阅读(279) | 评论 (0)编辑 收藏

http://www.ibm.com/developerworks/cn/aix/library/au-kerbauthent/
posted @ 2013-05-20 12:15 ivaneeo 阅读(274) | 评论 (0)编辑 收藏

Kerberos Server Configuration

These notes are for MIT Kerberos 1.3 or higher.

  • /etc/krb5.conf
  • The /etc/krb5.conf configuration file should include rc4-hmac support under the [libdefaults] section. Windows XP uses rc4-hmac. However, do not include rc4-hmac in the default* encryption types, as older Unix clients may not support rc4-hmac.

    [libdefaults]
    default_realm = EXAMPLE.ORG
    default_etypes = des3-hmac-sha1 des-cbc-crc
    default_tkt_enctypes = des3-hmac-sha1 des-cbc-crc
    default_tgs_enctypes = des3-hmac-sha1 des-cbc-crc
    permitted_enctypes = des3-hmac-sha1 des-cbc-crc rc4-hmac
    dns_lookup_realm = false
    dns_lookup_kdc = true

  • kdc.conf
  • The kdc.conf configuration file on the Kerberos servers must support rc4-hmac as an encryption type.

    [realms]
    EXAMPLE.ORG = {
    database_name = /var/kerberos/krb5kdc/principal
    key_stash_file = /var/kerberos/krb5kdc/.k5.EXAMPLE.ORG
    supported_enctypes = des3-hmac-sha1:normal des-cbc-crc:normal ?
    rc4-hmac:normal
    }

Windows Client Setup

  • Kerberos Configuration
  • Use the ksetup.exe command to add the site Kerberos servers.

    $ ksetup.exe /addkdc EXAMPLE.ORG kerberos-1.example.org
    $ ksetup.exe /addkdc EXAMPLE.ORG kerberos-2.example.org
    $ ksetup.exe /addkdc EXAMPLE.ORG kerberos.example.org
    $ ksetup.exe /addkpasswd EXAMPLE.ORG kerberos.example.org
    $ ksetup.exe /setrealm EXAMPLE.ORG

  • Host principals
  • Create host principals on each Windows client, then use the same password to create an equivalent principal in the MIT Kerberos database. If using an installation system such as Unattended, use a script to generate the random password and setup the host principal.

    #!/usr/bin/perl

    my $domain = 'example.org';

    my $password = '';
    my @chars = grep { /[[:print:]]/ and /\S/ } map { chr } 1..128;
    $password .= $chars[rand @chars] for 1..(int (rand 7)) + 8;

    system qw{ksetup.exe /setcomputerpassword}, $password;

    print "Principal: host/", lc( $ENV{COMPUTERNAME} ), ".$domain\n";
    print "Password: $password\n";

    Then, use kdamin to add an equivalent principal to the Kerberos database, using the same password as above. Use the -e rc4-hmac:normal encryption option if adding a principal for a Windows XP system.

    kadmin: ank -e rc4-hmac:normal host/client.example.org

  • User Mapping
  • User mapping translates local accounts to the Kerberos domain. See module:users for user account management under CFEngine.

    $ ksetup.exe /mapuser * *

Samba

Windows clients can authenticate to Samba using Kerberos. Use Samba version 3.0.14a or higher on the server, and enable Kerberos support in the smb.conf configuration file.

[global]
use kerberos keytab = yes
realm = EXAMPLE.ORG
security = ads

Multiple host and cifs principals must be created for each Samba server, as principals are case sensitive, and Windows systems may randomly start using Server.example.org or SERVER.EXAMPLE.ORG when connecting. Extract these principals to the /etc/krb5.keytab file on each Samba server.

kadmin: ank -randkey host/server.example.org
kadmin: ank -randkey host/Server.example.org
kadmin: ank -randkey host/SERVER.EXAMPLE.ORG
kadmin: ank -randkey cifs/server.example.org
kadmin: ank -randkey cifs/Server.example.org
kadmin: ank -randkey cifs/SERVER.EXAMPLE.ORG
kadmin: ktadd -k /etc/krb5.keytab host/server.example.org
kadmin: ktadd -k /etc/krb5.keytab host/Server.example.org
kadmin: ktadd -k /etc/krb5.keytab host/SERVER.EXAMPLE.ORG
kadmin: ktadd -k /etc/krb5.keytab cifs/server.example.org
kadmin: ktadd -k /etc/krb5.keytab cifs/Server.example.org
kadmin: ktadd -k /etc/krb5.keytab cifs/SERVER.EXAMPLE.ORG

posted @ 2013-05-18 15:04 ivaneeo 阅读(352) | 评论 (0)编辑 收藏


1.首先安装后,有一个180天的试用期。
2.在180天试用期即将结束时,使用下面的评估序列号激活Svr 2008 R2 可以重新恢复180天试用期
Windows Server 2008 R2 Web: KBV3Q-DJ8W7-VPB64-V88KG-82C49
Windows Server 2008 R2 Standard: 4GGC4-9947F-FWFP3-78P6F-J9HDR
Windows Server 2008 R2 Enterprise: 7PJBC-63K3J-62TTK-XF46D-W3WMD
Windows Server 2008 R2 Datacenter: QX7TD-2CMJR-D7WWY-KVCYC-6D2YT
3.在180天试用期即将结束时,用“Rearm”后,重新输入上面的序列号,重启电脑,剩余时间又恢复到180天。微软官方文档中声明该命令只能重复使用5次。
4.上面的方法5次后,此后将无法再次使用。就要进行下一步,修改注册表中的一处键值(SkipRearm),以后就可以再次使用“Rearm”的命令,这个键值总共可以修改8次。
5.因此……。
posted @ 2013-05-08 17:47 ivaneeo 阅读(326) | 评论 (0)编辑 收藏

        char Str[20];
        int ret;
        ret = sprintf(Str, "%llu",ifconfig.flags);
posted @ 2013-04-22 21:29 ivaneeo 阅读(299) | 评论 (0)编辑 收藏

1.资源池要展示的。
2.在初始化和后期是可以管理的。
分别在资源中心和基础设施里面加模块就可以了。
资源中心就是展示。
不参与管理。
资源中心全是统计性的和展示性的。
posted @ 2012-12-29 23:11 ivaneeo 阅读(308) | 评论 (0)编辑 收藏


https://help.ubuntu.com/10.04/serverguide/kerberos.html

Kerberos

Kerberos is a network authentication system based on the principal of a trusted third party. The other two parties being the user and the service the user wishes to authenticate to. Not all services and applications can use Kerberos, but for those that can, it brings the network environment one step closer to being Single Sign On (SSO).

This section covers installation and configuration of a Kerberos server, and some example client configurations.

Overview

If you are new to Kerberos there are a few terms that are good to understand before setting up a Kerberos server. Most of the terms will relate to things you may be familiar with in other environments:

  • Principal: any users, computers, and services provided by servers need to be defined as Kerberos Principals.

  • Instances: are used for service principals and special administrative principals.

  • Realms: the unique realm of control provided by the Kerberos installation. Usually the DNS domain converted to uppercase (EXAMPLE.COM).

  • Key Distribution Center: (KDC) consist of three parts, a database of all principals, the authentication server, and the ticket granting server. For each realm there must be at least one KDC.

  • Ticket Granting Ticket: issued by the Authentication Server (AS), the Ticket Granting Ticket (TGT) is encrypted in the user's password which is known only to the user and the KDC.

  • Ticket Granting Server: (TGS) issues service tickets to clients upon request.

  • Tickets: confirm the identity of the two principals. One principal being a user and the other a service requested by the user. Tickets establish an encryption key used for secure communication during the authenticated session.

  • Keytab Files: are files extracted from the KDC principal database and contain the encryption key for a service or host.

To put the pieces together, a Realm has at least one KDC, preferably two for redundancy, which contains a database of Principals. When a user principal logs into a workstation, configured for Kerberos authentication, the KDC issues a Ticket Granting Ticket (TGT). If the user supplied credentials match, the user is authenticated and can then request tickets for Kerberized services from the Ticket Granting Server (TGS). The service tickets allow the user to authenticate to the service without entering another username and password.

Kerberos Server

Installation

Before installing the Kerberos server a properly configured DNS server is needed for your domain. Since the Kerberos Realm by convention matches the domain name, this section uses the example.com domain configured in the section called “Primary Master”.

Also, Kerberos is a time sensitive protocol. So if the local system time between a client machine and the server differs by more than five minutes (by default), the workstation will not be able to authenticate. To correct the problem all hosts should have their time synchronized using the Network Time Protocol (NTP). For details on setting up NTP see the section called “Time Synchronisation with NTP”.

The first step in installing a Kerberos Realm is to install the krb5-kdc and krb5-admin-server packages. From a terminal enter:

sudo apt-get install krb5-kdc krb5-admin-server

You will be asked at the end of the install to supply a name for the Kerberos and Admin servers, which may or may not be the same server, for the realm.

Next, create the new realm with the kdb5_newrealm utility:

sudo krb5_newrealm

Configuration

The questions asked during installation are used to configure the /etc/krb5.conf file. If you need to adjust the Key Distribution Center (KDC) settings simply edit the file and restart the krb5-kdc daemon.

  1. Now that the KDC running an admin user is needed. It is recommended to use a different username from your everyday username. Using the kadmin.local utility in a terminal prompt enter:

    sudo kadmin.local
    Authenticating as principal root/admin@EXAMPLE.COM with password.
    kadmin.local: addprinc steve/admin
    WARNING: no policy specified for steve/admin@EXAMPLE.COM; defaulting to no policy
    Enter password for principal "steve/admin@EXAMPLE.COM": 
    Re-enter password for principal "steve/admin@EXAMPLE.COM": 
    Principal "steve/admin@EXAMPLE.COM" created.
    kadmin.local: quit
    

    In the above example steve is the Principal, /admin is an Instance, and @EXAMPLE.COM signifies the realm. The "every day" Principal would be steve@EXAMPLE.COM, and should have only normal user rights.

    [Note]

    Replace EXAMPLE.COM and steve with your Realm and admin username.

  2. Next, the new admin user needs to have the appropriate Access Control List (ACL) permissions. The permissions are configured in the /etc/krb5kdc/kadm5.acl file:

    steve/admin@EXAMPLE.COM        *
    

    This entry grants steve/admin the ability to perform any operation on all principals in the realm.

  3. Now restart the krb5-admin-server for the new ACL to take affect:

    sudo /etc/init.d/krb5-admin-server restart
    
  4. The new user principal can be tested using the kinit utility:

    kinit steve/admin
    steve/admin@EXAMPLE.COM's Password:
    

    After entering the password, use the klist utility to view information about the Ticket Granting Ticket (TGT):

    klist
    Credentials cache: FILE:/tmp/krb5cc_1000
            Principal: steve/admin@EXAMPLE.COM
    
      Issued           Expires          Principal
    Jul 13 17:53:34  Jul 14 03:53:34  krbtgt/EXAMPLE.COM@EXAMPLE.COM
    

    You may need to add an entry into the /etc/hosts for the KDC. For example:

    192.168.0.1   kdc01.example.com       kdc01
    

    Replacing 192.168.0.1 with the IP address of your KDC.

  5. In order for clients to determine the KDC for the Realm some DNS SRV records are needed. Add the following to /etc/named/db.example.com:

    _kerberos._udp.EXAMPLE.COM.     IN SRV 1  0 88  kdc01.example.com.
    _kerberos._tcp.EXAMPLE.COM.     IN SRV 1  0 88  kdc01.example.com.
    _kerberos._udp.EXAMPLE.COM.     IN SRV 10 0 88  kdc02.example.com. 
    _kerberos._tcp.EXAMPLE.COM.     IN SRV 10 0 88  kdc02.example.com. 
    _kerberos-adm._tcp.EXAMPLE.COM. IN SRV 1  0 749 kdc01.example.com.
    _kpasswd._udp.EXAMPLE.COM.      IN SRV 1  0 464 kdc01.example.com.
    
    [Note]

    Replace EXAMPLE.COM, kdc01, and kdc02 with your domain name, primary KDC, and secondary KDC.

    See Chapter 7, Domain Name Service (DNS) for detailed instructions on setting up DNS.

Your new Kerberos Realm is now ready to authenticate clients.

Secondary KDC

Once you have one Key Distribution Center (KDC) on your network, it is good practice to have a Secondary KDC in case the primary becomes unavailable.

  1. First, install the packages, and when asked for the Kerberos and Admin server names enter the name of the Primary KDC:

    sudo apt-get install krb5-kdc krb5-admin-server
    
  2. Once you have the packages installed, create the Secondary KDC's host principal. From a terminal prompt, enter:

    kadmin -q "addprinc -randkey host/kdc02.example.com"
    
    [Note]

    After, issuing any kadmin commands you will be prompted for your username/admin@EXAMPLE.COM principal password.

  3. Extract the keytab file:

    kadmin -q "ktadd -k keytab.kdc02 host/kdc02.example.com"
    
  4. There should now be a keytab.kdc02 in the current directory, move the file to /etc/krb5.keytab:

    sudo mv keytab.kdc02 /etc/krb5.keytab
    
    [Note]

    If the path to the keytab.kdc02 file is different adjust accordingly.

    Also, you can list the principals in a Keytab file, which can be useful when troubleshooting, using the klist utility:

    sudo klist -k /etc/krb5.keytab
    
  5. Next, there needs to be a kpropd.acl file on each KDC that lists all KDCs for the Realm. For example, on both primary and secondary KDC, create /etc/krb5kdc/kpropd.acl:

    host/kdc01.example.com@EXAMPLE.COM
    host/kdc02.example.com@EXAMPLE.COM
    
  6. Create an empty database on the Secondary KDC:

    sudo kdb5_util -s create
    
  7. Now start the kpropd daemon, which listens for connections from the kprop utility. kprop is used to transfer dump files:

    sudo kpropd -S
    
  8. From a terminal on the Primary KDC, create a dump file of the principal database:

    sudo kdb5_util dump /var/lib/krb5kdc/dump
    
  9. Extract the Primary KDC's keytab file and copy it to /etc/krb5.keytab:

    kadmin -q "ktadd -k keytab.kdc01 host/kdc01.example.com"
    sudo mv keytab.kdc01 /etc/kr5b.keytab
    
    [Note]

    Make sure there is a host for kdc01.example.com before extracting the Keytab.

  10. Using the kprop utility push the database to the Secondary KDC:

    sudo kprop -r EXAMPLE.COM -f /var/lib/krb5kdc/dump kdc02.example.com
    
    [Note]

    There should be a SUCCEEDED message if the propagation worked. If there is an error message check /var/log/syslog on the secondary KDC for more information.

    You may also want to create a cron job to periodically update the database on the Secondary KDC. For example, the following will push the database every hour:

    # m h  dom mon dow   command
    0 * * * * /usr/sbin/kdb5_util dump /var/lib/krb5kdc/dump && /usr/sbin/kprop -r EXAMPLE.COM -f /var/lib/krb5kdc/dump kdc02.example.com
    
  11. Back on the Secondary KDC, create a stash file to hold the Kerberos master key:

    sudo kdb5_util stash
    
  12. Finally, start the krb5-kdc daemon on the Secondary KDC:

    sudo /etc/init.d/krb5-kdc start
    

The Secondary KDC should now be able to issue tickets for the Realm. You can test this by stopping the krb5-kdc daemon on the Primary KDC, then use kinit to request a ticket. If all goes well you should receive a ticket from the Secondary KDC.

Kerberos Linux Client

This section covers configuring a Linux system as a Kerberos client. This will allow access to any kerberized services once a user has successfully logged into the system.

Installation

In order to authenticate to a Kerberos Realm, the krb5-user and libpam-krb5 packages are needed, along with a few others that are not strictly necessary but make life easier. To install the packages enter the following in a terminal prompt:

sudo apt-get install krb5-user libpam-krb5 libpam-ccreds auth-client-config

The auth-client-config package allows simple configuration of PAM for authentication from multiple sources, and the libpam-ccreds will cache authentication credentials allowing you to login in case the Key Distribution Center (KDC) is unavailable. This package is also useful for laptops that may authenticate using Kerberos while on the corporate network, but will need to be accessed off the network as well.

Configuration

To configure the client in a terminal enter:

sudo dpkg-reconfigure krb5-config

You will then be prompted to enter the name of the Kerberos Realm. Also, if you don't have DNS configured with Kerberos SRV records, the menu will prompt you for the hostname of the Key Distribution Center (KDC) and Realm Administration server.

The dpkg-reconfigure adds entries to the /etc/krb5.conf file for your Realm. You should have entries similar to the following:

[libdefaults]
        default_realm = EXAMPLE.COM
...
[realms]
        EXAMPLE.COM = }                
                kdc = 192.168.0.1               
                admin_server = 192.168.0.1
        }

You can test the configuration by requesting a ticket using the kinit utility. For example:

kinit steve@EXAMPLE.COM
Password for steve@EXAMPLE.COM:

When a ticket has been granted, the details can be viewed using klist:

klist
Ticket cache: FILE:/tmp/krb5cc_1000
Default principal: steve@EXAMPLE.COM

Valid starting     Expires            Service principal
07/24/08 05:18:56  07/24/08 15:18:56  krbtgt/EXAMPLE.COM@EXAMPLE.COM
        renew until 07/25/08 05:18:57


Kerberos 4 ticket cache: /tmp/tkt1000
klist: You have no tickets cached

Next, use the auth-client-config to configure the libpam-krb5 module to request a ticket during login:

sudo auth-client-config -a -p kerberos_example

You will should now receive a ticket upon successful login authentication.

Resources

posted @ 2012-12-19 18:15 ivaneeo 阅读(2684) | 评论 (0)编辑 收藏

一、什么是 SSL 证书,什么是 HTTPS

SSL 证书是一种数字证书,它使用 Secure Socket Layer 协议在浏览器和 Web 服务器之间建立一条安全通道,从而实现:
1、数据信息在客户端和服务器之间的加密传输,保证双方传递信息的安全性,不可被第三方窃听;
2、用户可以通过服务器证书验证他所访问的网站是否真实可靠。
(via百度百科

HTTPS 是以安全为目标的 HTTP 通道,即 HTTP 下加入 SSL 加密层。HTTPS 不同于 HTTP 的端口,HTTP默认端口为80,HTTPS默认端口为443.

二、什么网站需要使用SSL证书

1、购物交易类网站
不用多说,网上银行、支付宝、Paypal等肯定会全程加密以保护你的信息安全。

2、注册与登陆
一些大的网站,比如电子邮箱,注册会员或者登陆的时候,会专门通过SSL通道,保证密码安全不被窃取。

3、某些在线代理
这个。。。嗯哼,就不说了。

4、装B
比如我……

三、自行颁发不受浏览器信任的SSL证书

为晒晒IQ网颁发证书。ssh登陆到服务器上,终端输入以下命令,使用openssl生成RSA密钥及证书。

# 生成一个RSA密钥  $ openssl genrsa -des3 -out 33iq.key 1024   # 拷贝一个不需要输入密码的密钥文件 $ openssl rsa -in 33iq.key -out 33iq_nopass.key   # 生成一个证书请求 $ openssl req -new -key 33iq.key -out 33iq.csr   # 自己签发证书 $ openssl x509 -req -days 365 -in 33iq.csr -signkey 33iq.key -out 33iq.crt

第3个命令是生成证书请求,会提示输入省份、城市、域名信息等,重要的是,email一定要是你的域名后缀的。这样就有一个 csr 文件了,提交给 ssl 提供商的时候就是这个 csr 文件。当然我这里并没有向证书提供商申请,而是在第4步自己签发了证书。

使用openssl生成密钥和证书

编辑配置文件nginx.conf,给站点加上HTTPS协议

server {     server_name YOUR_DOMAINNAME_HERE;     listen 443;     ssl on;     ssl_certificate /usr/local/nginx/conf/33iq.crt;     ssl_certificate_key /usr/local/nginx/conf/33iq_nopass.key;     # 若ssl_certificate_key使用33iq.key,则每次启动Nginx服务器都要求输入key的密码。 }

重启Nginx后即可通过https访问网站了。

自行颁发的SSL证书能够实现加密传输功能,但浏览器并不信任,会出现以下提示:
不信任的安全证书

四、受浏览器信任的证书

要获取受浏览器信任的证书,则需要到证书提供商处申请。证书授证中心,又叫做CA机构,为每个使用公开密钥的用户发放一个数字证书。浏览器在默认情况下内置了一些CA机构的证书,使得这些机构颁发的证书受到信任。VeriSign即 是一个著名的国外CA机构,工行、建行、招行、支付宝、财付通等网站均使用VeriSign的证书,而网易邮箱等非金融网站采用的是中国互联网信息中心 CNNIC颁发的SSL证书。一般来说,一个证书的价格不菲,以VeriSign的证书为例,价格在每年8000元人民币左右。

据说也有免费的证书可以申请。和VeriSign一样,StartSSL也 是一家CA机构,它的根证书很久之前就被一些具有开源背景的浏览器支持(Firefox浏览器、谷歌Chrome浏览器、苹果Safari浏览器等)。后 来StartSSL竟然搞定了微软:在升级补丁中,微软更新了通过Windows根证书认证(Windows Root Certificate Program)的厂商清单,并首次将StartCom公司列入了该认证清单。现在,在Windows 7或安装了升级补丁的Windows Vista或Windows XP操作系统中,系统会完全信任由StartCom这类免费数字认证机构认证的数字证书,从而使StartSSL也得到了IE浏览器的支持。(来源及申请步骤

五、只针对注册、登陆进行https加密处理

既然HTTPS能保证安全,为什么全世界大部分网站都仍旧在使用HTTP呢?使用HTTPS协议,对服务器来说是很大的负载开销。从性能上考虑,我 们无法做到对于每个用户的每个访问请求都进行安全加密(当然,Google这种大神除外)。作为一个普通网站,我们所追求的只是在进行交易、密码登陆等操 作时的安全。通过配置Nginx服务器,可以使用rewrite来做到这一点。

在https server下加入如下配置:

if ($uri !~* "/logging.php$") {     rewrite ^/(.*)$ http://$host/$1 redirect; }

在http server下加入如下配置:

if ($uri ~* "/logging.php$") {     rewrite ^/(.*)$ https://$host/$1 redirect; }

这样一来,用户会且只会在访问logging.php的情况下,才会通过https访问。

更新:有一些开发框架会根据 $_SERVER['HTTPS'] 这个 PHP 变量是否为 on 来判断当前的访问请求是否是使用 https。为此我们需要在 Nginx 配置文件中添加一句来设置这个变量。遇到 https 链接重定向后会自动跳到 http 问题的同学可以参考一下。

server {     ...     listen 443;     location \.php$ {         ...         include fastcgi_params;         fastcgi_param HTTPS on; # 多加这一句     } }   server {     ...     listen 80;     location \.php$ {         ...         include fastcgi_params;     } }

参考链接:
http://zou.lu/nginx-https-ssl-module
http://blog.s135.com/startssl/
http://www.baalchina.net/2008/08/nginx-https-rewrite/

0
posted @ 2012-12-11 02:42 ivaneeo 阅读(11388) | 评论 (0)编辑 收藏


com.mysql.jdbc.CommunicationsException: The last packet successfully received from the server was58129 seconds ago.The last packet sent successfully to the server was 58129 seconds ago, which is longer than the server configured value of 'wait_timeout'. You should consider either expiring and/or testing connection validity before use in your application, increasing the server configured values for client timeouts, or using the Connector/J connection property 'autoReconnect=true' to avoid this problem.

 

查了一下,原来是mysql超时设置的问题
如果连接闲置8小时 (8小时内没有进行数据库操作), mysql就会自动断开连接, 要重启tomcat.

 

 

解决办法:

 

 

    一种. 如果不用hibernate的话, 则在 connection url中加参数: autoReconnect=true

jdbc.url=jdbc:mysql://ipaddress:3306/database?autoReconnect=true&amp;autoReconnectForPools=true

 


    二种。用hibernate的话, 加如下属性:
        <property name="connection.autoReconnect">true</property>
        <property name="connection.autoReconnectForPools">true</property>
        <property name="connection.is-connection-validation-required">true</property>

 


    三。要是还用c3p0连接池:
        <property name="hibernate.c3p0.acquire_increment">1</property>
        <property name="hibernate.c3p0.idle_test_period">0</property>
        <property name="hibernate.c3p0.timeout">0</property>
        <property name="hibernate.c3p0.validate">true</property>

 

 

 四。最不好的解决方案

 

使用Connector/J连接MySQL数据库,程序运行较长时间后就会报以下错误:

Communications link failure,The last packet successfully received from the server was *** millisecond ago.The last packet successfully sent to the server was ***  millisecond ago。

其中错误还会提示你修改wait_timeout或是使用Connector/J的autoReconnect属性避免该错误。

后来查了一些资料,才发现遇到这个问题的人还真不少,大部分都是使用连接池方式时才会出现这个问题,短连接应该很难出现这个问题。这个问题的原因:

MySQL服务器默认的“wait_timeout”是28800秒即8小时,意味着如果一个连接的空闲时间超过8个小时,MySQL将自动断开该连接,而连接池却认为该连接还是有效的(因为并未校验连接的有效性),当应用申请使用该连接时,就会导致上面的报错。

1.按照错误的提示,可以在JDBC URL中使用autoReconnect属性,实际测试时使用了autoReconnect=true& failOverReadOnly=false,不过并未起作用,使用的是5.1版本,可能真像网上所说的只对4之前的版本有效。

2.没办法,只能修改MySQL的参数了,wait_timeout最大为31536000即1年,在my.cnf中加入:

[mysqld]

wait_timeout=31536000

interactive_timeout=31536000

重启生效,需要同时修改这两个参数
posted @ 2012-11-06 16:29 ivaneeo 阅读(4075) | 评论 (0)编辑 收藏

SET SQL_MODE="NO_AUTO_VALUE_ON_ZERO"
NO_AUTO_VALUE_ON_ZERO影响AUTO_INCREMENT列的处理。一般情况,你可以向该列插入NULL或0生成下一个序列号。NO_AUTO_VALUE_ON_ZERO禁用0,因此只有NULL可以生成下一个序列号。

如 果将0保存到表的AUTO_INCREMENT列,该模式会很有用。(不推荐采用该惯例)。例如,如果你用mysqldump转储表并重载,MySQL遇 到0值一般会生成新的序列号,生成的表的内容与转储的表不同。重载转储文件前启用NO_AUTO_VALUE_ON_ZERO可以解决该问题。
posted @ 2012-11-02 15:45 ivaneeo 阅读(341) | 评论 (0)编辑 收藏

8 Virtual Desktop program: Ulteo, NX Enteprise Server, FoSS CLOUD, Orcale Virtualbox, Thinstuff, JetClouding, Go Grid,2xCloud Computing
posted @ 2012-10-20 13:18 ivaneeo 阅读(395) | 评论 (0)编辑 收藏

sudo qemu-img create -f qcow2 -o size=30240M,preallocation=metadata win2003_hda.img
http://blog.kreyolys.com/2011/09/27/kvm-virtual-machines-disk-format-file-basedqcow2-or-block-devicelvm2/---比较
sudo virt-install \
--name win2003_test \
--ram=1024 \
--vcpus=2 \
--disk /kvm/win2003_hda.img,bus=virtio \
--network bridge:br0,model=virtio \
--vnc \
--accelerate \
-c /share/os/win2003-i386.iso \
--disk /home/kvm/virtio-win-1.1.16.vfd,device=floppy \
-c /home/kvm/virtio-win-0.1-22.iso \
--os-type=windows \
--os-variant=win2k3 \
--noapic \
--connect \
qemu:///system \
--hvm

http://www.howtoforge.com/installing-kvm-guests-with-virt-install-on-ubuntu-12.04-lts-server


半虚拟化参考:
  1. #!/bin/sh
  2. WINISO=/path/to/win7.iso    #Windows ISO
  3. INSTALLDISK=win7virtio.img  #Disk location. Can be LVM LV
  4. VFD=http://alt.fedoraproject.org/pub/alt/virtio-win/latest/images/bin/virtio-win-1.1.16.vfd
  5. DRVRISO=http://alt.fedoraproject.org/pub/alt/virtio-win/latest/images/bin/virtio-win-0.1-22.iso
  6.  
  7. [ -e $(basename $VFD) ]     || wget $VFD
  8. [ -e $(basename $DRVRISO) ] || wget $DRVRISO
  9. [ -e $INSTALLDISK ]         || qemu-img create $INSTALLDISK 30G
  10.  
  11. sudo virt-install -c qemu:///system --virt-type kvm --name win7virtio --ram 1024 --disk path="$INSTALLDISK",bus=virtio \
  12. --disk $(basename $VFD),device=floppy --os-variant win7 --cdrom $(basename $DRVRISO) --cdrom "$WINISO" --vcpus 2
  13. ENDING OF BASH SCRIPT

其他参考:

 

In my previous article KVM Guests: Using Virt-Install to Import an Existing Disk Image we discussed how to use virt-install to import an existing disk image, which already has an OS installed into it.  Additionally in KVM Guests: Using Virt-Install to Install Debian and Ubuntu Guests I documented how to initiate an install directly off of the apt mirror of your choice for Debian and Ubuntu Guests using virt-install.  In this article we will use virt-install to create a guest and begin the installation using a CD or ISO image for installation media.

Assumptions I Have Made

  • My KVM host is Ubuntu 10.10 and I am assuming that yours is as well.  If it is not then the syntax might be slightly different or may not include the same features.
  • That you have kvm installed on the host and you can manually create VMs using virt-manager and they work perfectly.
  • That you have a bridge configured and working on other guests.
  • That you have virt-install and libvirt-bin installed as well as virt-manager or virt-viewer so that you can complete the install after the virt-install command has completed.
  • That you are trying to import disk images that support VirtIO devices (most recent Linux distributions, Windows does not natively support the VirtIO interface, so you will had to have manually installed the VirtIO drivers into your disk image).

The Basic Command

# virt-install -n vmname -r 2048 --os-type=linux --os-variant=ubuntu --disk /kvm/images/disk/vmname_boot.img,device=disk,bus=virtio,size=40,sparse=true,format=raw -w bridge=br0,model=virtio --vnc --noautoconsole -c /kvm/images/iso/ubuntu.iso

Parameters Detailed

  • -n vmname [the name of your VM]
  • -r 2048 [the amount of RAM in MB for your VM]
  • –os-type=linux [the type of OS linux or windows]
  • –os-variant=ubuntu [the distribution or version of Windows for a full list see man virt-install]
  • –disk /kvm/images/disk/vmname_boot.img,device=disk,bus=virtio,size=40,sparse=true,format=raw [this is a long one you define the path, then comma delimited options, device is the type of storage cdrom, disk, floppy, bus is the interface ide, scsi, usb, virtio - virtio is the fastest but you need to install the drivers for Windows and older versions of Linux don't have support]
  • -w bridge=br0,model=virtio [the network configuration, in this case we are connecting to a bridge named br0, and using the virtio drivers which perform much better if you are using an OS which doesn't support virtio you can use e1000 or rtl8139.  You could alternatively use --nonetworks if you do not need networking]
  • –vnc [configures the graphics card to use VNC allowing you to use virt-viewer or virt-manager to see the desktop as if you were at the a monitor of a physical machine]
  • –noautoconsole [configures the installer to NOT automatically try to open virt-viewer to view the console to complete the installation - this is helpful if you are working on a remote system through SSH]
  • -c /kvm/images/iso/ubuntu.iso [this option specifies the cdrom device or iso image with which to boot off of.  You could additionally specify the cdrom device as a disk device, and not use the -c option, it will then boot off of the cdrom if you don't specify another installation method]

LVM Disk Variation

# virt-install -n vmname -r 2048 --os-type=linux --os-variant=ubuntulucid  --disk  /dev/vg_name/lv_name,device=disk,bus=virtio  -w bridge=br0,model=virtio --vnc --noautoconsole -c  /kvm/images/iso/ubuntu.iso

No VirtIO Variation (Uses IDE and e1000 NIC Emulation)

# virt-install -n vmname -r 2048 --os-type=linux  --os-variant=ubuntulucid --disk  /kvm/images/disk/vmname_boot.img,device=disk,bus=ide,size=40,sparse=true,format=raw  -w bridge=br0,model=e1000 --vnc --noautoconsole -c  /kvm/images/iso/ubuntu.iso

Define VM Without Installation Method

# virt-install -n vmname -r 2048 --os-type=linux --os-variant=ubuntulucid --disk /kvm/images/disk/vmname_boot.img,device=disk,bus=virtio,size=40,sparse=true,format=raw --disk /kvm/images/iso/ubuntu.iso,device=cdrom -w bridge=br0,model=virtio --vnc --noautoconsole

 

posted @ 2012-06-08 17:55 ivaneeo 阅读(852) | 评论 (0)编辑 收藏

###################
#安装Xming 和 Putty:
###################
Xming是一个在Microsoft Windows操作系统上运行X Window System(也常称为X11或X X的工作站)的自由软件,可用于在Windows运行Linux的程序(需要在本地Windows上运行一个X Server,即是本程序)。
Linux 以及各种Unix like的操作系统现在都用基于X Window图形界面。但是由于体积臃肿导致在Linux运行3D游戏十分困难。但是得益于其接口良好、扩展性和可移植性优秀的特点(重要的是具有网络透 明性),利用它可以很方便的远程启动Linux的图形程序。

下载地址:
https://sourceforge.net/projects/xming/
或者http://www.straightrunning.com/XmingNotes/

Xming 用OpenGL展示界面
Xming-fonts 标准X字体,部分传统的X应用的显示也需要这些字体
Xming-mesa 用更慢的Mesa展示界面, 有时X转发会更好
Xming-portable-PuTTY 提供X界面转发ssh程序
Xming-tools-and-clients 提供一些X应用专用的工具

Putty: http://www.putty.org/

####################################################
# 通过SSH来使用Xming,在putty terminal 中打开Linux下的图形界面
####################################################
1)保证Linux server中 /etc/ssh/sshd_config
X11Forwarding yes

2)Putty中X11 forwarding:

Putty Configuration-->Preffered SSH protocal version->SSH版本是2.

Connection-->SSH-->X11-->Enable X11 forwarding, X display location填上localhost:0, 下面的协议选择MIT-Magic-Cookie-1.

3)windows下起linux下的图形界面

启动Xming,"Display number"中的数字, 使用默认的0.

使用Putty连接Linux server,在putty终端下运行

set DISPLAY=10.160.13.229:0(注意:这里IP是Xming安装程序所在的主机的IP地址,即:X Server的IP地址,这里就是你的windows的地址,X Client是linux 服务器)

(DISPLAY 环境变量格式如下hostname: displaynumber.screennumber,我们需要知道,在某些机器上,可能有多个显示设备共享使用同一套输入设备,例如在一台PC上连接 两台CRT显示器,但是它们只共享使用一个键盘和一个鼠标。这一组显示设备就拥有一个共同的displaynumber,而这组显示设备中的每个单独的设 备则拥有自己单独的 screennumber。displaynumber和screennumber都是从零开始的数字。这样,对于我们普通用户来说, displaynumber、screennumber就都是0。

hostname指Xserver所在的主机主机名或者ip地址, 图形将显示在这一机器上, 可以是启动了图形界面的Linux/Unix机器, 也可以是安装了Exceed, X-Deep/32等Windows平台运行的Xserver的Windows机器.如果Host为空, 则表示Xserver运行于本机, 并且图形程序(Xclient)使用unix socket方式连接到Xserver, 而不是TCP方式.

使用TCP方式连接时, displaynumber为连接的端口减去6000的值, 如果displaynumber为0, 则表示连接到6000端口;

使用unix socket方式连接时则表示连接的unix socket的路径,如果displaynumber为0, 则表示连接到/tmp/.X11-unix/X0 .

creennumber则几乎总是0. )

然后运行gvim,发现linux下的gvim显示在你的windows桌面上了。

如果出现:
Xlib: connection to "10.160.13.229:0.0" refused by server Xlib: No protocol specified

在右下角点击Xming server的view log,发现有如下消息

AUDIT: ... Xming: client 4 rejected from IP 10.160.23.18

这个10.160.23.18正是linux server的地址

解决办法:
右键桌面上的Xming图标,修改Xming的命令,取消权限控制,使用-ac选项:

C:\Program Files\XMing\Xming.exe :0 -clipboard -multiwindow -ac


然后启动Xming,发现可以在windows下显示linux的图形界面了。。
posted @ 2012-04-26 12:21 ivaneeo 阅读(13216) | 评论 (2)编辑 收藏

Nginx 的 location 指令,允许对不同的 URI 进行不同的配置,既可以是字符串,也可以是正则表达式。使用正则表达式,须使用以下前缀:
        (1) ~*, 表示不区分大小写的匹配。
        (2) ~, 表示区分大小写的匹配。

        对于非正则的匹配,即字符串匹配,有如下前缀:
        (1) ^~, 表示匹配到字符串后,终止正则匹配。
        (2) =, 表示精确匹配。
        (3) @, 当然,这个也算不上字符串匹配。如果可以,你也可以将其理解成是正则匹配。它是一个命名标记,这种 location 不会用于正常的请求,它们通常只用于处理内部的重定向。

        在匹配过程中,Nginx 将首先匹配字符串,然后匹配正则表达式。匹配到第一个正则表达式后,会停止搜索。如果匹配到正则表达式,则使用正则表达式的搜索结果,如果没有匹配到正则表达式,则使用字符串的搜索结果。

        上面这段话的意思是说,有一个字符串和正则表达式均能匹配上,那么会使用正则表达式的搜索结果。这里,我们可以使用前缀"^~" 来禁止匹配到字符串后,继续检查正则表达式。匹配到 URI 后,将停止搜索。

        使用前缀 "=" 可以进行精确的 URI 匹配,如果找到匹配的 URI,则停止搜索。"location = /" 只能匹配到 "/",而 "/test.html" 则不能被匹配。

        正则表达式的匹配,按照它们在配置文件中的顺序进行,写在前面的优先。

        另外,前缀 "@" 是一个命名标记,这种 location 不会用于正常的请求,它们通常只用于处理内部的重定向(例如:error_page, try_files)。

        最后总结一下匹配的过程:
        (1) 前缀 "=" 先进行匹配,如果找到了,终止搜索。
        (2) 对所有其它 location 进行非正则的匹配,找到最精确匹配(对于 /blog/admin/ 这个 URI, location /blog 要比 location / 长,因此 location /blog 要比 location / 要精确)的那个。如果找到的这个是带"^~" 前缀的,则终止搜索并直接返回找到的这个,否则开始正则查找。会不会出现所有的非正则匹配都无法匹配到 URI 呢,当然,你若不定义一个 location /,这种情况的确会发生,没关系啊,它会进行正则查找的。
        (3) 正则查找,按照我们配置文件中配置的 location 顺序进行查找。

        (4) 如果正则查找匹配成功,则使用此正则匹配的 location,否则,使用第二步查找的结果。如果『否则』发生了,同时,第二步中的粗体字部分的假设的情况也发生了,怎么办?404 会等着你的。


参考:nginx location的管理以及查找


例子:

location = / {
# 只匹配 / 查询。
[ configuration A ]
}

location / {
# 匹配任何查询,因为所有请求都已 / 开头。但是正则表达式规则和长的块规则将被优先和查询匹配。
[ configuration B ]
}

location ^~ /images/ {
# 匹配任何已 /images/ 开头的任何查询并且停止搜索。任何正则表达式将不会被测试。
[ configuration C ]
}

location ~* \.(gif|jpg|jpeg)$ {
# 匹配任何已 gif、jpg 或 jpeg 结尾的请求。然而所有 /images/ 目录的请求将使用 Configuration C。
[ configuration D ]
}

例子请求:

1, /   ->   精确匹配到第1个location,匹配停止,使用configuration A
2,/some/other/url    ->  首先前缀部分字符串匹配到了第2个location,然后进行正则匹配,显然没有匹配上,则使用第2个location的配置configurationB
3,/images /1.jpg  ->  首先前缀部分字符串匹配到了第2个location,但是接着对第3个location也前缀匹配上了,而且这时已经是配置文件里面对这个url的最大字 符串匹配了,并且location带有 "^~" 前缀,则不再进行正则匹配,最终使用configuration C
4,/some/other/path/to/1.jpg  -> 首先前缀部分同样字符串匹配到了第2个location,然后进行正则匹配,这时正则匹配成功,则使用congifuration D

注意:按任意顺序定义这4个配置结果将仍然一样。

posted @ 2012-04-17 19:45 ivaneeo 阅读(1055) | 评论 (0)编辑 收藏

网上搜索到的是在配置文件中添加:

optimize_server_names off;
server_name_in_redirect off;

但在nginx0.8.38中提示:

Restarting nginx: [warn]: the "optimize_server_names" directive is deprecated, use the "server_name_in_redirect" directive instead in /etc/nginx/nginx.conf:44
[emerg]: "server_name_in_redirect" directive is duplicate in /etc/nginx/nginx.conf:45
configuration file /etc/nginx/nginx.conf test failed

大意是说:
optimize_server_names已经被弃用,只用server_name_in_redirect即可。

因此,只需在nginx.conf中添加以下一行即可。

server_name_in_redirect off;
posted @ 2012-04-10 15:25 ivaneeo 阅读(1762) | 评论 (0)编辑 收藏

功能描述:在Flex中嵌套框架,并且进行数值传递
1、编辑Flex框架组件iFrame.mxml
<?xml version="1.0" encoding="utf-8"?>
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"
    resize="callLater(moveIFrame)"
    move="callLater(moveIFrame)">
    <mx:Script>
    <![CDATA[
        import flash.external.ExternalInterface;
        import flash.geom.Point;
        import flash.net.navigateToURL;
        private var __source: String;
        /**
         * Move iframe through ExternalInterface. The location is determined using localToGlobal()
         * on a Point in the Canvas.
         **/
        private function moveIFrame(): void
        {
            var localPt:Point = new Point(0, 0);
            var globalPt:Point = this.localToGlobal(localPt);
            ExternalInterface.call("moveIFrame", globalPt.x, globalPt.y, this.width, this.height);
        }
        /**
         * The source URL for the IFrame. When set, the URL is loaded through ExternalInterface.
         **/
        public function set source(source: String): void
        {
            if (source)
            {
                if (! ExternalInterface.available)
                {
                    throw new Error("ExternalInterface is not available in this container. Internet Explorer ActiveX, Firefox, Mozilla 1.7.5 and greater, or other browsers that support NPRuntime are required.");
                }
                __source = source;
                ExternalInterface.call("loadIFrame", source);
                moveIFrame();
            }
        }
        public function get source(): String
        {
            return __source;
        }
        /**
         * Whether the IFrame is visible.
         **/
        override public function set visible(visible: Boolean): void
        {
            super.visible=visible;
            if (visible)
            {
                ExternalInterface.call("showIFrame");
            }
            else
            {
                ExternalInterface.call("hideIFrame");
            }
        }
    ]]>
    </mx:Script>
</mx:Canvas>
2、放置到要使用框架的Flex中index.mxml,并写入引用哪个frame.html
<ui:IFrame id="iFrame" source="frame.html" visible="true" width="100%" height="300"/>
3、在引用框架的Flex生成页index.html里加入:
     <1. wmode set to opaque
     在调用swf的后面加上"wmode","opaque"
     例如:"pluginspage", "http://www.adobe.com/go/getflashplayer",
           "wmode","opaque"
     <2. the moveIFrame,hideIFrame,showIFrame,loadIFrame methods
     <script language="JavaScript" type="text/javascript">

<!--
// -----------------------------------------------------------------------------
// Globals
// Major version of Flash required
var requiredMajorVersion = 9;
// Minor version of Flash required
var requiredMinorVersion = 0;
// Minor version of Flash required
var requiredRevision = 28;
// -----------------------------------------------------------------------------
// -->
function moveIFrame(x,y,w,h) {
    var frameRef=document.getElementById("myFrame");
    frameRef.style.left=x;
    frameRef.style.top=y;
    var iFrameRef=document.getElementById("myIFrame");
      iFrameRef.width=w;
      iFrameRef.height=h;
}
function hideIFrame(){
    document.getElementById("myFrame").style.visibility="hidden";
}

function showIFrame(){
    document.getElementById("myFrame").style.visibility="visible";
}
function loadIFrame(url){
      document.getElementById("myFrame").innerHTML = "<iframe id='myIFrame' src='" + url + "'frameborder='0'></iframe>";
}
//要调用的内容,加载前三个就可以了,后面这个函数是用来调用返回值
function getEditorText(){
      return document.getElementById("myIFrame").contentWindow.GetEditorText1();
}
</script>
     <3. the 'myFrame' div
         在</body>这前写入:
         <div id="myFrame" style="position:absolute;background-color:transparent;border:0         px;visibility:hidden;"></div>
4、在Flex页面index.mxml输入的函数值,调用index.html中的'getEditorText'函数,并且写入到text1.text中
     text1.text=ExternalInterface.call('getEditorText',param1,param2,param3,...)
     getEditorText:函数名称
     param:参数值
5、在生成页中取得框架中的函数
     框架内的frame.html,放置在head之间:
    function GetEditorText1(){
     return getHTML(params);
     index.html生成页的调用,设置在head之间:
     function getEditorText(){
      return document.getElementById("myIFrame").contentWindow.GetEditorText1();
     }
    
后记:实际中在这里只是调用一个层放在对应位置而已,当我们在Flex中做申缩动作时,层也要跟着改变,我是如此处理的:
     设置move或show事件,当move或show时则调用:iFrame.source = "frame.html"
参考:

具体的一个例子——使用IFrame这个框架的一个页面的代码如下:

<!-- saved from url=(0014)about:internet -->
<html lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title></title>
<script src="AC_OETags.js" language="javascript"></script>
<style>
body { margin: 0px; overflow:hidden }
</style>


<script>
<!--
function moveIFrame(x,y,w,h) {
// alert("move to " + x + "," + y + ", " + w + "/" + h);
    var frameRef=document.getElementById("myFrame");
    frameRef.style.left=x;
   frameRef.style.top=y;
    frameRef.width=w;
    frameRef.height=h;
}

function hideIFrame(){
// alert("hide");
    document.getElementById("myFrame").style.visibility="hidden";
}

function showIFrame(){
// alert("show");
    document.getElementById("myFrame").style.visibility="visible";
}

function navigateTo(url) {
// alert("nav to " + url);
// alert("from " + document.getElementById("myFrame").location);
document.getElementById("myFrame").src = url;
}

-->
</script>


<script language="VBScript">
<!--

// Catch FS Commands in IE, and pass them to the corresponding JavaScript function.
Sub flexapp_FSCommand(ByVal command, ByVal str)
    call flexapp_DoFSCommand(command, str)
end sub

// -->
</script>
</head>
<body style="margin:0px">

<object onMouseDown="document.body.focus();"
   classid='clsid:D27CDB6E-AE6D-11cf-96B8-444553540000'
  

codebase='http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=7,0,14

,0'
   width='100%' height='100%'
   id='flexapp' name='flexapp'>
   <param name='flashvars' value=''>
   <param name='src' value='EXPIframe.swf'>
   <param name="wmode" value="opaque">
   <embed pluginspage='http://www.macromedia.com/go/getflashplayer' width='100%'

height='100%'
       flashvars=''
       src='EXPIframe.swf'
       name='flexapp'
       wmode="opaque"
       swLiveConnect="true"
   />
</object>

<iframe id="myFrame" name="myFrame"
    frameborder="0"
    style="position:absolute;background-

color:transparent;border:0px;visibility:hidden;"></iframe>

</body>
</html>

posted @ 2012-03-08 22:48 ivaneeo 阅读(2550) | 评论 (1)编辑 收藏

浏览-选择文件-点击 “上传 ”后,效果如下:

弹出透明UI遮罩层 并显示上传这个过程 我这里设置太透明了 效果不是很立体

曾祥展

文件结构如图:

曾祥展

 

说明:用到“高山来客”的大文件上传组件 http://www.cnblogs.com/bashan/archive/2008/05/23/1206095.html

以及Newtonsoft.Json.dll Json字符串反序列化为对象 http://james.newtonking.com/projects/json-net.aspx

jquery.blockUI.js 弹出透明遮罩层 http://malsup.com/jquery/block/

jquery.form.js   表单验证Ajax提交 

参照了“蚂蚁飞了”的文章 多谢多谢 http://blog.csdn.net/jetsteven

 

 

HTML:

<form id="uploadForm" runat="server" enctype="multipart/form-data">   <div id="uploadfield"  style="width:600px; height:500px">    <input id="File1" type="file" runat="server" />    <asp:Button ID="Button1" runat="server"  Text="上传" onclick="Button1_Click" />     <p>文件上传进度条</p>     <p>文件上传进度条</p>     <p>文件上传进度条</p>     <p>文件上传进度条</p>     <p>文件上传进度条</p>     <p>文件上传进度条</p>      <p>文件上传进度条</p>    </div>                    <div id="ui"  style="display:none"  >      <div id="output" > </div>        <div id="progressbar"class="ui-progressbar ui-widget ui-widget-content ui-corner-all" style="width:296px; height:20px;"></div>    <input id="btn_cancel" type="button" value="取消上传" />   </div> </form>
 
js:
 
var inte; $(function() { $('#uploadForm').submit(function() {     return false; });  $('#uploadForm').ajaxForm({ //这里调用jquery.form.js表单注册方法     beforeSubmit: function(a, f, o) {//提交前的处理         o.dataType = "json";         $('#uploadfield').block({ message: $('#ui'), css: { width: '300px', border: '#b9dcfe 1px solid',padding: '0.5em 0.2em'  }         });         inte = self.setInterval("getprogress()", 500);     } });  $('#btn_cancel').click(function() {     var uploadid = $("#UploadID").val();     $.ajax({         type: "POST",         dataType: "json",         async: false, //ajax的请求时同步 只有一个线程         url: "upload_ajax.ashx",         data: "UploadID=" + uploadid + "&cancel=true",         success: function(obj) {             $("#output").html(obj.msg);             inte = self.clearInterval(inte);             $('#uploadfield').unblock();                            }     }); }); });  function getprogress() { var uploadid = $("#UploadID").val() $.ajax({     type: "POST",     dataType: "json",     async: false,     url: "upload_ajax.ashx",     data: "UploadID=" + uploadid,     success: function(obj) {     var p = obj.msg.Readedlength / obj.msg.TotalLength * 100;     var info = "<FONT color=Green> 当前上传文件:</FONT>" + obj.msg.CurrentFile;     info += "<br><FONT color=Green>" + obj.msg.FormatStatus + ":</FONT>" + obj.msg.Status;     info += "<br><FONT color=Green>文件大小:</FONT>" + obj.msg.TotalLength;     info += "<br><FONT color=Green>速度:</FONT>" + obj.msg.FormatRatio;     info += "<br><FONT color=Green>剩余时间:</FONT>" + obj.msg.LeftTime;       $("#output").html(info);     $("#progressbar").progressbar({ value: 0 }); //初始化     $("#progressbar").progressbar("option", "value", p);     $("#progressbar div").html(p.toFixed(2) + "%");     $("#progressbar div").addClass("percentText");     if (obj.msg.Status == 4) {         inte = self.clearInterval(inte);         $('#uploadfield').unblock();      }            } }); }
 
交互过程代码:
 
<%@ WebHandler Language="C#" Class="progressbar" %>  using System; using System.Web;  using BigFileUpload;//大文件引用命名空间 using Newtonsoft.Json;//对象到JSON的相互转换 using System.Text.RegularExpressions;//正则  public class progressbar : IHttpHandler {      private string template = "{{statue:'{0}',msg:{1}}}";    public void ProcessRequest(HttpContext context)    {        context.Response.ContentType = "text/plain";        try       {        string guid = context.Request["UploadID"];        string cancel =context.Request["cancel"];     UploadContext c = UploadContextFactory.GetUploadContext(guid);       if (!string.IsNullOrEmpty(cancel))     {                    c.Abort=true;                    throw new Exception("用户取消");        }        string json = Newtonsoft.Json.JsonConvert.SerializeObject(c);                    WriteResultJson(1, json, context,template);                 }catch (Exception err)        {            WriteResultJson(0, err.Message, context);        }    }      public static void WriteResultJson(int resultno, string description, HttpContext context) {     WriteResultJson(resultno, description, context, "{{statue:'{0}',msg:'{1}'}}"); }  public static void WriteResultJson(int resultno, string description, HttpContext context, string template) {     description = ClearBR(ReplaceString(description, "'", "|", false));     context.Response.Write(string.Format(template, resultno, description)); }  public static string ClearBR(string str) {     Regex r = null;     Match m = null;     r = new Regex(@"(\r|\n)", RegexOptions.IgnoreCase);     for (m = r.Match(str); m.Success; m = m.NextMatch())     {         str = str.Replace(m.Groups[0].ToString(), @"\n");     }     return str; }  public static string ReplaceString(string SourceString, string SearchString, string ReplaceString, bool IsCaseInsensetive) {     return Regex.Replace(SourceString, Regex.Escape(SearchString), ReplaceString, IsCaseInsensetive ? RegexOptions.IgnoreCase : RegexOptions.None); }    public bool IsReusable    {        get       {         return false;        }    }  }         
http://www.cnblogs.com/jcomet/archive/2010/03/24/1693467.html
posted @ 2012-02-29 20:42 ivaneeo 阅读(593) | 评论 (0)编辑 收藏

原理简单的不能再简单,就是替换变量,用转义字符替换你的字符串,把整个js变成一个字符串,然后随便加密替换,最后用eval来解释他。最后把整个js文件压缩下,没有注释,没有换行,没有空格,一般人都会看到吐血。

说了半天不够爽,总不能让大家手动加密和替换吧,以下是我的御用在线加密工具,jQuery就是用其中一个加密和压缩的:

http://www.javascriptobfuscator.com/Default.aspx

http://dean.edwards.name/packer/

这2网站只提供加密,不提供解密,其实你解密了看得人也很痛苦,没有注释,没有格式,全是abcd这样无意义的变量,真有心想学你js的人,那就让他学吧。你如果真的变态,那你不妨两边混合加密几次,保准没人看得懂,不过估计浏览器解释起来也挺费劲的。

特别友情提醒:meebe.net

1.加密后记着留住你原本的js文件,不要到时候改bug都改不了了。

2.加密后如果出现运行不了,请把你加密前的文件每次函数结束都加上";",因为去除换行后,浏览器解释器没碰到";"有时候会报错。如果加密后有错,请务必多加几个";"在每个语句结束或者定义结束的时候。


转自 meebe.net

posted @ 2012-02-28 22:41 ivaneeo 阅读(571) | 评论 (0)编辑 收藏

Step 1 – Install Visual Studio 2008

  1. If you don’t have it, get the express edition here: http://www.microsoft.com/Express/VC/
  2. Run through the installer, not much else to do.

Step 2 – Install wxWidgets

  1. Download wxWidgets (select the wxMSW installer file) from here:
    http://www.wxwidgets.org/downloads/
  2. I choose to install to c:\dev\wxwidgets\wxWidgets-2.8.10 but you can choose a different path if you want.

Step 3 – Create an environment variable for the wxWidgets path.

  1. Click the Start icon.
  2. Right click on Computer and choose Properties.
  3. Click Advanced system settings.
  4. Click the Environment variables button.
  5. Under System Variables, click New.
  6. Enter the Variable name: WXWIN
  7. Enter the Variable Value: C:\Dev\wxWidgets-2.8.10
  8. Click OK, click OK, click OK (yes three times).

Step 4 – Compile the wxWidgets Libraries.

  1. Browse to the following folder: C:\Dev\wxWidgets-2.8.10\build\msw
  2. Located the file called wx.dsw and open it with Visual Studio. (I just double-clicked on it.)
  3. Choose “Yes to all” when Visual Studio prompts you to convert the project.
  4. Build the project.
  5. Wait for the build to complete. It took approximately two minutes on my Lenovo T61p (dual core, 4 GB, Windows 7 64 bit). You should a line like this when it finishes successfully.
    ========== Build: 20 succeeded, 0 failed, 0 up-to-date, 0 skipped ==========
  6. Close Visual Studio.

Step 5 – Create a new project

  1. In Visual Studio 2008, go to File | New Project.
  2. Select Visual C++ | Empty Project.
  3. Give the project a name and click OK. I named this wxTest.

Step 6 – Create/Copy your source to this project.

  1. Right-click on the Project name and choose Open Folder in Windows Explorer. This will open to the home folder of your project. (Don’t right click the Solution name, make sure to right click the project under the solution name.)
  2. Open a second Windows Explore window.
  3. In the second window, browse to the wxWidgets sample directory and open the Minimal folder: C:\Dev\wxWidgets-2.8.10\samples\Minimal
    Note: You can choose other projects but you may want to start with Minimal and move on from there.
  4. Copy only the minimal.cpp and minimal.rc files to your project directory (the rest are not needed).
  5. Close the second window pointing to the C:\Dev\wxWidgets-2.8.10\samples\Minimal directory, it is not needed anymore.
  6. From the explorer window open to your project directory, use ctrl+click to highlight both the minimal.cpp and minimal.rc files.
  7. Drag both highlighted files into the Visual Studio Window and drop them over the project name.
    The minimal.cpp file should automatically be placed under the Source files section of your project.
    The minimal.rc file should automatically be placed under the Resource files section of your project.

Step 7 – Customize the project properties

  1. Right-click on the wxTest project and select Properties. (Don’t right click the Solution name, make sure to right click the project under the solution name.)
  2. In the top left of the properties window there is a Configuration drop down menu. Select All Configurations.
  3. Click to expand Configuration Properties.
  4. Click to expand C/C++.

    Note: If you don’t see a C/C++ section, then you don’t have any source files.  You need at least one C++ source file for this section to show up.

  5. Click to highlight General.
  6. Enter the following in Additional Include Directories.
    $(WXWIN)\include;$(WXWIN)\lib\vc_lib\mswd
  7. Click to highlight Preprocessor.
  8. Enter the following in Preprocessor Definitions.
    WIN32;__WXMSW__;_WINDOWS;_DEBUG;__WXDEBUG__
  9. Click to expand Linker.
  10. Click to highlight General.
  11. Enter the following in Additional Library Directories.
    $(WXWIN)\lib\vc_lib
  12. Click to highlight Input.
  13. Enter the following in Additional Dependencies.
    wxmsw28d_core.lib wxbase28d.lib wxtiffd.lib wxjpegd.lib wxpngd.lib wxzlibd.lib wxregexd.lib wxexpatd.lib winmm.lib comctl32.lib rpcrt4.lib wsock32.lib odbc32.lib

    Note: Not all of these libraries are required for this project, however, I list all of these because you may use some of them at some point. If you don’t think one is needed, remove it and recompile and if you don’t get errors, you were right, you probably didn’t need it.

  14. Click to expand Resources. (If you don’t see a Resources option, then you don’t have any files under resources so that is normal. Did you skip Step 5 because you probably should have added a resource in Step 5.)
  15. Click to highlight General.
  16. Enter the following in Preprocessor Definitions.
    _DEBUG;__WXMSW__;__WXDEBUG__;_WINDOWS;NOPCH
  17. Enter the following in Additional Include Directories.
    $(WXWIN)\include;$(WXWIN)\lib\vc_lib\mswd

You are now ready to build your wxWidgets application using Visual Studio 2008 on Windows 7.

Build your project and if you get any errors, go through it again, you probably missed a step (or I did, since I have already been caught with one step left out).

posted @ 2012-02-17 15:43 ivaneeo 阅读(542) | 评论 (0)编辑 收藏

最近发现bootstrap toolkit非常好用,现在收集一下sample网站:
1.http://twitter.github.com/bootstrap/(首先主站,可惜要fq)
2.http://webdesigntutsplus.s3.amazonaws.com/tuts/195_bootstrap/demo/main.html (也是一个简单的列子,可以作为参考)
3.http://www.breakingnews.com/ (新闻类网站,做的漂亮呀。。。)
4.http://www.mobile-loft.com/  (整体风格简洁)
5.http://demo.newfies-dialer.org/ (ajax登录的例子)
posted @ 2012-02-14 00:26 ivaneeo 阅读(1346) | 评论 (0)编辑 收藏

void ConvertGBKToUtf8(CString& strGBK) {
    int len=MultiByteToWideChar(CP_ACP, 0, (LPCTSTR)strGBK, -1, NULL,0);
    unsigned short * wszUtf8 = new unsigned short[len+1];
    memset(wszUtf8, 0, len * 2 + 2);
    MultiByteToWideChar(CP_ACP, 0, (LPCTSTR)strGBK, -1, wszUtf8, len);

    len = WideCharToMultiByte(CP_UTF8, 0, wszUtf8, -1, NULL, 0, NULL, NULL);
    char *szUtf8=new char[len + 1];
    memset(szUtf8, 0, len + 1);
    WideCharToMultiByte (CP_UTF8, 0, wszUtf8, -1, szUtf8, len, NULL,NULL);

    strGBK = szUtf8;
    delete[] szUtf8;
    delete[] wszUtf8;
}

void ConvertUtf8ToGBK(CString& strUtf8) {
    int len=MultiByteToWideChar(CP_UTF8, 0, (LPCTSTR)strUtf8, -1, NULL,0);
    unsigned short * wszGBK = new unsigned short[len+1];
    memset(wszGBK, 0, len * 2 + 2);
    MultiByteToWideChar(CP_UTF8, 0, (LPCTSTR)strUtf8, -1, wszGBK, len);

    len = WideCharToMultiByte(CP_ACP, 0, wszGBK, -1, NULL, 0, NULL, NULL);
    char *szGBK=new char[len + 1];
    memset(szGBK, 0, len + 1);
    WideCharToMultiByte (CP_ACP, 0, wszGBK, -1, szGBK, len, NULL,NULL);

    strUtf8 = szGBK;
    delete[] szGBK;
    delete[] wszGBK;
}
posted @ 2012-02-09 12:58 ivaneeo 阅读(1154) | 评论 (0)编辑 收藏

背景

        luacom是一个非常强大的模块,它使我们可以应用各种com组件,比如Word,但是,有一个问题,中文文件名它不识别。为什么呢?因为com内部是 unicode的,于是luacom要求所有输入都是utf-8的,而且luacom的输出也是utf-8的。这可肿么办啊?

iconv

        GNU有个libiconv库,要是有这个我们就不怕了! luaforge上搜索下,果然有lua-iconv,安装!

        luarocks install lua-iconv  不好意思,出错啦!出错的原因有两个:

  • 我们没有安装libiconv库
  • lua-iconv没有提供用cl编译的方法

自己编译lua-iconv

  1. 下载编译好的Windows版的 libiconv
  2. 下载 lua-iconv 源代码
  3. 解压 libiconv-1.9.1.bin.woe32.zip 文件,并将include目录添加为vs2008的包含文件目录,将lib目录添加为vs2008的库文件目录中(参见上一篇文章
  4. 解压lua-iconv的源代码
  5. vs2008新建一个空的Win32 DLL工程(参见上一篇文章),命名为luaiconv,将 luaiconv.c 文件添加到工程中
  6. 修改源代码:int luaopen_iconv(lua_State *L)  -> __declspec(dllexport) int luaopen_luaiconv(lua_State *L)
    • 注意:最后生成的dll文件名,必须和 luaopen_luaiconv 中的 luaiconv 一样(参见上一篇文章
  7. 项目属性 -> 链接器 -> 输入 -> 附加库文件 : lua51.lib iconv.lib charset.lib
  8. 编译生成release版的 luaiconv.dll 文件
  9. 将luaiconv.dll文件,以及libiconv-1.9.1.bin.woe32.zip解压出来的 iconv.dll(知道我为什么要改luaopen_iconv函数名了吧)和charset.dll文件一起拷贝到 luaforwindows的clibs目录中

测试

  1. require "luacom"  
  2. require "luaiconv"  
  3.   
  4. function createIconv(to, from)  
  5.     local cd = iconv.new(to, from)  
  6.     return function(txt)  
  7.         return cd:iconv(txt)  
  8.     end  
  9. end  
  10.   
  11. L = createIconv("utf-8", "gbk")  
  12.   
  13. -- 注意:运行本文件会修改 C:\你好word.docx 文件,请注意备份  
  14.   
  15. wordApp = assert(luacom.CreateObject("Word.Application"))  
  16. wordApp.Visible = true  
  17.   
  18. wordDocPath = L"C:\\你好word.docx"  
  19. if not pcall(function() wordDoc = wordApp.Documents:Open(wordDocPath) end) then  
  20.     wordDoc = wordApp.Documents:Add()  
  21. end  
  22.   
  23. wordApp.Selection:TypeText(L"你好word")  
  24. wordDoc:SaveAs2(wordDocPath, wdFormatDocument)  

以上测试代码,第一次运行时会创建 C:\你好word.docx 文件,以后再运行时会打开这个文件,每次运行都会输入 “你好word” 文字。如果你是Word 2003,那么,请将docx改为doc即可。

参考文献

http://hi.baidu.com/nivrrex/blog/item/17c231adad9e8a0f4b36d6ca.html

这位大哥自己用VC的函数写了转换函数,不过没有封装成库,而且我觉得写得不够简洁,用iconv库比较好,还不容易出错

http://www.cppblog.com/darkdestiny/archive/2009/04/25/81055.html

这位大哥,自己用iconv实现了转换,也没有封装成库。我的“L”函数也是从他这借来的,非常感谢!不过,我认为它这个相比我这个有两个弱点:

1、每次调用L函数,都要经过 iconv 打开、转换、关闭的过程,而我对一种形式的转换只需要打开一次(lua-iconv实现的^_^)

2、如果要实现反向转换,即utf-8到gbk,那么还得修改模块,而我这里就不用了(当然也是lua-iconv实现的^_^)

libiconv的说明
posted @ 2012-02-09 01:48 ivaneeo 阅读(637) | 评论 (0)编辑 收藏

Cocos2d-x 已经提供了对 Lua 的基本支持,但除了 Lua 的基本库外,并没有捆绑一些常用库,例如 LuaSocket。

经过一番尝试,终于搞定了此问题 :)

获得 LuaSocket 源代码后,在 cocos2d-x 项目的 libs/lua 目录中建立子目录 exts/luasocket,并将 luasocket-2.0.2/src 目录中所有的 *.c/*.h 文件拷贝到 libs/lua/exts/luasocket 目录中。

在 libs/lua/exts 目录中建立文件:

lualoadexts.h

#ifndef __LUALOADEXTS_H_ #define __LUALOADEXTS_H_  #include "lauxlib.h"  void luax_initpreload(lua_State *L);  #endif // __LUALOADEXTS_H_ 

lualoadexts.c

#include "lualoadexts.h"  // luasocket #include "luasocket.h" #include "mime.h"  static luaL_Reg luax_preload_list[] = {     {"socket.core", luaopen_socket_core},     {"mime.core", luaopen_mime_core},     {NULL, NULL} };  void luax_initpreload(lua_State *L) {     luaL_Reg* lib = luax_preload_list;     luaL_findtable(L, LUA_GLOBALSINDEX, "package.preload",                    sizeof(luax_preload_list)/sizeof(luax_preload_list[0])-1);     for (; lib->func; lib++) {         lua_pushstring(L, lib->name);         lua_pushcfunction(L, lib->func);         lua_rawset(L, -3);     }     lua_pop(L, 1); } 

最后,打开 libs/lua/cocos2dx_support/LuaEngineImpl.cpp 文件,在 CCLuaScriptModule::CCLuaScriptModule() 构造函数最后载入 Lua 标准库和扩展库的代码:

CCLuaScriptModule::CCLuaScriptModule() {     d_ownsState = true;     d_state = lua_open();     luaL_openlibs(d_state);     int nOpen = tolua_Cocos2d_open(d_state);     CC_UNUSED_PARAM(nOpen);     nOpen = tolua_SimpleAudioEngine_open(d_state);     CC_UNUSED_PARAM(nOpen);      // init standard libraries     luaL_openlibs(d_state);     // init more libraries     luax_initpreload(d_state); } 

LuaScoket 除了 C 代码,还有一部分是 Lua 代码,所以需要将 luasocket-2.0.2/src/*.lua 复制到项目中,然后用下列 Lua 代码进行测试:

local socket = require("socket") print("socket module:", socket) print("socket.connect function:", socket.connect) print("socket.bind function:", socket.bind)  print("\n") print("io module:", io) 
posted @ 2012-02-08 00:03 ivaneeo 阅读(4039) | 评论 (0)编辑 收藏

将 Lua 源代码直接放入最终产品,显然不是个理想选择。利用 LOOP 提供的 Precompiler 工具,可以将 Lua 模块编译为 C 代码。

准备工作

LOOP 是一个 Lua 的 OOP 框架,Precompiler 则是 LOOP 中包含的一个工具。要安装 LOOP,得先安装 LuaRocks

$ wget http://luarocks.org/releases/luarocks-2.0.5.tar.gz $ tar zxf luarocks-2.0.5.tar.gz $ cd luarocks-2.0.5 $ ./configure $ make $ sudo make install 

然后安装 LOOP:

$ sudo luarocks install loop 

OK,现在准备工作完成了,接下来就是编译 Lua 模块为 C 代码。

编译

我们的框架中有一个 display.lua 模块,下面的代码可以将这个模块编译出来:

$ precompiler.lua -o luaqeeplayscripts -l "?.lua" -b -p qeeplay qeeplay/display.lua 

最后会得到 luaqeeplayscripts.c/.h 文件。其中定义了函数:

qeeplay int luaopen_qeeplay_display(lua_State *L); 

在上述命令行中,各个参数的意义如下:

-o: 指定输出文件名,例如 -o luaqeeplayscripts 会输出 luaqeeplayscripts.c/.h  -l: 指定推断 lua 模块名的模式,设定为 -l "?.lua" 就会以 lua 源文件名称作为模块名。     例如 display.lua 就是 display 模块。如果 display.lua 文件在 qeeplay 子目录中,     那么 qeeplay/display.lua 的模块名就是 qeeplay.display。  -b: 编译为字节码  -p: 函数定义的前缀,一般指定一个可以方便以后对生成的 .c/.h 文件进行再处理 

如果要将多个 lua 文件编译为一个 C 代码,可以添加更多的文件名到命令行中,例如:

$ precompiler.lua -o luasocketscripts -l "?.lua" -b -p socket \     socket.lua \     socket/url.lua \     socket/tp.lua \     socket/smtp.lua \     socket/mime.lua \     socket/ltn12.lua \     socket/http.lua \     socket/ftp.lua 

会创建 luasocketscripts.c/.h 文件,其中定义下列函数:

socket int luaopen_socket(lua_State *L); socket int luaopen_socket_url(lua_State *L); socket int luaopen_socket_tp(lua_State *L); socket int luaopen_socket_smtp(lua_State *L); socket int luaopen_socket_mime(lua_State *L); socket int luaopen_socket_ltn12(lua_State *L); socket int luaopen_socket_http(lua_State *L); socket int luaopen_socket_ftp(lua_State *L); 

载入编译好的 C 代码

利用前一篇文章中的 lualoadexts.c/lualoadexts.h,做一些修改即可:

luaqeeplayscripts.c

#include "lualoadexts.h"  // qeeplay #include "luaqeeplayscripts.h"  static luaL_Reg luax_preload_list[] = {     {"qeeplay.display", luaopen_qeeplay_display},     {NULL, NULL} };  void luax_initpreload(lua_State *L) {     .... } 

如果有更多模块需要载入,只需要 include 相应的头文件,并修改 luax_preload_list 定义即可。

posted @ 2012-02-08 00:01 ivaneeo 阅读(1098) | 评论 (0)编辑 收藏

今天在flex里通过addEventListener函数给控件动态加载click事件侦听函数时,除了事件本身传递的Event类型参数外,还需要传递更多的参数,在网上找了一段代码,用起来还不错,张贴到这里。

package
{
    public class EventArgExtend
    {
        public function EventArgExtend()
        {
        }
       
        public static function create(f:Function,... arg):Function
        {
               var F:Boolean=false;
               var _f:Function=function(e:*,..._arg)
               {
                   _arg=arg
                   if(!F)
                   {
                       F=true
                       _arg.unshift(e)
                   }
                   f.apply(null,_arg)
               };
               return _f;
          }
          public static function toString():String
          {
               return "Class JEventDelegate";
          }
    }
}

=========================================== 使用的方式:
txtShow.addEventListener(MouseEvent.CLICK,EventArgExtend.create(clickHandler,1,"str"));

            private function clickHandler(e:Event,...arg):void
            {
                Alert.show(arg[0].toString());
                Alert.show(arg[1].toString());
            }


还有另外一个方法,没有封装效果,不过代码更加容易理解:

var sayHello:String = "欢迎光临www.FlashJ.cn -Flash,Ria技术博客";
btn1.addEventListener(MouseEvent.CLICK,function (e:MouseEvent){clickHandlerWithArg(e,sayHello)});
function clickHandlerWithArg(e:MouseEvent,arg:String):void
{
var out:String= e.target + "发出事件(有参数) :" + arg;
trace(out);
}
posted @ 2011-12-16 17:43 ivaneeo 阅读(470) | 评论 (0)编辑 收藏

编辑
作用域   功能   快捷键  
全局   查找并替换   Ctrl+F  
文本编辑器   查找上一个   Ctrl+Shift+K  
文本编辑器   查找下一个   Ctrl+K  
全局   撤销   Ctrl+Z  
全局   复制   Ctrl+C  
全局   恢复上一个选择   Alt+Shift+↓  
全局   剪切   Ctrl+X  
全局   快速修正   Ctrl1+1  
全局   内容辅助   Alt+/  
全局   全部选中   Ctrl+A  
全局   删除   Delete  
全局   上下文信息   Alt+?
Alt+Shift+?
Ctrl+Shift+Space  
Java编辑器   显示工具提示描述   F2  
Java编辑器   选择封装元素   Alt+Shift+↑  
Java编辑器   选择上一个元素   Alt+Shift+←  
Java编辑器   选择下一个元素   Alt+Shift+→  
文本编辑器   增量查找   Ctrl+J  
文本编辑器   增量逆向查找   Ctrl+Shift+J  
全局   粘贴   Ctrl+V  
全局   重做   Ctrl+Y  


 
查看
作用域   功能   快捷键  
全局   放大   Ctrl+=  
全局   缩小   Ctrl+-  


 
窗口
作用域   功能   快捷键  
全局   激活编辑器   F12  
全局   切换编辑器   Ctrl+Shift+W  
全局   上一个编辑器   Ctrl+Shift+F6  
全局   上一个视图   Ctrl+Shift+F7  
全局   上一个透视图   Ctrl+Shift+F8  
全局   下一个编辑器   Ctrl+F6  
全局   下一个视图   Ctrl+F7  
全局   下一个透视图   Ctrl+F8  
文本编辑器   显示标尺上下文菜单   Ctrl+W  
全局   显示视图菜单   Ctrl+F10  
全局   显示系统菜单   Alt+-  


导航
作用域   功能   快捷键  
Java编辑器   打开结构   Ctrl+F3  
全局   打开类型   Ctrl+Shift+T  
全局   打开类型层次结构   F4  
全局   打开声明   F3  
全局   打开外部javadoc   Shift+F2  
全局   打开资源   Ctrl+Shift+R  
全局   后退历史记录   Alt+←  
全局   前进历史记录   Alt+→  
全局   上一个   Ctrl+,  
全局   下一个   Ctrl+.  
Java编辑器   显示大纲   Ctrl+O  
全局   在层次结构中打开类型   Ctrl+Shift+H  
全局   转至匹配的括号   Ctrl+Shift+P  
全局   转至上一个编辑位置   Ctrl+Q  
Java编辑器   转至上一个成员   Ctrl+Shift+↑  
Java编辑器   转至下一个成员   Ctrl+Shift+↓  
文本编辑器   转至行   Ctrl+L  

 
搜索
作用域   功能   快捷键  
全局   出现在文件中   Ctrl+Shift+U  
全局   打开搜索对话框   Ctrl+H  
全局   工作区中的声明   Ctrl+G  
全局   工作区中的引用   Ctrl+Shift+G  

 
文本编辑
作用域   功能   快捷键  
文本编辑器   改写切换   Insert  
文本编辑器   上滚行   Ctrl+↑  
文本编辑器   下滚行   Ctrl+↓  

 
文件
作用域   功能   快捷键  
全局   保存   Ctrl+X  
Ctrl+S  
全局   打印   Ctrl+P  
全局   关闭   Ctrl+F4  
全局   全部保存   Ctrl+Shift+S  
全局   全部关闭   Ctrl+Shift+F4  
全局   属性   Alt+Enter  
全局   新建   Ctrl+N  

 
项目
作用域   功能   快捷键  
全局   全部构建   Ctrl+B  

源代码
作用域   功能   快捷键  
Java编辑器   格式化   Ctrl+Shift+F  
Java编辑器   取消注释   Ctrl+\  
Java编辑器   注释   Ctrl+/  
Java编辑器   添加导入   Ctrl+Shift+M  
Java编辑器   组织导入   Ctrl+Shift+O  
Java编辑器   使用try/catch块来包围   未设置,太常用了,所以在这里列出,建议自己设置。
也可以使用Ctrl+1自动修正。  

 
运行
作用域   功能   快捷键  
全局   单步返回   F7  
全局   单步跳过   F6  
全局   单步跳入   F5  
全局   单步跳入选择   Ctrl+F5  
全局   调试上次启动   F11  
全局   继续   F8  
全局   使用过滤器单步执行   Shift+F5  
全局   添加/去除断点   Ctrl+Shift+B  
全局   显示   Ctrl+D  
全局   运行上次启动   Ctrl+F11  
全局   运行至行   Ctrl+R  
全局   执行   Ctrl+U  

 
重构
作用域   功能   快捷键  
全局   撤销重构   Alt+Shift+Z  
全局   抽取方法   Alt+Shift+M  
全局   抽取局部变量   Alt+Shift+L  
全局   内联   Alt+Shift+I  
全局   移动   Alt+Shift+V  
全局   重命名   Alt+Shift+R  
全局   重做   Alt+Shift+Y  
posted @ 2011-12-16 10:30 ivaneeo 阅读(285) | 评论 (0)编辑 收藏

configure 脚本确定系统所具有一些特性,特别是 nginx 用来处理连接的方法。然后,它创建 Makefile 文件。

configure 支持下面的选项:

--prefix=<path> - Nginx安装路径。如果没有指定,默认为 /usr/local/nginx。

--sbin-path=<path> - Nginx可执行文件安装路径。只能安装时指定,如果没有指定,默认为<prefix>/sbin/nginx。

--conf-path=<path> - 在没有给定-c选项下默认的nginx.conf的路径。如果没有指定,默认为<prefix>/conf/nginx.conf。

--pid-path=<path> - 在nginx.conf中没有指定pid指令的情况下,默认的nginx.pid的路径。如果没有指定,默认为 <prefix>/logs/nginx.pid。

--lock-path=<path> - nginx.lock文件的路径。

--error-log-path=<path> - 在nginx.conf中没有指定error_log指令的情况下,默认的错误日志的路径。如果没有指定,默认为 <prefix>/logs/error.log。

--http-log-path=<path> - 在nginx.conf中没有指定access_log指令的情况下,默认的访问日志的路径。如果没有指定,默认为 <prefix>/logs/access.log。

--user=<user> - 在nginx.conf中没有指定user指令的情况下,默认的nginx使用的用户。如果没有指定,默认为 nobody。

--group=<group> - 在nginx.conf中没有指定user指令的情况下,默认的nginx使用的组。如果没有指定,默认为 nobody。

--builddir=DIR - 指定编译的目录

--with-rtsig_module - 启用 rtsig 模块

--with-select_module --without-select_module - Whether or not to enable the select module. This module is enabled by default if a more suitable method such as kqueue, epoll, rtsig or /dev/poll is not discovered by configure.

//允许或不允许开启SELECT模式,如果 configure 没有找到更合适的模式,比如:kqueue(sun os),epoll (linux kenel 2.6+), rtsig(实时信号)或者/dev/poll(一种类似select的模式,底层实现与SELECT基本相 同,都是采用轮训方法) SELECT模式将是默认安装模式

--with-poll_module --without-poll_module - Whether or not to enable the poll module. This module is enabled by default if a more suitable method such as kqueue, epoll, rtsig or /dev/poll is not discovered by configure.

--with-http_ssl_module - Enable ngx_http_ssl_module. Enables SSL support and the ability to handle HTTPS requests. Requires OpenSSL. On Debian, this is libssl-dev.

//开启HTTP SSL模块,使NGINX可以支持HTTPS请求。这个模块需要已经安装了OPENSSL,在DEBIAN上是libssl-dev

--with-http_realip_module - 启用 ngx_http_realip_module

--with-http_addition_module - 启用 ngx_http_addition_module

--with-http_sub_module - 启用 ngx_http_sub_module

--with-http_dav_module - 启用 ngx_http_dav_module

--with-http_flv_module - 启用 ngx_http_flv_module

--with-http_stub_status_module - 启用 "server status" 页

--without-http_charset_module - 禁用 ngx_http_charset_module

--without-http_gzip_module - 禁用 ngx_http_gzip_module. 如果启用,需要 zlib 。

--without-http_ssi_module - 禁用 ngx_http_ssi_module

--without-http_userid_module - 禁用 ngx_http_userid_module

--without-http_access_module - 禁用 ngx_http_access_module

--without-http_auth_basic_module - 禁用 ngx_http_auth_basic_module

--without-http_autoindex_module - 禁用 ngx_http_autoindex_module

--without-http_geo_module - 禁用 ngx_http_geo_module

--without-http_map_module - 禁用 ngx_http_map_module

--without-http_referer_module - 禁用 ngx_http_referer_module

--without-http_rewrite_module - 禁用 ngx_http_rewrite_module. 如果启用需要 PCRE 。

--without-http_proxy_module - 禁用 ngx_http_proxy_module

--without-http_fastcgi_module - 禁用 ngx_http_fastcgi_module

--without-http_memcached_module - 禁用 ngx_http_memcached_module

--without-http_limit_zone_module - 禁用 ngx_http_limit_zone_module

--without-http_empty_gif_module - 禁用 ngx_http_empty_gif_module

--without-http_browser_module - 禁用 ngx_http_browser_module

--without-http_upstream_ip_hash_module - 禁用 ngx_http_upstream_ip_hash_module

--with-http_perl_module - 启用 ngx_http_perl_module

--with-perl_modules_path=PATH - 指定 perl 模块的路径

--with-perl=PATH - 指定 perl 执行文件的路径

--http-log-path=PATH - Set path to the http access log

--http-client-body-temp-path=PATH - Set path to the http client request body temporary files

--http-proxy-temp-path=PATH - Set path to the http proxy temporary files

--http-fastcgi-temp-path=PATH - Set path to the http fastcgi temporary files

--without-http - 禁用 HTTP server

--with-mail - 启用 IMAP4/POP3/SMTP 代理模块

--with-mail_ssl_module - 启用 ngx_mail_ssl_module

--with-cc=PATH - 指定 C 编译器的路径

--with-cpp=PATH - 指定 C 预处理器的路径

--with-cc-opt=OPTIONS - Additional parameters which will be added to the variable CFLAGS. With the use of the system library PCRE in FreeBSD, it is necessary to indicate --with-cc-opt="-I /usr/local/include". If we are using select() and it is necessary to increase the number of file descriptors, then this also can be assigned here: --with-cc-opt="-D FD_SETSIZE=2048".

--with-ld-opt=OPTIONS - Additional parameters passed to the linker. With the use of the system library PCRE in FreeBSD, it is necessary to indicate --with-ld-opt="-L /usr/local/lib".

--with-cpu-opt=CPU - 为特定的 CPU 编译,有效的值包括:pentium, pentiumpro, pentium3, pentium4, athlon, opteron, amd64, sparc32, sparc64, ppc64

--without-pcre - 禁止 PCRE 库的使用。同时也会禁止 HTTP rewrite 模块。在 "location" 配置指令中的正则表达式也需要 PCRE 。

--with-pcre=DIR - 指定 PCRE 库的源代码的路径。

--with-pcre-opt=OPTIONS - Set additional options for PCRE building.

--with-md5=DIR - Set path to md5 library sources.

--with-md5-opt=OPTIONS - Set additional options for md5 building.

--with-md5-asm - Use md5 assembler sources.

--with-sha1=DIR - Set path to sha1 library sources.

--with-sha1-opt=OPTIONS - Set additional options for sha1 building.

--with-sha1-asm - Use sha1 assembler sources.

--with-zlib=DIR - Set path to zlib library sources.

--with-zlib-opt=OPTIONS - Set additional options for zlib building.

--with-zlib-asm=CPU - Use zlib assembler sources optimized for specified CPU, valid values are: pentium, pentiumpro

--with-openssl=DIR - Set path to OpenSSL library sources

--with-openssl-opt=OPTIONS - Set additional options for OpenSSL building

--with-debug - 启用调试日志

--add-module=PATH - Add in a third-party module found in directory PATH

在不同版本间,选项可能会有些许变化,请总是使用 ./configure --help 命令来检查一下当前的选项列表。

posted @ 2011-12-13 15:01 ivaneeo 阅读(332) | 评论 (0)编辑 收藏

见配置,摘自nginx.conf 里的server 段:

server { listen 80; server_name abc.163.com ; location / { proxy_pass http://ent.163.com/ ; } location /star/ { proxy_pass http://ent.163.com ; } }

里面有两个location,我先说第一个,/ 。其实这里有两种写法,分别是:

location / { proxy_pass http://ent.163.com/ ; }
location / { proxy_pass http://ent.163.com ; }

出来的效果都一样的。

第二个location,/star/。同样两种写法都有,都出来的结果,就不一样了。

location /star/ { proxy_pass http://ent.163.com ; }

当访问 http://abc.163.com/star/ 的时候,nginx 会代理访问到 http://ent.163.com/star/ ,并返回给我们。

location /star/ { proxy_pass http://ent.163.com/ ; }

当访问 http://abc.163.com/star/ 的时候,nginx 会代理访问到 http://ent.163.com/ ,并返回给我们。

这两段配置,分别在于, proxy_pass http://ent.163.com/ ; 这个”/”,令到出来的结果完全不同。

前者,相当于告诉nginx,我这个location,是代理访问到http://ent.163.com 这个server的,我的location是什么,nginx 就把location 加在proxy_pass 的 server 后面,这里是/star/,所以就相当于 http://ent.163.com/star/。如果是location /blog/ ,就是代理访问到 http://ent.163.com/blog/。

后者,相当于告诉nginx,我这个location,是代理访问到http://ent.163.com/的,http: //abc.163.com/star/ == http://ent.163.com/ ,可以这样理解。改变location,并不能改变返回的内容,返回的内容始终是http://ent.163.com/ 。 如果是location /blog/ ,那就是 http://abc.163.com/blog/ == http://ent.163.com/ 。

这样,也可以解释了上面那个location / 的例子,/ 嘛,加在server 的后面,仍然是 / ,所以,两种写法出来的结果是一样的。

PS: 如果是 location ~* ^/start/(.*)\.html 这种正则的location,是不能写”/”上去的,nginx -t 也会报错的了。因为,路径都需要正则匹配了嘛,并不是一个相对固定的locatin了,必然要代理到一个server。

posted @ 2011-12-13 13:21 ivaneeo 阅读(513) | 评论 (0)编辑 收藏

location

syntax: location [=|~|~*|^~] /uri/ { … }
语法:location [=|~|~*|^~] /uri/ { … }

default: no
默认:否

context: server
上下文:server

This directive allows different configurations depending on the URI. It can be configured using both conventional strings and regular expressions. To use regular expressions, you must use the prefix ~* for case insensitive match and ~ for case sensitive match.
这个指令随URL不同而接受不同的结构。你可以配置使用常规字符串和正则表达式。如果使用正则表达式,你必须使用 ~* 前缀选择不区分大小写的匹配或者 ~ 选择区分大小写的匹配。

To determine which location directive matches a particular query, the conventional strings are checked first. Conventional strings match the beginning portion of the query and are case-sensitive – the most specific match will be used (see below on how nginx determines this). Afterwards, regular expressions are checked in the order defined in the configuration file. The first regular expression to match the query will stop the search. If no regular expression matches are found, the result from the convention string search is used.
确定 哪个location 指令匹配一个特定指令,常规字符串第一个测试。常规字符串匹配请求的开始部分并且区分大小写,最明确的匹配将会被使用(查看下文明白 nginx 怎么确定它)。然后正则表达式按照配置文件里的顺序测试。找到第一个比配的正则表达式将停止搜索。如果没有找到匹配的正则表达式,使用常规字符串的结果。

There are two ways to modify this behavior. The first is to use the prefix “=”, which matches an exact query only. If the query matches, then searching stops and the request is handled immediately. For example, if the request “/” occurs frequently, then using “location = /” will expedite the processing of this request.
有两个方法修改这个行为。第一个方法是使用 “=”前缀,将只执行严格匹配。如果这个查询匹配,那么将停止搜索并立即处理这个请求。例子:如果经常发生”/”请求,那么使用 “location = /” 将加速处理这个请求。

The second is to use the prefix ^~. This prefix is used with a conventional string and tells nginx to not check regular expressions if the path provided is a match. For instance, “location ^~ /images/” would halt searching if the query begins with /images/ – all regular expression directives would not be checked.
第二个是使用 ^~ 前缀。如果把这个前缀用于一个常规字符串那么告诉nginx 如果路径匹配那么不测试正则表达式。

Furthermore it is important to know that NGINX does the comparison not URL encoded, so if you have a URL like “/images/%20/test” then use “/images/ /test” to determine the location.
而且它重要在于 NGINX 做比较没有 URL 编码,所以如果你有一个 URL 链接’/images/%20/test’ , 那么使用 “images/ /test” 限定location。

To summarize, the order in which directives are checked is as follows:
总结,指令按下列顺序被接受:

1. Directives with the = prefix that match the query exactly. If found, searching stops.
1. = 前缀的指令严格匹配这个查询。如果找到,停止搜索。
2. All remaining directives with conventional strings, longest match first. If this match used the ^~ prefix, searching stops.
2. 剩下的常规字符串,长的在前。如果这个匹配使用 ^~ 前缀,搜索停止。
3. Regular expressions, in order of definition in the configuration file.
3. 正则表达式,按配置文件里的顺序。
4. If #3 yielded a match, that result is used. Else the match from #2 is used.
4. 如果第三步产生匹配,则使用这个结果。否则使用第二步的匹配结果。

Example:
例子:

location = / {
# matches the query / only.
# 只匹配 / 查询。
[ configuration A ]
}
location / {
# matches any query, since all queries begin with /, but regular
# expressions and any longer conventional blocks will be
# matched first.
# 匹配任何查询,因为所有请求都已 / 开头。但是正则表达式规则和长的块规则将被优先和查询匹配。
[ configuration B ]
}
location ^~ /images/ {
# matches any query beginning with /images/ and halts searching,
# so regular expressions will not be checked.
# 匹配任何已 /images/ 开头的任何查询并且停止搜索。任何正则表达式将不会被测试。
[ configuration C ]
}
location ~* “.(gif|jpg|jpeg)$ {
# matches any request ending in gif, jpg, or jpeg. However, all
# requests to the /images/ directory will be handled by
# Configuration C.
# 匹配任何已 gif、jpg 或 jpeg 结尾的请求。然而所有 /images/ 目录的请求将使用 Configuration C。
[ configuration D ]
}

Example requests:
例子请求:

*

/ -> configuration A
*

/documents/document.html -> configuration B
*

/images/1.gif -> configuration C
*

/documents/1.jpg -> configuration D

Note that you could define these 4 configurations in any order and the results would remain the same.
注意:按任意顺序定义这4个配置结果将仍然一样。

一、介绍Nginx是俄罗斯人编写的十分轻量级的HTTP服务器,Nginx,它的发音为“engine X”, 是一个高性能的HTTP和反向代理服务器,同时也是一个IMAP/POP3/SMTP 代理服务器.
二、Location语法语法:location [=|~|~*|^~] /uri/ { … }
注:
1、~   为区分大小写匹配
2、~* 为不区分大小写匹配
3、!~和!~*分别为区分大小写不匹配及不区分大小写
不匹配
示例一:
location  / {
}
匹配任何查询,因为所有请求都以 / 开头。但是正则表达式规则将被优先和查询匹配。
示例二:
location =/ {}
仅仅匹配/

示例三:
location ~* \.(gif|jpg|jpeg)$ {
rewrite \.(gif|jpg)$ /logo.png;

注:不区分大小写匹配任何以gif,jpg,jpeg结尾的文件

三、ReWrite语法
last – 基本上都用这个Flag。
break – 中止Rewirte,不在继续匹配
redirect – 返回临时重定向的HTTP状态302
permanent – 返回永久重定向的HTTP状态301

1、下面是可以用来判断的表达式:
-f和!-f用来判断是否存在文件
-d和!-d用来判断是否存在目录
-e和!-e用来判断是否存在文件或目录
-x和!-x用来判断文件是否可执行
2、下面是可以用作判断的全局变量
例:http://localhost:88/test1/test2/test.php
$host:localhost
$server_port:88
$request_uri:
http://localhost:88/test1/test2/test.php
$document_uri:/test1/test2/test.php
$document_root:D:\nginx/html
$request_filename:D:\nginx/html/test1/test2/test.php

四、Redirect语法
server {
listen 80;
server_name start.igrow.cn;
index index.html index.php;
root html;
if ($http_host !~ “^star\.igrow\.cn

正则表达式匹配,其中:

  1. * ~ 为区分大小写匹配
  2. * ~* 为不区分大小写匹配
  3. * !~和!~*分别为区分大小写不匹配及不区分大小写不匹配

文件及目录匹配,其中:

  1. * -f和!-f用来判断是否存在文件
  2. * -d和!-d用来判断是否存在目录
  3. * -e和!-e用来判断是否存在文件或目录
  4. * -x和!-x用来判断文件是否可执行

flag标记有:

  1. * last 相当于Apache里的[L]标记,表示完成rewrite
  2. * break 终止匹配, 不再匹配后面的规则
  3. * redirect 返回302临时重定向 地址栏会显示跳转后的地址
  4. * permanent 返回301永久重定向 地址栏会显示跳转后的地址

一些可用的全局变量有,可以用做条件判断(待补全)

  1. $args
  2. $content_length
  3. $content_type
  4. $document_root
  5. $document_uri
  6. $host
  7. $http_user_agent
  8. $http_cookie
  9. $limit_rate
  10. $request_body_file
  11. $request_method
  12. $remote_addr
  13. $remote_port
  14. $remote_user
  15. $request_filename
  16. $request_uri
  17. $query_string
  18. $scheme
  19. $server_protocol
  20. $server_addr
  21. $server_name
  22. $server_port
  23. $uri

结合QeePHP的例子

  1. if (!-d $request_filename) {
  2. rewrite ^/([a-z-A-Z]+)/([a-z-A-Z]+)/?(.*)$ /index.php?namespace=user&amp;controller=$1&amp;action=$2&amp;$3 last;
  3. rewrite ^/([a-z-A-Z]+)/?$ /index.php?namespace=user&amp;controller=$1 last;
  4. break;

多目录转成参数
abc.domian.com/sort/2 => abc.domian.com/index.php?act=sort&name=abc&id=2

  1. if ($host ~* (.*)\.domain\.com) {
  2. set $sub_name $1;
  3. rewrite ^/sort\/(\d+)\/?$ /index.php?act=sort&cid=$sub_name&id=$1 last;
  4. }

目录对换
/123456/xxxx -> /xxxx?id=123456

  1. rewrite ^/(\d+)/(.+)/ /$2?id=$1 last;

例如下面设定nginx在用户使用ie的使用重定向到/nginx-ie目录下:

  1. if ($http_user_agent ~ MSIE) {
  2. rewrite ^(.*)$ /nginx-ie/$1 break;
  3. }

目录自动加“/”

  1. if (-d $request_filename){
  2. rewrite ^/(.*)([^/])$ http://$host/$1$2/ permanent;
  3. }

禁止htaccess

  1. location ~/\.ht {
  2. deny all;
  3. }

禁止多个目录

  1. location ~ ^/(cron|templates)/ {
  2. deny all;
  3. break;
  4. }

禁止以/data开头的文件
可以禁止/data/下多级目录下.log.txt等请求;

  1. location ~ ^/data {
  2. deny all;
  3. }

禁止单个目录
不能禁止.log.txt能请求

  1. location /searchword/cron/ {
  2. deny all;
  3. }

禁止单个文件

  1. location ~ /data/sql/data.sql {
  2. deny all;
  3. }

给favicon.ico和robots.txt设置过期时间;
这里为favicon.ico为99天,robots.txt为7天并不记录404错误日志

  1. location ~(favicon.ico) {
  2. log_not_found off;
  3. expires 99d;
  4. break;
  5. }

  6. location ~(robots.txt) {
  7. log_not_found off;
  8. expires 7d;
  9. break;
  10. }

设定某个文件的过期时间;这里为600秒,并不记录访问日志

  1. location ^~ /html/scripts/loadhead_1.js {
  2. access_log off;
  3. root /opt/lampp/htdocs/web;
  4. expires 600;
  5. break;
  6. }

文件反盗链并设置过期时间
这里的return 412 为自定义的http状态码,默认为403,方便找出正确的盗链的请求
“rewrite ^/ http://leech.c1gstudio.com/leech.gif;”显示一张防盗链图片
“access_log off;”不记录访问日志,减轻压力
“expires 3d”所有文件3天的浏览器缓存

  1. location ~* ^.+\.(jpg|jpeg|gif|png|swf|rar|zip|css|js)$ {
  2. valid_referers none blocked *.c1gstudio.com *.c1gstudio.net localhost 208.97.167.194;
  3. if ($invalid_referer) {
  4. rewrite ^/ http://leech.c1gstudio.com/leech.gif;
  5. return 412;
  6. break;
  7. }
  8. access_log off;
  9. root /opt/lampp/htdocs/web;
  10. expires 3d;
  11. break;
  12. }

只充许固定ip访问网站,并加上密码

  1. root /opt/htdocs/www;
  2. allow 208.97.167.194;
  3. allow 222.33.1.2;
  4. allow 231.152.49.4;
  5. deny all;
  6. auth_basic “C1G_ADMIN”;
  7. auth_basic_user_file htpasswd;

将多级目录下的文件转成一个文件,增强seo效果
/job-123-456-789.html 指向/job/123/456/789.html

  1. rewrite ^/job-([0-9]+)-([0-9]+)-([0-9]+)\.html$ /job/$1/$2/jobshow_$3.html last;

将根目录下某个文件夹指向2级目录
如/shanghaijob/ 指向 /area/shanghai/
如果你将last改成permanent,那么浏览器地址栏显是/location/shanghai/

  1. rewrite ^/([0-9a-z]+)job/(.*)$ /area/$1/$2 last;

上面例子有个问题是访问/shanghai 时将不会匹配

  1. rewrite ^/([0-9a-z]+)job$ /area/$1/ last;
  2. rewrite ^/([0-9a-z]+)job/(.*)$ /area/$1/$2 last;

这样/shanghai 也可以访问了,但页面中的相对链接无法使用,
如./list_1.html真实地址是/area/shanghia/list_1.html会变成/list_1.html,导至无法访问。

那我加上自动跳转也是不行咯
(-d $request_filename)它有个条件是必需为真实目录,而我的rewrite不是的,所以没有效果

  1. if (-d $request_filename){
  2. rewrite ^/(.*)([^/])$ http://$host/$1$2/ permanent;
  3. }

知道原因后就好办了,让我手动跳转吧

  1. rewrite ^/([0-9a-z]+)job$ /$1job/ permanent;
  2. rewrite ^/([0-9a-z]+)job/(.*)$ /area/$1/$2 last;

文件和目录不存在的时候重定向:

  1. if (!-e $request_filename) {
  2. proxy_pass http://127.0.0.1;
  3. }

域名跳转

  1. server
  2. {
  3. listen 80;
  4. server_name jump.c1gstudio.com;
  5. index index.html index.htm index.php;
  6. root /opt/lampp/htdocs/www;
  7. rewrite ^/ http://www.c1gstudio.com/;
  8. access_log off;
  9. }

多域名转向

  1. server_name www.c1gstudio.com www.c1gstudio.net;
  2. index index.html index.htm index.php;
  3. root /opt/lampp/htdocs;
  4. if ($host ~ “c1gstudio\.net”) {
  5. rewrite ^(.*) http://www.c1gstudio.com$1 permanent;
  6. }

三级域名跳转

  1. if ($http_host ~* “^(.*)\.i\.c1gstudio\.com$”) {
  2. rewrite ^(.*) http://top.yingjiesheng.com$1;
  3. break;
  4. }

域名镜向

  1. server
  2. {
  3. listen 80;
  4. server_name mirror.c1gstudio.com;
  5. index index.html index.htm index.php;
  6. root /opt/lampp/htdocs/www;
  7. rewrite ^/(.*) http://www.c1gstudio.com/$1 last;
  8. access_log off;
  9. }

某个子目录作镜向

  1. location ^~ /zhaopinhui {
  2. rewrite ^.+ http://zph.c1gstudio.com/ last;
  3. break;
  4. }

discuz ucenter home (uchome) rewrite

  1. rewrite ^/(space|network)-(.+)\.html$ /$1.php?rewrite=$2 last;
  2. rewrite ^/(space|network)\.html$ /$1.php last;
  3. rewrite ^/([0-9]+)$ /space.php?uid=$1 last;

discuz 7 rewrite

  1. rewrite ^(.*)/archiver/((fid|tid)-[\w\-]+\.html)$ $1/archiver/index.php?$2 last;
  2. rewrite ^(.*)/forum-([0-9]+)-([0-9]+)\.html$ $1/forumdisplay.php?fid=$2&page=$3 last;
  3. rewrite ^(.*)/thread-([0-9]+)-([0-9]+)-([0-9]+)\.html$ $1/viewthread.php?tid=$2&extra=page\%3D$4&page=$3 last;
  4. rewrite ^(.*)/profile-(username|uid)-(.+)\.html$ $1/viewpro.php?$2=$3 last;
  5. rewrite ^(.*)/space-(username|uid)-(.+)\.html$ $1/space.php?$2=$3 last;
  6. rewrite ^(.*)/tag-(.+)\.html$ $1/tag.php?name=$2 last;

给discuz某版块单独配置域名

  1. server_name bbs.c1gstudio.com news.c1gstudio.com;

  2. location = / {
  3. if ($http_host ~ news\.c1gstudio.com$) {
  4. rewrite ^.+ http://news.c1gstudio.com/forum-831-1.html last;
  5. break;
  6. }
  7. }

discuz ucenter 头像 rewrite 优化

  1. location ^~ /ucenter {
  2. location ~ .*\.php?$
  3. {
  4. #fastcgi_pass unix:/tmp/php-cgi.sock;
  5. fastcgi_pass 127.0.0.1:9000;
  6. fastcgi_index index.php;
  7. include fcgi.conf;
  8. }

  9. location /ucenter/data/avatar {
  10. log_not_found off;
  11. access_log off;
  12. location ~ /(.*)_big\.jpg$ {
  13. error_page 404 /ucenter/images/noavatar_big.gif;
  14. }
  15. location ~ /(.*)_middle\.jpg$ {
  16. error_page 404 /ucenter/images/noavatar_middle.gif;
  17. }
  18. location ~ /(.*)_small\.jpg$ {
  19. error_page 404 /ucenter/images/noavatar_small.gif;
  20. }
  21. expires 300;
  22. break;
  23. }
  24. }

jspace rewrite

  1. location ~ .*\.php?$
  2. {
  3. #fastcgi_pass unix:/tmp/php-cgi.sock;
  4. fastcgi_pass 127.0.0.1:9000;
  5. fastcgi_index index.php;
  6. include fcgi.conf;
  7. }

  8. location ~* ^/index.php/
  9. {
  10. rewrite ^/index.php/(.*) /index.php?$1 break;
  11. fastcgi_pass 127.0.0.1:9000;
  12. fastcgi_index index.php;
  13. include fcgi.conf;
  14. }

amp;quot {
rewrite ^(.*)
http://star.igrow.cn$1 redirect;
}
}

五、防盗链location ~* \.(gif|jpg|swf)$ {
valid_referers none blocked start.igrow.cn sta.igrow.cn;
if ($invalid_referer) {
rewrite ^/
http://$host/logo.png;
}
}

六、根据文件类型设置过期时间
location ~* \.(js|css|jpg|jpeg|gif|png|swf)$ {
if (-f $request_filename) {
expires    1h;
break;
}
}

七、禁止访问某个目录
location ~* \.(txt|doc)${
root /data/www/wwwroot/linuxtone/test;
deny all;
}

XX

Posted in linux

Tags:

You can leave a response , or trackback from your own site.

Advertisement

Leave a Reply

November 12th, 2010 by admin Leave a reply » 站长统计
posted @ 2011-12-12 22:25 ivaneeo 阅读(4168) | 评论 (0)编辑 收藏

先用现成的组件玩一下,一会再去看看组件源码研究一下。

http://code.google.com/p/flex-iframe/

下载了flexiframe.swc,引入工程。

flex代码

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
    layout="absolute"
    xmlns:code="http://code.google.com/p/flex-iframe/">
 <mx:Panel width="500"
     height="400">

  <code:IFrame id="googleIFrame"
      label="Google"
      source="http://www.google.com"
      width="100%"
      height="100%"/>
 </mx:Panel>

</mx:Application>

运行,发现,可以了。

 

不过,有个问题,鼠标点击别处的时候,网页消失了。

找了很多地方,找到了解决方法。设置wmode。

首先了解一下wmode是什么。

window mode(wmode)

wmode即窗口模式总共有三种:

window 模式

默认情况下的显示模式,在这种模式下flash player有自己的窗口句柄,这就意味着flash影片是存在于Windows中的一个显示实例,并且是在浏览器核心显示窗口之上的,所以flash只 是貌似显示在浏览器中,但这也是flash最快最有效率的渲染模式。由于他是独立于浏览器的HTML渲染表面,这就导致默认显示方式下flash总是会遮 住位置与他重合的所有DHTML层。

但是大多数苹果电脑浏览器会允许DHTML层显示在flash之上,但当flash影片播放时会出现比较诡异的现象,比如DHTML层像被flash刮掉一块一样显示异常。

Opaque 模式

这 是一种无窗口模式,在这种情况下flash player没有自己的窗口句柄,这就需要浏览器需要告诉flash player在浏览器的渲染表面绘制的时间和位置。这时flash影片就不会在高于浏览器HTML渲染表面而是与其他元素一样在同一个页面上,因此你就可 以使用z-index值来控制DHTML元素是遮盖flash或者被遮盖。

Transparent 模式

透明模式, 在这种模式下flash player会将stage的背景色alpha值将为0并且只会绘制stage上真实可见的对象,同样你也可以使用z-index来控制flash影片的 深度值,但是与Opaque模式不同的是这样做会降低flash影片的回放效果,而且在9.0.115之前的flash player版本设置wmode=”opaque”或”transparent”会导致全屏模式失效。

 

这边,我们将wmode设置为transparent。

我直接修改了工程的html模板,红色字体部分为新增加的代码。

if ( hasProductInstall && !hasRequestedVersion ) {
 // DO NOT MODIFY THE FOLLOWING FOUR LINES
 // Location visited after installation is complete if installation is required
 var MMPlayerType = (isIE == true) ? "ActiveX" : "PlugIn";
 var MMredirectURL = window.location;
    document.title = document.title.slice(0, 47) + " - Flash Player Installation";
    var MMdoctitle = document.title;

 AC_FL_RunContent(
  "src", "playerProductInstall",
  "FlashVars", "MMredirectURL="+MMredirectURL+'&MMplayerType='+MMPlayerType+'&MMdoctitle='+MMdoctitle+"",
  "width", "${width}",
  "height", "${height}",
  "align", "middle",
  "id", "${application}",
  "quality", "high",
  "bgcolor", "${bgcolor}",
  "name", "${application}",
  "allowScriptAccess","sameDomain",
  "type", "application/x-shockwave-flash",
  "pluginspage", "http://www.adobe.com/go/getflashplayer",
  "wmode","transparent"
 );
} else if (hasRequestedVersion) {
 // if we've detected an acceptable version
 // embed the Flash Content SWF when all tests are passed
 AC_FL_RunContent(
   "src", "${swf}",
   "width", "${width}",
   "height", "${height}",
   "align", "middle",
   "id", "${application}",
   "quality", "high",
   "bgcolor", "${bgcolor}",
   "name", "${application}",
   "allowScriptAccess","sameDomain",
   "type", "application/x-shockwave-flash",
   "pluginspage", "http://www.adobe.com/go/getflashplayer",
   "wmode","transparent"
 );
  } else {  // flash is too old or we can't detect the plugin
    var alternateContent = 'Alternate HTML content should be placed here. '
   + 'This content requires the Adobe Flash Player. '
    + '<a href=http://www.adobe.com/go/getflash/>Get Flash</a>';
    document.write(alternateContent);  // insert non-flash content
  }

 

   <embed src="${swf}.swf" quality="high" bgcolor="${bgcolor}"
    width="${width}" height="${height}" name="${application}" align="center"
    play="true"
    loop="false"
    quality="high"
    allowScriptAccess="sameDomain"
    type="application/x-shockwave-flash"
    pluginspage="http://www.adobe.com/go/getflashplayer"
    wmode="transparent">
   </embed>

 

保存,运行。问题解决了。

posted @ 2011-12-01 14:48 ivaneeo 阅读(427) | 评论 (0)编辑 收藏

restrict限制的意思

1. 限制某个字符的输入,用符号 ^ 跟上要限制的字符,可跟多个字符 

      <!-- 限制字符"~"的输入 --> 

      <mx:TextInput id="xxx"  restrict="^~" /> 

      <!-- 限制字符"ab"的输入 --> 

      <mx:TextInput id="xxx"  restrict="^ab" /> 

2. 设置只能输入某些字符,将允许输入的字符罗列出来即可,也可以用 - 组合表示字符范围 

      <!-- 只能输入abc --> 

      <mx:TextInput id="xxx"  restrict="abc" /> 

      <!-- 只能输入小写字母 --> 

      <mx:TextInput id="xxx"  restrict="a-z" /> 

      <!-- 只能输入小写字母、大写字母和数字 --> 

      <mx:TextInput id="xxx"  restrict="a-zA-Z0-9" /> 

3. 组合使用 

      <!-- 只能输入数字和符号"." --> 

      <mx:TextInput id="xxx"  restrict="0-9." /> 

      <!-- 只能输入除ab之外的小写字母 --> 

      <mx:TextInput id="xxx"  restrict="a-z^ab" /> 
 

下面罗列出了一些常用的正则表达式:

^/d+$  //匹配非负整数(正整数 + 0)
^[0-9]*[1-9][0-9]*$  //匹配正整数
^((-/d+)|(0+))$  //匹配非正整数(负整数 + 0)
^-[0-9]*[1-9][0-9]*$  //匹配负整数
^-?/d+$    //匹配整数
^/d+(/./d+)?$  //匹配非负浮点数(正浮点数 + 0)
^(([0-9]+/.[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*/.[0-9]+)|([0-9]*[1-9][0-9]*))$  //匹配正浮点数
^((-/d+(/./d+)?)|(0+(/.0+)?))$  //匹配非正浮点数(负浮点数 + 0)
^(-(([0-9]+/.[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*/.[0-9]+)|([0-9]*[1-9][0-9]*)))$  //匹配负浮点数
^(-?/d+)(/./d+)?$  //匹配浮点数
^[A-Za-z]+$  //匹配由26个英文字母组成的字符串
^[A-Z]+$  //匹配由26个英文字母的大写组成的字符串
^[a-z]+$  //匹配由26个英文字母的小写组成的字符串
^[A-Za-z0-9]+$  //匹配由数字和26个英文字母组成的字符串
^/w+$  //匹配由数字、26个英文字母或者下划线组成的字符串
^[/w-]+(/.[/w-]+)*@[/w-]+(/.[/w-]+)+$    //匹配email地址
^[a-zA-z]+://匹配(/w+(-/w+)*)(/.(/w+(-/w+)*))*(/?/S*)?$  //匹配url

匹配中文字符的正则表达式: [/u4e00-/u9fa5]
匹配双字节字符(包括汉字在内):[^/x00-/xff]
匹配空行的正则表达式:/n[/s| ]*/r
匹配HTML标记的正则表达式:/<(.*)>.*<//>|<(.*) //>/
匹配首尾空格的正则表达式:(^/s*)|(/s*$)
匹配Email地址的正则表达式:/w+([-+.]/w+)*@/w+([-.]/w+)*/./w+([-.]/w+)*
匹配网址URL的正则表达式:^[a-zA-z]+://(/w+(-/w+)*)(/.(/w+(-/w+)*))*(/?/S*)?$
匹配帐号是否合法(字母开头,允许5-16字节,允许字母数字下划线):^[a-zA-Z][a-zA-Z0-9_]{4,15}$
匹配国内电话号码:(/d{3}-|/d{4}-)?(/d{8}|/d{7})?
匹配腾讯QQ号:^[1-9]*[1-9][0-9]*$
下表是元字符及其在正则表达式上下文中的行为的一个完整列表:
/ 将下一个字符标记为一个特殊字符、或一个原义字符、或一个后向引用、或一个八进制转义符。
^ 匹配输入字符串的开始位置。如果设置了 RegExp 对象的Multiline 属性,^ 也匹配 ’/n’ 或 ’/r’ 之后的位置。
$ 匹配输入字符串的结束位置。如果设置了 RegExp 对象的Multiline 属性,$ 也匹配 ’/n’ 或 ’/r’ 之前的位置。
* 匹配前面的子表达式零次或多次。
+ 匹配前面的子表达式一次或多次。+ 等价于 {1,}。
? 匹配前面的子表达式零次或一次。? 等价于 {0,1}。
{n} n 是一个非负整数,匹配确定的n 次。
{n,} n 是一个非负整数,至少匹配n 次。
{n,m} m 和 n 均为非负整数,其中n <= m。最少匹配 n 次且最多匹配 m 次。在逗号和两个数之间不能有空格。
? 当该字符紧跟在任何一个其他限制符 (*, +, ?, {n}, {n,}, {n,m}) 后面时,匹配模式是非贪婪的。非贪婪模式尽可能少的匹配所搜索的字符串,而默认的贪婪模式则尽可能多的匹配所搜索的字符串。
. 匹配除 “/n” 之外的任何单个字符。要匹配包括 ’/n’ 在内的任何字符,请使用象 ’[./n]’ 的模式。
(pattern) 匹配pattern 并获取这一匹配。
(?:pattern) 匹配pattern 但不获取匹配结果,也就是说这是一个非获取匹配,不进行存储供以后使用。
x|y 匹配 x 或 y。
[xyz] 字符集合。
[^xyz] 负值字符集合。
[a-z] 字符范围,匹配指定范围内的任意字符。
[^a-z] 负值字符范围,匹配任何不在指定范围内的任意字符。
/b 匹配一个单词边界,也就是指单词和空格间的位置。
/B 匹配非单词边界。
/cx 匹配由x指明的控制字符。
/d 匹配一个数字字符。等价于 [0-9]。

/D 匹配一个非数字字符。等价于 [^0-9]。
/f 匹配一个换页符。等价于 /x0c 和 /cL。
/n 匹配一个换行符。等价于 /x0a 和 /cJ。
/r 匹配一个回车符。等价于 /x0d 和 /cM。
/s 匹配任何空白字符,包括空格、制表符、换页符等等。等价于[ /f/n/r/t/v]。
/S 匹配任何非空白字符。等价于 [^ /f/n/r/t/v]。
/t 匹配一个制表符。等价于 /x09 和 /cI。
/v 匹配一个垂直制表符。等价于 /x0b 和 /cK。
/w 匹配包括下划线的任何单词字符。等价于’[A-Za-z0-9_]’。
/W 匹配任何非单词字符。等价于 ’[^A-Za-z0-9_]’。
/xn 匹配 n,其中 n 为十六进制转义值。十六进制转义值必须为确定的两个数字长。
/num 匹配 num,其中num是一个正整数。对所获取的匹配的引用。
/n 标识一个八进制转义值或一个后向引用。如果 /n 之前至少 n 个获取的子表达式,则 n 为后向引用。否则,如果 n 为八进制数字 (0-7),则 n 为一个八进制转义值。
/nm 标识一个八进制转义值或一个后向引用。如果 /nm 之前至少有is preceded by at least nm 个获取得子表达式,则 nm 为后向引用。如果 /nm 之前至少有 n 个获取,则 n 为一个后跟文字 m 的后向引用。如果前面的条件都不满足,若 n 和 m 均为八进制数字 (0-7),则 /nm 将匹配八进制转义值 nm。

posted @ 2011-11-21 18:24 ivaneeo 阅读(3106) | 评论 (0)编辑 收藏

众所周知Flex主要用于B/S结构程序的开发,凡是这类型的开发都存在页面间的传值的问题,通常一般的B/S开发主要不外乎使用地址修改法,隐藏表单域等方法,但是这些方法在Flex中确没有用,原因是应为Flex支持的模型和普通的B/S开发语言不一样,一般的B/S开发语言使用的主要是请求/响应模型,而Flex采用的是事件驱动模型(这种模型主要见于C/S结构程序),所以我们的Form表单等传值方法就无效了,哪么我们如何在两个这样模型的页面中传递数据呢?下面我们讲述下两种常用的传值方法:
一、 利用ExternalInterface调用Javascript
a) 该方法主要利用ExternalInterface的call方法调用Javascript函数,进而修改地址(有点类似于地址修改法),在接受页面上主要是靠BrowserManager获取地址栏信息,并利用URLUtil截取参数。
b) 该方法虽然简单但是确调用了2种语言,给编写带来一定的困难
发送页面代码(second.html):
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute">
 <mx:Script>
  <![CDATA[
  function kk():void{
   var val:String = myparam.text;
 ExternalInterface.call("function(){window.location.href='http://localhost:8080/send/page.html#param1="+val+"'}");  }
  ]]>
 </mx:Script>
 <mx:TextInput  id="myparam"></mx:TextInput>
 <mx:Button name="ok" click="kk()" x="185" label="提交"></mx:Button>
</mx:Application>
接收页面代码(page.html):
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="init()" >
 <mx:Script>
  <![CDATA[
   import mx.managers.IBrowserManager;
   import mx.managers.BrowserManager;
   import mx.utils.URLUtil;
   [Bindable]
   var param:String;
   function init():void
   {
    var bm:IBrowserManager = BrowserManager.getInstance(); 
    bm.init();
    var o:Object = URLUtil.stringToObject(bm.fragment,"&");
    param = o.param1;
   }
  ]]>
 </mx:Script>
 <mx:TextInput id="val" text="{param}">
 </mx:TextInput>
</mx:Application>
二、 利用SharedObject(本地共享对象传送)
a) 该对象类似于Cookie,将需要传送的数据放在SharedObject对象中,而实际上在本机大致在(win2k和 win xp中,默认路径为C:/Documents and Settings/username/Application Data/Macromedia/Flash Player/#SharedObjects (username为机器的用户名))位置生成一个sol文件,该对象具有一个data属性,只要将你要传的数据按键值对放进去就好了,下次读取的时候就在本地直接读取即可
b) 遗憾的是,该对象要求你自己创建还要自己清除,并且在写入数据时一定要强制刷新,否则数据无法希尔
发送页面代码(index.html):
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute">
 <mx:Script>
  <![CDATA[
   function s mit():void
   {
    var param:String = myparam.text;
    //创建全局SharedObject,如果不用全局就去掉后面的"/",一旦去掉那么cookie只能被自己的Application使用,其他Applicaiton无法看见
    //myparam是要求在本机创建一个叫cookie.sol的文件
    var obj:SharedObject = SharedObject.getLocal("cookie","/");
    obj.data.username=myparam.text;
    obj.flush();
    //调用URLReqst将跳转到second.html页面
    var reqst:URLReqst =new URLReqst();
    reqst.url="second.html";
    navigateToURL(reqst);
   }
  ]]>
 </mx:Script>
 <mx:TextInput id="myparam"></mx:TextInput>
 <mx:Button label="提交" click="s mit()" x="177"></mx:Button>
</mx:Application>
接收页面代码(second.html):
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="init()">
 <mx:Script>
  <![CDATA[
   [Bindable]
   var param:String;
   function init():void
   {
    //在本地找到myparam.sol文件
    var obj:SharedObject =SharedObject.getLocal("cookie","/");
    //读取前页存入的数据
    param = obj.data.username;
    //用完了别忘了将myparam.sol文件删除
    obj.clear();
   }
  ]]>
 </mx:Script>
 <mx:TextInput id="mypar" text="{param}"></mx:TextInput>
</mx:Application>


posted @ 2011-10-21 16:32 ivaneeo 阅读(514) | 评论 (0)编辑 收藏

参数输入进程号...
#!/bin/bash

    if [ -z $1 ]
    then
        echo "Need a pid argument"
        exit 1
    fi

    if [ -d /proc/$1 ];then
        exit 0
    else
        exit 1
    fi

posted @ 2011-10-20 16:06 ivaneeo 阅读(360) | 评论 (0)编辑 收藏

nc -vv -w 2 -z vm-node10 22
ID=$?
echo $ID

1为失败、0为成功
posted @ 2011-10-20 16:04 ivaneeo 阅读(277) | 评论 (0)编辑 收藏

首先把自己的脚本放到/etc/init.d中,,然后执行如下指令:

update-rc.d a start 90 2 3 4 5 . stop 90 0 1 6 .

其中a就是你的脚本,注意有两个点。

a脚本范例。

 

#!/bin/sh


# Source function library.
if [ -f /etc/init.d/functions ]; then
    . /etc/init.d/functions
else
    . /lib/lsb/init-functions
fi

MOD=/a.ko

start() 
{
        echo -n $"insert a kernel module: "
    /sbin/insmod $MOD
        echo
}

stop() 
{
        echo -n $"remove a kernel module: "
        /sbin/rmmod a -f
        echo
}

[ -f $MOD ] || exit 0

# See how we were called.
case "$1" in
  start)
    start
        ;;
  stop)
    stop
        ;;
  restart|reload)
    stop
    start
    ;;
  *)
     echo $"Usage: $0 {start|stop|restart|reload}"

 

 

update-rc.d命令,是用来自动的升级System V类型初始化脚本,简单的讲就是,哪些东西是你想要系统在引导初始化的时候运行的,哪些是希望在关机或重启时停止的,可以用它来帮你设置。这些脚本的连接 位于/etc/rcn.d/LnName,对应脚本位于/etc/init.d/Script-name.

1、设置指定启动顺序、指定运行级别的启动项:
update-rc.d <service> start <order> <runlevels>
2、设置在指定运行级中,按指定顺序停止:
update-rc.d <service> stop <order> <runlevels>
3、从所有的运行级别中删除指定的启动项:
update-rc.d -f <script-name> remove

例如:
update-rc.d script-name start 90 1 2 3 4 5 . stop 52 0 6 .
start 90 1 2 3 4 5 . : 表示在1、2、3、4、5这五个运行级别中,按先后顺序,由小到大,第90个开始运行这个脚本。
stop 52 0 6 . :表示在0、6这两个运行级别中,按照先后顺序,由小到大,第52个停止这个脚本的运行。

 

 

如果在 /etc/init.d 中加入一个 script,还须要制作相关的 link
在 /etc/rc*.d 中。K 开头是 kill , S 开头是 start , 数字顺序代表启动的顺序。(SysV)

update-rc.d 可以帮你的忙。

例:

在 /etc/init.d 中建立一个叫作 zope 的 script , 然后

update-rc.d zope defaults

就会产生以下链結::

Adding system startup for /etc/init.d/zope ...
/etc/rc0.d/K20zope -> ../init.d/zope
/etc/rc1.d/K20zope -> ../init.d/zope
/etc/rc6.d/K20zope -> ../init.d/zope
/etc/rc2.d/S20zope -> ../init.d/zope
/etc/rc3.d/S20zope -> ../init.d/zope
/etc/rc4.d/S20zope -> ../init.d/zope
/etc/rc5.d/S20zope -> ../init.d/zope

其他进阶使用方式请 man update-rc.d

posted @ 2011-10-20 14:56 ivaneeo 阅读(1449) | 评论 (0)编辑 收藏

Linux
一旦内核加载完成,内核会启动 init 进程,然后运行 rc6 脚本,之后运行所有属于其运行级别的命令脚本。这
些脚本都储存在 /etc/rc.d/rcN.d 中(N代表运行级别),并且都建立着到 /etc/init.d 子目录中命令脚本程序
的符号链接。
默认运行级别配置在 /etc/inittab 中。它通常为 3 或 5:

 # grep default: /etc/inittab
 id:3:initdefault:

可以使用 init 来改变当前运行级别。举个例子:

 # init 5                       # 进入运行级别 5

运行级别列表如下:
0 系统停止
1 进入单用户模式(也可以是 S)
2 没有 NFS 特性的多用户模式
3 完全多用户模式(正常操作模式)
4 未使用
5 类似于级别3,但提供 XWindow 系统登录环境
6 重新启动系统
使用 chkconfig 工具控制程序在一个运行级别启动和停止。

 # chkconfig --list             # 列出所有 init 脚本
 # chkconfig --list sshd        # 查看 sshd 在各个运行级别中的启动配置
 # chkconfig sshd --level 35 on # 对 sshd 在级别 3 和 5 下创建启动项
 # chkconfig sshd off           # 在所有的运行级别下禁用 sshd

Debian 和基于Debian 发行版像 Ubuntu 或 Knoppix 使用命令 update-rc.d 来管理运行级别脚本。默认启动为
2,3,4 和 5,停止为 0,1 和 6。

 # update-rc.d  sshd defaults          # 设置 sshd 为默认启动级别
 # update-rc.d  sshd start 20 2 3 4 5 . stop 20 0 1 6 . # 用显示参数
 # update-rc.d  -f sshd remove         # 在所有的运行级别下禁用 sshd
 # shutdown -h  now (或者 # poweroff)    # 关闭停止系统

FreeBSD
BSD 启动步骤不同于 SysV, 她没有运行级别。她的启动状态(单用户,有或没有 XWindow)被配置在 /etc/
ttys中。所有的系统脚本都位于 /etc/rc.d/中,第三方应用程序位于 /usr/local/etc/rc.d/中。service 的启
动顺序被配置在 /etc/rc.conf 和/etc/rc.conf.local中。默认行为可在 /etc/defaults/rc.conf 中进行配
置。 这些脚本至少响应 start|stop|status.

 # /etc/rc.d/sshd status
 sshd is running as pid 552.
 # shutdown now                        # 进入单用户模式
 # exit                                # 返回到多用户模式
 # shutdown -p now                     # 关闭停止系统
 # shutdown -r now                     # 重新启动系统

同样可以使用进程 init 进入下列状态级别。举个例子: # init 6 为重启。
0 停止系统并关闭电源 (信号 USR2)
1 进入单用户模式 (信号 TERM)
6 重新启动 (信号 INT)
c 阻止进一步登录 (信号 TSTP)
q 重新检查 ttys(5) 文件 (信号 HUP)

在FreeBSD下,查看系统的内核安全级别可以用命令:

sysctl -a |grep securelevel

 

posted @ 2011-10-20 14:51 ivaneeo 阅读(298) | 评论 (0)编辑 收藏

用ssh登录一个机器(换过ip地址),提示输入yes后,屏幕不断出现y,只有按ctrl + c结束

 

错误是:The authenticity of host 192.168.0.xxx can't be established.

 

以前和同事碰到过这个问题,解决了,没有记录,这次又碰到了不知道怎么处理,还好有QQ聊天记录,查找到一下,找到解决方案:

 

执行ssh  -o StrictHostKeyChecking=no  192.168.0.xxx 就OK

posted @ 2011-10-10 18:30 ivaneeo 阅读(1366) | 评论 (0)编辑 收藏

先说flash as3吧,可以用root.loaderInfo.parameters

AS3类 GSPManager.as 代码:   

package
{
    import flash.display.Sprite;
    import flash.events.Event;
    import flash.text.TextField;    
    public class GSPManager extends Sprite
    {
        public 
function GSPManager()
        {
            
this.addEventListener(Event.ADDED_TO_STAGE,addedToStageHandler);
        }
        
        private 
function addedToStageHandler(e:Event):void
        {
            
this.removeEventListener(Event.ADDED_TO_STAGE,addedToStageHandler);
            
            init();
        }
        private 
function init():void
        {            
            
var out_txt:TextField = new TextField();
            
//边框
            out_txt.border = true;
            
//边框颜色
            out_txt.borderColor = 0x80FF3300;
            
//大小
            out_txt.width = 100;
            out_txt.height 
= 20;
            
//位置
            out_txt.x = (stage.stageWidth - out_txt.width)/2;
            out_txt.y = (stage.stageHeight - out_txt.height)/2;
            //添加到舞台
            addChild(out_txt);
            
            
//获得参数对象
            var param:Object = root.loaderInfo.parameters;
              
if (param["name"]!=null
            {
                      out_txt.text 
= param["name"+ param["num"];
                      trace(
"value:"+param["name"]);
                              
//判断
              } 
            
else 
            {
                    out_txt.text 
= "null";
                    trace(
"value:null");
              }
        }        
    }
}

GetSwfParam.fla 绑定的文档类为GSPManager.as ,在文档类绑定框里写GSPManager这个就可以了

之后编译出来的GetSwfParam.swf 就可以添加到页面了

Java web页面代码:  

<%@ page language="java" import="java.util.*" contentType="text/html;charset=GBK"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  
<head>
  
</head>
  
  
<body>
    
<object id="g" classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" codebase="http://download.macromedia.com/pub/shockwave/_cabs/flash/swflash.cab#version=6,0,29,0" width="300" height="200">
      
<param name="movie" value="GetSwfParam.swf?name=sange&num=66" />
    <param name="quality" value="high" />
    <param name="allowScriptAccess" value="sameDomain" />    
    <param name="scale" value="exactfit" />
    <embed name="g" src="GetSwfParam.swf" quality="high" scale="exactfit" align="middle" play="true" loop="false" pluginspage="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" width="300" height="200" ></embed>
  </object>
  </body>
</html>

 

 这里要说的是swf后有很多参数就用&符号 , 比如GetSwfParam.swf?name=sange&num=66&id=1

 

现在说Flex了,因为让同事也做了这样的东西,但他只会Flex,他没弄出来,所以我试下,发现用root没反映,但我很肯定Flex应该也可以弄出来,发现跟flash as3确实不同,不能用root,因为Flex中没有root这个概念。问了群里的人,收获大了,原来就Application,哈哈,不就是根节点么,也就相当于root,就是名称不一样。

Flex就用Application.application.parameters

GetSwfParam.mxml 代码: 

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" backgroundColor="#ffffff" layout="absolute" creationComplete="init()">
    
<mx:Script>
        
<![CDATA[
            private 
function init():void
            {
                
//获得参数对象                
                var param:Object = Application.application.parameters;
                
if(param["name"!= null)
                {
                    mytxt.text 
= param["name"];
                }
                
else
                {
                    mytxt.text 
= "null";
                }
            }
        ]]
>
    
</mx:Script>
    <mx:TextInput id="mytxt" x="60" y="47"/>
</mx:Application>

 

把编译好的swf添加到页面就可以了。同上,Java web页面代码不变。

posted @ 2011-09-27 14:53 ivaneeo 阅读(334) | 评论 (0)编辑 收藏

Flex页面跳转的五种实现方式

2010-08-13 13:25 Dboyqiao javaeye.com 我要评论() 字号:T | T
一键收藏,随时查看,分享好友!

Flex页面跳转有很多值得学习的地方,本文向大家介绍一下Flex页面跳转的几种方式,主要包括五种方式,这里为大家一一介绍。

AD:

在学习Flex的过程中,你可能会遇到Flex页面跳转的概念,这里和大家分享一下Flex中实现Flex页面跳转以下几种方式,相信本文介绍一定会让你有所收获。

Flex页面跳转

Flex中实现Flex页面跳转以下几种方式:

Flex页面跳转方式一:使用ViewStack组件,把要跳转的页新建成MXMLComponent,然后通过ViewStack组件把这些页包含进来,然后再通过改变ViewStack的selectedItem或者selectedChild来切换这些页。

  1. <mx:ViewStackidmx:ViewStackid="storeViews"width="100%"height="550" 
  2. creationPolicy="all"> 
  3. <shouyeidshouyeid="homeView"label="首页"showEffect="WipeDown"hideEffect="WipeUp"/> 
  4. <leixingidleixingid="pView"label="模板类型"showEffect="WipeDown"hideEffect="WipeUp"/> 
  5. <makeidmakeid="supportView"label="立即制作"showEffect="WipeDown"hideEffect="WipeUp"/> 
  6. </mx:ViewStack> 
  7. <mx:Buttonclickmx:Buttonclick="storeViews.selectedChild=homeView;"/> 
  8.  

Flex页面跳转方式二:使用navigateToURL,主要方式如下:

  1. varurl:String="http://localhost:8080/Flex_Java_Demo/  
  2. welcome.html";  
  3. varrequest:URLRequest=newURLRequest(url);  
  4. navigateToURL(request,"_blank");  
  5.  

这个方法实现Flex页面切换时会弹出新的页面,而不是只变换url

Flex页面跳转方式三:引用flash中的importflash.external.ExternalInterface这个接口,它能提供像jsp中window.location.href方法一样方便,主要代码为:
 

  1. ExternalInterface.call("function(){window.location.  
  2. href='http://localhost:8080/Flex_J2eeDemo  
  3. /bin/Welcome.html';}");  

Flex页面跳转方式四:使用组件技术,把不同的页面做成component,然后通过TabNavigator等进行切换,通过使用state实现跳转。

Flex页面跳转方式五:把不同的页面做成Module,然后使用ModuleLoder来进行加载切换。

【编辑推荐】

  1. 实现Flex页面跳转行之有效的办法
  2. 四种方式实现Flex页面跳转
  3. 全面认识Flex应用程序的六大元素
  4. 揭开Flex正则表达式的神秘面纱
  5. Flex数据绑定及其使用频繁的几种情况 


 

【责任编辑:程华权 TEL:(010)68476606】

网友评论TOP5

查看所有评论(

提交评论
通行证: 密码:   注册通行证


验证码: 请点击后输入验证码 匿名发表

posted @ 2011-09-27 14:47 ivaneeo 阅读(1490) | 评论 (0)编辑 收藏

flash builder 4.5注册方法
2011-06-30 12:53

先在C:\Windows\System32\drivers\etc的hosts文件中添加以下内容,(用记事本打开就行):

127.0.0.1 activate.adobe.com
127.0.0.1 practivate.adobe.com
127.0.0.1 ereg.adobe.com
127.0.0.1 activate.wip3.adobe.com
127.0.0.1 wip3.adobe.com
127.0.0.1 3dns-3.adobe.com
127.0.0.1 3dns-2.adobe.com
127.0.0.1 adobe-dns.adobe.com
127.0.0.1 adobe-dns-2.adobe.com
127.0.0.1 adobe-dns-3.adobe.com
127.0.0.1 ereg.wip3.adobe.com
127.0.0.1 activate-sea.adobe.com
127.0.0.1 wwis-dubc1-vip60.adobe.com
127.0.0.1 activate-sjc0.ado


这是注册:
1424-4938-3077-5736-3940-5640
1424-4827-8874-7387-0243-7331

posted @ 2011-09-26 17:28 ivaneeo 阅读(485) | 评论 (0)编辑 收藏

Flash Builder 4.5高级版试用版免费高速下载

Company: Adobe

vcr.cover

官方下载地址:http://trials3.adobe.com/AdobeProducts/FLBR/4_5/win32/FlashBuilder_4_5_LS10.exe

1424-4827-8874-7387-0243-7331
1424-4938-3077-5736-3940-5640
 

FB4.5 序列号 Flex4.5   5月17日发布,本人的用第一个已经激活成功,大家看看还能用不。

Adobe Flash Builder 4.5 软件(曾为 Adobe Flex Builder)是基于 Eclipse的开发工具,使用 ActionScript 和开源 Flex 框架快速构建具有表现力的移动、Web 和桌面应用程序。

最具表现力的体验

创建更直观和更具吸引力的 Web 应用程序,帮助人们理解并使用数据以支持重要的业务活动,从而提高生产力和工作效率。

用于 Android、iOS 和 RIM 的移动应程序

受益于对移动应用程序开发和测试的新支持,可以使用通用代码库构建用于 Android、Apple iOS和 Blackberry Tablet OS的应用程序,同时共享 Web 应用程序的代码。

更具生产力,功能更强大

使用广泛新工具功能和改进的工具功能加速 Flex 和 ActionScript 项目的代码编写和测试过程。

新集成的 PHP 工具支持

使用 Flash Builder 4.5 for PHP 中的 Zend Studio 8 软件完整副本,获得最佳的 Flex/PHP 开发体验。

Adobe官方下载(本地服务器)

Adobe官方下载(国外服务器)

本文件大小为581.2M,Adobe独家提供本地高速下载,您可以通过浏览器直接点击下载或者通过下载加速器(如迅雷、QQ旋风)下载,实际的下载速度和您的实际网络环境相关。考虑到文件较大,我们推荐您使用具有断点续传功能的下载加速器辅助下载。

官方下载地址:http://trials3.adobe.com/AdobeProducts/FLBR/4_5/win32/FlashBuilder_4_5_LS10.exe

1424-4827-8874-7387-0243-7331
1424-4938-3077-5736-3940-5640
 

FB4.5 序列号 Flex4.5   5月17日发布,本人的用第一个已经激活成功,大家看看还能用不。

posted @ 2011-09-26 16:58 ivaneeo 阅读(1142) | 评论 (1)编辑 收藏

引言

Apache Axis2(主要的开源 Web 服务平台之一)提供了一系列新功能,最为可贵的是,其中的很多功能都对向开发人员提供更为用户友好的方法起到了促进作用。在之前的 Axis 版本中,并不十分重视用户友好性。例如,在 Axis1 中,用户必须手动调用管理客户机并更新服务器类路径,然后重新启动服务器以应用更改。这个有点麻烦的部署模型对新手肯定是一道障碍。因此,Axis2 经过了精心的设计,能够克服此缺点,并提供更为灵活、可方便进行配置的部署模型。

Axis2 部署新功能

Axis2 部署模型将一系列新功能引入了 Apache Web 服务堆栈中(其中一些功能对于 Web 服务范式并非新事物)。以下列出了最为重要的主要更改和新功能:

  • 类似于 Java™ 2 Platform Enterprise Edition (J2EE) 的部署机制(基于存档)
  • 热部署和热更新
  • 存储库(可以在其中放置服务和模块)
  • 处理程序(模块)部署的更改
  • 新部署描述符
  • 多个部署选项

在下面的内容中,我们将逐个对每个方面进行详细讨论。

回页首

类似于 J2EE 的部署机制

在任何 J2EE 应用服务器中,都可以将应用程序作为自包含包部署,可以将所有的资源、配置文件和二进制文件打包为一个文件并进行部署。这显然非常实用,而也正是因为如此,Axis2 也引入了相同的机制来更方便地部署服务(和模块)。

考虑这样的情况,假如您有一个存在多个第三方依赖关系和一组属性文件的服务,同时假定没有类似于 J2EE 的部署机制。必须手动将所有这些依赖 JAR 文件和属性文件放入类路径中。如果有一个或两个服务器,这项工作的量将翻倍!在存在数百副本的集群环境中,将依赖 JAR 文件和其他资源添加到类路径中的做法并不实际。有了类似于 J2EE 的部署机制后,就没有这些问题了,只需要将服务放入副本中,而不需要进行任何其他工作了。

Axis2 自包含包(或存档文件)的内部结构如图 1 中所示。两种 Axis2 服务(存档和模块存档)非常相似。二者之间的细微差别包括:

  • 对于 Axis 服务,描述符文件是 services.xml;而对于 Axis 模块,描述符文件是 module.xml。
  • Axis2 服务的文件扩展名是 .aar(服务的文件名将为 foo.aar),模块的文件扩展名为 .mar(模块的文件名将为 foo.mar)。

图 1. 存档文件的结构
存档文件的结构 

回页首

热部署和热更新

对于企业级应用程序,可用性是一个大问题。即使短时间的停机都可能带来很大损失,因此重新启动服务器并不是一个较好的做法。需要在不用关闭系统的情况下对其进行更新。而这就是热部署和热更新的用武之地。热部署和热更新是 Apache Web 服务堆栈(如 Axis 和 Axis2)中的新功能。这两个新功能如下所述:

  • 热部署是指在系统启动并运行的情况下部署新服务的能力。例如,假定您有两个服务——service1 和 service2——已启动并运行,现在要在不用关闭系统的情况下部署名为 service3 的新服务。部署 service3 就是一个热部署场景。作为系统管理员,如果不喜欢服务的热部署,则可以通过更改名为 axis2.xml 的 Axis2 全局配置文件,将全局配置参数更改为以下所示,从而关闭此功能:<parameter name="hotdeployment">false</parameter>
  • 热更新是指在不关闭系统的情况下更改现有 Web 服务的能力。这是一个重要的特性,是测试环境中需要的一个功能。不过,在实时系统中使用热更新并不明智,因为这可能导致系统进入未知状态。此外,还可能会丢失该服务的现有服务数据。为了防止出现这种情况,Axis2 缺省将热更新参数设置为 FALSE。如果希望使用此功能,请按照以下所示更改配置参数,从而启用此功能:<parameter name="hotupdate">true</parameter>

回页首

存储库

Axis2 存储库实际上就是文件系统中具有特定结构的目录。它可以位于本地,也可以位于远程计算机上。之所以引入存储库概念,目的是为了方便地支持基于存档的热部署功能。

存储库目录包含两个主要子目录,分别名为 services 和 modules。还可能有一个可选的子目录,名为 lib。如果希望部署服务,需要将服务存档文件放入 services 目录中。类似地,如果希望部署模块,请将模块存档文件放入 modules 目录。对于 lib 目录,要将其作为放置对服务和模块公用的第三方库的位置。图 2 显示了存储库的图形表示形式。


图 2. Axis2 存储库
Axis2 存储库 

注意:如果 modules 目录中的部分或全部模块希望共享某些资源,可以将这些资源添加到 modules 目录中的 lib 目录内。类似地,如果 services 目录中的全部或部分服务希望共享公共资源,恰当的位置是在 services 目录内的 lib 目录。

回页首

处理程序(模块)部署的更改

服务扩展(或模块)的概念是 Apache Axis 范式的一个新功能。其基本思想是对系统的核心功能进行扩展或提供服务质量保证。对于 Axis1,如果希望扩展其核心功能,则需要编写处理程序(执行链中的最小单位),更改全局配置文件添加该处理程序,最后要重新启动系统。

模块进行相同的工作,但会减少所需进行的工作量。同时,模块可以通过使用模块描述文件 modul.xml 来包含一个或多个处理程序。大多数情况下,模块是特定 WS 规范的实现,例如 Axis2 addressing 模块就是 WS-Addressing 的实现。

如前面提到的,可以将模块作为存档文件部署。模块存档文件的结构如图 3 中所示。


图 3. 模块存档文件的结构 
模块存档文件的结构  

回页首

新部署描述符

Axis2 的灵活性和可扩展性的重点是其部署描述符。将不再仅处理一个配置文件,而是针对不同的配置级别有不同的配置文件。例如,如果希望向系统添加处理程序,则没有必要更改全局配置;可以通过仅更改模块配置文件来完成此工作。Axis2 中有三种类型的描述符或配置文件:

  • 全局描述符 (axis2.xml)
  • 服务描述符 (services.xml)
  • 模块描述符 (module.xml)

在全局描述符中,所有系统级的配置都在 axis2.xml 中给出,包括以下内容:

  • 参数
  • 传输发送方
  • 传输侦听器
  • 阶段
  • 全局模块

Axis2 提供了缺省 axis2.xml。其中包含启动 Axis2 所需的最小配置,但可以自由对其进行更改,从而使用您自己的 axis2.xml 启动 Axis2。务必注意,如果对 axis2.xml 进行了任何更改,则必须重新启动系统,以使这些更改生效。

在服务描述符中,由 services.xml 给出关于服务的配置。为了使服务有效,需要在服务存档文件中包含 services.xml 文件。服务配置文件包含以下内容:

  • 服务级别的参数
  • 服务的描述
  • 消息接收方
  • 需要作为 Web 操作(服务中的操作)公开的操作
  • 服务级别的模块

模块描述符文件 (module.xml) 包含将模块插入到系统中所需的配置数据。主要配置包括以下方面:

  • 处理程序及其阶段规则
  • 模块参数

务必注意,module.xml 还可能包含以下元素:

  • 关于模块的描述(及其实现的规范)
  • 端点(对于可靠消息传递的情况,就是类似于 create sequence 的端点)

回页首

Axis2 中可用的部署方法

在 Axis2 中,可采用三种主要方式部署服务:

  • 将服务存档文件放入存储库中。
  • 使用存档文件以编程方式创建服务。
  • 将服务作为传统 Java 对象(Plain Old Java Object,POJO)部署。

在 Axis2 中,部署服务的最常用方法是直接将服务存档文件复制或放置到存储库中(services 目录)。如果使用基于 Axis2 WAR 文件的分发版本,则有两个选择:

  • 手动将存档文件放置到存储库中。
  • 使用 Web 控制台上载服务。

以编程方式部署并非用户需求,而是模块创建者的需求,因为某些模块要求 Web 服务的部署提供模块的全部功能。若要以编程方式创建服务,需要使用 services.xml、类加载器(可用于加载您的类文件)和 AxisConfiguration。此方法的优势在于,您并不需要将服务存档文件复制到存储库中,而且仅在运行时服务才可见。清单 1 可帮助您形成对编程服务部署方法的基本认识。


清单 1. 编程服务部署
                AxisConfiguration axisConfig;  // you need to have reference to AxisConfiguration  File file = new File("Location of the file""); ClassLoader clsLoader = new URLClassLoader(new URL[]{file.toURL()}); InputStream in = new FileInputStream("location of service.xml"); AxisService service = DeploymentEngine.buildService(in, clsLoader, axisConfig); 

使用 Java 类部署服务是 Axis2 中提供的一项使用非常方便的功能,在这种情况下没有必要生成服务存档文件或 services.xml。唯一的要求是,必须在创建服务前将 Java 类放入类路径中。在运行时,可以由模块或服务创建新服务并进行部署。在 Axis2 中部署 POJO 仅需要三行代码,如清单 2 中所示。


清单 2. 在 Axis2 中部署 POJO
                AxisService service = AxisService.createService(  MyService.class.getName(), axisConfig, RPCMessageReceiver.class); axisConfig.addService(service); 

回页首

总结

Axis2 在这里并不是证明 Web 服务概念,而是提供更好的 SOAP 处理模型,且相对于 Axis1 及其他现有 Web 服务引擎而言,此模型在速度和内存方面性能有了很大的改善。此外,它还提供了方便的部署机制。现在已经进入 Axis2 的时代了!

posted @ 2011-08-24 16:27 ivaneeo 阅读(310) | 评论 (0)编辑 收藏

一、环境安装(tomcat,本人5.5): 
首先下载到官方网站下载axis2 war包。 
将war包复制到webapps目录下边,启动tomcat,服务器加载了war包后会生成axis2目录,跟我们平时的应用目录没神马区别,唯一要注意的是axis的配置文件在WEB-INFconf, 
在开发过程中要修改一下这个的配置文件。 

二、(改造配置文件): 
配置axis2的文件,axis2支持热部署,意味着你可以再编译好的class文件,直接复制到pojo目录下(默认是pojo,等会有说明修改)。 
在配置文件中找到<parameter name="hotdeployment">true</parameter>默认已经为热部署; 
另外一个在开发过程中你常需要把热更新打开,默认是false 不打开,找到hotupdate 
<parameter name="hotupdate">true</parameter> 
发布pojo的目录只是默认的,如果需要使用其他的目录,需要添加配置元素,在axisconfig下面添加 
<deployer extension=".class" directory="mymulu" class="org.apache.axis2.deployment.POJODeployer"/> 
上面的配置文件只需要修改 directory的属性,改为目录名 

二、(使用POJO方式发布webservice): 
在pojo目录(此目录没有,在axis2WEB-INF下面创建,其实细心的同学会发现,在配置文件axis就已经给我们定义了pojo目录,看前面添加发布pojo目录)下面的webservice可以通过重写url去访问(后面带一些参数,类似action),如果遇到数据类型则需要做转换,原因传输过程是以字符串形式传输,而且重写URL的参数名必须要与方法的参数名相同。感觉比较土的方法 

好吧说了那么多,现在让我们来个helloworld吧~!! 
首先我们先发布一个webservice, 
编写一个MyTest类

public class MyTest { 	 	public String getString(String str){ 		System.out.println("调用了getString()传入参数"+str); 		return str; 	} 	public void doNoThing(String str){ 		System.out.println("调用了doNothing()传入参数:"+str); 	}  } 


1.启动你的tomcat,访问这个url:http://127.0.0.1:8080/axis2/ (确保axis2是正常运行了), 
2.神马,没改配置文件,好吧,就在%tomcat_home%webappsaxis2WEB-INF下面建立一个pojo文件夹。编写好的类编译成class文件后,直接复制到你所指定的目录下。 
3.最后访问你的服务吧http://127.0.0.1:8080/axis2/services/MyTest?wsdl 


现在开始客户端开发,这里省略了使用axis的API开发客户端,个人觉得这样的开发效率好低吖,新手上手(本人懒的去看那个API),应该快速掌握怎么使用,所以这里介绍stub方式,使用了axis自带的命令,可以根据wsdl生成客户端,在%AXIS2_HOME%in目录下有一个wsdl2java脚本(注意是wsdl to java)。 
前提准备 
下载了axis2 bin 文件,配置环境变量 例如: 
变量名:AXIS2_HOME  
值:E:studywebserviceaxis2-1.5.4-binaxis2-1.5.4 

这里要用到前面的发布的webservice,保持你的服务器是启动的,你的服务正常。 
打开CMD 
输入下面的命令 
%AXIS2_HOME%/bin/wsdl2java -uri http://localhost:8080/axis2/services/MyTest?wsdl -p com.lj.mywebservice  -s -o c:/mywebservice 

这里说一下参数, -uri 当然是服务的wsdl文件地址,-p 报名 , -o 表示目录,这里写的是绝对路径,也可以写相对路径 

回车,你会发现在C盘下多了一个文件目录,打开里边一层层进去后,有一个MyTestStub类,这个类实现非常复杂,不用管他,拿过来直接用。 
新建一个工程,写个测试类,把刚才生成的类复制进去,当然别忘记了引入axis的jar包。

package com.lj.myswebservice;  import java.rmi.RemoteException;  import org.apache.axis2.AxisFault;  public class TestClass { 	public static void main(String[] args) { 		 		try { 			MyTestStub my=new MyTestStub(); 			//在MYTestStub里边定义了三个静态嵌套类,分别作为参数对象,返回值对象。 			//这里定义了donothing方法的参数对象 			MyTestStub.DoNoThing donothing=new MyTestStub.DoNoThing(); 			//这里定义了getstring方法的参数对象 			MyTestStub.GetString getstring=new MyTestStub.GetString(); 			////这里定义了getString方法的返回值对象 			MyTestStub.GetStringResponse getstringresponse=new MyTestStub.GetStringResponse(); 			//设置参数值 			donothing.setArgs0("神马也不做啊"); 			//设置参数值 			getstring.setArgs0("我是帅锅"); 			//调用donothing方法 			my.doNoThing(donothing); 			//调用getString发放,设置参数,并返回值 			getstringresponse=my.getString(getstring); 			//打印返回值 			System.out.println(getstringresponse.get_return()); 		} catch (AxisFault e) { 			// TODO Auto-generated catch block 			e.printStackTrace(); 		} catch (RemoteException e) { 			// TODO Auto-generated catch block 			e.printStackTrace(); 		} 		 	} }  


运行结果如下。 
<!--StartFragment -->

 
服务器结果如下。 
<!--StartFragment -->



总结,使用axis2构建服务是非常快的,这个例子使用的是deploy pojo的方式发布服务,所谓pojo就是个普通的JAVA类,与javabean区别就是不一定有get set方法(是不是这样理解?)。在客户端调用服务的时候,采取stub方式(貌似现在很流行,这样编写客户端是灰常直观的),只要拿到wsdl文件,就可以使用 wsdl2java命令生成客户端,大大减少了开发量。

还差得远( ⊙ o ⊙ )啊!··明晚再看看别的方式发布鸟··

晚了睡觉了··明天早起上班( ⊙ o ⊙ )啊!···

posted @ 2011-08-24 11:08 ivaneeo 阅读(683) | 评论 (0)编辑 收藏

www.s135.com 和 blog.s135.com 域名均指向 Nginx 所在的服务器IP。

  用户访问http://www.s135.com,将其负载均衡到192.168.1.2:80、192.168.1.3:80、192.168.1.4:80、192.168.1.5:80四台服务器。

  用户访问http://blog.s135.com,将其负载均衡到192.168.1.7服务器的8080、8081、8082端口。

  以下为配置文件nginx.conf:

引用
user  www www;

worker_processes 10;

#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

#pid        logs/nginx.pid;

#最大文件描述符
worker_rlimit_nofile 51200;

events
{
      use epoll;

      worker_connections 51200;
}

http
{
      include       conf/mime.types;
      default_type  application/octet-stream;

      keepalive_timeout 120;

      tcp_nodelay on;

      upstream  www.s135.com  {
              server   192.168.1.2:80;
              server   192.168.1.3:80;
              server   192.168.1.4:80;
              server   192.168.1.5:80;
      }

      upstream  blog.s135.com  {
              server   192.168.1.7:8080;
              server   192.168.1.7:8081;
              server   192.168.1.7:8082;
      }

      server
      {
              listen  80;
              server_name  www.s135.com;

              location / {
                       proxy_pass        http://www.s135.com;
                       proxy_set_header   Host             $host;
                       proxy_set_header   X-Real-IP        $remote_addr;
                       proxy_set_header   X-Forwarded-For  $proxy_add_x_forwarded_for;
              }

              log_format  www_s135_com  '$remote_addr - $remote_user [$time_local] $request '
                                '"$status" $body_bytes_sent "$http_referer" '
                                '"$http_user_agent" "$http_x_forwarded_for"';
              access_log  /data1/logs/www.log  www_s135_com;
      }

      server
      {
              listen  80;
              server_name  blog.s135.com;

              location / {
                       proxy_pass        http://blog.s135.com;
                       proxy_set_header   Host             $host;
                       proxy_set_header   X-Real-IP        $remote_addr;
                       proxy_set_header   X-Forwarded-For  $proxy_add_x_forwarded_for;
              }

              log_format  blog_s135_com  '$remote_addr - $remote_user [$time_local] $request '
                                '"$status" $body_bytes_sent "$http_referer" '
                                '"$http_user_agent" "$http_x_forwarded_for"';
              access_log  /data1/logs/blog.log  blog_s135_com;
      }
}

  附:Nginx 的安装方法可参照《Nginx 0.5.31 + PHP 5.2.4(FastCGI)搭建可承受3万以上并发连接数,胜过Apache 10倍的Web服务器》文章的以下段落(仅做负载均衡,无需支持PHP的安装方法):

  二、安装PHP 5.2.4(FastCGI模式)
  4、创建www用户和组,以及其使用的目录:

  三、安装Nginx 0.5.31
  1、安装Nginx所需的pcre库:
  2、安装Nginx
  3、创建Nginx日志目录
  5、启动Nginx
posted @ 2011-08-16 11:55 ivaneeo 阅读(277) | 评论 (0)编辑 收藏

vc2008确实好使,不过缺陷也非常明显,只要是它编译的东西,在其他电脑经常会出现无法顺利运行的情况,最常见的错误就是:“由于应用程序配置不正确,应用程序未能启动。重新安装应用程序可能会纠正这个问题。”

经过各种努力,最后发现,一般情况下只需要安装一下vcredist_x86.exe这个vc的可重发行组件包就可以了。其主要原理是因为vc2008的版本比较高,其编译时链接的相关dll版本比xp下的高太多,而我们在xp下运行的时候调用的是老版本的dll,所以出现了问题。安装新版的可重发行组件包后,旧版本的dll被替换成新版本的,问题就解决了。

可是又出现了新的问题,总不能让用户使用我们软件的时候,非要去安装其他组件吧~~而且,其他很多软件都是用vc开发的,这些软件为什么不需要呢?本着钻牛角尖的态度,进行了更深一步的探索;

最近研究ccv,突然发现ccv的bin目录下有一个Microsoft.VC90.CRT目录,下面有几个dll文件,还有一个manifast文件。看到这个不禁眼前一亮,在我的程序中把这几个文件打包进去就ok了吧?于是进行尝试,查找本机安装vs2008目录下的Microsoft.VC90.CRT目录一顿cp,结果,很沮丧,测试失败~~告一段落~~

某天又在网上发现有人在帖子里的回答,其中两个字吸引了我:“版本”。我灵机一动,赶紧去查看版本,发现我当前的版本是9.0.30729.4148,而帖子里的manifast文件中的版本是9.0.21022.8。于是,我赶紧找了一个这个版本的下载下来,替换我的程序中的这几个dll和manifast,再运行,果然成功了。

 

因此得到以下结论:

1、可重发行组件包是没问题的,肯定可以用,因为它替换了系统的这几个dll,所以可行;

2、如果不想在自己的“绿色”软件的基础上再要安装这么个组件,或者自己的非绿色软件在安装的过程中再安装这么个组件,只需要处理这几个关键的dll就行啦。

3、即使有了这几个dll也不一定行,一定要注意版本!实在不行这几个版本多试一试。我到现在还不太明白,我的vs2008的版本是9.0.30729.4148,编译出来的东西应该也是这个版本的啊,可是为什么用了老版本才好用,新版本的反而不好用呢?

4、具体文件如下:

Microsoft.VC90.CRT.manifest

msvcm90.dll

msvcp90.dll

msvcr90.dll

posted @ 2011-07-25 14:15 ivaneeo 阅读(514) | 评论 (0)编辑 收藏

本文有标题党之嫌。在NoSQL如日中天的今天,各种NoSQL产品可谓百花齐放,但每一个产品都有自己的特点,有长处也有不适合的场景。本文对CassandraMongodbCouchDBRedisRiak 以及 HBase 进行了多方面的特点分析,希望看完此文的您能够对这些NoSQL产品的特性有所了解。

CouchDB

  • Written in: Erlang
  • Main point: DB consistency, ease of use
  • License: Apache
  • Protocol: HTTP/REST
  • Bi-directional (!) replication,
  • continuous or ad-hoc,
  • with conflict detection,
  • thus, master-master replication. (!)
  • MVCC – write operations do not block reads
  • Previous versions of documents are available
  • Crash-only (reliable) design
  • Needs compacting from time to time
  • Views: embedded map/reduce
  • Formatting views: lists & shows
  • Server-side document validation possible
  • Authentication possible
  • Real-time updates via _changes (!)
  • Attachment handling
  • thus, CouchApps (standalone js apps)
  • jQuery library included

Best used: For accumulating, occasionally changing data, on which pre-defined queries are to be run. Places where versioning is important.

For example: CRM, CMS systems. Master-master replication is an especially interesting feature, allowing easy multi-site deployments.

Redis

  • Written in: C/C++
  • Main point: Blazing fast
  • License: BSD
  • Protocol: Telnet-like
  • Disk-backed in-memory database,
  • but since 2.0, it can swap to disk.
  • Master-slave replication
  • Simple keys and values,
  • but complex operations like ZREVRANGEBYSCORE
  • INCR & co (good for rate limiting or statistics)
  • Has sets (also union/diff/inter)
  • Has lists (also a queue; blocking pop)
  • Has hashes (objects of multiple fields)
  • Of all these databases, only Redis does transactions (!)
  • Values can be set to expire (as in a cache)
  • Sorted sets (high score table, good for range queries)
  • Pub/Sub and WATCH on data changes (!)

Best used: For rapidly changing data with a foreseeable database size (should fit mostly in memory).

For example: Stock prices. Analytics. Real-time data collection. Real-time communication.

MongoDB

  • Written in: C++
  • Main point: Retains some friendly properties of SQL. (Query, index)
  • License: AGPL (Drivers: Apache)
  • Protocol: Custom, binary (BSON)
  • Master/slave replication
  • Queries are javascript expressions
  • Run arbitrary javascript functions server-side
  • Better update-in-place than CouchDB
  • Sharding built-in
  • Uses memory mapped files for data storage
  • Performance over features
  • After crash, it needs to repair tables
  • Better durablity coming in V1.8

Best used: If you need dynamic queries. If you prefer to define indexes, not map/reduce functions. If you need good performance on a big DB. If you wanted CouchDB, but your data changes too much, filling up disks.

For example: For all things that you would do with MySQL or PostgreSQL, but having predefined columns really holds you back.

Cassandra

  • Written in: Java
  • Main point: Best of BigTable and Dynamo
  • License: Apache
  • Protocol: Custom, binary (Thrift)
  • Tunable trade-offs for distribution and replication (N, R, W)
  • Querying by column, range of keys
  • BigTable-like features: columns, column families
  • Writes are much faster than reads (!)
  • Map/reduce possible with Apache Hadoop
  • I admit being a bit biased against it, because of the bloat and complexity it has partly because of Java (configuration, seeing exceptions, etc)

Best used: When you write more than you read (logging). If every component of the system must be in Java. (“No one gets fired for choosing Apache’s stuff.”)

For example: Banking, financial industry (though not necessarily for financial transactions, but these industries are much bigger than that.) Writes are faster than reads, so one natural niche is real time data analysis.

Riak

  • Written in: Erlang & C, some Javascript
  • Main point: Fault tolerance
  • License: Apache
  • Protocol: HTTP/REST
  • Tunable trade-offs for distribution and replication (N, R, W)
  • Pre- and post-commit hooks,
  • for validation and security.
  • Built-in full-text search
  • Map/reduce in javascript or Erlang
  • Comes in “open source” and “enterprise” editions

Best used: If you want something Cassandra-like (Dynamo-like), but no way you’re gonna deal with the bloat and complexity. If you need very good single-site scalability, availability and fault-tolerance, but you’re ready to pay for multi-site replication.

For example: Point-of-sales data collection. Factory control systems. Places where even seconds of downtime hurt.

HBase

  • Written in: Java
  • Main point: Billions of rows X millions of columns
  • License: Apache
  • Protocol: HTTP/REST (also Thrift)
  • Modeled after BigTable
  • Map/reduce with Hadoop
  • Query predicate push down via server side scan and get filters
  • Optimizations for real time queries
  • A high performance Thrift gateway
  • HTTP supports XML, Protobuf, and binary
  • Cascading, hive, and pig source and sink modules
  • Jruby-based (JIRB) shell
  • No single point of failure
  • Rolling restart for configuration changes and minor upgrades
  • Random access performance is like MySQL

Best used: If you’re in love with BigTable. :) And when you need random, realtime read/write access to your Big Data.

For example: Facebook Messaging Database (more general example coming soon)

原文链接:Cassandra vs MongoDB vs CouchDB vs Redis vs Riak vs HBase comparison

posted @ 2011-07-05 15:11 ivaneeo 阅读(1258) | 评论 (0)编辑 收藏

xStream性能不高,参考
https://github.com/eishay/jvm-serializers/wiki
如果纯java场景应用,可以参考kryo
如果需要跨语言,可以参考ProtoBuf
posted @ 2011-07-01 23:33 ivaneeo 阅读(325) | 评论 (0)编辑 收藏

如果有不明白的地方或者陌生的端口可以在这里查到。以便于检查系统是否感染病毒或木马。但是在有防火墙的情况下,一般的防火墙都是严格审核程序的网络连接 的,所以会预先封闭所有的端口,有需要访问网络的程序会预先向防火墙提出申请,防火墙做出响应,并弹出提示,要求用户做出选择,这时候我们就要认真看了, 是哪一个程序,在文件夹的哪一个位置,要做一个估计,陌生程序就更要检查。这样才能不给恶意程序任何余地。同时系统自动升级最好打开,或者定期到 windows的微软网站下载系统更新程序,这样也非常有利于系统安全。系统漏洞可能会使恶意程序通过系统漏洞绕过防火墙连接到网络。

端口:1
服务:tcpmux
说 明:这显示有人在寻找sgi irix机器。irix是实现tcpmux的主要提供者,默认情况下tcpmux在这种系统中被打开。irix机器在发布是含有几个默认的无密码的帐户, 如:ip、guest uucp、nuucp、demos 、tutor、diag、outofbox等。许多管理员在安装后忘记删除这些帐户。因此hacker在internet上搜索tcpmux并利用这些帐 户。

端口:7
服务:echo
说明:能看到许多人搜索fraggle放大器时,发送到x.x.x.0和x.x.x.255的信息。

端口:19
服务:character generator
说 明:这是一种仅仅发送字符的服务。udp版本将会在收到udp包后回应含有**字符的包。tcp连接时会发送含有**字符的数据流直到连接关闭。 hacker利用ip欺骗可以发动dos攻击。伪造两个chargen服务器之间的udp包。同样fraggle dos攻击向目标地址的这个端口广播一个带有伪造受害者ip的数据包,受害者为了回应这些数据而过载。

端口:21
服务:ftp
说 明:ftp服务器所开放的端口,用于上传、下载。最常见的攻击者用于寻找打开anonymous的ftp服务器的方法。这些服务器带有可读写的目录。木马 doly trojan、fore、invisible ftp、webex、wincrash和blade runner所开放的端口。

端口:22
服务:ssh
说明:pcanywhere建立的tcp和这一端口的连接可能是为了寻找ssh。这一服务有许多弱点,如果配置成特定的模式,许多使用rsaref库的版本就会有不少的漏洞存在。

端口:23
服务:telnet
说明:远程登录,入侵者在搜索远程登录unix的服务。大多数情况下扫描这一端口是为了找到机器运行的操作系统。还有使用其他技术,入侵者也会找到密码。木马tiny telnet server就开放这个端口。

端口:25
服务:smtp
说 明:smtp服务器所开放的端口,用于发送邮件。入侵者寻找smtp服务器是为了传递他们的spam。入侵者的帐户被关闭,他们需要连接到高带宽的 e-mail服务器上,将简单的信息传递到不同的地址。木马antigen、email password sender、haebu coceda、shtrilitz stealth、winpc、winspy都开放这个端口。

端口:31
服务:msg authentication
说明:木马master paradise、hackers paradise开放此端口。

端口:42
服务:wins replication
说明:wins复制

端口:53
服务:domain name server(dns)
说明:dns服务器所开放的端口,入侵者可能是试图进行区域传递(tcp),欺骗dns(udp)或隐藏其他的通信。因此防火墙常常过滤或记录此端口。

端口:67
服务:bootstrap protocol server
说 明:通过dsl和cable modem的防火墙常会看见大量发送到广播地址255.255.255.255的数据。这些机器在向dhcp服务器请求一个地址。hacker常进入它 们,分配一个地址把自己作为局部路由器而发起大量中间人(man-in-middle)攻击。客户端向68端口广播请求配置,服务器向67端口广播回应请 求。这种回应使用广播是因为客户端还不知道可以发送的ip地址。

端口:69
服务:trival file transfer
说明:许多服务器与bootp一起提供这项服务,便于从系统下载启动代码。但是它们常常由于错误配置而使入侵者能从系统中窃取任何 文件。它们也可用于系统写入文件。

端口:79
服务:finger server
说明:入侵者用于获得用户信息,查询操作系统,探测已知的缓冲区溢出错误,回应从自己机器到其他机器finger扫描。

端口:80
服务:http
说明:用于网页浏览。木马executor开放此端口。

端口:99
服务:metagram relay
说明:后门程序ncx99开放此端口。

端口:102
服务:message transfer agent(mta)-x.400 over tcp/ip
说明:消息传输代理。

端口:109
服务:post office protocol -version3
说明:pop3服务器开放此端口,用于接收邮件,客户端访问服务器端的邮件服务。pop3服务有许多公认的弱点。关于用户名和密码交 换缓冲区溢出的弱点至少有20个,这意味着入侵者可以在真正登陆前进入系统。成功登陆后还有其他缓冲区溢出错误。

端口:110
服务:sun公司的rpc服务所有端口
说明:常见rpc服务有rpc.mountd、nfs、rpc.statd、rpc.csmd、rpc.ttybd、amd等

端口:113
服务:authentication service
说 明:这是一个许多计算机上运行的协议,用于鉴别tcp连接的用户。使用标准的这种服务可以获得许多计算机的信息。但是它可作为许多服务的记录器,尤其是 ftp、pop、imap、smtp和irc等服务。通常如果有许多客户通过防火墙访问这些服务,将会看到许多这个端口的连接请求。记住,如果阻断这个端 口客户端会感觉到在防火墙另一边与e-mail服务器的缓慢连接。许多防火墙支持tcp连接的阻断过程中发回rst。这将会停止缓慢的连接。

端口:119
服务:network news transfer protocol
说明:news新闻组传输协议,承载usenet通信。这个端口的连接通常是人们在寻找usenet服务器。多数isp限制,只有他们的客户才能访问他们的新闻组服务器。打开新闻组服务器将允许发/读任何人的帖子,访问被限制的新闻组服务器,匿名发帖或发送spam。

端口:135
服务:本地 service
说 明:microsoft在这个端口运行dce rpc end-point mapper为它的dcom服务。这与unix 111端口的功能很相似。使用dcom和rpc的服务利用计算机上的end-point mapper注册它们的位置。远端客户连接到计算机时,它们查找end-point mapper找到服务的位置。hacker扫描计算机的这个端口是为了找到这个计算机上运行exchange server吗?什么版本?还有些dos攻击直接针对这个端口。

端口:137、138、139
服务:netbios name service
说明:其中137、138是udp端口,当通过网上邻居传输文件时用这个端口。而139端口:通过这个端口进入的连接试图获得netbios/smb服务。这个协议被用于windows文件和打印机共享和samba。还有wins regisrtation也用它。

端口:143
服务:interim mail access protocol v2
说 明:和pop3的安全问题一样,许多imap服务器存在有缓冲区溢出漏洞。记住:一种linux蠕虫(admv0rm)会通过这个端口繁殖,因此许多这个 端口的扫描来自不知情的已经被感染的用户。当redhat在他们的linux发布版本中默认允许imap后,这些漏洞变的很流行。这一端口还被用于 imap2,但并不流行。

端口:161
服务:snmp
说明:snmp允许远程管理设备。所有配置和运行信息的储存 在数据库中,通过snmp可获得这些信息。许多管理员的错误配置将被暴露在internet。cackers将试图使用默认的密码public、 private访问系统。他们可能会试验所有可能的组合。snmp包可能会被错误的指向用户的网络。

端口:177
服务:x display manager control protocol
说明:许多入侵者通过它访问x-windows操作台,它同时需要打开6000端口。

端口:389
服务:ldap、ils
说明:轻型目录访问协议和netmeeting internet locator server共用这一端口。

端口:443
服务:https
说明:网页浏览端口,能提供加密和通过安全端口传输的另一种http。

端口:456
服务:【null】
说明:木马hackers paradise开放此端口。

端口:513
服务:login,remote login
说明:是从使用cable modem或dsl登陆到子网中的unix计算机发出的广播。这些人为入侵者进入他们的系统提供了信息。

端口:544
服务:【null】
说明:kerberos kshell

端口:548
服务:macintosh,file services(afp/ip)
说明:macintosh,文件服务。

端口:553
服务:corba iiop (udp)
说明:使用cable modem、dsl或vlan将会看到这个端口的广播。corba是一种面向对象的rpc系统。入侵者可以利用这些信息进入系统。

端口:555
服务:dsf
说明:木马phase1.0、stealth spy、inikiller开放此端口。

端口:568
服务:membership dpa
说明:成员资格 dpa。

端口:569
服务:membership msn
说明:成员资格 msn。

端口:635
服务:mountd
说 明:linux的mountd bug。这是扫描的一个流行bug。大多数对这个端口的扫描是基于udp的,但是基于tcp的mountd有所增加(mountd同时运行于两个端口)。 记住mountd可运行于任何端口(到底是哪个端口,需要在端口111做portmap查询),只是linux默认端口是635,就像nfs通常运行于 2049端口。

端口:636
服务:ldap
说明:ssl(secure sockets layer)

端口:666
服务:doom id software
说明:木马attack ftp、satanz backdoor开放此端口

端口:993
服务:imap
说明:ssl(secure sockets layer)

端口:1001、1011
服务:【null】
说明:木马silencer、webex开放1001端口。木马doly trojan开放1011端口。

端口:1024
服务:reserved
说 明:它是动态端口的开始,许多程序并不在乎用哪个端口连接网络,它们请求系统为它们分配下一个闲置端口。基于这一点分配从端口1024开始。这就是说第一 个向系统发出请求的会分配到1024端口。你可以重启机器,打开telnet,再打开一个窗口运行natstat -a 将会看到telnet被分配1024端口。还有sql session也用此端口和5000端口。

端口:1025、1033
服务:1025:network blackjack 1033:【null】
说明:木马netspy开放这2个端口。

端口:1080
服务:socks
说 明:这一协议以通道方式穿过防火墙,允许防火墙后面的人通过一个ip地址访问internet。理论上它应该只允许内部的通信向外到达internet。 但是由于错误的配置,它会允许位于防火墙外部的攻击穿过防火墙。wingate常会发生这种错误,在加入irc聊天室时常会看到这种情况。
端口:1170
服务:【null】
说明:木马streaming audio trojan、psyber stream server、voice开放此端口。

端口:1234、1243、6711、6776
服务:【null】
说明:木马subseven2.0、ultors trojan开放1234、6776端口。木马subseven1.0/1.9开放1243、6711、6776端口。

端口:1245
服务:【null】
说明:木马vodoo开放此端口。

端口:1433
服务:sql
说明:microsoft的sql服务开放的端口。

端口:1492
服务:stone-design-1
说明:木马ftp99cmp开放此端口。

端口:1500
服务:rpc client fixed port session queries
说明:rpc客户固定端口会话查询

端口:1503
服务:netmeeting t.120
说明:netmeeting t.120

端口:1524
服务:ingress
说 明:许多攻击脚本将安装一个后门shell于这个端口,尤其是针对sun系统中sendmail和rpc服务漏洞的脚本。如果刚安装了防火墙就看到在这个 端口上的连接企图,很可能是上述原因。可以试试telnet到用户的计算机上的这个端口,看看它是否会给你一个shell。连接到 600/pcserver也存在这个问题。

端口:1600
服务:issd
说明:木马shivka-burka开放此端口。

端口:1720
服务:netmeeting
说明:netmeeting h.233 call setup。

端口:1731
服务:netmeeting audio call control
说明:netmeeting音频调用控制。

端口:1807
服务:【null】
说明:木马spysender开放此端口。

端口:1981
服务:【null】
说明:木马shockrave开放此端口。

端口:1999
服务:cisco identification port
说明:木马backdoor开放此端口。

端口:2000
服务:【null】
说明:木马girlfriend 1.3、millenium 1.0开放此端口。

端口:2001
服务:【null】
说明:木马millenium 1.0、trojan cow开放此端口。

端口:2023
服务:xinuexpansion 4
说明:木马pass ripper开放此端口。

端口:2049
服务:nfs
说明:nfs程序常运行于这个端口。通常需要访问portmapper查询这个服务运行于哪个端口。

端口:2115
服务:【null】
说明:木马bugs开放此端口。

端口:2140、3150
服务:【null】
说明:木马deep throat 1.0/3.0开放此端口。

端口:2500
服务:rpc client using a fixed port session replication
说明:应用固定端口会话复制的rpc客户

端口:2583
服务:【null】
说明:木马wincrash 2.0开放此端口。

端口:2801
服务:【null】
说明:木马phineas phucker开放此端口。

端口:3024、4092
服务:【null】
说明:木马wincrash开放此端口。

端口:3128
服务:squid
说 明:这是squid http代理服务器的默认端口。攻击者扫描这个端口是为了搜寻一个代理服务器而匿名访问internet。也会看到搜索其他代理服务器的端口8000、 8001、8080、8888。扫描这个端口的另一个原因是用户正在进入聊天室。其他用户也会检验这个端口以确定用户的机器是否支持代理。

端口:3129
服务:【null】
说明:木马master paradise开放此端口。

端口:3150
服务:【null】
说明:木马the invasor开放此端口。

端口:3210、4321
服务:【null】
说明:木马schoolbus开放此端口

端口:3333
服务:dec-notes
说明:木马prosiak开放此端口

端口:3389
服务:超级终端
说明:windows 2000终端开放此端口。

端口:3700
服务:【null】
说明:木马portal of doom开放此端口

端口:3996、4060
服务:【null】
说明:木马remoteanything开放此端口

端口:4000
服务:qq客户端
说明:腾讯qq客户端开放此端口。

端口:4092
服务:【null】
说明:木马wincrash开放此端口。

端口:4590
服务:【null】
说明:木马icqtrojan开放此端口。

端口:5000、5001、5321、50505
服务:【null】
说明:木马blazer5开放5000端口。木马sockets de troie开放5000、5001、5321、50505端口。

端口:5400、5401、5402
服务:【null】
说明:木马blade runner开放此端口。

端口:5550
服务:【null】
说明:木马xtcp开放此端口。

端口:5569
服务:【null】
说明:木马robo-hack开放此端口。

端口:5632
服务:pcanywere
说 明:有时会看到很多这个端口的扫描,这依赖于用户所在的位置。当用户打开pcanywere时,它会自动扫描局域网c类网以寻找可能的代理(这里的代理是 指agent而不是proxy)。入侵者也会寻找开放这种服务的计算机。,所以应该查看这种扫描的源地址。一些搜寻pcanywere的扫描包常含端口 22的udp数据包。

端口:5742
服务:【null】
说明:木马wincrash1.03开放此端口。

端口:6267
服务:【null】
说明:木马广外女生开放此端口。

端口:6400
服务:【null】
说明:木马the thing开放此端口。

端口:6670、6671
服务:【null】
说明:木马deep throat开放6670端口。而deep throat 3.0开放6671端口。

端口:6883
服务:【null】
说明:木马deltasource开放此端口。

端口:6969
服务:【null】
说明:木马gatecrasher、priority开放此端口。

端口:6970
服务:realaudio
说明:realaudio客户将从服务器的6970-7170的udp端口接收音频数据流。这是由tcp-7070端口外向控制连接设置的。

端口:7000
服务:【null】
说明:木马remote grab开放此端口。

端口:7300、7301、7306、7307、7308
服务:【null】
说明:木马netmonitor开放此端口。另外netspy1.0也开放7306端口。

端口:7323
服务:【null】
说明:sygate服务器端。

端口:7626
服务:【null】
说明:木马giscier开放此端口。

端口:7789
服务:【null】
说明:木马ickiller开放此端口。

端口:8000
服务:oicq
说明:腾讯qq服务器端开放此端口。

端口:8010
服务:wingate
说明:wingate代理开放此端口。

端口:8080
服务:代理端口
说明:www代理开放此端口。

端口:9400、9401、9402
服务:【null】
说明:木马incommand 1.0开放此端口。

端口:9872、9873、9874、9875、10067、10167
服务:【null】
说明:木马portal of doom开放此端口。

端口:9989
端口:9989
服务:【null】
说明:木马ini-killer开放此端口。

端口:11000
服务:【null】
说明:木马sennaspy开放此端口。

端口:11223
服务:【null】
说明:木马progenic trojan开放此端口。

端口:12076、61466
服务:【null】
说明:木马telecommando开放此端口。

端口:12223
服务:【null】
说明:木马hack? keylogger开放此端口。

端口:12345、12346
服务:【null】
说明:木马netbus1.60/1.70、gabanbus开放此端口。

端口:12361
服务:【null】
说明:木马whack-a-mole开放此端口。

端口:13223
服务:powwow
说 明:powwow是tribal voice的聊天程序。它允许用户在此端口打开私人聊天的连接。这一程序对于建立连接非常具有攻击性。它会驻扎在这个tcp端口等回应。造成类似心跳间隔 的连接请求。如果一个拨号用户从另一个聊天者手中继承了ip地址就会发生好象有很多不同的人在测试这个端口的情况。这一协议使用opng作为其连接请求的 前4个字节。

端口:16969
服务:【null】
说明:木马priority开放此端口。

端口:17027
服务:conducent
说明:这是一个外向连接。这是由于公司内部有人安装了带有conducent"adbot"的共享软件。conducent"adbot"是为共享软件显示广告服务的。使用这种服务的一种流行的软件是pkware。

端口:19191
服务:【null】
说明:木马蓝色火焰开放此端口。

端口:20000、20001
服务:【null】
说明:木马millennium开放此端口。

端口:20034
服务:【null】
说明:木马netbus pro开放此端口。

端口:21554
服务:【null】
说明:木马girlfriend开放此端口。

端口:22222
服务:【null】
说明:木马prosiak开放此端口。

端口:23456
服务:【null】
说明:木马evil ftp、ugly ftp开放此端口。

端口:26274、47262
服务:【null】
说明:木马delta开放此端口。

端口:27374
服务:【null】
说明:木马subseven 2.1开放此端口。

端口:30100
服务:【null】
说明:木马netsphere开放此端口。

端口:30303
服务:【null】
说明:木马socket23开放此端口。

端口:30999
服务:【null】
说明:木马kuang开放此端口。

端口:31337、31338
服务:【null】
说明:木马bo(back orifice)开放此端口。另外木马deepbo也开放31338端口。

端口:31339
服务:【null】
说明:木马netspy dk开放此端口。

端口:31666
服务:【null】
说明:木马bowhack开放此端口。

端口:33333
服务:【null】
说明:木马prosiak开放此端口。

端口:34324
服务:【null】
说明:木马tiny telnet server、biggluck、tn开放此端口。

端口:40412
服务:【null】
说明:木马the spy开放此端口。

端口:40421、40422、40423、40426、
服务:【null】
说明:木马masters paradise开放此端口。

端口:43210、54321
服务:【null】
说明:木马schoolbus 1.0/2.0开放此端口。

端口:44445
服务:【null】
说明:木马happypig开放此端口。

端口:50766
服务:【null】
说明:木马fore开放此端口。

端口:53001
服务:【null】
说明:木马remote windows shutdown开放此端口。

端口:65000
服务:【null】
说明:木马devil 1.03开放此端口。


端口:88
说明:kerberos krb5。另外tcp的88端口也是这个用途。

端口:137
说 明:sql named pipes encryption over other protocols name lookup(其他协议名称查找上的sql命名管道加密技术)和sql rpc encryption over other protocols name lookup(其他协议名称查找上的sql rpc加密技术)和wins netbt name service(wins netbt名称服务)和wins proxy都用这个端口。

端口:161
说明:simple network management protocol(smtp)(简单网络管理协议)。

端口:162
说明:snmp trap(snmp陷阱)

端口:445
说明:common internet file system(cifs)(公共internet文件系统)

端口:464
说明:kerberos kpasswd(v5)。另外tcp的464端口也是这个用途。

端口:500
说明:internet key exchange(ike)(internet密钥交换)

端口:1645、1812
说明:remot authentication dial-in user service(radius)authentication(routing and remote access)(远程认证拨号用户服务)

端口:1646、1813
说明:radius accounting(routing and remote access)(radius记帐(路由和远程访问))

端口:1701
说明:layer two tunneling protocol(l2tp)(第2层隧道协议)

端口:1801、3527
说明:microsoft message queue server(microsoft消息队列服务器)。还有tcp的135、1801、2101、2103、2105也是同样的用途。

端口:2504
说明:network load balancing(网络平衡负荷)
posted @ 2011-06-20 20:17 ivaneeo 阅读(430) | 评论 (0)编辑 收藏

 前面系统讨论过java类型加载(loading)的问题,在这篇文章中简要分析一下java类型卸载(unloading)的问题,并简要分析一下如何解决如何运行时加载newly compiled version的问题。

【相关规范摘要】
    首先看一下,关于java虚拟机规范中时如何阐述类型卸载(unloading)的:
    A class or interface may be unloaded if and only if its class loader is unreachable. The bootstrap class loader is always reachable; as a result, system classes may never be unloaded.
    Java虚拟机规范中关于类型卸载的内容就这么简单两句话,大致意思就是:只有当加载该类型的类加载器实例(非类加载器类型)为unreachable状态时,当前被加载的类型才被卸载.启动类加载器实例永远为reachable状态,由启动类加载器加载的类型可能永远不会被卸载.

    我们再看一下Java语言规范提供的关于类型卸载的更详细的信息(部分摘录):
    //摘自JLS 12.7 Unloading of Classes and Interfaces
    1、An implementation of the Java programming language may unload classes.
    2、Class unloading is an optimization that helps reduce memory use. Obviously,the semantics of a program should not depend  on whether and how a system chooses to implement an optimization such as class unloading.
    3、Consequently,whether a class or interface has been unloaded or not should be transparent to a program

    通过以上我们可以得出结论: 类型卸载(unloading)仅仅是作为一种减少内存使用的性能优化措施存在的,具体和虚拟机实现有关,对开发者来说是透明的.

    纵观java语言规范及其相关的API规范,找不到显示类型卸载(unloading)的接口, 换句话说:
    1、一个已经加载的类型被卸载的几率很小至少被卸载的时间是不确定的
    2、一个被特定类加载器实例加载的类型运行时可以认为是无法被更新的

【类型卸载进一步分析】
     前面提到过,如果想卸载某类型,必须保证加载该类型的类加载器处于unreachable状态,现在我们再看看有 关unreachable状态的解释:
    1、A reachable object is any object that can be accessed in any potential continuing computation from any live thread.
    2、finalizer-reachable: A finalizer-reachable object can be reached from some finalizable object through some chain of references, but not from any live thread. An unreachable object cannot be reached by either means.

    某种程度上讲,在一个稍微复杂的java应用中,我们很难准确判断出一个实例是否处于unreachable状态,所    以为了更加准确的逼近这个所谓的unreachable状态,我们下面的测试代码尽量简单一点.
    
    【测试场景一】使用自定义类加载器加载, 然后测试将其设置为unreachable的状态
    说明:
    1、自定义类加载器(为了简单起见, 这里就假设加载当前工程以外D盘某文件夹的class)
    2、假设目前有一个简单自定义类型MyClass对应的字节码存在于D:/classes目录下
    
public class MyURLClassLoader extends URLClassLoader {
   public MyURLClassLoader() {
      super(getMyURLs());
   }

   private static URL[] getMyURLs() {
    try {
       return new URL[]{new File ("D:/classes/").toURL()};
    } catch (Exception e) {
       e.printStackTrace();
       return null;
    }
  }
}

 1 public class Main {
 2     public static void main(String[] args) {
 3       try {
 4          MyURLClassLoader classLoader = new MyURLClassLoader();
 5          Class classLoaded = classLoader.loadClass("MyClass");
 6          System.out.println(classLoaded.getName());
 7
 8          classLoaded = null;
 9          classLoader = null;
10
11          System.out.println("开始GC");
12          System.gc();
13          System.out.println("GC完成");
14        } catch (Exception e) {
15            e.printStackTrace();
16        }
17     }
18 }

        我们增加虚拟机参数-verbose:gc来观察垃圾收集的情况,对应输出如下:   
MyClass
开始GC
[Full GC[Unloading class MyClass]
207K->131K(1984K), 0.0126452 secs]
GC完成

    【测试场景二】使用系统类加载器加载,但是无法将其设置为unreachable的状态
      说明:将场景一中的MyClass类型字节码文件放置到工程的输出目录下,以便系统类加载器可以加载
        
 1 public class Main {
 2     public static void main(String[] args) {
 3      try {
 4       Class classLoaded =  ClassLoader.getSystemClassLoader().loadClass(
 5 "MyClass");
 6
 7
 8      System.out.printl(sun.misc.Launcher.getLauncher().getClassLoader());
 9      System.out.println(classLoaded.getClassLoader());
10      System.out.println(Main.class.getClassLoader());
11
12      classLoaded = null;
13
14      System.out.println("开始GC");
15      System.gc();
16      System.out.println("GC完成");
17
18      //判断当前系统类加载器是否有被引用(是否是unreachable状态)
19      System.out.println(Main.class.getClassLoader());
20     } catch (Exception e) {
21         e.printStackTrace();
22     }
23   }
24 }
        
        我们增加虚拟机参数-verbose:gc来观察垃圾收集的情况, 对应输出如下:
sun.misc.Launcher$AppClassLoader@197d257
sun.misc.Launcher$AppClassLoader@197d257
sun.misc.Launcher$AppClassLoader@197d257
开始GC
[Full GC 196K->131K(1984K), 0.0130748 secs]
GC完成
sun.misc.Launcher$AppClassLoader@197d257

        由于系统ClassLoader实例(AppClassLoader@197d257">sun.misc.Launcher$AppClassLoader@197d257)加载了很多类型,而且又没有明确的接口将其设置为null,所以我们无法将加载MyClass类型的系统类加载器实例设置为unreachable状态,所以通过测试结果我们可以看出,MyClass类型并没有被卸载.(说明: 像类加载器实例这种较为特殊的对象一般在很多地方被引用, 会在虚拟机中呆比较长的时间)

    【测试场景三】使用扩展类加载器加载, 但是无法将其设置为unreachable的状态

        说明:将测试场景二中的MyClass类型字节码文件打包成jar放置到JRE扩展目录下,以便扩展类加载器可以加载的到。由于标志扩展ClassLoader实例(ExtClassLoader@7259da">sun.misc.Launcher$ExtClassLoader@7259da)加载了很多类型,而且又没有明确的接口将其设置为null,所以我们无法将加载MyClass类型的系统类加载器实例设置为unreachable状态,所以通过测试结果我们可以看出,MyClass类型并没有被卸载.
        
 1 public class Main {
 2      public static void main(String[] args) {
 3        try {
 4          Class classLoaded = ClassLoader.getSystemClassLoader().getParent()
 5 .loadClass("MyClass");
 6
 7          System.out.println(classLoaded.getClassLoader());
 8
 9          classLoaded = null;
10
11          System.out.println("开始GC");
12          System.gc();
13          System.out.println("GC完成");
14          //判断当前标准扩展类加载器是否有被引用(是否是unreachable状态)
15          System.out.println(Main.class.getClassLoader().getParent());
16       } catch (Exception e) {
17          e.printStackTrace();
18       }
19    }
20 }

        我们增加虚拟机参数-verbose:gc来观察垃圾收集的情况,对应输出如下:
sun.misc.Launcher$ExtClassLoader@7259da
开始GC
[Full GC 199K->133K(1984K), 0.0139811 secs]
GC完成
sun.misc.Launcher$ExtClassLoader@7259da


    关于启动类加载器我们就不需再做相关的测试了,jvm规范和JLS中已经有明确的说明了.


    【类型卸载总结】
    通过以上的相关测试(虽然测试的场景较为简单)我们可以大致这样概括:
    1、有启动类加载器加载的类型在整个运行期间是不可能被卸载的(jvm和jls规范).
    2、被系统类加载器和标准扩展类加载器加载的类型在运行期间不太可能被卸载,因为系统类加载器实例或者标准扩展类的实例基本上在整个运行期间总能直接或者间接的访问的到,其达到unreachable的可能性极小.(当然,在虚拟机快退出的时候可以,因为不管ClassLoader实例或者Class(java.lang.Class)实例也都是在堆中存在,同样遵循垃圾收集的规则).
    3、被开发者自定义的类加载器实例加载的类型只有在很简单的上下文环境中才能被卸载,而且一般还要借助于强制调用虚拟机的垃圾收集功能才可以做到.可以预想,稍微复杂点的应用场景中(尤其很多时候,用户在开发自定义类加载器实例的时候采用缓存的策略以提高系统性能),被加载的类型在运行期间也是几乎不太可能被卸载的(至少卸载的时间是不确定的).

      综合以上三点,我们可以默认前面的结论1, 一个已经加载的类型被卸载的几率很小至少被卸载的时间是不确定的.同时,我们可以看的出来,开发者在开发代码时候,不应该对虚拟机的类型卸载做任何假设的前提下来实现系统中的特定功能.
    
      【类型更新进一步分析】
    前面已经明确说过,被一个特定类加载器实例加载的特定类型在运行时是无法被更新的.注意这里说的
         是一个特定的类加载器实例,而非一个特定的类加载器类型.
    
        【测试场景四】
        说明:现在要删除前面已经放在工程输出目录下和扩展目录下的对应的MyClass类型对应的字节码
        
 1 public class Main {
 2      public static void main(String[] args) {
 3        try {
 4          MyURLClassLoader classLoader = new MyURLClassLoader();
 5          Class classLoaded1 = classLoader.loadClass("MyClass");
 6          Class classLoaded2 = classLoader.loadClass("MyClass");
 7          //判断两次加载classloader实例是否相同
 8           System.out.println(classLoaded1.getClassLoader() == classLoaded2.getClassLoader());
 9
10         //判断两个Class实例是否相同
11           System.out.println(classLoaded1 == classLoaded2);
12       } catch (Exception e) {
13          e.printStackTrace();
14       }
15    }
16 }
        输出如下:
        true
        true

        通过结果我们可以看出来,两次加载获取到的两个Class类型实例是相同的.那是不是确实是我们的自定义
       类加载器真正意义上加载了两次呢(即从获取class字节码到定义class类型…整个过程呢)?
      通过对java.lang.ClassLoader的loadClass(String name,boolean resolve)方法进行调试,我们可以看出来,第二
      次  加载并不是真正意义上的加载,而是直接返回了上次加载的结果.

       说明:为了调试方便, 在Class classLoaded2 = classLoader.loadClass("MyClass");行设置断点,然后单步跳入, 可以看到第二次加载请求返回的结果直接是上次加载的Class实例. 调试过程中的截图 最好能自己调试一下).
      
     
        【测试场景五】同一个类加载器实例重复加载同一类型
        说明:首先要对已有的用户自定义类加载器做一定的修改,要覆盖已有的类加载逻辑, MyURLClassLoader.java类简要修改如下:重新运行测试场景四中的测试代码
      
 1 public class MyURLClassLoader extends URLClassLoader {
 2     //省略部分的代码和前面相同,只是新增如下覆盖方法
 3     /*
 4     * 覆盖默认的加载逻辑,如果是D:/classes/下的类型每次强制重新完整加载
 5     *
 6     * @see java.lang.ClassLoader#loadClass(java.lang.String)
 7     */
 8     @Override
 9     public Class<?> loadClass(String name) throws ClassNotFoundException {
10      try {
11        //首先调用系统类加载器加载
12         Class c = ClassLoader.getSystemClassLoader().loadClass(name);
13        return c;
14      } catch (ClassNotFoundException e) {
15       // 如果系统类加载器及其父类加载器加载不上,则调用自身逻辑来加载D:/classes/下的类型
16          return this.findClass(name);
17      }
18   }
19 }
说明: this.findClass(name)会进一步调用父类URLClassLoader中的对应方法,其中涉及到了defineClass(String name)的调用,所以说现在类加载器MyURLClassLoader会针对D:/classes/目录下的类型进行真正意义上的强制加载并定义对应的类型信息.

        测试输出如下:
        Exception in thread "main" java.lang.LinkageError: duplicate class definition: MyClass
       at java.lang.ClassLoader.defineClass1(Native Method)
       at java.lang.ClassLoader.defineClass(ClassLoader.java:620)
       at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:124)
       at java.net.URLClassLoader.defineClass(URLClassLoader.java:260)
       at java.net.URLClassLoader.access$100(URLClassLoader.java:56)
       at java.net.URLClassLoader$1.run(URLClassLoader.java:195)
       at java.security.AccessController.doPrivileged(Native Method)
       at java.net.URLClassLoader.findClass(URLClassLoader.java:188)
       at MyURLClassLoader.loadClass(MyURLClassLoader.java:51)
       at Main.main(Main.java:27)
      
       结论:如果同一个类加载器实例重复强制加载(含有定义类型defineClass动作)相同类型,会引起java.lang.LinkageError: duplicate class definition.
    
       【测试场景六】同一个加载器类型的不同实例重复加载同一类型
       
 1 public class Main {
 2     public static void main(String[] args) {
 3       try {
 4         MyURLClassLoader classLoader1 = new MyURLClassLoader();
 5         Class classLoaded1 = classLoader1.loadClass("MyClass");
 6         MyURLClassLoader classLoader2 = new MyURLClassLoader();
 7         Class classLoaded2 = classLoader2.loadClass("MyClass");
 8
 9         //判断两个Class实例是否相同
10          System.out.println(classLoaded1 == classLoaded2);
11       } catch (Exception e) {
12          e.printStackTrace();
13       }
14    }
15 }

      测试对应的输出如下:
      false
     
    
        【类型更新总结】   
     由不同类加载器实例重复强制加载(含有定义类型defineClass动作)同一类型不会引起java.lang.LinkageError错误, 但是加载结果对应的Class类型实例是不同的,即实际上是不同的类型(虽然包名+类名相同). 如果强制转化使用,会引起ClassCastException.(说明: 头一段时间那篇文章中解释过,为什么不同类加载器加载同名类型实际得到的结果其实是不同类型, 在JVM中一个类用其全名和一个加载类ClassLoader的实例作为唯一标识,不同类加载器加载的类将被置于不同的命名空间).


        应用场景:我们在开发的时候可能会遇到这样的需求,就是要动态加载某指定类型class文件的不同版本,以便能动态更新对应功能.
         建议:
        1. 不要寄希望于等待指定类型的以前版本被卸载,卸载行为对java开发人员透明的.
        2. 比较可靠的做法是,每次创建特定类加载器的新实例来加载指定类型的不同版本,这种使用场景下,一般就要牺牲缓存特定类型的类加载器实例以带来性能优化的策略了.对于指定类型已经被加载的版本, 会在适当时机达到unreachable状态,被unload并垃圾回收.每次使用完类加载器特定实例后(确定不需要再使用时), 将其显示赋为null, 这样可能会比较快的达到jvm 规范中所说的类加载器实例unreachable状态, 增大已经不再使用的类型版本被尽快卸载的机会.
        3. 不得不提的是,每次用新的类加载器实例去加载指定类型的指定版本,确实会带来一定的内存消耗,一般类加载器实例会在内存中保留比较长的时间. 在bea开发者网站上找到一篇相关的文章(有专门分析ClassLoader的部分):http://dev2dev.bea.com/pub/a/2005/06/memory_leaks.html

           写的过程中参考了jvm规范和jls, 并参考了sun公司官方网站上的一些bug的分析文档。

           欢迎大家批评指正!


本博客中的所有文章、随笔除了标题中含有引用或者转载字样的,其他均为原创。转载请注明出处,谢谢!
posted @ 2011-06-16 20:05 ivaneeo 阅读(346) | 评论 (0)编辑 收藏

启动集群中所有的regionserver
./hbase-daemons.sh start regionserver
启动某个regionserver
./hbase-daemon.sh start regionserver
posted @ 2011-06-16 12:10 ivaneeo 阅读(1513) | 评论 (0)编辑 收藏

做了几天工程,对HBase中的表操作熟悉了一下。下面总结一下常用的表操作和容易出错的几个方面。当然主要来源于大牛们的文章。我在前人的基础上稍作解释。

1.连接HBase中的表testtable,用户名:root,密码:root

public void ConnectHBaseTable()
 {
  Configuration conf = new Configuration();       
        conf.set("hadoop.job.ugi", "root,root");      
  HBaseConfiguration config = new HBaseConfiguration();
  try
  {
   table = new HTable(config, "testtable");
  }catch(Exception e){e.printStackTrace();}
 }

2.根据行名name获得一行数据,存入Result.注意HBase中的表数据是字节存储的。

   下面的例子表示获得行名为name的行的famA列族col1列的数据。

      String rowId = "name";
      Get get = new Get(rowId);
      Result result = hTable.get(get);
      byte[] value = result.getValue(famA, col1);
      System.out.println(Bytes.toString(value));

3.向表中存数据

      下面的例子表示写入一行。行名为abcd,famA列族col1列的数据为"hello world!"。

      byte[] rowId = Bytes.toBytes("abcd");
      byte[] famA = Bytes.toBytes("famA");
      byte[] col1 = Bytes.toBytes("col1");
      Put put = new Put(rowId).
         add(famA, col1, Bytes.toBytes("hello world!"));
      hTable.put(put);
     

4.扫描的用法(scan):便于获得自己需要的数据,相当于SQL查询。

      byte[] famA = Bytes.toBytes("famA");
      byte[] col1 = Bytes.toBytes("col1");  

      HTable hTable = new HTable("test");  

      //表示要查询的行名是从a开始,到z结束。
      Scan scan = new Scan(Bytes.toBytes("a"), Bytes.toBytes("z"));
     

      //用scan.setStartRow(Bytes.toBytes(""));设置起始行

      //用scan.setStopRow(Bytes.toBytes(""));设置终止行

      //表示查询famA族col1列

      scan.addColumn(famA, col1);  

      //注意,下面是filter的写法。相当于SQL的where子句

      //表示famA族col1列的数据等于"hello world!"
      
SingleColumnValueFilter singleColumnValueFilterA = new SingleColumnValueFilter(
           famA, col1, CompareOp.EQUAL, Bytes.toBytes("hello world!"));
      singleColumnValueFilterA.setFilterIfMissing(true);  

      //表示famA族col1列的数据等于"hello hbase!"
      
SingleColumnValueFilter singleColumnValueFilterB = new SingleColumnValueFilter(
           famA, col1, CompareOp.EQUAL, Bytes.toBytes("hello hbase!"));
      singleColumnValueFilterB.setFilterIfMissing(true);  
      

      //表示famA族col1列的数据是两者中的一个
      FilterList filter = new FilterList(Operator.MUST_PASS_ONE, Arrays
           .asList((Filter) singleColumnValueFilterA,
                singleColumnValueFilterB));  

      scan.setFilter(filter);  

      ResultScanner scanner = hTable.getScanner(scan);  
      //遍历每个数据
      for (Result result : scanner) {
         System.out.println(Bytes.toString(result.getValue(famA, col1)));
      }

5.上面的代码容易出错的地方在于,需要导入HBase的类所在的包。导入时需要选择包,由于类可能出现在HBase的各个子包中,所以要选择好,下面列出常用的包。尽量用HBase的包

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.hbase.HBaseConfiguration;
import org.apache.hadoop.hbase.client.Get;
import org.apache.hadoop.hbase.client.HTable;
import org.apache.hadoop.hbase.client.Put;
import org.apache.hadoop.hbase.client.Result;
import org.apache.hadoop.hbase.client.ResultScanner;
import org.apache.hadoop.hbase.client.Scan;
import org.apache.hadoop.hbase.filter.Filter;
import org.apache.hadoop.hbase.filter.FilterList;
import org.apache.hadoop.hbase.filter.SingleColumnValueFilter;
import org.apache.hadoop.hbase.filter.CompareFilter.CompareOp;
import org.apache.hadoop.hbase.filter.FilterList.Operator;
import org.apache.hadoop.hbase.util.Bytes;

import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;

6.下面列出HBase常用的操作

(1)时间戳到时间的转换.单一的时间戳无法给出直观的解释。

public String GetTimeByStamp(String timestamp)
 {

  long datatime= Long.parseLong(timestamp); 
     Date date=new Date(datatime);   
     SimpleDateFormat   format=new   SimpleDateFormat("yyyy-MM-dd HH:MM:ss");   
     String timeresult=format.format(date);
     System.out.println("Time : "+timeresult);
     return timeresult;
 }

(2)时间到时间戳的转换。注意时间是字符串格式。字符串与时间的相互转换,此不赘述

public String GetStampByTime(String time)
 {
  String Stamp="";
  SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
  Date date;
  try
  {
   date=sdf.parse(time);
   Stamp=date.getTime()+"000";
   System.out.println(Stamp);
  }catch(Exception e){e.printStackTrace();}
  return Stamp;
 }

上面就是我的一点心得。以后碰到什么问题,再来解决。

参考文献:http://www.nearinfinity.com/blogs/aaron_mccurry/using_hbase-dsl.html

posted @ 2011-06-15 17:17 ivaneeo 阅读(502) | 评论 (0)编辑 收藏

官方Book Performance Tuning部分章节没有按配置项进行索引,不能达到快速查阅的效果。所以我以配置项驱动,重新整理了原文,并补充一些自己的理解,如有错误,欢迎指正。

配置优化

zookeeper.session.timeout
默认值:3分钟(180000ms)
说明:RegionServer与Zookeeper间的连接超时时间。当超时时间到后,ReigonServer会 被Zookeeper从RS集群清单中移除,HMaster收到移除通知后,会对这台server负责的regions重新balance,让其他存活的 RegionServer接管.
调优
这个timeout决定了RegionServer是否能够及时的failover。设置成1分钟或更低,可以减少因等待超时而被延长的failover时间。
不过需要注意的是,对于一些Online应用,RegionServer的宕机到恢复时间本身就很短的(网络闪断,crash等故障,运维可快速介入), 如果调低timeout时间,会得不偿失。因为当ReigonServer被正式从RS集群中移除时,HMaster就开始做balance了,当故障的 RS快速恢复后,这个balance动作是毫无意义的,反而会使负载不均匀,给RS带来更多负担。

hbase.regionserver.handler.count
默认值:10
说明:RegionServer的请求处理IO线程数。
调优
这个参数的调优与内存息息相关。
较少的IO线程,适用于处理单次请求内存消耗较高的Big PUT场景(大容量单次PUT或设置了较大cache的scan,均属于Big PUT)或ReigonServer的内存比较紧张的场景。
较多的IO线程,适用于单次请求内存消耗低,TPS要求非常高的场景。
这里需要注意的是如果server的region数量很少,大量的请求都落在一个region上,因快速充满memstore触发flush导致的读写锁会影响全局TPS,不是IO线程数越高越好。
压测时,开启Enabling RPC-level logging,可以同时监控每次请求的内存消耗和GC的状况,最后通过多次压测结果来合理调节IO线程数。
这里是一个案例 Hadoop and HBase Optimization for Read Intensive Search Applications,作者在SSD的机器上设置IO线程数为100,仅供参考。

hbase.hregion.max.filesize
默认值:256M
说明:在当前ReigonServer上单个Reigon的大小,单个Region超过指定值时,这个Region会被自动split成更小的region。
调优
小region对split和compaction友好,因为拆分region或compact小region里的storefile速度很快,内存占用低。缺点是split和compaction会很频繁。
特别是数量较多的小region不停地split, compaction,会使响应时间波动很大,region数量太多不仅给管理上带来麻烦,甚至引发一些Hbase的bug。
一般512以下的都算小region。

大region,则不太适合经常split和compaction,因为做一次compact和split会产生较长时间的停顿,对应用的读写性能冲击非常大。此外,大region意味着较大的storefile,compaction时对内存也是一个挑战。
当然,大region还是有其用武之地,你只要在某个访问量低峰的时间点统一做compact和split,大region就可以发挥优势了,毕竟它能保证绝大多数时间平稳的读写性能。

既然split和compaction如此影响性能,有没有办法去掉?
compaction是无法避免的,split倒是可以从自动调整为手动。
只要通过将这个参数值调大到某个很难达到的值,比如100G,就可以间接禁用自动split(RegionServer不会对未到达100G的region做split)。
再配合RegionSplitter这个工具,在需要split时,手动split。
手动split在灵活性和稳定性上比起自动split要高很多,相反,管理成本增加不多,比较推荐online实时系统使用。

内存方面,小region在设置memstore的大小值上比较灵活,大region则过大过小都不行,过大会导致flush时app的IO wait增高,过小则因store file过多读性能降低。

hbase.regionserver.global.memstore.upperLimit/lowerLimit

默认值:0.4/0.35
upperlimit说明:hbase.hregion.memstore.flush.size 这个参数的作用是 当单个memstore达到指定值时,flush该memstore。但是,一台ReigonServer可能有成百上千个memstore,每个 memstore也许未达到flush.size,jvm的heap就不够用了。该参数就是为了限制memstores占用的总内存。
当ReigonServer内所有的memstore所占用的内存综合达到heap的40%时,HBase会强制block所有的更新并flush这些memstore以释放所有memstore占用的内存。
lowerLimit说明: 同upperLimit,只不过当全局memstore的内存达到35%时,它不会flush所有的memstore,它会找一些内存占用较大的 memstore,个别flush,当然更新还是会被block。lowerLimit算是一个在全局flush前的补救措施。可以想象一下,如果 memstore需要在一段时间内全部flush,且这段时间内无法接受写请求,对HBase集群的性能影响是很大的。
调优:这是一个Heap内存保护参数,默认值已经能适用大多数场景。它的调整一般是为了配合某些专属优化,比如读密集型应用,将读缓存开大,降低该值,腾出更多内存给其他模块使用。
这个参数会给使用者带来什么影响?
比如,10G内存,100个region,每个memstore 64M,假设每个region只有一个memstore,那么当100个memstore平均占用到50%左右时,就会达到lowerLimit的限制。 假设此时,其他memstore同样有很多的写请求进来。在那些大的region未flush完,就可能又超过了upperlimit,则所有 region都会被block,开始触发全局flush。

hfile.block.cache.size

默认值:0.2
说明:storefile的读缓存占用Heap的大小百分比,0.2表示20%。该值直接影响数据读的性能。
调优:当然是越大越好,如果读比写少,开到0.4-0.5也没问题。如果读写较均衡,0.3左右。如果写比读多,果断 默认吧。设置这个值的时候,你同时要参考 hbase.regionserver.global.memstore.upperLimit ,该值是 memstore占heap的最大百分比,两个参数一个影响读,一个影响写。如果两值加起来超过80-90%,会有OOM的风险,谨慎设置。

hbase.hstore.blockingStoreFiles

默认值:7
说明:在compaction时,如果一个Store(Coulmn Family)内有超过7个storefile需要合并,则block所有的写请求,进行flush,限制storefile数量增长过快。
调优:block请求会影响当前region的读写性能,将值设为单个region可以支撑的最大store file数量会是个不错的选择。最大storefile数量可通过region size/memstore size来计算。如果你将region size设为无限大,那么你需要预估一个region可能产生的最大storefile数。

hbase.hregion.memstore.block.multiplier

默认值:2
说明:当一个region里的memstore超过单个memstore.size两倍的大小时,block该 region的所有请求,进行flush,释放内存。虽然我们设置了memstore的总大小,比如64M,但想象一下,在最后63.9M的时候,我 Put了一个100M的数据或写请求量暴增,最后一秒钟put了1万次,此时memstore的大小会瞬间暴涨到超过预期的memstore.size。 这个参数的作用是当memstore的大小增至超过memstore.size时,block所有请求,遏制风险进一步扩大。
调优: 这个参数的默认值还是比较靠谱的。如果你预估你的正常应用场景(不包括异常)不会出现突发写或写的量可控,那么保持默认值即可。如果正常情况下,你的写量 就会经常暴增,那么你应该调大这个倍数并调整其他参数值,比如hfile.block.cache.size和 hbase.regionserver.global.memstore.upperLimit/lowerLimit,以预留更多内存,防止HBase server OOM。

其他

启用LZO压缩
LZO对比Hbase默认的GZip,前者性能较高,后者压缩比较高,具体参见 Using LZO Compression对于想提高HBase读写性能的开发者,采用LZO是比较好的选择。对于非常在乎存储空间的开发者,则建议保持默认。

不要在一张表里定义太多的Column Family

Hbase目前不能良好的处理超过2-3个CF的表。因为某个CF在flush发生时,它邻近的CF也会因关联效应被触发flush,最终导致系统产生很多IO。

批量导入

在批量导入数据到Hbase前,你可以通过预先创建region,来平衡数据的负载。详见 Table Creation: Pre-Creating Regions

Hbase客户端优化

AutoFlush

HTable的setAutoFlush设为false,可以支持客户端批量更新。即当Put填满客户端flush缓存时,才发送到服务端。
默认是true。

Scan Caching

scanner一次缓存多少数据来scan(从服务端一次抓多少数据回来scan)。
默认值是 1,一次只取一条。

Scan Attribute Selection

scan时建议指定需要的Column Family,减少通信量,否则scan默认会返回整个row的所有数据(所有Coulmn Family)。

Close ResultScanners

通过scan取完数据后,记得要关闭ResultScanner,否则RegionServer可能会出现问题。

Optimal Loading of Row Keys

当你scan一张表的时候,返回结果只需要row key(不需要CF, qualifier,values,timestaps)时,你可以在scan实例中添加一个filterList,并设置 MUST_PASS_ALL操作,filterList中add FirstKeyOnlyFilterKeyOnlyFilter。这样可以减少网络通信量。

Turn off WAL on Puts

当Put某些非重要数据时,你可以设置writeToWAL(false),来进一步提高写性能。writeToWAL(false)会在Put时放弃写WAL log。风险是,当RegionServer宕机时,可能你刚才Put的那些数据会丢失,且无法恢复。

启用Bloom Filter

Bloom Filter通过空间换时间,提高读操作性能。

转载请注明原文链接:http://kenwublog.com/hbase-performance-tuning

posted @ 2011-06-15 13:39 ivaneeo 阅读(2794) | 评论 (0)编辑 收藏

We recently set up HBase and HBase-trx (from https://github.com/hbase-trx) to use multiple-column indexes with this code.  After you compile it, just copy the jar and the hbase-trx jar into your hbase’s lib folder and you should be good to to!

When you create a composite index, you can see the metadata for the index by looking at the table description.  One of the properties will read “INDEXES =>” followed by index names and ‘family:qualifier’ style column names in the index.

KeyGeneratorFactory:

package com.ir.store.hbase.indexes;

import java.util.List;

import org.apache.hadoop.hbase.client.tableindexed.IndexKeyGenerator;

public class KeyGeneratorFactory {

public static IndexKeyGenerator getInstance(List columns) {
return new HBaseIndexKeyGenerator(columns);
}
}

HBaseIndexKeyGenerator:

package com.ir.store.hbase.indexes;

import java.io.DataInput;
import java.io.DataOutput;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.apache.hadoop.hbase.client.tableindexed.IndexKeyGenerator;
import org.apache.hadoop.hbase.util.Bytes;

public class HBaseIndexKeyGenerator extends Object implements IndexKeyGenerator {
public static byte[] KEYSEPERATOR = "~;?".getBytes();

private int columnCount;
private List columnNames = new ArrayList();

public HBaseIndexKeyGenerator(List memberColumns) {
// For new key generators
columnNames = memberColumns;
columnCount = memberColumns.size();
}

public HBaseIndexKeyGenerator() {
// Hollow constructor for deserializing -- should call readFields shortly
columnCount = 0;
}

public void readFields(DataInput binaryInput) throws IOException {
columnCount = binaryInput.readInt();
for (int currentColumn = 0; currentColumn < columnCount; currentColumn++)
columnNames.add(Bytes.readByteArray(binaryInput));
}

public void write(DataOutput binaryOutput) throws IOException {
binaryOutput.writeInt(columnCount);
for (byte[] columnName : columnNames)
Bytes.writeByteArray(binaryOutput, columnName);
}

public byte[] createIndexKey(byte[] baseRowIdentifier, Map baseRowData) {
byte[] indexRowIdentifier = null;
for (byte[] columnName: columnNames) {
if (indexRowIdentifier == null)
indexRowIdentifier = baseRowData.get(columnName);
else indexRowIdentifier = Bytes.add(indexRowIdentifier, HBaseIndexKeyGenerator.KEYSEPERATOR, baseRowData.get(columnName));
}
if (baseRowIdentifier != null)
return Bytes.add(indexRowIdentifier, HBaseIndexKeyGenerator.KEYSEPERATOR, baseRowIdentifier);
return indexRowIdentifier;
}
}
posted @ 2011-06-11 16:21 ivaneeo 阅读(401) | 评论 (0)编辑 收藏

对于Bigtable类型的分布式数据库应用来说,用户往往会对其性能状况有极大的兴趣,这其中又对实时数据插入性能更为关注。HBase作为Bigtable的一个实现,在这方面的性能会如何呢?这就需要通过测试数据来说话了。

数据插入性能测试的设计场景是这样的,取随机值的Rowkey长度为2000字节,固定值的Value长度为4000字节,由于单行Row插入速度太快,系统统计精度不够,所以将插入500行Row做一次耗时统计。

这里要对HBase的特点做个说明,首先是Rowkey值为何取随机数,这是因为HBase是对Rowkey进行排序的,随机Rowkey将被分配到不同的region上,这样才能发挥出分布式数据库的性能优点。而Value对于HBase来说不会进行任何解析,其数据是否变化,对性能是不应该有任何影响的。同时为了简单起见,所有的数据都将只插入到一个表格的同一个Column中。

在测试之初,需要对集群进行调优,关闭可能大量耗费内存、带宽以及CPU的服务,例如Apache的Http服务。保持集群的宁静度。此外,为了保证测试不受干扰,Hbase的集群系统需要被独立,以保证不与HDFS所在的Hadoop集群有所交叉。

那么做好一切准备,就开始进行数据灌入,客户端从Zookeeper上查询到Regionserver的地址后,开始源源不断的向Hbase的Regionserver上喂入Row。

这里,我写了一个通过JFreeChart来实时生成图片的程序,每3分钟,喂数据的客户端会将获取到的耗时统计打印在一张十字坐标图中,这些图又被保存在制定的web站点中,并通过http服务展示出来。在通过长时间不间断的测试后,我得到了如下图形:

这个图形非常有特点,好似一条直线上,每隔一段时间就会泛起一个波浪,且两个高峰之间必有一个较矮的波浪。高峰的间隔则呈现出越来越大的趋势。而较矮的波浪恰好处于两高峰的中间位置。

为了解释这个现象,我对HDFS上Hbase所在的主目录下文件,以及被插入表格的region情况进行了实时监控,以期发现这些波浪上发生了什么事情。

回溯到客户端喂入数据的开始阶段,创建表格,在HDFS上便被创建了一个与表格同名的目录,该目录下将出现第一个region,region中会以family名创建一个目录,这个目录下才存在记录具体数据的文件。同时在该表表名目录下,还会生成一个“compaction.dir”目录,该目录将在family名目录下region文件超过指定数目时用于合并region。

当第一个region目录出现的时候,内存中最初被写入的数据将被保存到这个文件中,这个间隔是由选项“hbase.hregion.memstore.flush.size”决定的,默认是64MB,该region所在的Regionserver的内存中一旦有超过64MB的数据的时候,就将被写入到region文件中。这个文件将不断增殖,直到超过由“hbase.hregion.max.filesize”决定的文件大小时(默认是256MB,此时加上内存刷入的数据,实际最大可能到256+64M),该region将被执行split,立即被一切为二,其过程是在该目录下创建一个名为“.splits”的目录作为标记,然后由Regionserver将文件信息读取进来,分别写入到两个新的region目录中,最后再将老的region删除。这里的标记目录“.splits”将避免在split过程中发生其他操作,起到类似于多线程安全的锁功能。在新的region中,从老的region中切分出的数据独立为一个文件并不再接受新的数据(该文件大小超过了64M,最大可达到(256+64)/2=160MB),内存中新的数据将被保存到一个重新创建的文件中,该文件大小将为64MB。内存每刷新一次,region所在的目录下就将增加一个64M的文件,直到总文件数超过由“hbase.hstore.compactionThreshold”指定的数量时(默认为3),compaction过程就将被触发了。在上述值为3时,此时该region目录下,实际文件数只有两个,还有额外的一个正处于内存中将要被刷入到磁盘的过程中。Compaction过程是Hbase的一个大动作,Hbase不仅要将这些文件转移到“compaction.dir”目录进行压缩,而且在压缩后的文件超过256MB时,还必须立即进行split动作。这一系列行为在HDFS上可谓是翻山倒海,影响颇大。待Compaction结束之后,后续的split依然会持续进行一小段时间,直到所有的region都被切割分配完毕,Hbase才会恢复平静并等待下一次数据从内存写入到HDFS的到来。

理解了上述过程,则必然对HBase的数据插入性能为何是上图所示的曲线的原因一目了然。与X轴几乎平行的直线,表明数据正在被写入HBase的Regionserver所在机器的内存中。而较低的波峰意味着Regionserver正在将内存写入到HDFS上,较高的波峰意味着Regionserver不仅正在将内存刷入到HDFS,而且还在执行Compaction和Split两种操作。如果调整“hbase.hstore.compactionThreshold”的值为一个较大的数量,例如改成5,可以预见,在每两个高峰之间必然会等间隔的出现三次较低的波峰,并可预见到,高峰的高度将远超过上述值为3时的高峰高度(因为Compaction的工作更为艰巨)。由于region数量由少到多,而我们插入的Row的Rowkey是随机的,因此每一个region中的数据都会均匀的增加,同一段时间插入的数据将被分布到越来越多的region上,因此波峰之间的间隔时间也将会越来越长。

再次理解上述论述,我们可以推断出Hbase的数据插入性能实际上应该被分为三种情况,即直线状态、低峰状态和高峰状态。在这三种情况下得到的性能数据才是最终Hbase数据插入性能的真实描述。那么提供给用户的数据该是采取哪一个呢?我认为直线状态由于其所占时间会较长,尤其在用户写入数据的速度也许并不是那么快的情况下,所以这个状态下得到的性能数据结果更应该提供给用户。

posted @ 2011-06-10 23:33 ivaneeo 阅读(1599) | 评论 (1)编辑 收藏

HBase的写效率还是很高的,但其随机读取效率并不高

可以采取一些优化措施来提高其性能,如:

1. 启用lzo压缩,见这里

2. 增大hbase.regionserver.handler.count数为100

3. 增大hfile.block.cache.size为0.4,提高cache大小

4. 增大hbase.hstore.blockingStoreFiles为15

5. 启用BloomFilter,在HBase0,89中可以设置

6.Put时可以设置setAutoFlush为false,到一定数目后再flushCommits

 

在14个Region Server的集群上,新建立一个lzo压缩表

测试的Put和Get的性能如下:

1. Put数据:

单线程灌入1.4亿数据,共花费50分钟,每秒能达到4万个,这个性能确实很好了,不过插入的value比较小,只有不到几十个字节

多线程put,没有测试,因为单线程的效率已经相当高了

2. Get数据:

在没有任何Block Cache,而且是Random Read的情况:

单线程平均每秒只能到250个左右

6个线程平均每秒能达到1100个左右

16个线程平均每秒能达到2500个左右

有BlockCache(曾经get过对应的row,而且还在cache中)的情况:

单线程平均每秒能到3600个左右

6个线程平均每秒能达到1.2万个左右

16个线程平均每秒能达到2.5万个左右

posted @ 2011-06-10 23:14 ivaneeo 阅读(1200) | 评论 (0)编辑 收藏

在Android的客户端编程中(特别是SNS 类型的客户端),经常需要实现注册功能Activity,要用户输入用户名,密码,邮箱,照片后注册。但这时就有一个问题,在HTML中用form表单就 能实现如上的注册表单,需要的信息会自动封装为完整的HTTP协议,但在Android中如何把这些参数和需要上传的文件封装为HTTP协议呢?

我们可以先做个试验,看一下form表单到底封装了什么样的信息。

第一步:编写一个Servlet,把接收到的HTTP信息保存在一个文件中,代码如下:

  1.     public void doPost(HttpServletRequest request, HttpServletResponse response)
  2.  
  3.            throws ServletException, IOException {
  4.  
  5.  
  6.  
  7.        //获取输入流,是HTTP协议中的实体内容
  8.  
  9.        ServletInputStream  sis=request.getInputStream();
  10.  
  11.      
  12.  
  13.        //缓冲区
  14.  
  15.        byte buffer[]=new byte[1024];
  16.  
  17.       
  18.  
  19.        FileOutputStream fos=new FileOutputStream("d:\\file.log");
  20.  
  21.       
  22.  
  23.        int len=sis.read(buffer, 0, 1024);
  24.  
  25.       
  26.  
  27.        //把流里的信息循环读入到file.log文件中
  28.  
  29.        while( len!=-1 )
  30.  
  31.        {
  32.  
  33.            fos.write(buffer, 0, len);
  34.  
  35.            len=sis.readLine(buffer, 0, 1024);
  36.  
  37.        }
  38.  
  39.       
  40.  
  41.        fos.close();
  42.  
  43.        sis.close();
  44.  
  45.       
  46.  
  47.     }
  48.  
  49.  

第二步:实现如下一个表单页面, 详细的代码如下:

  1. &lt;form action="servlet/ReceiveFile" method="post" enctype="multipart/form-data"&gt;
  2.  
  3.     第一个参数&lt;input type="text" name="name1"/&gt; &lt;br/&gt;
  4.  
  5.     第二个参数&lt;input type="text" name="name2"/&gt; &lt;br/&gt;
  6.  
  7.     第一个上传的文件&lt;input type="file" name="file1"/&gt; &lt;br/&gt;
  8.  
  9.     第二个上传的文件&lt;input type="file" name="file2"/&gt; &lt;br/&gt;
  10.  
  11.     &lt;input type="submit" value="提交"&gt;
  12.  
  13. &lt;/form&gt;

注意了,由于要上传附件,所以一定要设置enctype为multipart/form-data,才可以实现附件的上传。

第三步:填写完信息后按“提交”按钮后,在D盘下查找file.log文件用记事本打开,数据如下:

—————————–7d92221b604bc

Content-Disposition: form-data; name=”name1″

hello

—————————–7d92221b604bc

Content-Disposition: form-data; name=”name2″

world

—————————–7d92221b604bc

Content-Disposition: form-data; name=”file1″; filename=”C:\2.GIF”

Content-Type: image/gif

GIF89a

      €   € €€   €€ € €€€€€览?                                                                                     3  f       3  33 3f 3 3 3 f  f3 ff f f f   ? 檉 櫃 櫶 ?   ? 蘤 虣 烫 ?   3 f   3  3 33 f3 ? ? 33 33333f33?3?33f 3f33ff3f?f?f3 3?3檉3櫃3櫶3?3 3?3蘤3虣3烫3?3 333f3??f  f 3f ff 檉 蘤 f3 f33f3ff3檉3蘤3ff ff3fffff檉f蘤ff f?f檉f櫃f櫶f?f f?f蘤f虣f烫f?f f3fff檉蘤   3 f 櫃 虣 ? ?3?f?櫃3虣3檉 檉3檉f檉櫃f虣f櫃 櫃3櫃f櫃櫃櫶櫃櫶 櫶3櫶f櫶櫃烫櫶? ?3?f?櫃虣   3 f 櫶 烫 ? ?3?f?櫶3烫3蘤 蘤3蘤f蘤櫶f烫f虣 虣3虣f虣櫶櫶虣烫 烫3烫f烫櫶烫烫? ?3?f?櫶烫   3 f ? ? 3 333f3?3?3f f3fff?f?f ?檉櫃櫶??蘤虣烫? 3f??!?   ,   

  e   ??羵Q鸚M!C囑lH馉脝远5荑p釩?3R?R愣?MV39V5?谈re琷?试   3??qn?薵Q燚c?獖i郸EW艗赥戟j ;

—————————–7d92221b604bc

Content-Disposition: form-data; name=”file2″; filename=”C:\2.txt”

Content-Type: text/plain

hello everyone!!!

—————————–7d92221b604bc–

       从表单源码可知,表单上传的数据有4个:参数name1和name2,文件file1和file2

首先从file.log观察两个参数name1和name2的情况。这时候使用UltraEdit打开file.log(因为有些字符在记事本里显示不出来,所以要用16进制编辑器)

       结合16进制数据和记事本显示的数据可知上传参数部分的格式规律:

1.       第一行是“—————————–7d92221b604bc”作为分隔符,然后是“\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

2.       第二行

(1)       首先是HTTP中的扩展头部分“Content-Disposition: form-data;”,表示上传的是表单数据。

(2)       “name=”name1″”参数的名称。

(3)       “\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

3.       第三行:“\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

4.       第四行:参数的值,最后是“\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

由观察可得,表单上传的每个参数都是按照以上1—4的格式构造HTTP协议中的参数部分。

结合16进制数据和记事本显示的数据可知上传文件部分的格式规律:

1.       第一行是“—————————–7d92221b604bc”作为分隔符,然后是“\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

2.       第二行:

a)         首先是HTTP中的扩展头部分“Content-Disposition: form-data;”,表示上传的是表单数据。

b)        “name=”file2″;”参数的名称。

c)        “filename=”C:\2.txt””参数的值。

d)        “\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

3.       第三行:HTTP中的实体头部分“Content-Type: text/plain”:表示所接收到得实体内容的文件格式。计算机的应用中有多种多种通用的文件格式,人们为每种通用格式都定义了一个名称,称为 MIME,MIME的英文全称是”Multipurpose Internet Mail Extensions” (多功能Internet 邮件扩充服务)

4.       第四行:“\r\n”(即16进制编辑器显示的0D 0A)回车换行符。

5.       第五行开始:上传的内容的二进制数。

6.       最后是结束标志“—————————–7d92221b604bc–”,注意:这个结束标志和分隔符的区别是最后多了“–”部分。

但现在还有一个问题,就是分隔符“—————————–7d92221b604bc”是怎么确定的呢?是不是一定要“7d92221b604bc”这串数字?

        我们以前的分析只是观察了HTTP请求的实体部分,可以借用工具观察完整的HTTP请求看一看有没有什么线索?

  在IE下用HttpWatch,在Firefox下用Httpfox这个插件,可以实现网页数据的抓包,从图4可看出,原来在Content-Type部分指定了分隔符所用的字符串。

 
根据以上总结的注册表单中的参数传递和文件上传的规律,我们可以能写出Android中实现一个用户注册功能(包括个人信息填写和上传图片部分)的工具类,

首先,要有一个javaBean类FormFile封装文件的信息:

  1. public class FormFile {
  2.  /* 上传文件的数据 */
  3.  private byte[] data;
  4.  /* 文件名称 */
  5.  private String filname;
  6.  /* 表单字段名称*/
  7.  private String formname;
  8.  /* 内容类型 */
  9.  private String contentType = "application/octet-stream"; //需要查阅相关的资料
  10.  
  11.  public FormFile(String filname, byte[] data, String formname, String contentType) {
  12.   this.data = data;
  13.   this.filname = filname;
  14.   this.formname = formname;
  15.   if(contentType!=null) this.contentType = contentType;
  16.  }
  17.  
  18.  public byte[] getData() {
  19.   return data;
  20.  }
  21.  
  22.  public void setData(byte[] data) {
  23.   this.data = data;
  24.  }
  25.  
  26.  public String getFilname() {
  27.   return filname;
  28.  }
  29.  
  30.  public void setFilname(String filname) {
  31.   this.filname = filname;
  32.  }
  33.  
  34.  public String getFormname() {
  35.   return formname;
  36.  }
  37.  
  38.  public void setFormname(String formname) {
  39.   this.formname = formname;
  40.  }
  41.  
  42.  public String getContentType() {
  43.   return contentType;
  44.  }
  45.  
  46.  public void setContentType(String contentType) {
  47.   this.contentType = contentType;
  48.  }
  49.  
  50. }
  51.  

 
实现文件上传的代码如下:

/** 
 * 直接通过HTTP协议提交数据到服务器,实现表单提交功能 
 * @param actionUrl 上传路径 
 * @param params 请求参数 key为参数名,value为参数值 
 * @param file 上传文件 
 */ 
public static String post(String actionUrl, Map<String, String> params, FormFile[] files) {  
    try {             
        String BOUNDARY = “———7d4a6d158c9″; //数据分隔线  
        String MULTIPART_FORM_DATA = “multipart/form-data”;  
          
        URL url = new URL(actionUrl);  
        HttpURLConnection conn = (HttpURLConnection) url.openConnection();  
        conn.setDoInput(true);//允许输入  
        conn.setDoOutput(true);//允许输出  
        conn.setUseCaches(false);//不使用Cache  
        conn.setRequestMethod(”POST”);            
        conn.setRequestProperty(”Connection”, “Keep-Alive”);  
        conn.setRequestProperty(”Charset”, “UTF-8″);  
        conn.setRequestProperty(”Content-Type”, MULTIPART_FORM_DATA + “; boundary=” + BOUNDARY);  
 
        StringBuilder sb = new StringBuilder();  
          
        //上传的表单参数部分,格式请参考文章  
        for (Map.Entry<String, String> entry : params.entrySet()) {//构建表单字段内容  
            sb.append(”–”);  
            sb.append(BOUNDARY);  
            sb.append(”\r\n”);  
            sb.append(”Content-Disposition: form-data; name=\”"+ entry.getKey() + “\”\r\n\r\n”);  
            sb.append(entry.getValue());  
            sb.append(”\r\n”);  
        }  
        DataOutputStream outStream = new DataOutputStream(conn.getOutputStream());  
        outStream.write(sb.toString().getBytes());//发送表单字段数据  
         
        //上传的文件部分,格式请参考文章  
        for(FormFile file : files){  
            StringBuilder split = new StringBuilder();  
            split.append(”–”);  
            split.append(BOUNDARY);  
            split.append(”\r\n”);  
            split.append(”Content-Disposition: form-data;name=\”"+ file.getFormname()+”\”;filename=\”"+ file.getFilname() + “\”\r\n”);  
            split.append(”Content-Type: “+ file.getContentType()+”\r\n\r\n”);  
            outStream.write(split.toString().getBytes());  
            outStream.write(file.getData(), 0, file.getData().length);  
            outStream.write(”\r\n”.getBytes());  
        }  
        byte[] end_data = (”–” + BOUNDARY + “–\r\n”).getBytes();//数据结束标志           
        outStream.write(end_data);  
        outStream.flush();  
        int cah = conn.getResponseCode();  
        if (cah != 200) throw new RuntimeException(”请求url失败”);  
        InputStream is = conn.getInputStream();  
        int ch;  
        StringBuilder b = new StringBuilder();  
        while( (ch = is.read()) != -1 ){  
            b.append((char)ch);  
        }  
        outStream.close();  
        conn.disconnect();  
        return b.toString();  
    } catch (Exception e) {  
        throw new RuntimeException(e);  
    }  

posted @ 2011-06-09 16:26 ivaneeo 阅读(3322) | 评论 (0)编辑 收藏

一. 相同配置(set....)的 Configuration 可以考虑只在整个 Application 中共享同一个实例: 

Create a configuration instance

First you have to create a freemarker.template.Configuration instance and adjust its settings. A Configuration instance is a central place to store the application level settings of FreeMarker. Also, it deals with the creation and caching of pre-parsed templates.

Probably you will do it only once at the beginning of the application (possibly servlet) life-cycle:

二. 具有不同配置(set....)的 Configuration 应该建立相互独立的实例:

From now you should use this single configuration instance. Note however that if a system has multiple independent components that use FreeMarker, then of course they will use their own private Configuration instance.

三. 共享的 Configuration 实例有利于开启 MRU Cache 功能:

Multithreading

In a multithreaded environment Configuration instances, Template instances and data models should be handled as immutable (read-only) objects. That is, you create and initialize them (for example with set... methods), and then you don't modify them later (e.g. you don't call set...). This allows us to avoid expensive synchronized blocks in a multithreaded environment. Beware with Template instances; when you get a Template instance with Configuration.getTemplate, you may get an instance from the template cache that is already used by other threads, so do not call its set... methods (calling process is of course fine).

The above restrictions do not apply if you access all objects from the same single thread only.

四. 开启 MRU Cache 策略

Template caching

FreeMarker caches templates (assuming you use the Configuration methods to create Template objects). This means that when you call getTemplate, FreeMarker not only returns the resulting Template object, but stores it in a cache, so when next time you call getTemplate with the same (or equivalent) path, it just returns the cached Template instance, and will not load and parse the template file again.

cfg.setCacheStorage(new freemarker.cache.MruCacheStorage(20, 250))  

Or, since MruCacheStorage is the default cache storage implementation:

cfg.setSetting(Configuration.CACHE_STORAGE_KEY, "strong:20, soft:250");  

When you create a new Configuration object, initially it uses an MruCacheStorage where maxStrongSize is 0, and maxSoftSize is Integer.MAX_VALUE (that is, in practice, infinite). But using non-0 maxStrongSize is maybe a better strategy for high load servers, since it seems that, with only softly referenced items, JVM tends to cause just higher resource consumption if the resource consumption was already high, because it constantly throws frequently used templates from the cache, which then have to be re-loaded and and re-parsed.

五. MRU (Most Recently Used) Cache 自动更新模板内容的特性

If you change the template file, then FreeMarker will re-load and re-parse the template automatically when you get the template next time. However, since checking if the file has been changed can be time consuming, there is a Configuration level setting called ``update delay''. This is the time that must elapse since the last checking for a newer version of a certain template before FreeMarker will check that again. This is set to 5 seconds by default. If you want to see the changes of templates immediately, set it to 0. Note that some template loaders may have problems with template updating. For example, class-loader based template loaders typically do not notice that you have changed the template file.

六. MRU Cache 的两级缓存策略

A template will be removed from the cache if you call getTemplate and FreeMarker realizes that the template file has been removed meanwhile. Also, if the JVM thinks that it begins to run out of memory, by default it can arbitrarily drop templates from the cache. Furthermore, you can empty the cache manually with the clearTemplateCache method of Configuration.

The actual strategy of when a cached template should be thrown away is pluggable with the cache_storage setting, by which you can plug any CacheStorage implementation. For most users freemarker.cache.MruCacheStorage will be sufficient. This cache storage implements a two-level Most Recently Used cache. In the first level, items are strongly referenced up to the specified maximum (strongly referenced items can't be dropped by the JVM, as opposed to softly referenced items). When the maximum is exceeded, the least recently used item is moved into the second level cache, where they are softly referenced, up to another specified maximum. The size of the strong and soft parts can be specified with the constructor. For example, set the size of the strong part to 20, and the size of soft part to 250:

posted @ 2011-06-09 15:50 ivaneeo 阅读(727) | 评论 (0)编辑 收藏

今早一来,突然发现使用-put命令往HDFS里传数据传不上去了,抱一大堆错误,然后我使用bin/hadoop dfsadmin -report查看系统状态

admin@adw1:/home/admin/joe.wangh/hadoop-0.19.2>bin/hadoop dfsadmin -report
Configured Capacity: 0 (0 KB)
Present Capacity: 0 (0 KB)
DFS Remaining: 0 (0 KB)
DFS Used: 0 (0 KB)
DFS Used%: ?%

-------------------------------------------------
Datanodes available: 0 (0 total, 0 dead)

使用bin/stop-all.sh关闭HADOOP

admin@adw1:/home/admin/joe.wangh/hadoop-0.19.2>bin/stop-all.sh
stopping jobtracker
172.16.197.192: stopping tasktracker
172.16.197.193: stopping tasktracker
stopping namenode
172.16.197.193: no datanode to stop
172.16.197.192: no datanode to stop

172.16.197.191: stopping secondarynamenode

哦,看到了吧,发现datanode前面并没有启动起来。去DATANODE上查看一下日志

admin@adw2:/home/admin/joe.wangh/hadoop-0.19.2/logs>vi hadoop-admin-datanode-adw2.hst.ali.dw.alidc.net.log

************************************************************/
2010-07-21 10:12:11,987 ERROR org.apache.hadoop.hdfs.server.datanode.DataNode: java.io.IOException: Incompatible namespaceIDs in /home/admin/joe.wangh/hadoop/data/dfs.data.dir: namenode namespaceID = 898136669; datanode namespaceID = 2127444065
        at org.apache.hadoop.hdfs.server.datanode.DataStorage.doTransition(DataStorage.java:233)
        at org.apache.hadoop.hdfs.server.datanode.DataStorage.recoverTransitionRead(DataStorage.java:148)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.startDataNode(DataNode.java:288)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.<init>(DataNode.java:206)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.makeInstance(DataNode.java:1239)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.instantiateDataNode(DataNode.java:1194)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.createDataNode(DataNode.java:1202)
        at org.apache.hadoop.hdfs.server.datanode.DataNode.main(DataNode.java:1324)
......

错误提示namespaceIDs不一致。

下面给出两种解决办法,我使用的是第二种。

Workaround 1: Start from scratch

I can testify that the following steps solve this error, but the side effects won't make you happy (me neither). The crude workaround I have found is to:

1.     stop the cluster

2.     delete the data directory on the problematic datanode: the directory is specified by dfs.data.dir in conf/hdfs-site.xml; if you followed this tutorial, the relevant directory is /usr/local/hadoop-datastore/hadoop-hadoop/dfs/data

3.     reformat the namenode (NOTE: all HDFS data is lost during this process!)

4.     restart the cluster

When deleting all the HDFS data and starting from scratch does not sound like a good idea (it might be ok during the initial setup/testing), you might give the second approach a try.

Workaround 2: Updating namespaceID of problematic datanodes

Big thanks to Jared Stehler for the following suggestion. I have not tested it myself yet, but feel free to try it out and send me your feedback. This workaround is "minimally invasive" as you only have to edit one file on the problematic datanodes:

1.     stop the datanode

2.     edit the value of namespaceID in <dfs.data.dir>/current/VERSION to match the value of the current namenode

3.     restart the datanode

If you followed the instructions in my tutorials, the full path of the relevant file is /usr/local/hadoop-datastore/hadoop-hadoop/dfs/data/current/VERSION (background: dfs.data.dir is by default set to ${hadoop.tmp.dir}/dfs/data, and we set hadoop.tmp.dir to /usr/local/hadoop-datastore/hadoop-hadoop).

If you wonder how the contents of VERSION look like, here's one of mine:

#contents of <dfs.data.dir>/current/VERSION

namespaceID=393514426

storageID=DS-1706792599-10.10.10.1-50010-1204306713481

cTime=1215607609074

storageType=DATA_NODE

layoutVersion=-13

 

原因:每次namenode format会重新创建一个namenodeId,而tmp/dfs/data下包含了上次format下的id,namenode format清空了namenode下的数据,但是没有晴空datanode下的数据,导致启动时失败,所要做的就是每次fotmat前,清空tmp一下 的所有目录.

posted @ 2011-06-09 14:20 ivaneeo 阅读(561) | 评论 (0)编辑 收藏

  1. private void buildZK() {  
  2.         System.out.println("Build zk client");  
  3.         try {  
  4.             zk = new ZooKeeper(zookeeperConnectionString, 10000, this);  
  5.             Stat s = zk.exists(rootPath, false);  
  6.             if (s == null) {  
  7.                 zk.create(rootPath, new byte[0], ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);  
  8.                 zk.create(rootPath + "/ELECTION", new byte[0], ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);  
  9.             }  
  10.             String value = zk.create(rootPath + "/ELECTION/n_", hostAddress, ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL_SEQUENTIAL);  
  11.         } catch (Exception e) {  
  12.             e.printStackTrace();  
  13.             System.err.println("Error connect to zoo keeper");  
  14.         }  
  15.     }  
  16.   
  17.   
  18.     public void process(WatchedEvent event) {  
  19.         System.out.println(event);  
  20.         if (event.getState() == Event.KeeperState.Disconnected || event.getState() == Event.KeeperState.Expired) {  
  21.             System.out.println("Zookeeper connection timeout.");  
  22.             buildZK();  
  23.         }  
  24.   
  25.     }  
  26.  
posted @ 2011-06-09 13:38 ivaneeo 阅读(451) | 评论 (0)编辑 收藏