Linux基础知识_Shell编程笔记

本文介绍了 CentOS 6.5 版本中常用的系统管理和维护命令,包括文件操作、网络配置、用户管理、定时任务设置等,并提供了几个实用的 shell 脚本示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 以下是一些 常用功能 , 基于 centos 6.5 x64

# cp /etc/localtime /etc/localtime.org  
# rm /etc/localtime  
# ln -s /usr/share/zoneinfo/Asia/Shanghai /etc/localtime  

#启用中文支持
vim /etc/profile

export LC_ALL="zh_CN.UTF-8"
export LANG="zh_CN.UTF-8"
export LC_CTYPE="zh_CN.UTF-8"
# en_US.UTF-8 还原

source /etc/profile 

netstat -nltp #  查看进程及端口
kill -9 ****  #  杀死指定PID的进程

# 开机启动界面  ########################################
vim /etc/inittab  # 6.5版本以下
systemctl set-default graphical.target  # 7版本 设置图形界面启动
##################################

useradd test
passwd test
su test # su是用来切换用户,但是之前的用户依然是登录状态.
    # su不加参数是默认切到root, 缺点是用户需要知道root密码.
su - # 加了横线表示切换到root及根目录下.

#### sudo  则是为普通用户临时提供root权限. 
#### 当用户使用sudo命令时, 系统会寻找/etc/sudoers文件,判断该用户是否有执行sudo权限
vim /etc/sudoers # 为新用户添加sudo权限. 这样test用户才可以使用sudo 或者直接使用visudo命令

    test  ALL=(ALL)    ALL
### 用户  主机=(谁的身份)   命令 

    hadoop master=NOPASSWD: /bin/ls, /bin/cat # 只允许hadoop用户在master上免密执行ls, cat命令.
### 实际环境中,管理员会给普通用户配置sudo权限. 
    
userdel -r test
vim /etc/passwd #可以查看系统中的所有用户 
    root:x:0:0:root:/root:/bin/bash
    # 用户名:密码x:用户id0:组id0:描述信息root:用户根目录/root/:用户登录后的shell
    # x 是表示此处为空;采用shadow passwd,影子密码在 /etc/shadow 文件
    

# 命令别名定义
alias drm="rm -rf"  # drm 代表了命令rm -rf
unalias drm  # 删除别名
alias  # 查看别名

ls -lh  --time-style=+"%Y-%m-%d %H:%M:%S" # 设置显示文件时间戳

############################ network ###############################
vim /etc/sysconfig/network-scripts/ifcfg-eth0
    DEVICE="eth0"
    BOOTPROTO="static"
    HWADDR="00:0C:29:F5:05:8E"
    NM_CONTROLLED="yes"
    ONBOOT="yes"
    TYPE="Ethernet"
    IPADDR=192.168.112.10
    NETMASK=255.255.255.0
    GATEWAY=192.168.112.2
    DNS1=192.168.112.2
##可删除HWADDR,UUID
service network restart  # 重启网络服务

##网卡更换后,可编辑 vim /etc/udev/rules.d/70-persistent-net.rules
# 将最后一条末尾改为 eth0 ,其它的网卡信息删除后保存
reboot      # 重启
ifconfig    # 网络信息
curl www.baidu.com  # 得到某url

netstat #网络端口监听 -a显示所有选项, -t仅显示TCP, -u仅显示UDP, -l仅列出有监听的.
netstat -nltp

#修改hosts和主机名
# 修改/etc/hosts 以及/etc/sysconfig/network 文件, 分别设置不同的HOSTNAME
vim /etc/hosts
192.168.112.10 master
192.168.112.11 slave1
192.168.112.12 slave2

hostname master
vim /etc/sysconfig/network
HOSTNAME=master

### 关闭防火墙
service iptables stop  
setenforce 0  
chkconfig iptables off


######################################### 资源 情况 ####################
du -hs db  # 显示db文件夹总大小
du -hs     # 显示当前目录大小 也可以加 --max-depth=1
df -h      # disk info
df -hT     # disk info with FileSystem
df -h db   # 查看db文件夹所在分区的磁盘使用情况
free       # Memory
top        # 任务管理器

cat /dev/null > create_data_prod_py.log  # 清空这个日志文件


## 重定向  
## 0 (STDIN)   1 (STDOUT)   2 (STDERR) 
date > a.txt # 是重写内容
date >> a.txt # 是附加内容
wall < /etc/issue.net  # 输入重定向,广播了某文件的内容 
ls /temp 2> ls.err # 错误重定向,出错时写入文件  数字2代表错误输出 
cp -R /usr /backup/usr.bak 2> /bak.error  # 备份出错时,保存记录

