Just mark it. :-)

#!/bin/sh
awk -F"_t_7_Y_" '{if($1==1) {printf $2; for(i=3;i<=NF;i++) if(i==NF) print $i;else printf $i}}' temp1  > 1.txt
awk -F"_t_7_Y_" '{if($1==2) if($2 in S22){S22[$2]=$2;S23[$2]=$3" "S23[$2];N2[$2]++}else {S22[$2]=$2;S23[$2]=$3;N2[$2]=1;} if($1==3) if($2 in S32){S32[$2]=$2;S33[$2]=$3" "S33[$2];N3[$2]++}else {S32[$2]=$2;S33[$2]=$3;N3[$2]=1;} if($1==4) if($2 in S42){S42[$2]=$2;S43[$2]=$3" "S43[$2];N4[$2]++}else {S42[$2]=$2;S43[$2]=$3;N4[$2]=1;} }END{for(i in S22) print S22[i],N2[i],S23[i]>>"2.txt";for(i in S32) print S32[i],N3[i],S33[i]>>"3.txt"; for(i in S42) print S42[i],N4[i],S43[i]>>"4.txt";}' temp1

awk 'NR==FNR {for(i=2;i<=NF;i++) S[$1]=S[$1]" "$i;}NR>FNR{print $0" "S[$1]}' 2.txt 1.txt > t1.txt
awk 'NR==FNR {for(i=2;i<=NF;i++) S[$1]=S[$1]" "$i;}NR>FNR{print $0" "S[$1]}' 3.txt t1.txt > t2.txt
awk 'NR==FNR {for(i=2;i<=NF;i++) S[$1]=S[$1]" "$i;}NR>FNR{print $0" "S[$1]}' 4.txt t2.txt > final.txt

| | Comments (0) | TrackBacks (0)

I have such a request, will rewrite url to google's search site,
type http://mysite/search/search.html?t=laday gaga --> http://www.google.com/search?q=lady%20gaga
I donn't want to use other tools(php/java etc.) except nginx.
For a long time googleing, finally find how to setting nginx dynamic url rewrite :)

 location /search/ {
  root   /var/2hei.net/nginx;
  if ($args){
  rewrite ^/search/search.html "http://www.google.com/search?q=$arg_t?" last;
  }
 }

and '?' is very important, or the rewrite url will add append query string,
http://mysite/search/search.html?t=laday gaga --> http://www.google.com/search?q=lady%20gaga?t=lady%20gaga
we will get wrong rewrite url.
alse we can use $query_string
 if ($query_string ~* t=(.*)){
  ...
 }


Just enjoy it!

| | Comments (0) | TrackBacks (0)
    I see there are so many api to operate memcached,such as get and set,but no list all items,so i write a shell just list all the items in memcached and we can delete the items when we don't know the exactly items key.


#!bin/bash
# get_items_from_memcached.sh
# Usge: sh get_items_from_memcached.sh localhost port
# Exp:  sh get_items_from_memcached.sh 2hei.net 11211
# By: @2hei.net


items=`echo "stats items" | nc $1 $2|grep number|awk -F: '{print $2}'|awk '{printf("%s ",$1) }'`
for i in ${items}
  do
    #get delete_items_list
    echo "stats cachedump $i 0" | nc $1 $2|awk -v HOST=$1 -v PORT=$2 '{if(length($2)>0) print "echo delete",$2," | nc",HOST,PORT}' >> $1_$2.txt
    #print all items
    echo "stats cachedump $i 0" | nc $1 $2|awk '{if($2) print $2}'
  done


##delete all items by item_list if needed
#/bin/sh $1_$2.txt

##END##


tips:
1. you just can use "flush_all" cmd
   echo "flush_all" | nc $1 $2
   
   "flush_all" is a command with an optional numeric argument. It always
