Docker系列 WordPress系列 WordPress上传或更新Markdown的最佳实践-m2w 2
本文最后更新于 101 天前,如有失效请评论区留言。

本博客由ZGOCLOUD大力赞助!如何更快地访问本站?有需要可加电报群获得更多帮助。本博客用什么VPS?创作不易,请支持苯苯!推荐购买本博客的VIP喔,10元/年即可畅享所有VIP专属内容!

日志

  • 2023-11-15:更新了m2w 2.5.12,优化了up.py代码、legacy*.json管理和myblog.py逻辑。
  • 2023-06-06:优化m2w 2.5的教程。
  • 2023-06-05:m2w 2.5正式发布,支持REST API!更新相关教程。
  • 2023-04-23:新增目录/格式不敏感的提示;新增更改已存在文章题目的相关技巧。
  • 2023-02-07:教程维护。无重要更新。
  • 2022-12-14:更新了一些使用细节。比如,建议运行脚本不要使用和m2w包同名(我改为了myblog.py),否则会出来一些bug。
  • 2022-12-11:将m2w 2上传至PyPi (v2.2.10),让大家可以通过pip安装m2w。具体用法去Github文档看吧,也蛮简单的。当然,像原来那样用也是可以的。
  • 2022-12-08:教程中增加post_metadata不可以为空值的提醒;更新了m2w v2.2.4,在上传新文件前先检查其是否已经存在于WordPress后台,避免重复上传。
  • 2022-12-06:升级至m2w 2.2。优化了user.json的参数结构使其更加灵活。至少在v2.2.1版本或以上。更新若干教程。
  • 2022-12-03:创建船新版本m2w 2.0!

前言

m2w 1.0的教程可见《Docker系列 WordPress系列 WordPress上传或更新Markdown的最佳实践》。

之前我一直使用m2w来管理自己的博客文章。某次和小伙伴liange交流时,我意识到大家管理本地文件夹的习惯不太一样。比如,我虽然会将某文件放在一个具有特定结构的文件目录里,但我定位文件的时候习惯使用Everything之类的软件搭配正则表达式,因此只是记文件大致名字而不怎么记文件位置。

但是,有相当一部分人定位文件的时候依赖对文件位置的记忆。基于这种现实,旧版本的m2w对于某些小伙伴来说是不友好的。其一,旧m2w需要用户指定legacynew文件夹,因此用户无法根据自己的喜好将待同步/更新的文件放到任意目录。其二,随着博客文章的数量与日俱增,这会带来管理上的困难。其三,将新文件“强行转移”至legacy里,这种操作也不太自然。其四,对于有多个站点/帐户的小伙伴来说,旧版本m2w的实现不够简洁。

因此,趁着周末休息,我设计了m2w的Plus版本——即所谓的m2w 2m2w 2有以下特性:

  • m2w 1.0 相比,使用 和config/user.json 略微不同的方式维护用户信息。
  • 用户可以开心地保留原有的文件结构 (~ ̄▽ ̄)~ 。
  • 通过多个legacy_*.json 同时管理多个网站/帐户。
  • 只需要使用1个 python 脚本 myblog.py 而不是两个(m2w 1.0 中的 update.pyupload.py)。
  • 像m2w 1.0 稳定且好用!
  • 即时更新,而不像基于Github Page的更新策略一样有一定延时。

项目地址和原来是一样的:

欢迎使用喔!用法比m2w 1.0要更简单一些。对于m2w v2.2.4或以上的版本在上传新文件前会对WordPress后台已存在的Post进行检测(基于文件名),所以不会导致重复上传,大家可以放心升级啦!

最后,所有的m2w版本均依赖xmlrcp.php,所以你的WordPress站点不要关闭其API(默认情况下是开放的)。在WordPress 6.0时代,配合Wordfence等安全插件,其实不需要太担心安全问题。建议WordPress站点有https的情况下再使用m2w,否则可能会造成帐号/密码泄露(如果博客仅有http,建议上https;可参考此教程)。

