使用metaweblog API实现通用博客发布 之 本地图片自动上传以及替换路径
阅读原文时间:2023年07月09日阅读:1

使用metaweblog API实现通用博客发布 之 本地图片自动上传以及替换路径

通过metaweblog API 发布博文的时候,由于markdown中的图片路径是本地路径,将导致发布的文章图片不能正确查看。两种通用的办法是: 1 将图片发布到专用的图片服务器,然后将链接替换; 2 将图片发布到博客平台,然后将链接替换。

这篇小文件探讨的是第二种方式。

使用正则表达式进行查找

def matchMarkdownLinks(post):
  return re.compile('!\\[.*?\\]\\((.*?)\\)').findall(post)

使用正则表达式判断是否是本地链接,如果已经是网络链接,就不用进行上传操作了

def isNetLink(link):
  return re.match('((http(s?))|(ftp))://.*', link)

判断图片的压缩格式,如果有必要,转换成gif格式(支持透明背景)

from PIL import Image

def replace_img_url(path, pictype):
  (name, suffix) = os.path.splitext(os.path.basename(path))
  if not pictype in ["gif","jpg"]:
    img = Image.open(path)
    localfile = "%s.gif"%(name)
    img.save(localfile, 'gif')
    with open(localfile, 'rb') as f:
      url = client.newMediaObject({
        "bits": f.read(),
        "name": os.path.basename(localfile),
        "type": "image/gif"
      })
    os.remove(localfile) #remove local temp file
    return url
  else:
    with open(path, 'rb') as f:
      url = client.newMediaObject({
        "bits": f.read(),
        "name": os.path.basename(path),
        "type": "image/" + suffix
      })
    return url

其中的client就是上篇文章中写的metaweblog 客户端。 转换图片时,使用了PIL图片库

首先使用正则获取所有链接,判断链接是否是本地链接

然后判断本地链接文件是否存在,使用 imghdr 模块猜测图片格式

最后上传本地图片,替换链接地址

import imghdr

def fixMarkdownLink(md_file):
  with open(md_file, 'r', encoding="utf-8") as f:
    post = f.read()
    matchs = matchMarkdownLinks(post)
    print(matchs)
    if matchs and len(matchs) > 0:
      for link in matchs:
        if not isNetLink(link):
          localPath = link
          if not os.path.exists(localPath) or not os.path.isfile(localPath):
            sep = os.path.sep if (md_file.find(os.path.sep) >= 0) else ("\\" if (md_file.find("\\") >= 0) else "/")
            localPath = md_file[:md_file.rfind(sep)+1] + localPath
          if os.path.exists(localPath) and os.path.isfile(localPath):
            imgtype = imghdr.what(localPath)
            if imgtype:
              file_url = replace_img_url(localPath, imgtype)
              if file_url and file_url["url"]:
                post = post.replace(link, file_url["url"])    # 替换md文件中的地址
    return post

未完待续,下篇继续探讨修改本地markdown文件后的自动更新方案