succeeds, and the server sends "OK\r\n" in response (unless "noreply"
is given as the last parameter). Its effect is to invalidate all
existing items immediately (by default) or after the expiration specified.
   flush_all doesn't actually free all the memory taken up by existing items; that
will happen gradually as new items are stored. The most precise
definition of what flush_all does is the following: it causes all
items whose update time is earlier than the time at which flush_all
was set to be executed to be ignored for retrieval purposes.

2. if your memcached has to many items, this shell will waste a long time, for it will establish a new connection when delete each time.
we can use other tools write by socket and do this in only one connection.
| | Comments (0) | TrackBacks (0)
Scripts and executables must do two things (at a minimum) in order to function as Nagios plugins:
1.Exit with one of several possible return values
2.Return at least one line of text output to STDOUT

Plugin Return Code Service State Host State
0 OK UP
1 WARNING UP or DOWN/UNREACHABLE*
2 CRITICAL DOWN/UNREACHABLE
3 UNKNOWN DOWN/UNREACHABLE
Note: If the use_aggressive_host_checking option is enabled, return codes of 1 will result in a host
state of DOWN or UNREACHABLE. Otherwise return codes of 1 will result in a host state of UP.

Plugin Output Spec
At a minimum, plugins should return at least one of text output. Beginning with Nagios 3, plugins can
optionally return multiple lines of output. Plugins may also return optional performance data that can
be processed by external applications. The basic format for plugin output is shown below:
TEXT OUTPUT | OPTIONAL PERFDATA
LONG TEXT LINE 1
LONG TEXT LINE 2
...
LONG TEXT LINE N | PERFDATA LINE 2
PERFDATA LINE 3
...
PERFDATA LINE N

this is my python scripts:
#!/usr/bin/evn python
# -*- coding: utf-8 -*-

import sys,getopt
import memcache

memcached_host='2hei.net'
memcached_port=11211
Warning_item=120
Critical_item=20

def usage():
    print """
Usage: check_memcached [-h|--help] [-w|--warning curr_items] [-c|--critical curr_items]"
Warning curr_items defaults to 120
Critical curr_items defaults to 20
"""
    sys.exit(3)

#get curr_items from memcache stats
def get_memcache_curr_items(mc):
    #mc = memcache.Client([memcached_host+':'+str(memcached_port)], debug=0)
    stats = mc.get_stats()[0][1]   
    #for i in xrange(0,100):
    #    mc.set('key'+str(i),'value'+str(i))
    #for k,v in stats.items():
    #    print k,v
    items = stats.get('curr_items')
    return items

if __name__ == "__main__":
    warning_item = 0
    critical_item = 0

    try:
        options, args = getopt.getopt(sys.argv[1:],"h:w:c:","--help --warning= --critical=",)
    except getopt.GetoptError:
        usage()
        sys.exit(3)

    try:
        mc = memcache.Client([memcached_host+':'+str(memcached_port)], debug=0)
        items = get_memcache_curr_items(mc)
        mc.disconnect_all()
    except Exception:
        print "Cannot get memcache's curr_items.",Exception
        sys.exit(3)

    for name, value in options:
        if name in ("-h", "--help"):
            usage()
            sys.exit(3)
        if name in ("-w", "--warning"):
            warning_item = value
        if name in ("-c", "--critical"):
            critical_item = value

    if warning_item == 0:
        warning_item = Warning_item
    if critical_item == 0:
        critical_item = Critical_item

    if int(items) <= int(critical_item):
        print 'MEMCACHED_ITEM CRITICAL: curr_items is:',items
        sys.exit(2)
    if int(items) <= int(warning_item):
        print 'MEMCACHED_ITEM WARNING: curr_items is:',items
        sys.exit(1)
    else:
        print 'MEMCACHED_ITEM OK: curr_items is:',items
        sys.exit(0)

when encounter errors:
CHECK_NRPE: No output returned from daemon.
or
CHECK_NRPE: Received 0 bytes from daemon.  Check the remote server logs for error messages.
this shows your plugins return output is null