write user # 向用户user 发送消息
wall  # 向所有用户发送消息


### 管道 
ll /etc | more # 将前一个命令的结果作为后一个命令的输入
ll /etc | grep init # 查看/etc下的以init筛选后的结果 
ll /etc | grep init | wc -l # 管道连用,查看上面的结果有多少行.


## 命令连接符 ;   &&    ||
pwd ; ls ; date # 就是类似于编程语言中分号的作用,命令依次执行。
ls && pwd  # 逻辑与,第一个命令成功,才会执行第二个命令。失败则不执行第二个。
ls || pwd  # 逻辑或,第一个命令成功,不执行第二个。失败则执行第二个。


## 命令替换符 将后边命令的输出作为前边命令的参数
ll `which java` # 找到java后,列出目录


## 如果要编译程序,通常需要安装依赖,可以一条命令多个组件.
yum install gcc gcc-c++ automake autoconf libtool openssl-devel pcre-devel -y 
## 以下是python2.7运行MySQLdb模块时,可能用到的:
yum install gcc gcc-c++ -y 
yum -y install mysql-devel  
yum install python-devel  
pip install --upgrade pip
pip install MySQL-python -i http://pypi.douban.com/simple --trusted-host pypi.douban.com

#################################  crontab  #################################

# crontab:
crontab -l #查看当前用户的crontab内容.
crontab -r #删除定时任务配置,如果不指定用户,则删除当前用户的.
crontab -e #编辑某个用户的crontab内容. 创建时也就先执行这个命令。
#crontab格式
#分 时 日 月 周 命令
0 0 * * * /shell/upFile2HDFS.sh   #每天0点执行一次

*/1 * * * * date >> /test/date.txt #每分钟将时间写入文件
 
30 21 * * * /usr/local/etc/rc.d/httpd restart #每天21:30执行一次命令

0,30 18-23 * * 6,0 /usr/local/etc/rc.d/httpd restart #每个周六,周日的18点到23点,每隔30分钟


# 不要忘记开启crond服务。
yum -y install crontabs   # 安装
service crond start       # 启动服务

nohup python -u myscript.py >> a.log &  #  指定脚本在后台运行。 nohup ... &

jobs -l       # 可查看nohup跑的进程 
ps -ef        # 通过进程查看
netstat -ntp  # 通过端口查看
#----------------------------------------------------------------------#
# 修改yum源为aliyun 
# 先备份:
  mv /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo.backup
# 下载配置文件 注意 centos版本
  wget -O /etc/yum.repos.d/CentOS-Base.repo http://mirrors.aliyun.com/repo/Centos-6.repo
  yum makecache  # 生成缓存
#----------------------------------------------------------------------#


lsb_release -a       # 查看发行版本号 如果需要安装 yum -y install redhat-lsb 
uname -a             # 查看内核版本
cat /etc/os-release  # 查看OS发行版
cat /etc/issue     # 查看发行版
ulimit -a            # 显示目前资源限制的设定
ulimit -n            # 打开文件描述符的最大值


# 参考: https://www.cnblogs.com/zhangmingcheng/p/6438994.html
View Code

设置时区时间相关

date -s "2018-01-01 14:22:33" # 修改时间 参数后面加字符串
clock -w # 写入硬件时钟
date -R #显示时区
tzselect #时区向导
cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime #修改时区

yum install ntp # 安装ntp服务
ntpdate pool.ntp.org  # ntp对时
chkconfig ntpd on
/etc/init.d/ntpd start  # centos7 改到了/sbin/ntpd
clock -w # 写入硬件时钟

vim /etc/rc.local #可设置开机启动项目 
#例如,在最后加上 /etc/init.d/mysqld start则可以启动mysqld
# centos7 若没有ifconfig,安装网络工具 ip addr yum -y install net-tools

# centos7 可以使用以下命令,安装大多数开发工具及依赖
yum groups info "Development Tools" # 查看
yum groups install "Development Tools" # 安装

rpm 命令:

rpm -qa |grep erlang      # 查找已安装的 erlang 相关软件
rpm -Uvh rabbitmq-server     # U 如果有旧版则升级安装
rpm -e --nodeps erlang-stdlib-R16B-03.18.el7.x86_64  # 卸载 忽略依赖,软件包

 

 

# 查找命令
find / -name tomcat  # 找tomcat

# 按常人理解的日期格式
ls -lh  --time-style=+"%Y-%m-%d %H:%M:%S" 

# 显示所有全局变量
export 

