使用git将code同时提交多个远程仓

想用一次git提交到多个仓库,可以通过以下命令实现:

# 设置第一个远程仓库
git git remote add origin https://github.com/w4ctech/hellogit.git

# 新增一个远程仓库
git remote set-url --add origin https://gitee.com/w4ctech/hellogit.git

# 新增另一个远程仓库
git remote set-url --add origin  https://git.coding.net/w4ctech/hellogit.git

# 查看当前远程仓库
git remote -v

此后的只需一次提交,就会将代码提交至三个仓库,如需删除某个仓库,只需执行:

git remote set-url --delete https://git.coding.net/w4ctech/hellogit.git

即可。

参考文献

Git 回滚到某个 commit 上及返回主分支

1. 代码回退

首先要用 git log 查看回到的版本,然后用以下命令,将本地代码回退到某个版本:

git reset --hard HEAD^        回退到上个版本
git reset --hard commit_id    退到/进到 指定 commit_id

如果需要将回退的某个版本提交远程,可执行以下命令:

git push origin HEAD --force

回滚之后,想恢复到新的版本怎么办?

  1. git reflog打印你记录你的每一次操作记录

git reflog 可以查看所有分支的所有操作记录(包括 commitreset 的操作),包括已经被删除的 commit 记录, git log 则不能察看已经删除了的 commit 记录,而且跟进结果可以回退道某一个修改。

2. 返回主分支

git checkout master

参考文献

解决群晖Moment不显示拷入照片

近期趁着双十一购入群晖一台,装好Moments,将照片导入Moment文件夹,但刷新并没有在Moments主页看到直接考入文件夹内的照片。

开始以为是正在转码,搜索一圈也有人这么说,后来有人提出是由于权限问题,于是尝试修复。

首先将Moment文件夹下的所有文件所有者授予当前账户:

https://imagehost-cdn.frytea.com/images/2020/11/07/202011072316057727cfb2f6215904.png

再给当前账户完全控制权限:

https://imagehost-cdn.frytea.com/images/2020/11/07/202011072316366ef3fe01d9080ef3.png

再进入Moment发现多出了许多照片的灰色占位区域,这才是正在转码的样子:

https://imagehost-cdn.frytea.com/images/2020/11/07/202011072313506369d4124d556308.png

猜测是由于此前文件所有者并非当前账户,因此群晖Moment无权访问这些文件,也就访问不到,更无法缓存,将所有文件权限给够,正常缓存。

这下好了,六年前的照片都躺在了这段时间线里,突然感受到科技的美好。

参考文献

【阅记】斯坦福高效睡眠法 | 高效睡眠 | 高效人生

时常会听到有人说抱怨自己失眠、睡眠不足,工作压力大没时间睡,有时间睡了反而辗转反侧睡不着。

这都是很常见的一些睡眠问题,大学室友就饱受睡眠问题的困扰,后来用了褪黑素效果还不错。我自己也有类似的苦恼,有时候在深夜里突然感觉全身难受,究其原因居然是饮水不足。总是导致睡满问题的原因有很多很多,可许多人都会有的共同烦恼可以总结为:睡不着、睡不够

https://imagehost-cdn.frytea.com/images/2020/11/05/202011052229225c36beda8581d2a9.png

前一阵子读了一本书,《斯坦福高效睡眠法》(ISBN: 9787514223736),科学得讲述了一些睡眠方法,如果不想看长篇大论,只需记住这一结论:前90分钟的睡眠至关重要,决定了整个睡眠的质量

首先就从贯穿全书的主线“完美睡眠法”谈起吧。

壹 · 完美睡眠法

全书都在顺着一个主线,列出大量依据支撑起第一章就抛出的“斯坦福完美睡眠”,即黄金90分钟法则

开篇就提到一点“睡眠质量是由睡眠初期的90分钟决定的,而不是取决于REM睡眠、非REM睡眠的周期。”。睡眠对人们很重要,而睡眠的前90分钟对整个睡眠至关重要。

人生的1/3时间是在黑夜中度过的,但是它却直接决定着余下的2/3。

这也就是全书的关键所在,抓住这睡眠之前的90分钟。究竟怎么抓住呢?在书的后面章节讲到诸如“大脑开关”等方法,经过这些日子的时间,我个人对此也有一些自己的想法。这便是:在最有睡意的时刻睡去

https://imagehost-cdn.frytea.com/images/2020/11/05/20201105222957a5b5e81d897d5fab.png