| | Comments (0) | TrackBacks (0)
we have two ways:

1. finding netcard driver by syslog
grep -i 'driver' /var/log/messages
or
dmesg | grep -i driver

2.lsmod  
#try to find netcard type.

[root@2hei.net]# modinfo e1000
filename:       /lib/modules/2.6.9-34.ELsmp/kernel/drivers/net/e1000/e1000.ko
parm:           debug:Debug level (0=none,...,16=all)
version:        6.1.16-k3-NAPI 4BCC06D27AAC4C711223CC9
license:        GPL
description:    Intel(R) PRO/1000 Network Driver
author:         Intel Corporation, <linux.nics@intel.com>


[root@2hei.net]# modinfo igb
filename:       /lib/modules/2.6.18-164.11.1.el5/kernel/drivers/net/igb/igb.ko
version:        1.3.16-k2
license:        GPL
description:    Intel(R) Gigabit Ethernet Network Driver
author:         Intel Corporation, <e1000-devel@lists.sourceforge.net>
srcversion:     78555F0A019E05BADBD95AA

[root@2hei.net]# modinfo bonding
filename:       /lib/modules/2.6.18-164.11.1.el5/kernel/drivers/net/bonding/bonding.ko
author:         Thomas Davis, tadavis@lbl.gov and many others
description:    Ethernet Channel Bonding Driver, v3.4.0
version:        3.4.0
license:        GPL
srcversion:     7989A7EEF2EE7B5D78C0E79
depends:        ipv6
vermagic:       2.6.18-164.11.1.el5 SMP mod_unload gcc-4.1
| | Comments (1) | TrackBacks (0)
require : python2.6 pytz

#!/usr/bin/env python
# -*- coding: gbk -*-
from datetime import datetime, timedelta
from time import gmtime, strftime
from pytz import timezone
import pytz, time,os

#def convert_datetime(unix_timestamp=1143408000, tz=1, long_fmt=1):
def convert_datetime(dt='2007-01-01 00:00:00', tz='', dest_fmt='', time_stamp=0):
    fmt      = '%Y-%m-%d %H:%M:%S'
    if time_stamp == 0:
        dt_stamp = time.mktime(time.strptime(dt, fmt))
    else:
        dt_stamp = float(dt)
    utc      = pytz.utc
    utc_dt   = datetime.utcfromtimestamp(dt_stamp).replace(tzinfo=utc)  
    dest_tz  = timezone(tz)
    dest_dt  = dest_tz.normalize(utc_dt.astimezone(dest_tz))  
    return dest_dt.strftime(dest_fmt)

#define all citys here
citys = {'Asia/Shanghai':'Asia/Shanghai 上 海',
        'America/Los_Angeles':'America/Los_Angeles 旧金山',
        'Etc/GMT':'Etc/GMT 格林威治标准时间',
        'US/Pacific':'US/Pacific PT 太平洋时间',
        'UTC':'UTC 世界标准时间',
        #'Etc/GMT+8':'Etc/GMT+8',
       }
 
if __name__ == '__main__':
    while True:
        os.system('cls')
        print '--------------时间对照--------------'
        for k,v in citys.items():
            print convert_datetime(dt=strftime("%Y-%m-%d %H:%M:%S", time.localtime()), tz=k,dest_fmt='%Y-%m-%d %H:%M:%S'),'\t['+v+']'
        print '------------------------------------'
        time.sleep(1)

       
run.bat
set path=D:\python26\;%path%
D:
cd D:\Profiles\2hei.net\eclipse-project\py\myapp\src\time_format
python world_time.py

running like this:

world_time_zone.png













 