# shell多行注释
:<<!
被注释掉的内容
!d


\cp -rf . /opt/apps/screen-frontend/dist/ # \cp表示调用原生cp命令,-rf 表示递归处理及强制覆盖不提示 . 当前目录

 

Vim的操作:

############# vim ###########################################
命令模式下:
1)把光标移动到要复制的行上,按yy (复制当前行) 
2)把光标移动到要复制的位置 ,按p (粘贴到指定行)
3)把光标移动到要复制的位置 ,按dd(删除当前行)

移动光标: hjkl 左下上右
ctrl+u:到文件头
ctrl+d:到文件尾
shift+h:到屏幕第一行,shift+m:到屏幕中间,shift+l:到最后一行, shift+zz 保存退出
:n 到第n 行
^ 到行首,$ 到行尾 (这两个与正则一样)

查找: /xxx 查找xxx   n下一个,N上一个
替换  :%s/原/新   #这是全部替换

:r! pwd # 执行这个shell并将结果插入到当前行的下一行。

撤销更改:u:取消更改
插入:a从光标后,i从光标前,o从光标下一行

列操作,比如每行开头加注释
ESC, Ctrl + v 进入visual
数字5,再下箭头,即可向下选中5行。
shift + i 插入,# 再按2次ESC,即可在所有选中行前插入#
按d 即删除选中的部分



# Vim批量注释
ctrl+v 列编辑模式,上下移动光标,开头标记起来,按大写I(shift+i),插入注释符,比如"//",再Esc,就会全部注释
# 批量去掉注释
ctrl+v 列编辑模式,先上下,横向选中列的个数(如"//"注释符号,需要选中两列),然后按d, 就会删除注释符号

##配置文件 vim /etc/vimrc
set nu   # 行号
set ts=4 # tab距离4空格
set et   # tab转换为真正的空格

# modeline 相当于文件格式配置
# vim:et:ts=4:sw=4:
############# vim  end #########################################

 

shell编程容易让人掉坑的是,变量名和=之间不能有空格; 原生bash不支持简单数学运算,必须借助expr表达式工具等。 

对于习惯其它开发语言的人来说,这个shell的格式很容易让人出错。

想要掌握并记忆,还是要多写几次练习。

#!/bin/bash 

# 上面第一行是解释器   bash shell是Linux默认的免费的
## 通常会在第二行开始写脚本说明,作者,时间等。

#chmod +x hello.sh # 给全部用户加上执行权限 脚本的执行需要有x权限
#chmod u+x hello.sh #给当前用户加上执行权限 
chmod 755 hello.sh  # 所有者 所属组 其他人。 7 = 4+2+1 表示拥有"读/写/执行"的权限

cat /etc/shells #查看当前系统中的所有shell

## 执行脚本时 -x 参数可以看到具体拭执行过程