有时说“强扭的瓜不甜”,在自然界常常是这样,对于生物需要顺着来,不能硬刚。人类更是如此,抓住瞌睡虫,在有困意的时候果断睡去。同样在没有睡意的时候,就去做些事情,不需要去担心睡的太少怎么办,后面会说道其实人们只要规律睡眠,并不需要太长时间的睡眠时间。因此偶然睡不着,就去做些事情,避免逃避现状,空想焦躁。

比起“量”来,“质”才更重要。吃饭也好,物品也好,工作也好,都是“质”重于“量”。可以说,这是一个全球性的认知。

贰 · 少睡的危害

为什么高质量的睡眠如此重要呢?书中用了一些例子讲述了其中危害,有时睡少比酒驾更危险。

书中举出了一个“夜班医生”的例子,很能说明问题,是说跟踪调查了一些值完夜班的医生,发现他们白天工作时很容易出现一种“瞬间睡眠”的状态。“值过夜班的医生们所呈现的状态,被称为瞬间睡眠,可以通过其脑电波来进行确认。瞬间睡眠指1秒到10秒的睡眠状态,它是保护大脑的一种防御反应”。

https://imagehost-cdn.frytea.com/images/2020/11/05/202011052230201e75bd87805ca034.png

试想如果是一位司机在正在驾驶,突然出现这种瞬间睡眠,后果会是怎样?

因此千万要重视起来睡眠问题,这并不一个小问题。睡眠的好坏,一定程度上决定了剩下的 2/3 时间,也就决定了我们的人生。要注意不要欠下“睡眠债”,不需要太多,也不能太少。只需身体感觉刚刚好,处于一种舒适的充满活力的状态,这就是每个人最合适的睡眠时间。这睡眠时间也每个人都不一样,需要去自己体验。

试着记下自己的睡眠时间及状体,找到自己最合适的睡眠时间,坚持下去,不要欠债。一旦欠债,身体会通过许多途径告诉我们,此时一定要小心。

“啊,每天都睡不够,周末得好好养精蓄锐咯”——这就是大脑在发出SOS的求救信号。你体内的睡眠负债,也许正像滚雪球似的越来越大呢。

总结

睡眠不好,还会导致女性发胖、记忆减退等不良后果。重视睡眠,就是重视自己的人生。如果对更详细的睡眠感兴趣,去看后面的阅读笔记吧。如果可能,还是去找几本相关的书来的实在。

好了,这次简单的分享就到这里了。其实几周前就读完了,但一直没时间写下这些东西。今天终于记下来了,真是很开心。最近就可以回去一趟了,很开心。我的存储服务器也到货了,可以开始规整自己的数据啦。还有我送给自己一个盼望了4年多的东西作为自己的生日礼物,还是要自己争取喜欢的东西呀,简直是太开心。好啦,晚安,祝君好梦。

局域网内跨平台传输文件、文字 | Dukto

在日常生活和实际工作中经常需要涉及到局域网内多设备传输文件,此前尝试过飞鸽传书,发现Mac平台体验并不好,也不够可靠;使用NAS等网络存储设备可以解决,但不能随时随地都带这个NAS,此时通过一款可跨平台传输文件的工具在网内分享文件就可极大提升效率。

使用Dukto可以在局域网内的 Mac 之间、Win之间、Android之间,以及跨平台之间传输文件、文字、文件夹。

https://imagehost-cdn.frytea.com/images/2020/10/30/20201030112556e831cefc342c413c.png

实测速度还是不错的,比较稳定,网内设备一下就能发现。

作者已经停止更新,但个人感觉也没有什么需要更新的了。

下载地址贴在这里:

参考文献

iTerms 常用快捷键

  • 切换 tab: ⌘+← , ⌘+→ , ⌘+{ , ⌘+} , ⌘+数字 直接定位到该 tab;
  • 新建 tab: ⌘+t
  • 顺序切换 pane: ⌘+[ , ⌘+]
  • 按方向切换 pane: ⌘+Option+方向键
  • 切分屏幕: ⌘+d 水平切分, ⌘+Shift+d 垂直切分;
  • 智能查找,支持正则查找: ⌘+f
  • 多个Tab、窗口执行同一个命令: ⌘Command + ⇧Shift + I

参考文献

Python执行或远程执行shell命令

最近想要实现通过脚本循环再 Linux 下运行 shell 命令,经过探索发现使用 Python 语言有几种解决方案,在此简单记录。

方案一:脚本本地执行命令

在 Python 中有两个库都可以实现运行 shell 命令的效果:

import subprocess
import os

使用方法也很简单:

# subprocess 使用方法
subprocess.call("ls") # 执行ls命令

# os 使用方法
# 使用system模块执行linux命令时,如果执行的命令没有返回值res的值是256
# 如果执行的命令有返回值且成功执行,返回值是0
res = os.system("ls")
# popen模块执行linux命令。返回值是类文件对象,获取结果要采用read()或者readlines()
val = os.popen('ls').read() # 执行结果包含在val中

方案二:脚本远程执行命令

在 Python 中有一个库可以实现 SSH 客户端及 SFTP 的功能。

#!/usr/bin/python
import paramiko

使用方法大致如下:

# 连接方法
def ssh_connect( _host, _username, _password ):
    try:
        _ssh_fd = paramiko.SSHClient()
        _ssh_fd.set_missing_host_key_policy( paramiko.AutoAddPolicy() )
        _ssh_fd.connect( _host, username = _username, password = _password )
    except Exception, e:
        print( 'ssh %s@%s: %s' % (_username, _host, e) )
        exit()
    return _ssh_fd

# 运行命令
def ssh_exec_cmd( _ssh_fd, _cmd ):
    return _ssh_fd.exec_command( _cmd )

# 关闭SSH
def ssh_close( _ssh_fd ):
    _ssh_fd.close()

方案三:使用 SecureCRT 脚本

该方法参见此前的博文:SecureCRT 下 Python 脚本编写

参考文献

终端抓包神器 | tcpdump参数解析及使用

本文整理转自:tcpdump参数解析及使用详解

tcpdump介绍

tcpdump 是一个运行在命令行下的抓包工具。它允许用户拦截和显示发送或收到过网络连接到该计算机的TCP/IP和其他数据包。tcpdump 适用于大多数的类Unix系统操作系统(如linux,BSD等)。类Unix系统的 tcpdump 需要使用libpcap这个捕捉数据的库就像 windows下的WinPcap。

tcpdump命令格式

Tcpdump的大概形式如下:

tcpdump –i eth0 ’port 1111‘ -X -c 3
  • X 告诉 tcpdump 命令,需要把协议头和包内容都原原本本的显示出来(tcpdump会以16进制和ASCII的形式显示),这在进行协议分析时是绝对的利器。

tcpdump 采用命令行方式,它的命令格式为:

tcpdump [ -adeflnNOpqStvx ] [ -c 数量 ] [ -F 文件名 ]
[ -i 网络接口 ] [ -r 文件名] [ -s snaplen ]
[ -T 类型 ] [ -w 文件名 ] [表达式 ]

tcpdump 参数

-a:将网络地址和广播地址转变成名字;

-d:将匹配信息包的代码以人们能够理解的汇编格式给出;

-dd:将匹配信息包的代码以c语言程序段的格式给出;

-ddd:将匹配信息包的代码以十进制的形式给出;

-e:在输出行打印出数据链路层的头部信息,包括源mac和目的mac,以及网络层的协议;

-f:将外部的Internet地址以数字的形式打印出来;

-l:使标准输出变为缓冲行形式;

-n:指定将每个监听到数据包中的域名转换成IP地址后显示,不把网络地址转换成名字;

-nn:指定将每个监听到的数据包中的域名转换成IP、端口从应用名称转换成端口号后显示

-t:在输出的每一行不打印时间戳;

-v:输出一个稍微详细的信息,例如在ip包中可以包括ttl和服务类型的信息;

-vv:输出详细的报文信息;

-c:在收到指定的包的数目后,tcpdump就会停止;

-F:从指定的文件中读取表达式,忽略其它的表达式;

-i:指定监听的网络接口;

-p:将网卡设置为非混杂模式,不能与host或broadcast一起使用

-r:从指定的文件中读取包(这些包一般通过-w选项产生);

-w:直接将包写入文件中,并不分析和打印出来;

-s:snaplen snaplen表示从一个包中截取的字节数。0表示包不截断,抓完整的数据包。默认的话 tcpdump 只显示部分数据包,默认68字节。

-T:将监听到的包直接解释为指定的类型的报文,常见的类型有rpc (远程过程调用)和snmp(简单网络管理协议;)

-X:告诉tcpdump命令,需要把协议头和包内容都原原本本的显示出来(tcpdump会以16进制和ASCII的形式显示),这在进行协议分析时是绝对的利器。

参考文献

SecureCRT下Python脚本编写

本文主要内容转自:SecureCRT中python脚本编写学习指南