| | Comments (0) | TrackBacks (0)
notice Hostnames should not contain an '_':
such as vm_test01.2hei.net
Please have a look at RFC952 (http://tools.ietf.org/html/rfc952) Hostnames should not contain an '_'!

ASSUMPTIONS:

   1. A "name" (Net, Host, Gateway, or Domain name) is a text string up
   to 24 characters drawn from the alphabet (A-Z), digits (0-9), minus
   sign (-), and period (.).  Note that periods are only allowed when
   they serve to delimit components of "domain style names". (See
   RFC-921, "Domain Name System Implementation Schedule", for
   background).  No blank or space characters are permitted as part of a
   name. No distinction is made between upper and lower case.  The first
   character must be an alpha character.  The last character must not be
   a minus sign or period.  A host which serves as a GATEWAY should have
   "-GATEWAY" or "-GW" as part of its name.  Hosts which do not serve as
   Internet gateways should not use "-GATEWAY" and "-GW" as part of
   their names. A host which is a TAC should have "-TAC" as the last
   part of its host name, if it is a DoD host.  Single character names
   or nicknames are not allowed.
| | Comments (0) | TrackBacks (0)
cat /proc/mdstat

Personalities : 
[raid1] read_ahead 1024 sectors 
md1 : active raid1 sda3[0] sdb3[1] 522048 blocks [2/2] [U_] 
md0 : active raid1 sda2[0] sdb2[1] 4192896 blocks [2/2] [U_] 
md2 : active raid1 sda1[0] sdb1[1] 128384 blocks [2/2] [U_] 
unused devices: <none> 

this shows disk hdb failed!  we will replace it.

work follow it:

Replacing A Failed Hard Drive In A Software RAID1 Array
Version 1.0 
Author: Falko Timme <ft [at] falkotimme [dot] com> 
Last edited 01/21/2007

This guide shows how to remove a failed hard drive from a Linux RAID1 array (software RAID), and how to add a new hard disk to the RAID1 array without losing data.

I do not issue any guarantee that this will work for you!

 

1 Preliminary Note
In this example I have two hard drives, /dev/sda and /dev/sdb, with the partitions /dev/sda1 and /dev/sda2 as well as /dev/sdb1 and /dev/sdb2.

/dev/sda1 and /dev/sdb1 make up the RAID1 array /dev/md0.

/dev/sda2 and /dev/sdb2 make up the RAID1 array /dev/md1.

/dev/sda1 + /dev/sdb1 = /dev/md0

/dev/sda2 + /dev/sdb2 = /dev/md1

/dev/sdb has failed, and we want to replace it.

 

2 How Do I Tell If A Hard Disk Has Failed?
If a disk has failed, you will probably find a lot of error messages in the log files, e.g. /var/log/messages or /var/log/syslog.
You can also run
cat /proc/mdstat
and instead of the string [UU] you will see [U_] if you have a degraded RAID1 array.
 

3 Removing The Failed Disk
To remove /dev/sdb, we will mark /dev/sdb1 and /dev/sdb2 as failed and remove them from their respective RAID arrays (/dev/md0 and /dev/md1).
First we mark /dev/sdb1 as failed:
mdadm --manage /dev/md0 --fail /dev/sdb1
The output of
cat /proc/mdstat
should look like this:

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0] sdb1[2](F)
      24418688 blocks [2/1] [U_]

md1 : active raid1 sda2[0] sdb2[1]
      24418688 blocks [2/2] [UU]

unused devices: <none>

Then we remove /dev/sdb1 from /dev/md0:

mdadm --manage /dev/md0 --remove /dev/sdb1

The output should be like this:

server1:~# mdadm --manage /dev/md0 --remove /dev/sdb1
mdadm: hot removed /dev/sdb1

And

cat /proc/mdstat

should show this:

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0]
      24418688 blocks [2/1] [U_]

md1 : active raid1 sda2[0] sdb2[1]
      24418688 blocks [2/2] [UU]

unused devices: <none>

Now we do the same steps again for /dev/sdb2 (which is part of /dev/md1):

mdadm --manage /dev/md1 --fail /dev/sdb2

cat /proc/mdstat

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0]
      24418688 blocks [2/1] [U_]