基本原理

无论是更新文章还是上传文章,不再分开,完全由myblog.py控制。大致的规则是这样的:

  • 如果legacy*.json不存在,则所有的文件都是新文件,需要全部上传。
  • 如果legacy*.json存在,如果某些key不存在,表明为新文件,需要上传这些key对应的md。
  • 如果legacy*.json存在,如果key存在但value不同,表明为旧文件有新的改动,需要更新这些key对应的md。

我觉得这种逻辑对于普通用户来说是挺友好的,但是对进阶选手来说就不一定了。不过,进阶选手操作能力强,在我的基础上魔改,应该问题不大 (~ ̄▽ ̄)~

判断文件改动的基本原理是md5算法。根据chatGPT的介绍,MD5是一种散列算法,用于确保信息传输完整一致。它通过对数据进行摘要来产生一个结果,该结果称为散列值。MD5被广泛用于生成文件或消息的指纹,以确保它们在传输过程中没有被篡改。在m2w中,md5算法主要用于快速并敏感地判断某个markdown文件是否有改动

user.json

该文件包含账户名及密码,请妥善保管。

新的user.json与旧版本略有不同,具体结构如下:

"web01": {
        "domain": "https://domain-01.com",
        "username": "username-01",
        "password": "password-01",
        "path_markdown": [
            "E:/Github/m2w/@test/main",
            "E:/Github/m2w/@test/main2"
        ],
        "post_metadata": {
            "category": ["test"],
            "tag": ["test"],
            "status": "publish"
        },
        "path_legacy_json": "/config/legacy"
    }

其中web01可以随便取名,它与legacy_*.json文件的命名和一些message有关,一但指定后不建议更改。可以添加多个类似于web01的对象,这对于多网站/帐户的用户来说是挺友好的。post_metadata指定了默认上传的类、标签和状态,不可以为空值。

值得一提的是,path_legacy_json表征了legacy_*.json类文件的位置,它一般不需要调整,保留默认的/config/legacy取值即可。

目录结构

m2w 2不会破坏用户的文件结构,它完全是通过legacy*.json文件来判断是否有文件需要上传/更新。需要提醒的是,尽管m2w 2将文件的绝对路径当成Key,但你尽量不要对不同的文件使用相同的文件名——如果你这样做,其实也会给看博客文章的人造成疑惑(尽管这不会报错,因为WordPress会自动分配不同的数字ID)。

m2w 2的目录结构进行了优化。在user.json文件中,依然由path_markdown变量控制:

"path_markdown": [
        "E:/Github/m2w/@test/main",
        "E:/Github/m2w/@test/main2"
    ],

这里你可以加任意数量的顶级目录。如果该目录里有子文件夹和.md文件,也可以正确识别。由于代码里具有去重机制,所以并不需要担心路径重复。如果这些目录里有非.md格式的文件,它们将会被m2w 2忽略。

网站/帐户

如下所示:

"domain": "https://domain-01.com",
"username": "username-01",
"password": "password-01"

domainusernamepassword则和m2w 1.0是一样的,即分别代表WordPress站点的域名、用户名、密码。

项目展示

为了演示多站点/帐号的功能,我使用了重复的站点/帐号。

基本使用

如下图,一条python myblog.py命令即可:

Typora_zKwwaE10Qe

目录/格式不敏感

m2w 2对于markdown所在文件夹的位置是不敏感的。一般来说,你只需要指定一个最上层的目录即可(下图示例中,只要指定new02即可):

此外,如果目标目录有其它格式的非markdown文件(比如jpg/gif),m2w 2会自动忽略它们——因为它们不太可能是博客文章。

其它提示

yaml头

和1.0版本一样,m2w 2支持在markdown文件添加yaml头。如下所示:

---
category: [docker]
tag: [wordpress, docker]
status: publish
---

其中category代表分类(一般是1个,但也可以多个),它在某些情况下参与文章默认链接的构成。tag代表标签(可有多个),status代表文章状态(publish发布/draft草稿/private隐私)。