SecureCRT 支持 VB、JavaScript、Python 等多种脚本语言。

一、使用 python 语言实现 SecureCRT 中的 Dialog 功能

# $language = "Python"
# $interface = "1.0"

#crt.Dialog.FileOpenDialog([title,[buttonLabel,[defaultFilename,[filter]]]])
#弹出一个对话框,用于选择单个文件;如果选择了具体文件则返回该文件的绝对路径,如果选择了弹窗的“取消”,则返回空。
filePath =  crt.Dialog.FileOpenDialog("please open a file","open","a.log","(*.log)|*.log")
#filePath =  crt.Dialog.FileOpenDialog("","","a.log","")
#crt.Dialog.MessageBox(message, [title, [icon|buttons]]) 警告、按钮类型弹出一个消息框,可以定义按钮,使用按钮和文本消息来实现和用户的简单对话;
crt.Dialog.MessageBox(filePath,"",64|0)
crt.Dialog.MessageBox("会话已断开","session",64|2)
crt.Dialog.MessageBox("确认是否退出","session",32|1)
crt.Dialog.MessageBox("确认是否退出","session",32|3)
crt.Dialog.MessageBox("是否继续安装","session",32|4)
crt.Dialog.MessageBox("此会话已打开","session",48|5)
crt.Dialog.MessageBox("无法连接此窗口","session",16|6)

#crt.Dialog.Prompt(message [, title [,default [,isPassword ]]])
#弹出一个输入框,用户可以填写文字,比如填写文件名,填写路径,填写IP地址等,运行结果如果点击'ok',返回输入的字符串,否则返回"" 
password = crt.Dialog.Prompt("password","session","admin",False)
crt.Dialog.MessageBox(password,"password",64|0)
password = crt.Dialog.Prompt("password","session","",True)
crt.Dialog.MessageBox(password,"password",64|0)

二、使用 python 语言实现 SecureCRT 中的 Screen 功能

# $language = "Python"
# $interface = "1.0"

# CurrentColumn返回当前光标的列坐标。
curCol =  crt.Screen.CurrentColumn
crt.Dialog.MessageBox(str(curCol))

# CurrentRow返回当前光标的行坐标。
curRow = crt.Screen.CurrentRow
crt.Dialog.MessageBox(str(curRow))

# Columns 返回当前屏幕的最大列宽
cols = crt.Screen.Columns
crt.Dialog.MessageBox(str(cols))

# Rows 返回当前屏幕的最大行宽
rows = crt.Screen.Rows
crt.Dialog.MessageBox(str(rows))

#IgnoreEscape 定义当使用WaitForString、WaitForStrings和ReadString这三个方法时是否获取Escape字符(特殊字符如回车)默认是会获取的
crt.Screen.IgnoreEscape = False
crt.Dialog.MessageBox(crt.Screen.ReadString(["\03"],5)) #获取ctrl+c

crt.Screen.IgnoreEscape = True
crt.Dialog.MessageBox(crt.Screen.ReadString(["\03"],2)) #不获取ctrl+c

# MatchIndex 定义当使用WaitForStrings和ReadString这三个方法时会根据参数的位置 获取返回值,从1开始计算,如果没有一个匹配则返回0.
outPut = crt.Screen.ReadString(["error","warning","#"],10)
index = crt.Screen.MatchIndex
if (index == 0):
    crt.Dialog.MessageBox("Timed out!")
elif (index == 1):
    crt.Dialog.MessageBox("Found 'error'")
elif (index == 2):
    crt.Dialog.MessageBox("Found 'warning'")
elif (index == 3):
    crt.Dialog.MessageBox("Found '#'")

# Synchronous 设置屏幕的同步属性。若设置为false,则在脚本中使用WaitForString、WaitForStrings、ReadString函数时可能存在丢失一部分数据的现象,设置为true后可能会存在屏幕卡顿的情况,默认为false
crt.Screen.Synchronous = True
crt.Screen.Send("\r\n")
crt.Screen.ReadString("#")
crt.Screen.Send("\r\n")
crt.Screen.WaitForString("#")
crt.Screen.Send("\r\n")
crt.Screen.WaitForStrings(["#",">"])
crt.Screen.Send("conf t\r\n") 

# 方法
# Clear()清屏功能
# crt.Screen.Clear()

# get()按照坐标取出一个矩形框内的屏幕上的字符(即从某行某列开始到其它行其它列),不包含字符串中的回车换行符,所以这个多用于获取无格式的光标处字符串或某小段特定区域字符串。
out = crt.Screen.Get(row1, col1, row2, col2)
crt.Dialog.MessageBox(out)