md1 : active raid1 sda2[0] sdb2[2](F)
      24418688 blocks [2/1] [U_]

unused devices: <none>


mdadm --manage /dev/md1 --remove /dev/sdb2

server1:~# mdadm --manage /dev/md1 --remove /dev/sdb2
mdadm: hot removed /dev/sdb2

cat /proc/mdstat

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0]
      24418688 blocks [2/1] [U_]

md1 : active raid1 sda2[0]
      24418688 blocks [2/1] [U_]

unused devices: <none>

Then power down the system:

shutdown -h now

and replace the old /dev/sdb hard drive with a new one (it must have at least the same size as the old one - if it's only a few MB smaller than the old one then rebuilding the arrays will fail).

 
4 Adding The New Hard Disk
After you have changed the hard disk /dev/sdb, boot the system.
The first thing we must do now is to create the exact same partitioning as on /dev/sda. We can do this with one simple command:
sfdisk -d /dev/sda | sfdisk /dev/sdb
You can run
fdisk -l
to check if both hard drives have the same partitioning now.
Next we add /dev/sdb1 to /dev/md0 and /dev/sdb2 to /dev/md1:
mdadm --manage /dev/md0 --add /dev/sdb1

server1:~# mdadm --manage /dev/md0 --add /dev/sdb1
mdadm: re-added /dev/sdb1
mdadm --manage /dev/md1 --add /dev/sdb2
server1:~# mdadm --manage /dev/md1 --add /dev/sdb2
mdadm: re-added /dev/sdb2

Now both arays (/dev/md0 and /dev/md1) will be synchronized. Run

cat /proc/mdstat
to see when it's finished.
During the synchronization the output will look like this:

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0] sdb1[1]
      24418688 blocks [2/1] [U_]
      [=>...................]  recovery =  9.9% (2423168/24418688) finish=2.8min speed=127535K/sec

md1 : active raid1 sda2[0] sdb2[1]
      24418688 blocks [2/1] [U_]
      [=>...................]  recovery =  6.4% (1572096/24418688) finish=1.9min speed=196512K/sec

unused devices: <none>
When the synchronization is finished, the output will look like this:

server1:~# cat /proc/mdstat
Personalities : [linear] [multipath] [raid0] [raid1] [raid5] [raid4] [raid6] [raid10]
md0 : active raid1 sda1[0] sdb1[1]
      24418688 blocks [2/2] [UU]

md1 : active raid1 sda2[0] sdb2[1]
      24418688 blocks [2/2] [UU]

unused devices: <none>

That's it, you have successfully replaced /dev/sdb!
| | Comments (0) | TrackBacks (0)
虚拟机上最小化安装centos5.3,传文件时发现非常方便的rz 和sz没有安装上,于是手工安装。

wget http://mirrors.163.com/centos/5/os/i386/CentOS/lrzsz-0.12.20-22.1.i386.rpm
(一个好消息是163和sohu都有了开源镜像哦,速度飞快!)

rpm ivh lrzsz-0.12.20-22.1.i386.rpm

或者直接用yum安装。
yum install lrzsz

then in your securecrt or xshell terminal:

sz filename
rz
 

| | Comments (0) | TrackBacks (0)

python版本:2.6

案例一: test.xml
<?xml version="1.0" encoding="utf8"?>
调用:
xmldoc = minidom.parse(test.xml)
报错:
Traceback (most recent call last):
  File "D:\project\src\myapp\src\xml\testdomxml.py", line 14, in <module>
    xmldoc = minidom.parse(response)
  File "D:\Python\lib\xml\dom\minidom.py", line 1918, in parse
    return expatbuilder.parse(file)
  File "D:\Python\lib\xml\dom\expatbuilder.py", line 928, in parse
    result = builder.parseFile(file)
  File "D:\Python\lib\xml\dom\expatbuilder.py", line 207, in parseFile
    parser.Parse(buffer, 0)