逻辑判断

myblog.py中,首先进行网站连接,只有成功连接时才会进行md5 sum判断。该特点对于连接网络不稳定站点是必要的,因为由于q的原因这些站点偶尔会无法连接。如果事先进行了md5 sum判断且连接错误/超时,尽管下一次成功连接网站,也无法同步上次更新(因为md5值已经更新过了),这会给用户带来不必要的困扰。该特性在m2w v1.0.7已经添加,但较早的m2w版本里我并未考虑到这种可能性(踩坑成长ing)。

用VSCode来运行myblog.py的小伙伴建议加个代理。打开VSCode,按F1可调出设置文件settings.json。下图示范v2ray的ip和端口:

Code_1SggTYt0An

根据自己本地代理所使用类型、ip和端口进行更改即可。

信息级别

如果你觉得代码运行时的提示信息太“多”、太“杂”,可以在myblog.py中设置verbose=False。如下图:

Code_eNWySeRgwc

更改题目

一般建议题目在上传前就确定好。如果你真的需要更改一篇文章的题目,建议遵循以下步骤:

  • 去WordPress后台更改为新题目
  • 在本地Markdown里将文件名改为新题目.md
  • 运行m2w。由于force_upload=False(默认值),所以该文章并不会上传;但是在legacy*.json中却留下了记录
  • 新题目.md有更改内容时,会自动更新内容

听上去挺复杂。自己实践一下吧!总的来说,最好就是一开始就可以定型题目——这完全是可以做到的。在我博客有145篇博文的时候,印象中我只改过2次题目。

m2w 2.5

从2.5版本开始,m2w支持REST API喽 (ฅ´ω`ฅ) REST API 利用的是WordPress Application Password,它是一个具有某种用途的临时密码,而不是博客的登陆密码。 一般来说,管理员的密码拥有所有可操作权限;但WordPress Application Password仅有部分权限。

因此,REST API天然地比传统的登陆密码模式更加安全。就算REST API不小心被泄露了,也没关系,直接删除换个新的就行。我和小伙伴@FoxSuzuran共同完成了m2w的REST API兼容和开发工作。由于最近我的毕业答辩及工作等事宜已经稳定,所以有空完成了相关测试。

我测试的Python版本包括3.7.63.8.13.10.10,都可以正常工作。一般都是建议使用conda啦!大家直接使用pip install m2w即可下载最新版。用法和m2w 2.0几乎是一样的,只是user.json多了一个application_password参数。

m2w 2.5的实际使用效果如图所示:

Code_RccbFCh9Nm

REST API模式的效率与Password模式相当。值得一提的是,REST API模式还有一个友好的模式,即支持Markdown修改yaml头信息同步至WordPress后台,这在Password模式里暂时是无法实现的。还不赶紧升级尝尝鲜?

启用REST API

为了启用REST API模式,WordPress后台需要做一些准备工作。具体如下:

  • 如果使用了wordfence之类的安全插件,请启用WordPress应用程序密码:

WBrffVs5Ty

  • 创建一个新的REST API:

sq7kG7Vsqp

  • 安全地保管该API。如果有必要,可以重新生成或删除:

GddR0nP8mn

myblog.py

注意:与m2w 2的旧myblog.py在内容上有很大变动,并不互通。

m2w 2.5中,一些比较重要的参数定义在myblog.py里。实际上,m2w 2.5只提供基础函数;正式工作时是通过类似myblog.py的脚本来完成的。我认为,这样可以给高级用户充分的自由去定义m2w的使用。

下面是一些比较重要的参数:

  • path_m2w:字符型。指定元数据(即config文件夹)的路径,它通常包含1个user.json和系列legacy_*.json。
  • force_upload:布尔型。如果WordPress已经存在一个名为a的文章,是否强制上传本地一个名为a的markdown文件。默认force_upload = False,这样则不会为同题目的文章分配多个ID,因为它们往往是同一个文件。
  • verbose:布尔型。是否显示工作报告。默认verbose = True。不喜欢关注工作细节的小伙伴可以设置verbose = False
  • last_update_time_change:布尔型。仅适用于REST API模式。是否在更新文章时强制更新文章的发布日期。默认值为False。如果你希望更新文章后会排在最前列(时间倒序),你应该设置为True
  • max_retries:正整型。如果由于网络波动等原因导致上传/更新失败,重新尝试的最大次数。默认值为10

从这些参数可以看出,m2w 2.5相比m2w 2有更多细致的考虑。这也是该项目逐渐成熟的标志啦 (ฅ´ω`ฅ)

