# ls /easy/test/info/ -> bin mytest.jar
# ls /easy/test/info/bin/ -> spring-boot.sh
#!/bin/bash
# 环境索引: 标识解释器为bash ./当前文件 等同于 sh 当前文件
# 本次解析执行命令= ./easy/test/info/bin/spring-boot.sh start
JAVA_OPTIONS_INITIAL=-Xms500M
JAVA_OPTIONS_MAX=-Xmx1000M
# 定义变量: 注意=左右不要有空格
BINPATH=$(cd `dirname $0`; pwd)
# 获取脚本所在的项目名称
# $0 获取当前脚本本身的名字,其他包执行则包含到当前文件的路径
# dirname 命令去除文件名中的非目录部分,仅显示与目录有关的内容
# $()和反引号``的作用结果相同都是用来作命令替换的,通俗来讲就是把命令执行后的结果作为参数返回
# pwd 命令用于显示工作目录的绝对路径名称
# 先执行 dirname $0 获取当前目录名称,
# 再执行cd 切换到当前目录,
# ; 分号; 用分号隔开两个命令
# 再执行pwd, 用BINPATH 接受pwd返回结果.
# $0 ==> ./easy/test/info/bin/spring-boot.sh
# `dirname $0` ==> ./easy/test/info/bin/
# BINPATH==> /easy/test/info/bin
if [ $(ls ${BINPATH%/bin*}|grep .*.jar|wc -l) -gt 1 ] ;then
# 字符串截取: ${parameter%word} # 删除匹配后缀
# ${BINPATH%/bin*} 获取BINPATH 删除/bin 后面部分
# grep 匹配
# wc 计数
# -gt 大于
# if 流程判断
# 获取脚本上级的.jar 结尾文件是否>1个.
echo "目录中含有多个jar文件"
exit 0
fi
_JAR_KEYWORDS=$(ls ${BINPATH%/bin*}|grep .*.jar)
# 获取当前jar包名称(mytest.jar)
if [ "$_JAR_KEYWORDS" = "" ] ;then
echo "${BINPATH%/bin*}下未找到jar包!!"
exit 0
fi
APP_NAME=${_JAR_KEYWORDS%.jar*}
# 字符串截取: ${parameter%word} # 删除匹配后缀
# ${_JAR_KEYWORDS%.jar*} 去掉jar包的.jar后缀, 赋值给appName字段(mytest)
if [ $1 == "start" ] ;then
echo "当前启动的项目为:$APP_NAME,项目所在目录:${BINPATH%/bin*}"
fi
# 查询进程,去掉grep查询, 取第二位(pid)
PID=$(ps aux | grep ${_JAR_KEYWORDS} | grep -v grep | awk '{print $2}' )
# ps 进程查看
# | grep -v grep 排除grep 进程,即当前的ps查询进程
# awk 行处理器, awk '{print $2}' 输出第2行数据, 即pid行.
function check_if_process_is_running {
if [ "$PID" = "" ]; then
return 1
fi
ps -p $PID | grep "java"
# ps 进程查看, 根据pid查看进程
return $?
# $? 上一指令的返回值,成功是0,不成功是1。
}
case "$1" in
status)
# case 选择命令
# $1 执行该文件的第一个参数.
if check_if_process_is_running
then
echo -e "\033[32m $APP_NAME is running \033[0m"
# echo -e 转义输出
# \033[xm 控制字符 \033[32m 指定当前文本绿色展示.
else
echo -e "\033[32m $APP_NAME not running \033[0m"
fi
;;
stop)
if ! check_if_process_is_running
then
echo -e "\033[32m $APP_NAME already stopped \033[0m"
exit 0
fi
kill -9 $PID
# kill 杀死指定进程
echo -e "\033[32m Waiting for process to stop \033[0m"
NOT_KILLED=1
for i in {1..20}; do
if check_if_process_is_running
then
echo -ne "\033[32m . \033[0m"
# echo -ne 转义输出, 不进行换行
sleep 1
else
NOT_KILLED=0
fi
done
echo
if [ $NOT_KILLED = 1 ]
then
echo -e "\033[32m Cannot kill process \033[0m"
exit 1
fi
echo -e "\033[32m $APP_NAME already stopped \033[0m"
;;
start)
if [ "$PID" != "" ] && check_if_process_is_running
then
echo -e "\033[32m $APP_NAME already running \033[0m"
exit 1
fi
cd ${BINPATH%/bin*}
JAVA_MEM_SIZE_OPTS="-Xmx256m -Xms128m -Xmn256m -XX:PermSize=200m -XX:MaxPermSize=200M -Xss256k"
JAVA_MEM_OPTS=" -server $JAVA_MEM_SIZE_OPTS -XX:SurvivorRatio=2 -XX:+UseParallelGC "
nohup java -jar $JAVA_OPTIONS_INITIAL $JAVA_OPTIONS_MAX $_JAR_KEYWORDS --debug> 123.log 2>&1 &
#nohup 不挂起执行
echo -ne "\033[32m Starting \033[0m"
for i in {1..20}; do
# 通配符(globbing) {1..20} 循环20次,分别取1,2,3...19,20
echo -ne "\033[32m.\033[0m"
sleep 1
done
if check_if_process_is_running
then
echo -e "\033[32m $APP_NAME fail \033[0m"
else
echo -e "\033[32m $APP_NAME started \033[0m"
fi
;;
restart)
$0 stop
# 重新执行该文件, 传递参数为 stop
if [ $? = 1 ]
then
exit 1
fi
$0 start
# 重新执行该文件, 传递参数为 start
;;
*)
# case 未匹配, 走的默认模组
echo "Usage: $0 {start|stop|restart|status}"
exit 1
esac
exit 0
环境索引
开头"#!/bin/bash"作用
这行注释的作用就是声明解析当前文件要使用的解释器
执行: sh xxx
执行: ./xxx(等同于 sh xxx)
执行: ./xxx(等同于 cat xxx)
变量定义和使用
定义变量, 变量名不加美元符号$
your_name="easy.com"
注意,变量名和等号之间不能有空格,这可能和你熟悉的所有编程语言都不一样。
在变量名前面加美元符号即可:
your_name="qinjx"
echo $your_name
echo ${your_name}
变量名外面的花括号可选,加花括号是为了帮助解释器识别变量的边界,比如下面这种情况
for skill in Ada Coffe Action Java; do
echo "I am good at ${skill}Script" # 识别为: skill
echo "I am good at $skillScript" # 自动识别为: skillScript
done
linux中$用法
$0:bash文件名。
$?:上一指令的返回值,成功是0,不成功是1。
$1,$2,$3....:表示命令后接的第几个参数
${var_name} 跟光$var_name差不多
但是用${ }会比较精确的界定变量名称的范围。
在bash中,$( )与` `(反引号)都是用来作命令替换的,执行括号或者反引号中的命令, 然后返回结果。
比如:echo "present dir is $(pwd)"
但是$()和``还是稍有不同的,在多层次的复合替换中,``必须要额外的跳脱处理(反斜线),而$( )则不用,比较直观。
# 将cmd1执行结果作为cmd2参数,再将cmd2结果作为cmd3的参数
cmd1 $(cmd2 $(cmd3))
# 如果是用反引号,直接引用是不行的,还需要作跳脱处理
cmd1 `cmd2 \`cmd3\``
Linux 特殊字符用法(;,|,&,||,&&)
; 分号; 用分号隔开两个命令,每条命令按照从左到右的顺序,顺序执行,彼此之间不关心是否失败,所有命令都会执行。
| 管道符; 上一条命令的输出,作为下一条命令参数
示例: grep "123" 1.txt | wc -l
& 放在启动命令参数后面表示设置此进程为后台进程
|| 逻辑或
只有在 || 左边的命令返回假,右边的命令才会被执行。
只要有一个命令返回真,后面的命令都不会被执行。一直到返回真的地方停止执行
&& 逻辑与
前一条命令执行成功,才会执行下一条命令。
linux ${}文本处理
将字符串变量a从第b个位置开始向后截取c个字符,b是指下标,下标从0开始
将变量a中的b全部替换为c,开头一个正斜杠为只匹配第一个字符串,两个正斜杠为匹配所有字符。
b支持正则示例: echo ${a//[^0-9]/c}
${parameter#word} # 删除匹配前缀
${parameter##word}
${parameter%word} # 删除匹配后缀
${parameter%%word}
# 去掉左边,#最短匹配模式,##最长匹配模式。
% 去掉右边,%最短匹配模式,%%最长匹配模式。
${VAR:-string} 如果 VAR 变量为空则返回 string
${VAR:+string} 如果 VAR 变量不为空则返回 string
${VAR:=string} 如果 VAR 变量为空则重新赋值 VAR 变量值为 string
${VAR:?string} 如果 VAR 变量为空则将 string 输出到 stderr
基本运算符
-eq //equals等于
-ne //no equals不等于
-gt //greater than 大于
-lt //less than小于
-ge //greater equals大于等于
-le //less equals小于等于
! 非运算,表达式为 true 则返回 false,否则返回 true。
-o 或运算,有一个表达式为 true 则返回 true。
-a 与运算,两个表达式都为 true 才返回 true。
双小括号 (( )) 是 Bash Shell 中专门用来进行整数运算的命令
注意:(( )) 只能进行整数运算,不能对小数(浮点数)或者字符串进行运算。后续讲到的 bc 命令可以用于小数运算。
在 (( )) 中使用变量无需加上$前缀,(( )) 会自动解析变量名,这使得代码更加简洁,也符合程序员的书写习惯
这种写法可以在计算完成后给变量赋值
示例: ((b=a-15)) 将 a-15 的运算结果赋值给变量 b。
使用变量时不用加$前缀,(( )) 会自动解析变量名.
可以在 (( )) 前面加上$符号获取 (( )) 命令的执行结果,也即获取整个表达式的值
示例: b=$((a-15)) 将 a-15 的运算结果赋值给变量 b。
类似 c=((a+b)) 这样的写法是错误的,不加$就不能取得表达式的结果
(( )) 也可以进行逻辑运算,在 if 语句中常会使用逻辑运算。
示例: ((a>7 && b==c)) 不用写 -gt -eq 等命令, 直接用数学写法即可.
流程控制
if xxx ; then xxx ; fi
if xxx ; then xxx ; else xxx ; fi
if xxx ; then xxx ; elif xxx ; then xxx ; else xxx ; fi
for xxx in xxx; do xxx done;
while xxx ; do xxx done;
while true;do curl --request POST --url http://127.0.0.1:8111/api/healthy/post; sleep 1; done
case xxx in x)xxx; ;;*)xxx; ;;esac
每个 case 取值后面必须为单词 in, 分支用右圆括号开始,用两个分号 ;; 表示 break,即执行结束; * 匹配所有
while:; do xxx ;done
while true;do xxx ;done
for ((;;));do xxx ;done
常用命令
详见: grep --help
具体见: info grep
详情见: wc --help
具体见: info wc
-c或--bytes或--chars 只显示Bytes数。
-l或--lines 显示行数。
-w或--words 只显示字数。
详情见: awk
具体见: info awk
示例: | awk '{print $1}' 以空格/tab作为分隔符,获取第2个字符
详情见: for i in s l o t m a ; do ps --help $i ;done
示例:
ps -ef |grep xxx
ps aux |grep xxx
详情见: help echo
选项:
-n 不要追加换行
-e 启用下列反斜杠转义的解释
-E 显式地抑制对于反斜杠转义的解释
echo "string" # 输出字符串
echo -e "开启转义"
echo -e "xxx\n" # 添加换行
ehco -e "xxx\c" # 强制不换行
多个参数采用;分割.
\033[0m 关闭所有属性
\033[1m 设置高亮度
\033[30~37m 设置前景色
\033[40~47;m 设置背景色
示例:
echo -e "\033[31;1m 这是一个红色高亮文字 \033[0m"
颜色编码示例:
黑=30,40
红=31,41
绿=32,42
黄=33,43
蓝=34,44
紫=35,45
靛蓝=36,46
白=37,47
示例:
# for i in {1..20};do echo -n "$i," ;done
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,
# ls {ex{1..3},ex4}.sh
ex1.sh ex2.sh ex3.sh ex4.sh
# ls {ex[1-3],ex4}.sh
ex1.sh ex2.sh ex3.sh ex4.sh
详见: sleep --help
sleep 1 # 程序睡眠1秒
用于在系统后台不挂断地运行命令,退出终端不会影响程序的运行
详见: nohup --help
示例1:
nohup COMMAND > nohup.out 2>&1 &
2>&1 解释:
将标准错误 2 重定向到标准输出 &1 ,标准输出 &1 再被重定向输入到 nohup.out 文件中。
0 – stdin (standard input,标准输入)
1 – stdout (standard output,标准输出)
2 – stderr (standard error,标准错误输出)
示例2:
nohup COMMAND > /dev/null 2>&1 & # /dev/null 文件不存在则不进行控制台信息输出.
详见: kill --help
信号名称: kill -l
常见信号:
1 (HUP):重新加载进程。
9 (KILL):杀死一个进程。
15 (TERM):正常停止一个进程。
强制杀死指定进程
kill -9 $(ps -ef |grep spring-boot)
cd `ls -t`
# 效果: ll -lrt 选择最后一个文件夹, copy文件名称 cd ${fileName} 回车.
kill -9 $(ps -ef |grep xxxxxx)
# 效果: ps -ef |grep xxxxx 选择pid行, 执行 kill -9 ${pid}
ll
mkdir BOOT-INF
mkdir BOOT-INF/lib
mkdir BOOT-INF/classes
yes | mv *SNAPSHOT.jar BOOT-INF/lib
yes | mv *.properties BOOT-INF/classes
yes | mv *.yml BOOT-INF/classes
yes | mv *.xml BOOT-INF/classes
ll
jar uvf0 *.jar BOOT-INF/
rm -rf BOOT-INF
ll
sh bin/spring-boot.sh restart
date
# 效果:
# 将*SNAPSHOT.jar 的jar包copy到 BOOT-INF/lib目录
# 将 *.properties 的 properties文件copy到BOOT-INF/classes目录
# 将 *.yml 的 yml文件copy到BOOT-INF/classes目录
# 将 *.xml 的 xml文件copy到BOOT-INF/classes目录
# 将 BOOT-INF 压缩到jar包内.
# 删除临时包, 并重启, 打印当前日期
我正在尝试使用ruby和Savon来使用网络服务。测试服务为http://www.webservicex.net/WS/WSDetails.aspx?WSID=9&CATID=2require'rubygems'require'savon'client=Savon::Client.new"http://www.webservicex.net/stockquote.asmx?WSDL"client.get_quotedo|soap|soap.body={:symbol=>"AAPL"}end返回SOAP异常。检查soap信封,在我看来soap请求没有正确的命名空间。任何人都可以建议我
我想安装一个带有一些身份验证的私有(private)Rubygem服务器。我希望能够使用公共(public)Ubuntu服务器托管内部gem。我读到了http://docs.rubygems.org/read/chapter/18.但是那个没有身份验证-如我所见。然后我读到了https://github.com/cwninja/geminabox.但是当我使用基本身份验证(他们在他们的Wiki中有)时,它会提示从我的服务器获取源。所以。如何制作带有身份验证的私有(private)Rubygem服务器?这是不可能的吗?谢谢。编辑:Geminabox问题。我尝试“捆绑”以安装新的gem..
我正在寻找执行以下操作的正确语法(在Perl、Shell或Ruby中):#variabletoaccessthedatalinesappendedasafileEND_OF_SCRIPT_MARKERrawdatastartshereanditcontinues. 最佳答案 Perl用__DATA__做这个:#!/usr/bin/perlusestrict;usewarnings;while(){print;}__DATA__Texttoprintgoeshere 关于ruby-如何将脚
我有一个在Linux服务器上运行的ruby脚本。它不使用rails或任何东西。它基本上是一个命令行ruby脚本,可以像这样传递参数:./ruby_script.rbarg1arg2如何将参数抽象到配置文件(例如yaml文件或其他文件)中?您能否举例说明如何做到这一点?提前谢谢你。 最佳答案 首先,您可以运行一个写入YAML配置文件的独立脚本:require"yaml"File.write("path_to_yaml_file",[arg1,arg2].to_yaml)然后,在您的应用中阅读它:require"yaml"arg
最近,当我启动我的Rails服务器时,我收到了一长串警告。虽然它不影响我的应用程序,但我想知道如何解决这些警告。我的估计是imagemagick以某种方式被调用了两次?当我在警告前后检查我的git日志时。我想知道如何解决这个问题。-bcrypt-ruby(3.1.2)-better_errors(1.0.1)+bcrypt(3.1.7)+bcrypt-ruby(3.1.5)-bcrypt(>=3.1.3)+better_errors(1.1.0)bcrypt和imagemagick有关系吗?/Users/rbchris/.rbenv/versions/2.0.0-p247/lib/ru
在Rails4.0.2中,我使用s3_direct_upload和aws-sdkgems直接为s3存储桶上传文件。在开发环境中它工作正常,但在生产环境中它会抛出如下错误,ActionView::Template::Error(noimplicitconversionofnilintoString)在View中,create_cv_url,:id=>"s3_uploader",:key=>"cv_uploads/{unique_id}/${filename}",:key_starts_with=>"cv_uploads/",:callback_param=>"cv[direct_uplo
我正在阅读SandiMetz的POODR,并且遇到了一个我不太了解的编码原则。这是代码:classBicycleattr_reader:size,:chain,:tire_sizedefinitialize(args={})@size=args[:size]||1@chain=args[:chain]||2@tire_size=args[:tire_size]||3post_initialize(args)endendclassMountainBike此代码将为其各自的属性输出1,2,3,4,5。我不明白的是查找方法。当一辆山地自行车被实例化时,因为它没有自己的initialize方法
我想在Ruby中创建一个用于开发目的的极其简单的Web服务器(不,不想使用现成的解决方案)。代码如下:#!/usr/bin/rubyrequire'socket'server=TCPServer.new('127.0.0.1',8080)whileconnection=server.acceptheaders=[]length=0whileline=connection.getsheaders想法是从命令行运行这个脚本,提供另一个脚本,它将在其标准输入上获取请求,并在其标准输出上返回完整的响应。到目前为止一切顺利,但事实证明这真的很脆弱,因为它在第二个请求上中断并出现错误:/usr/b
我正在玩HTML5视频并且在ERB中有以下片段:mp4视频从在我的开发环境中运行的服务器很好地流式传输到chrome。然而firefox显示带有海报图像的视频播放器,但带有一个大X。问题似乎是mongrel不确定ogv扩展的mime类型,并且只返回text/plain,如curl所示:$curl-Ihttp://0.0.0.0:3000/pr6.ogvHTTP/1.1200OKConnection:closeDate:Mon,19Apr201012:33:50GMTLast-Modified:Sun,18Apr201012:46:07GMTContent-Type:text/plain
您如何在Rails中的实时服务器上进行有效调试,无论是在测试版/生产服务器上?我试过直接在服务器上修改文件,然后重启应用,但是修改好像没有生效,或者需要很长时间(缓存?)我也试过在本地做“脚本/服务器生产”,但是那很慢另一种选择是编码和部署,但效率很低。有人对他们如何有效地做到这一点有任何见解吗? 最佳答案 我会回答你的问题,即使我不同意这种热修补服务器代码的方式:)首先,你真的确定你已经重启了服务器吗?您可以通过跟踪日志文件来检查它。您更改的代码显示的View可能会被缓存。缓存页面位于tmp/cache文件夹下。您可以尝试手动删除