xml.parsers.expat.ExpatError: unknown encoding: line 1, column 30


修改后:test2.xml
<?xml version="1.0" encoding="utf-8"?>
再次调用
xmldoc = minidom.parse(test2.xml)
没有问题了。 囧一个!

详细可见python bug 列表: http://bugs.python.org/msg63471


案例二:
xmldoc = minidom.parse(urllib.urlopen('http://rss.sina.com.cn/news/marquee/ddt.xml'))
正常调用

xmldoc = minidom.parse(urllib.urlopen('http://news.163.com/special/00011K6L/rss_newstop.xml''))
报错:
  File "D:\Python\lib\xml\dom\expatbuilder.py", line 207, in parseFile
    parser.Parse(buffer, 0)
xml.parsers.expat.ExpatError: unknown encoding: line 1, column 30

观察sina和163的两个rss源文件看,并未发现特别的异常,不过将163的保存为文件rssnew163.xml,在其头部添加
<?xml version="1.0" encoding="utf-8"?>
然后再调用
xmldoc = minidom.parse("rssnew163.xml")
问题解决,看来还是字符编码的问题了。
对于使用urllib实时更新rss的就需要预先处理一下了,先保存rss文件,然后添加上述行,或者将xml文件转换成utf-8编码即可。

| | Comments (3) | TrackBacks (0)

一、16进制转换成10进制
printf %d 0xF
15
或者
echo $((16#F))
15

二、10进制转换成16进制
printf %x 15
f
或者
echo "obase=16;15"|bc
F

三、10进制转换成8进制
printf %o 9
11

四、8进制转换成10进制
echo $((8#11))
9

五、同理二进制转换成10进制
echo $((2#111))
7

六、10进制转换成二进制
echo "obase=2;15"|bc
1111

| | Comments (0) | TrackBacks (0)

resin的配置文件类似xml,语法规范也遵循xml的写法,今天遇到了特殊字符的问题,数据库密码包含了特殊字符。
<init-param driver-name="oracle.jdbc.driver.OracleDriver"/>
  <init-param url="jdbc:oracle:thin:@localhost:1521:Test"/>
  <init-param user="username"/>
  <init-param password="123&(45aq"/>
...
</resource-ref>

#sh start_server.sh
Starting Resin on Thu, 22 Apr 2010 18:39:48 +0800 (CST)
com.caucho.xml.XmlParseException: /home/resin/conf/resin.conf:8: malformed entity ref at `('
        at com.caucho.xml.XmlParser.error(XmlParser.java:2769)
        at com.caucho.xml.XmlParser.parseCharacterReference(XmlParser.java:1002)
        at com.caucho.xml.XmlParser.parseValue(XmlParser.java:1192)
        at com.caucho.xml.XmlParser.parseAttributes(XmlParser.java:702)
        at com.caucho.xml.XmlParser.parseElement(XmlParser.java:603)
        at com.caucho.xml.XmlParser.parseNode(XmlParser.java:377)
        at com.caucho.xml.XmlParser.parseInt(XmlParser.java:248)
        at com.caucho.xml.AbstractParser.parse(AbstractParser.java:645)
        at com.caucho.util.Registry.parse(Registry.java:199)
        at com.caucho.util.Registry.parse(Registry.java:174)
        at com.caucho.server.http.ResinServer.init(ResinServer.java:311)
        at com.caucho.server.http.ResinServer.main(ResinServer.java:1176)


其原因并不是“(”引起的,罪魁祸首是“&”

解决办法是使用&amp;替换&
如:
  <init-param password="123&amp;(45aq"/>


xml文件中其他的几个特殊字符做同样处理即可:
    * &amp; = & (ampersand)
    * &lt; = < (left angle bracket, less-than sign)
    * &gt; = > (right angle bracket, greater-than sign)
    * &quot; = " (quotation mark)
    * &apos; = ' (apostrophe)

| | Comments (1) | TrackBacks (0)