###################### shell 第一个例子:查看系统概况 ###################
# echo -e 参数可以识别字符串中的转义字符
#
!/bin/sh # auto mail for sys info /bin/date +%F >> /tmp/sysinfo # 日期信息写入临时文件 echo "disk info:" >> /tmp/sysinfo /bin/df -h >> /tmp/sysinfo # 真正的disk信息 echo >> /tmp/sysinfo # 显示空行 echo "online users:" >> /tmp/sysinfo /usr/bin/who | /bin/grep -v root >> /tmp/sysinfo # 列出所有用户,不看root echo >> /tmp/sysinfo echo "memory info:" >> /tmp/sysinfo /usr/bin/free -m >> /tmp/sysinfo echo >> /tmp/sysinfo # write root /usr/bin/write root < /tmp/sysinfo && /bin/rm /tmp/sysinfo #信息发给root,然后删除 # crontab -e # 0 9 * * 1-5 script ###################### end 第一个例子 ################################## ###################### 变量 #################################### name="abcde" # 变量名和=之间不能有空格 export a='aaaaa' #声明为全局变量 # 在a.sh中调用b.sh 写上source则表示在同一个进程中执行. source ./b.sh . ./b.sh # 也可用. 来代替source echo "${name}s a bcd." # 大括号确定了变量的边界 注意需要使用双引号;单引号则不会识别变量 readonly aa=1234 # 只读变量aa,不可修改 unset a ## 删除变量 ##局部变量仅能在当前会话中访问. set ##set命令可以查看环境变量 ###################### 变量参数 #################################### #脚本内获取参数的格式为$n n代表数字, 1第一个参数,2是第二个参数,以此类推... #特殊符号: $#参数个数, $*所有参数为一个字符串, $$脚本运行的当前进程ID, $!后台运行的最后一个进程ID, $@ 与$*相同,但是使用时加引号,在引号中返回每个参数. $? 显示最后命令状态, $*与$@区别: 是否被双引号包含. #!/bin/bash echo "脚本名称: $0"; echo "第一个参数: $1"; echo "参数个数: $#"; echo "传递的参数作为一个字符串: $*"; echo "进程号: $$"; echo "结束: $?"; ###################### 第二个例子: 备份 ################################## # $1 利用了位置参数. 例如执行 sh autobak.sh /usr 时,$1 即表示/usr #!/bin/bash # backup files by date DATE=`/bin/date +%Y%m%d` /bin/tar -cf /backup/$1.$DATE.tar $1 > /dev/null 2>> /backup/$1.bak.log /bin/gzip /backup/$1.$DATE.tar if [ $? -eq 0 ] then echo "$1 $DATE backup successful" >> /backup/$1.bak.log else echo "ERROR: failure $1 $DATE backup!" >> /backup/$1.bak.log fi # crontab -e # 0 3 * * 2,5 script ###################### 第二个例子: 备份 ################################## ################################ shell 运算符############################## # 原生bash不支持简单数学运算,可借助expr表达式工具以及``符号 ,完成求值. # 其实``叫命令替换符 val=`expr 2+3` #输出2+3 val=`expr 2 + 3` #输出5 val=`expr 2 \* 3` #输出6 乘法要转义 val=`expr 2 / 3` #除法 val=`expr 2 % 3` #取模 #也可以用$(())或$[] 进行算术运算 #!/bin/bash count=1 ((count++)) echo $count a=$((1+2)) b=$[3+4] echo $a $b # 关系运算符 简称: -eq等于, -nq不等于, -gt大于, -lt小于, -ge大于等于, -le小于等于 # 关系运算符只支持数据,不支持字符串,除非是数字形字符串 #!/bin/bash a=10 b=20 if [ $a -eq $b ] then echo "$a -eq $b : a等于b" else echo "$a -nq $b : a不等于b" fi if [ 1 -lt 5 ]; then echo OK; else echo notok; fi ##单行写法. # 布尔运算符 -a且 -o或 只需单层方括号 if [ $a -lt 100 -a $b -gt 15 ] then echo "$a 小于100且 $b 大于15 : 返回true" else echo "$a 不小于100或 $b 不大于15 : 返回false" fi # 逻辑运算符 && 及|| 需要双层方括号 if [[ $a -lt 100 || $b -gt 100 ]] then echo "返回true" else echo "返回false" fi # 字符串运算符 #!/bin/bash a="" b="abc" if [ -z $a ] # 字符串长度为0返回true then echo "长度0" else echo "长度非0" fi if [ -n $b ] # 字符串长度不为0返回true 和-z相反 then echo "长度不为0" else echo "长度为0" fi ## if [ $a ] #字符串是否存在 # 文件测试运算符 #!/bin/bash file="/test/1.sh" if [ -r $file ] # -r 可读, -w 可写, -x 可执行, -d 是否目录 -f是否文件 -e是否存在 then echo "文件可读" else echo "文件不可读" fi ############################# 流程控制 ################################### # 单if语句可以写成一行, 用;隔开,但也必须有fi结尾 if [ $(ps -ef | grep -c "ssh") -gt 1 ]; then echo "true"; fi # 查找当前系统中有多少个ssh进程 # 中间如果有多个判断用 elif ## read 用于从控制台读取输入. #!/bin/bash read -p "please input your name: " NAME if [ $NAME = root ] then echo "hello ${NAME}, welcome!" elif [ $NAME = itcast ] then echo "hello ${NAME}, Wlcm" else echo "SB, get out here." fi #### 注意空格不能少. ######## for循环,有几种写法 for N in 1 2 3; do echo $N; done #一句写完,循环3次 for N in {1..5}; do echo $N; done #一句写完,循环5次 for((i=0;i<=5;i++));do echo "welcome $i times"; done #和其它语言相近的写法. #或者: for((i=0;i<=5;i++)) do echo "welcome $i times" done ####### while #!/bin/bash i=1 while((i<=3)) do echo $i let i++ # let是bash中用于计算的工具,变量计算中不需加$ done ####### case #!/bin/bash echo '输入1到4之间的数字:' read aNum case $aNum in 1) echo '你选择了1' ;; 2) echo '你选择了2' ;; 3) echo '你选择了3' ;; 4) echo '你选择了4' ;; *) echo '你没有输入1到4之间的数' ;; esac #注意分支的半括号和双分号. ############################# 函数 ########################################## #函数必须在使用前定义, 函数名前面可以省略function. #参数返回,可加return,如果不加,会将最后一条命令的结果作为返回值. return后跟数值(0-255) #调用时直接写函数名即可. #!/bin/bash #fun2.sh funWithReturn(){ echo "此函数会对输入的两个数进行相加运算..." echo "输入第一个数:" read aNum echo "输入第二个数:" read bNum echo "两个数分别为 $aNum 和$bNum " return $(($aNum + $bNum)) } #funWithReturn #echo "两数之和为: $?" #!/bin/bash #caller.sh . /test/fun2.sh #跨脚本调用函数 funWithReturn ####### 函数传参 #!/bin/bash funWithParam(){ echo "第一个参数为 $1 " echo "第二个参数为 $2 " a=$4 b=$9 echo $(($a + $b)) echo "第10个参数为 $10 " echo "第十个参数为 ${10} " echo "第十一个参数为 ${11} " echo "参数总共有 $# " echo "作为一个字符串输出所有参数 $* " } funWithParam 1 2 3 4 5 6 7 8 9 34 73

 

 