# get2()解释按照坐标取出一个矩形框内的屏幕上的字符(即从某行某列开始到其它行其它列),包含字符串中的回车换行符,所以这个多用于获取大段带格式的字符串。
crt.Screen.Get2(row1, col1, row2, col2)

# IgnoreCase 使用全局参数设置控制在使用WaitForString、WaitForStrings和ReadString这三个函数时是否对大小写敏感,默认为false大小写字符串都会检查,设置为true时则不会检测大小写。
crt.Screen.IgnoreCase = True
crt.Screen.Send("show memory\r\n")
crt.Screen.WaitForString("more")
crt.Screen.Send("\r\n")
crt.Screen.WaitForStrings("more","#")
crt.Screen.Send("\r\n")
crt.Screen.ReadString("more","#")

# Send() 向远端设备或者屏幕发送字符串,当向屏幕发送字符串时需要指定第二个参数为Ture
crt.Screen.Send("show version\r\n")
crt.Screen.Send("\r\nhello,world!\r\n",True)
crt.Screen.IgnoreCase = True
while (crt.Screen.WaitForString("more",10)):    
    crt.Screen.Send("\r\n")

# SendKeys()向当前窗口发送按键,包含组合按键,比如可以发送类似"CTRL+ALT+C"等这样的组合键,这样写即可:crt.screen.sendkeys("^%c");这个功能需要语言本身支持,目前只有VBS和JS脚本可以使用。

# SendSpecial()可以发送特殊控制码,这个控制码是Crt内置的功能,具体可以包含的有Menu、Telnet、VT functions功能列表中提供的所有功能,
crt.Screen.SendSpecial("vT_HOLD_SCREEN")

# WaitForCursor()等待光标移动,当移动时返回值为true,当有超时时间参数且超时时返回false,否则会一直等待光标移动。利用这个功能可以用来判断一个命令的输出是否结束,
crt.Screen.WaitForCursor(5)
crt.Screen.Send("\r\nhello,world!\r\n",True)
if ( crt.Screen.WaitForCursor(5)):
    crt.Screen.Send("show version\r\n")

# WaitForKey()检测有键盘按键时返回true,当有超时时间参数且超时时返回false,否则会一直等待按键
if (crt.Screen.WaitForKey(5)):
    crt.Screen.Send("show version\r\n")

# WaitForString()一般用于发送命令后等待某字符串
# crt.Screen.WaitForString(string,[timeout],[bCaseInsensitive])
crt.Screen.WaitForString("#",10)

# WaitForStrings()与WaitForString是同样的功能,可以等待多个字符串
outPut = crt.Screen.WaitForStrings(["error","warning","#"],10)
index = crt.Screen.MatchIndex
if (index == 0):
    crt.Dialog.MessageBox("Timed out!")
elif (index == 1):
    crt.Dialog.MessageBox("Found 'error'")
elif (index == 2):
    crt.Dialog.MessageBox("Found 'warning'")
elif (index == 3):
    crt.Dialog.MessageBox("Found '#'")

# ReadString()与WaitForStrings功能类似,都是等待某几个字符出现,不同的是它还会读取字符串之前出现的所有字符。
crt.Screen.ReadString([string1,string2..],[timeout],[bCaseInsensitive])        
1. string,必选参数,等待的字符串,最少有一个,可以是特殊字符比如:\r\n;
2. timeout,可选参数,超时时间,当检测不到对应字符串时会返回false,没有此参数时会一直等待;
3. bCaseInsensitive,可选参数,大小写不敏感,默认值是false,表示将检测字符串的大小写,当为true时不检测大小写。

三、实例

1. 实例一,循环运行命令

# $language = "python"
# $interface = "1.0"

# This automatically generated script may need to be
# edited in order to work correctly.

import time

start_time = time.time()
end_time = time.time()

def Main():
    while True:
        end_time = time.time()
        crt.Screen.Synchronous = False
        crt.Screen.Send("?")
        crt.Screen.Send("\r\n")
        crt.Screen.Send("\r\n")
        time.sleep(1)
    running_time = end_time - start_time
    msg = "会话已断开\n" + \
            "running ms : " + str(running_time) + "\n" + \
            "start ms   : " + str(start_time) + "\n" + \
            "ent ms     : " + str(end_time) + "\n"
    crt.Dialog.MessageBox(msg,"session",64|2)
Main()

参考文献