一般来说,只要改一下path_m2w,其它参数默认即可:

Code_jdWkHK4hhA

user.json

如果你要使用REST API模式,可以类似这样配置user.json

{
    "web01": {
        "domain": "https://blognas.hwb0307.com",
        "username": "your_username",
        "application_password": "your_rest_api",
        "path_markdown": [
            "E:/Github/m2w/@test/main",
            "E:/Github/m2w/@test/main2"
        ],
        "post_metadata": {
            "category": ["test"],
            "tag": ["test"],
            "status": "publish"
        },
        "path_legacy_json": "/config/legacy"
    }
}

如果你要使用旧的Password模式,可以类似这样配置user.jsonapplication_password也可以删除):

{
    "web01": {
        "domain": "https://blognas.hwb0307.com",
        "password": "your_password",
        "application_password": "",
        "path_markdown": [
            "E:/Github/m2w/@test/main",
            "E:/Github/m2w/@test/main2"
        ],
        "post_metadata": {
            "category": ["test"],
            "tag": ["test"],
            "status": "publish"
        },
        "path_legacy_json": "/config/legacy"
    }
}

小结

个人感觉m2w还是不错的。大家使用时有啥问题可以多多反馈,评论区留言或提issue都可以的!

扩展阅读

---------------
完结,撒花!如果您点一下广告,可以养活苯苯😍😍😍