模拟上传log文件到HDFS的shell示例:

假设logs/log/ 下的access.log文件是正在采集中的日志. 而后面带有数字的 access.log.1 文件是前一天的日志文件.

这个shell要做的是将前一天的日志都上传到hdfs上去. 如果结合crontab 就可以实现定时上传.

upload2hdfs.sh 文件: 

#!/bin/bash

#set java env
export JAVA_HOME=/usr/local/src/jdk1.8.0_161
export JRE_HOME=${JAVA_HOME}/jre
export CLASSPATH=.:${JAVA_HOME}/lib:${JRE_HOME}/lib
export PATH=${JAVA_HOME}/bin:$PATH
#set hadoop env
export HADOOP_HOME=/usr/local/src/hadoop-2.7.5
export PATH=${HADOOP_HOME}/bin:${HADOOP_HOME}/sbin:$PATH

#日志文件存放的目录
log_src_dir=/root/logs/log/

#待上传文件存放的目录
log_toupload_dir=/root/logs/toupload/

#日志文件上传到hdfs的根路径
date1=`date -d last-day +%Y_%m_%d`
hdfs_root_dir=/data/clickLog/$date1/

#打印环境变量信息
echo "envs: hadoop_home: $HADOOP_HOME"

#读取日志文件的目录,判断是否有需要上传的文件
echo "log_src_dir:" $log_src_dir
ls $log_src_dir | while read fileName
do 
    if [[ "$fileName" == access.log.* ]]; then
        date=`date +%Y_%m_%d_%H_%M_%S`
        #将文件移动到待上传目录并重命名
        #打印信息
        echo "moving $log_src_dir$fileName to $log_toupload_dir"xxxxx_click_log_$fileName"$date"
        mv $log_src_dir$fileName $log_toupload_dir"xxxxx_click_log_$fileName"$date
        #将待上传的文件path写入一个列表文件willDoing
        echo $log_toupload_dir"xxxxx_click_log_$fileName"$date >> $log_toupload_dir"willDoing."$date
    fi
done
#找到列表文件willDoing  ## grep -v是不包含
ls $log_toupload_dir | grep will | grep -v "_COPY_" | grep -v "_DONE_" | while read line
do
    #打印信息
    echo "toupload is in file:"$line
    #将待上传文件列表willDoing改名为winllDoing_COPY_
    mv $log_toupload_dir$line $log_toupload_dir$line"_COPY_"
    #读列表文件willDoing_COPY_的内容(一个一个的待上传文件名), 此处的line就是列表中的一个待上传文件的path
    cat $log_toupload_dir$line"_COPY_" | while read line
    do
        #打印信息
        echo "puting... $line to hdfs path...  $hdfs_root_dir"
        hdfs dfs -mkdir -p $hdfs_root_dir
        hdfs dfs -put $line $hdfs_root_dir
    done
    mv $log_toupload_dir$line"_COPY_" $log_toupload_dir$line"_DONE_"
done

 

假设hdfs在正常运行, 本地执行:

cd /root
mkdir -p logs/log

vim upload2hdfs.sh
# 将代码贴上, 检查各路径是否正确.  保存退出.

chmod 755 ./upload2hdfs.sh  # 给予执行权限.

./upload2hdfs.sh 

#等待成功执行完成后, 检查hdfs上是否有刚上传的文件. 

  

转载于:https://www.cnblogs.com/frx9527/p/bash.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值