很久没有做Android开发了,最近上海遇到抢菜高峰,为了家里能有稳定的食物来源,我不得不使用重启这部分专业知识来完成一些小小的工作。

时隔几年之后,Android Studio(以下简称AS)也有了多个版本的升级,我照例把开发环境升级到最新版,版本信息如下:

Android Studio Bumblebee | 2021.1.1 Patch 3
Build #AI-211.7628.21.2111.8309675, built on March 17, 2022
Runtime version: 11.0.11+0-b60-7590822 x86_64
VM: OpenJDK 64-Bit Server VM by JetBrains s.r.o.
macOS 10.15.7
GC: G1 Young Generation, G1 Old Generation
Memory: 1280M
Cores: 16
Registry: external.system.auto.import.disabled=true
Non-Bundled Plugins: Lombook Plugin (0.34.1-2019.1), org.intellij.plugins.markdown (211.7142.37)

当我开发好之后想要推送代码到Github时,AS突然报了个错给我,如下图:

iShot2022-04-15_21.05.37.png

具体信息如下:

21:02:26.126: [food-grabber] git -c credential.helper= -c core.quotepath=false -c log.showSignature=false push --progress --porcelain origin refs/heads/master:master --set-upstream
Invocation failed Unexpected end of file from server
java.lang.RuntimeException: Invocation failed Unexpected end of file from server
    at org.jetbrains.git4idea.GitAppUtil.sendXmlRequest(GitAppUtil.java:30)
    at org.jetbrains.git4idea.http.GitAskPassApp.main(GitAskPassApp.java:58)
Caused by: java.net.SocketException: Unexpected end of file from server
    at java.base/sun.net.www.http.HttpClient.parseHTTPHeader(HttpClient.java:866)
    at java.base/sun.net.www.http.HttpClient.parseHTTP(HttpClient.java:689)
    at java.base/sun.net.www.http.HttpClient.parseHTTPHeader(HttpClient.java:863)
    at java.base/sun.net.www.http.HttpClient.parseHTTP(HttpClient.java:689)
    at java.base/sun.net.www.protocol.http.HttpURLConnection.getInputStream0(HttpURLConnection.java:1615)
    at java.base/sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1520)
    at org.apache.xmlrpc.DefaultXmlRpcTransport.sendXmlRpc(DefaultXmlRpcTransport.java:87)
    at org.apache.xmlrpc.XmlRpcClientWorker.execute(XmlRpcClientWorker.java:72)
    at org.apache.xmlrpc.XmlRpcClient.execute(XmlRpcClient.java:194)
    at org.apache.xmlrpc.XmlRpcClient.execute(XmlRpcClient.java:185)
    at org.apache.xmlrpc.XmlRpcClient.execute(XmlRpcClient.java:178)
    at org.jetbrains.git4idea.GitAppUtil.sendXmlRequest(GitAppUtil.java:27)
    ... 1 more
error: unable to read askpass response from '/Users/xxx/Library/Caches/Google/AndroidStudio2021.1/tmp/intellij-git-askpass-local.sh'
fatal: could not read Username for 'http://gitxxx.com': Device not configured

搜到的解决办法多数是让我到“.git”目录下修改“config”文件,把用户名和密码加到Git远程地址的URL中,如下,其中xxx是用户名,yyy是密码:

[remote "origin"]
url = http://xxx:yyy@github.com/aaa/bbb.git
fetch = +refs/heads/*:refs/remotes/origin/*

然而这个解决方法对我无效,多方查证无果,最后在一个国外网站上找到了相关的解决办法,只需勾选一个选项即可解决问题。如下图:

iShot2022-04-15_21.05.55.png

勾选之后再次提交,问题解决。

iShot2022-04-15_21.06.10.png

21:06:01.750: [food-grabber] git -c core.quotepath=false -c log.showSignature=false push --progress --porcelain origin refs/heads/master:master --set-upstream
Enumerating objects: 66, done.
Counting objects:   1% (1/66)
Counting objects: 100% (66/66), done.
Delta compression using up to 16 threads
Compressing objects:   1% (1/55)
Compressing objects: 100% (55/55), done.
Writing objects:   1% (1/66)
Writing objects: 100% (66/66), 136.46 KiB | 13.65 MiB/s, done.
Total 66 (delta 2), reused 0 (delta 0), pack-reused 0
To http://git.hotsun168.com/HomeApps/food-grabber.git
*    refs/heads/master:refs/heads/master    [new branch]
Branch 'master' set up to track remote branch 'master' from 'origin'.
Done

什么时候熊厂能够给点力???

公司UAT服务器故障,备份文件后重装了系统。将nginx配置还原并启动Gogs后,尝试拉取一个文件数多容量大的仓库时,终端报错:

error: RPC failed; curl 18 transfer closed with outstanding read data remaining
fatal: The remote end hung up unexpectedly
fatal: early EOF
fatal: index-pack failed

在国内外网站查了很久资料,基本都提示是网络问题,有建议在Git配置项中关闭压缩、增加上传缓冲区的:

git config --global http.postBuffer 524288000
git config --global core.compression 0

或是建议只拉取最近的提交的:

git clone --depth 1 <repo_URI>

成功后再补充后续数据:

git fetch --unshallow 

还有建议增加弱网优化配置或换网络的。

git config --global http.lowSpeedLimit 0
git config --global http.lowSpeedTime 999999

很遗憾,这些配置均无法解决问题。但既然提示了可能是网络有关的问题,则有必要基于网络通信的全流程查看一下问题。

首先贯彻分治法的原则,先测试问题出在哪个环节。直接使用Gogs本地地址在服务器上进行仓库克隆。

git clone http://127.0.0.1:3000/xxx/xxx.git

克隆成功完成,因此即可断定,问题一定出在nginx端。在查看了nginx的error.log之后,一段很明显的错误信息指示了问题最终的原因:

2022/03/24 09:00:55 [crit] 129923#0: *12212 open() "/usr/xxx/nginx/proxy_temp/1/01/0000000011" failed (13: Permission denied) while reading upstream, client: 10.130.0.19, server: xxx.cn, request: "POST /git/xxx/xxx.git/git-upload-pack HTTP/1.1", upstream: "http://127.0.0.1:3000/xxx/xxx.git/git-upload-pack", host: "xxx.cn"

因此,问题的根源是nginx在大请求中为了保证通信效率,使用了缓冲区进行数据收发,但在使用缓冲区目录中的文件进行操作写入时,因为无权限进而导致网络请求失败。查看进程信息之后也印证了这个结果:

nobody    33361  69816  0 09:13 ?        00:00:08 nginx: worker process
root      69816      1  0 3月23 ?       00:00:00 nginx: master process sbin/nginx
root     123433  96635  0 10:56 pts/0    00:00:00 grep --color=auto nginx

后经询问,是负责处理服务器恢复的同事漏掉了配置文件的第一行:

user root;

将该配置补上并更新nginx配置再次测试,问题解决。

综上所述,别人的解决方案不一定适合自己,还需要基于自身经验从头开始全面详细的排查问题,才能找到最终的原因。

phpvirtualbox是一个使用PHP写成的可以在Web端远程管理VirtualBox虚拟机的服务。它与VirtualBox之间是通过vboxwebsrv这个进程对外提供的SOAP服务进行通信,从而做到对虚拟机的信息获取与操控的效果的。

显然,远程服务器上安装好的VirtualBox绝大多数情况都是运行在无头模式(headless)下,没有图形化界面,这给虚拟机的系统安装造成了很大不便。那么如何远程连接虚拟机的图形化界面以安装操作系统呢?

我们知道,VirtualBox提供了VRDP功能,可以通过phpvirtualbox的Settings界面对虚拟机的VRDP进行设置,打开该功能,并设置服务端口。如下图。

iShot2022-03-03 13.50.12.png

但可能是因为phpvirtualbox本身的配置没有增加监听地址这一选项,打开VRDP之后,虚拟机监听的VRDP端口是在本地环回地址(127.0.0.1或localhost)上的,导致通过远程方式连接VRDP无效。如下图。

iShot2022-03-03 14.18.24.png

解决这一问题的办法是,进入VirtualBox所在服务器,使用vboxmanage命令手工设置虚拟机的vrdeaddress属性即可。具体命令如下:

#查看虚拟机列表。
[vbox@localhost ~]$ vboxmanage list vms
"test" {befd693e-02c0-4312-b267-b357e5f38f6d}

#修改vrdeaddress属性,指定为空则允许所有地址访问。
[vbox@localhost ~]$ vboxmanage modifyvm befd693e-02c0-4312-b267-b357e5f38f6d --vrdeaddress ""

上述操作要在虚拟机关机情况下进行,否则无法修改成功。命令执行结束后可以在phpvirtualbox界面看到VRDP监听的地址已经发生变化,不再是本地环回地址了。如下图。

iShot2022-03-03 14.19.45.png

此时,通过mstsc也可以连接到虚拟机显示器,可以正常安装系统。如下图。

iShot2022-03-03 14.01.41.png

Elasticsearch默认安装后,如果不进行任何配置的修改直接启动,则大概率会报出如下错误:

max file descriptors [4096] for elasticsearch process is too low

此时网上搜到的结果一般是需要修改/etc/security/limits.conf文件,并加入如下配置:

*               soft    nofile          65536
*               hard    nofile          65536

然后通过如下命令来验证是否已经改动:

# ulimit -Hn
65536

# ulimit -Sn
65536

但如果在Supervisor管理下的Elasticsearch,则采用上述修改方式是无效的。将ulimit命令写入Elasticsearch的启动脚本,看到的值仍然是4096。

此问题的原因是,修改limit.conf只是修改了操作系统层面的限制,但Supervisor本身的限制没有被修改。Supervisor对文件数量的限制是保存在/etc/supervisor.conf文件中。所以,需要在/etc/supervisor.conf的“[supervisord]”段加入或修改如下配置:

minfds=65536                  ; min. avail startup file descriptors; default 1024
minprocs=4096                 ; min. avail process descriptors;default 200

supervisord拉起的其他进程都是子进程,共享了supervisord的配置,所以修改上述配置之后,需要重启supervisord方可生效。

值得注意的是,通过“supervisorctl reload”命令无法让supervisord立即更新上述已修改的配置。所以需要通过“kill -9”杀掉并重新运行supervisord,或者直接重启机器。