感谢ZGOCLOUD友情赞助 (ฅ´ω`ฅ) 本博客基于m2w创作。版权声明:除特殊说明,博客文章均为Bensz原创,依据CC BY-SA 4.0许可证进行授权,转载请附上出处链接及本声明。VIP内容严禁转载!由于可能会成为AI模型(如chatGPT)的训练样本,本博客禁止将AI自动生成内容作为文章上传(特别声明时除外)。如有需要,请至学习地图系统学习本博客的教程。加Telegram群可获得更多帮助喔! | 博客订阅:RSS | 广告招租请留言 | 博客VPS | 致谢渺软公益CDN |

评论

  1. 东山月光下
    Windows Chrome 120.0.0.0
    已编辑
    1月前
    2024-1-26 0:36:43

    大佬你好,我这里运行myblog.py,部分文章提示“Messages:分类法中已存在同名项目”,相应的文章传不上去,删掉所有tag就好了。再加上tags运行myblog.py,不能更新tags,有的又报错。不太理解这是为啥,为啥要筛查tag,我的tags大概始终就是从十几个词里挑的。m2w版本是2.5.12。感谢!

    • 博主
      东山月光下
      Windows Edge 120.0.0.0
      4周前
      2024-1-27 7:55:51

      没有遇到过这个bug喔,你贴一下markdown的yaml头、user.json内容(隐藏帐号和密码/token)和myblog.py内容。 可以发到邮箱 [email protected]

      • 东山月光下
        Bensz
        Windows Chrome 121.0.0.0
        4周前
        2024-1-29 16:27:09

        发啦

  2. DongLi
    Windows Chrome 119.0.0.0
    已编辑
    3月前
    2023-11-15 17:48:55

    大佬,我在pycharm中运行该项目,依赖装入虚拟环境,运行后出现了这个问题,好像是找不到版本维护的json文件,这个版本维护文件不是自动生成的吗,求大佬帮忙看一看,感谢:

    
    ========Website: donglistudio
    Traceback (most recent call last):
      File "F:\MyBlog\m2w\myblog.py", line 103, in <module>
        asyncio.run(main())
      File "E:\Work\Python\lib\asyncio\runners.py", line 44, in run
        return loop.run_until_complete(main)
      File "E:\Work\Python\lib\asyncio\base_events.py", line 642, in run_until_complete
        return future.result()
      File "F:\MyBlog\m2w\myblog.py", line 80, in main
        await up(
      File "F:\MyBlog\m2w\m2w\up.py", line 36, in up
        shutil.copyfile(path_legacy_json, path_legacy_json + "_temporary_old")
      File "E:\Work\Python\lib\shutil.py", line 261, in copyfile
        with open(src, 'rb') as fsrc, open(dst, 'wb') as fdst:
    FileNotFoundError: [Errno 2] No such file or directory: 'F:/MyBlog/m2w/config/legacy_donglistudio.json'
    • 博主
      DongLi
      Windows Edge 119.0.0.0
      3月前
      2023-11-15 21:58:19

      这个Json并不是自己自成的。 你直接根据模板修改一下就好了 如果实在不太懂的话,可以Todesk远程协助你

      • DongLi
        Bensz
        Windows Chrome 119.0.0.0
        3月前
        2023-11-15 22:50:52

        legacy*.json这个json文件我在教程文中以及github项目README都找了一遍,没能找到,大佬方便指个路吗

      • 博主
        DongLi
        Windows Edge 119.0.0.0
        3月前
        2023-11-15 22:55:28

        啊不好意思,我迷糊了 ~ 这个文件是自动生成的,它的作用是记录md5值 (~ ̄▽ ̄)~ 我已经意识到自己的错误了。因为当时我是在自己的网站里测试的,这个时候legacy文件已经是存在了的。 所以最新版本的m2w存在这个很严重的bug。我更新一下代码,之后通知您。 谢谢啦!

      • 博主
        DongLi
        Windows Edge 119.0.0.0
        3月前
        2023-11-15 23:12:15

        已经修复该bug。请更新m2w 2.5.12。谢谢提醒啦!

      • DongLi
        Bensz
        Windows Chrome 119.0.0.0
        3月前
        2023-11-15 23:27:27

        嗯嗯,大佬辛苦啦 ୧(๑•̀⌄•́๑)૭

      • DongLi
        Bensz
        Windows Chrome 119.0.0.0
        3月前
        2023-11-16 2:04:48

        大佬,发现一个小bug,就是如果定义一个一级标题,并且这个一级标题以#结尾,那么上传之后#会丢失,比如 C# 作为标题,那么上传之后就会变成 C,不过我感觉这个也有可能不是您代码的bug,说不定是wordpress解析问题?

      • 博主
        DongLi
        iPhone Chrome 119.0.6045.109
        已编辑
        3月前
        2023-11-16 6:05:29

        可以在markdown里面使用转义符,C\#,这样转化为html的时候就不会有问题了

      • DongLi
        Bensz
        Android Chrome 99.0.4844.88
        3月前
        2023-11-16 9:49:31

        好的,感谢大佬!

  3. Jkevin
    Linux Firefox 113.0
    9月前
    2023-5-22 14:29:26

    貌似修改tag跟catagory不会跟着更新|´・ω・)ノ

    • 博主
      Jkevin
      Windows Edge 113.0.1774.50
      9月前
      2023-5-24 8:01:42

      是的。如果你要改tag,自己在后台修改就行。 一般我文章的tag都是固定的,文章完成时就已经确定了。

  4. 咕咕
    Macintosh Chrome 108.0.0.0
    1年前
    2023-1-06 16:54:09

    这个我测试了一下,很不错!非常实用!不过我用argon主题测试发现,上传上去之后,图片如果比较小的话(外链),是居左显示的,这个argon主题应该可以通过修改css让文章里的图片全部居中显示的吧,不知道你折腾过没

    • 博主
      咕咕
      Windows Edge 108.0.1462.54
      1年前
      2023-1-06 16:57:19

      详见《特效》。具体方法是添加一个额外CSS:

      /*正文图片居中显示*/
      .fancybox-wrapper {
          margin: auto;
      }

      我记得你用的不是halo?

      • 咕咕
        Bensz
        Macintosh Chrome 108.0.0.0
        1年前
        2023-1-06 18:28:32

        啊哈,我是用halo,昨天正好有时间就折腾了一下你的m2w?

      • 博主
        咕咕
        Windows Edge 108.0.1462.54
        1年前
        2023-1-06 18:47:14

        我个人觉得m2w还不错的,写作和修改博文比较方便 ୧(๑•̀⌄•́๑)૭

    • 博主
      咕咕
      Windows Edge 114.0.1823.43
      9月前
      2023-6-11 8:33:09

      咕咕,最近m2w更新了2.5+版本,比以前要强大很多。 感兴趣可多多关注!

  5. Windows Edge 108.0.1462.42
    1年前
    2022-12-07 22:47:54

    请问博主这个错误是为啥 xmlrpc.client.Fault: <Fault 500: ‘项目需要一个名字。’>

    • 博主
      infinity
      Windows Edge 107.0.1418.62
      1年前
      2022-12-07 23:17:11

      啊这,我还没遇到过哎。可以贴一下你的user.json内容吗(请将安全信息隐藏)

      • Bensz
        Windows Edge 108.0.1462.42
        已编辑
        1年前
        2022-12-08 8:48:00

        我看了一下能自动获取到md文件的名字,但是还是会报错,下面是我的userjson

        
            "web01": {
                "domain": "https://www.infinityday.cn/",
        
                "path_markdown": [
                    "D:/m2w/@test/main1/test1",
                    "D:/m2w/@test/main2/test2"
                ],
                "post_metadata": {
                    "category": [
                        "建站"
                    ],
                    "tag": [
                        ""
                    ],
                    "status": "publish"
                },
                "path_legacy_json": "/config/legacy"
            }
        } ```隐去了账户与密码
      • infinity
        Windows Edge 108.0.1462.42
        1年前
        2022-12-08 8:52:51

        早上起来debug了一下,发现是tag为空的问题,加上一个tag就可以正常推送了

      • 博主
        infinity
        Windows Edge 107.0.1418.62
        1年前
        2022-12-08 8:54:23

        tag确实不可以是空的。另外,你这markdown的路径是不是也有点问题?这不是我默认的路径嘛,你的应该也不一样

      • Bensz
        Windows Edge 108.0.1462.42
        已编辑
        1年前
        2022-12-08 8:58:05

        我的markdown路径就是按照博文自己建立的,测试好了之后我再改成自己的,现在发现是可以正常推送和更新的。但是我觉得一篇博文不需要tag也是可以的,所以昨天死活没有找到问题,去对应位置print一下,发现也能出现md的文件名,所以我猜可能是配置的问题,今天早上改了tag就可以了

      • 博主
        infinity
        Windows Edge 107.0.1418.62
        1年前
        2022-12-08 9:02:38

        加tag好一些,这样文章系统会比较有条理。如果没有特别倾向,可以设定默认tag为common、general之类的词。一般我写博文的时候,该博文都会对应某个主题。就算是吐槽,也有一个关于“吐槽”的tag或category ヾ(≧∇≦*)ゝ

      • 博主
        infinity
        Windows Edge 107.0.1418.62
        已编辑
        1年前
        2022-12-08 8:53:14

        你这个user.json文件感觉问题很大? 可以远程连线看一下。你有telegram的话可以加群: https://t.me/benszhub 。没有就加QQ吧

      • Bensz
        Windows Edge 108.0.1462.42
        1年前
        2022-12-08 8:55:21

        我弄一个telegram去向大佬们学习一下

      • 博主
        infinity
        Windows Edge 107.0.1418.62
        1年前
        2022-12-08 8:56:14

        好的,加油! (๑•̀ㅁ•́ฅ)

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