deepin優雅地創作和分享技術博客


最新更新於2022年02月24日

1. 閑言碎語

好記性不如爛筆頭。我們很多人喜歡寫技術博客,構建知識庫,然后把它們分享到網絡平台,比如自建博客,主流博客平台,又或者記錄在自己的筆記軟件。

以下是我個人觀點:

寫技術博客,博文格式首選markdown。寫makrdown,博文內容所見即所得比預覽或者人腦渲染更爽。

博客發布平台,首選比較干凈整潔的博客園。其他比如CSDN,簡書,開源中國。很多人喜歡多平台一起發布,也沒啥問題。

把博客當作代碼,托管在github/gitee。把博客當作知識庫,放在個人博客網站,筆記軟件,導圖軟件,都是主流選擇。

實際上我也想這么做,還沒有付出更多的實際行動。

有人說,使用windowns系列操作系統+寫作或者筆記軟件來寫,或者在線寫不香嗎?或者離線寫好,同步軟件同步,粘貼到在線平台不香嗎?

實話說,挺香。

選擇【創作】【保存】【同步】【分享】的組合方式很多,但是我還是喜歡找到適合自己的舒服的方式。

用typora寫好了,右鍵分享一下,就能發布到博客,也挺香

我個人的組合方式:deepin+typora+cnblogs+wiznote

當然typora已經收費,wiznote已經發布Linux版本。更多更好的替代,都在排着隊......

===================================================================

着重和正式強調:不要拿博客平台當圖床用,后果自負!!!

===================================================================

2. 正式入題

之前也寫過一篇比較全面的博客《Deepin15和20使用命令行快捷鍵鼠標右鍵發布博客至博客園和為知筆記》

在上面這篇博客中,你能在deepin上,用快捷鍵,用命令行,用右鍵三種姿勢,來分享你的博客

但是今天,我把代碼改了改,2.0版本出來了。最重要的就是,能夠上傳圖片了,香不香?

2.1 python3+xmrpc.client實現代碼

以下是主要的代碼:

#!/usr/bin/env python3
# -*- coding:utf-8 -*-
# ***************************************************************************
# * 
# * @file:send_to_cnblogs.py 
# * @author:liwanliang 
# * @date:2021-12-08
# * @version 2.0  
# * @description: Python Script 
# * @Copyright (c)  all right reserved 
# * 
# ***************************************************************************
# 本腳本發送博客至www.cnblogs.com
# --file 指定要上傳的markdown博客文件
# --upload 指定要上傳的(多個)圖片
# 更新:
# 2022-02-24: 更新博客時,如果博客之前有標簽,推送博客保持之前的標簽
# ***************************************************************************

import sys
import xmlrpc.client #{'python3':"xmlrpc.client",'python2':"xmlrpclib"}
import mimetypes
import os
import json
import subprocess
from optparse import OptionParser

class CnblogsAPI():
    """
    從配置文件讀取用戶的:url,帳號,密碼
    """
    def __init__(self,config_json):
        self.__url,self.__user,self.__password = self.__read_config(config_json)
        self.__cnblogs_api = xmlrpc.client.ServerProxy(self.__url)
        self.__user_info = self.__cnblogs_api.blogger.getUsersBlogs('',self.__user,self.__password)
        self.__user_blogid = self.__user_info[0].get('blogid')

    def __read_config(self,config):
        try:
            with open(config,'r') as f:
                data = json.load(f)
                url = data.get('url')
                user = data.get('user')
                password = data.get('password')
                if not all([url,user,password]):
                    print("配置文件未正確指定:url,user,password")
                    sys.exit(0)
        except IOError:
            print("未指定配置文件")
            sys.exit(0)
        return (url,user,password)
                
    def get_all_blogs(self):
        """
        獲取全部博客:{title:postid}
        """
        blogs_title_postid = {}
        all_blogs = self.__cnblogs_api.metaWeblog.getRecentPosts(self.__user_blogid,self.__user,self.__password,0)
        for blog in all_blogs:
            blogs_title_postid.update({blog.get('title'):blog.get('postid')})
        return blogs_title_postid

    def __get_post_id(self,post_name):
        """
        通過博客標題獲取博客的post_id
        """
        return self.get_all_blogs().get(post_name)
    
    def __get_mt_keywords(self,post_name):
        """
        獲取tag
        """
        return self.__cnblogs_api.metaWeblog.getPost(self.__get_post_id(post_name),self.__user,self.__password).get('mt_keywords')

    def upload_image_get_url(self,image):
        """
        指定圖片上傳圖片,返回圖片的url
        """
        with open(image,'rb') as f:
            image_bits = xmlrpc.client.Binary(f.read())
        image_type = mimetypes.guess_type(image)[0]
        image_name = os.path.basename(image)
        url = self.__cnblogs_api.metaWeblog.newMediaObject(
            	self.__user_blogid,
            	self.__user,
            	self.__password,
            	dict(bits=image_bits,name=image_name,type=image_type))
        return url.get('url')

    def edit_post(self,blog_file):
        """
        指定博客文件上傳,發送通知到操作系統
        """
        with open(blog_file,'r') as blog:
            blog_content = blog.read()

        post_name = os.path.basename(blog_file)
        post_id = self.__get_post_id(post_name)
        mt_keywords = self.__get_mt_keywords(post_name) if post_id else "" #判斷tag是否存在,存在添加tag
        post_info = {
            'title':post_name,
            'description':blog_content,
            'categories':['[]','[Markdown]'],#默認不發送到博客園首頁候選區,默認markdown格式
            'mt_keywords':mt_keywords, #添加tag
        }

        if post_id:
            return self.__cnblogs_api.metaWeblog.editPost(
                	post_id,
                	self.__user,
                	self.__password,
                	post_info,True)
        else:
            return self.__cnblogs_api.metaWeblog.newPost(
                	self.__user_blogid,
                	self.__user,
                	self.__password,
                	post_info,True)

#****************************************************************************#
#上面的代碼,主要是封裝接口,復用性很強,ctrl+c,ctrl+v拿走就行。
# 下面的代碼,就是個性化功能配置了
# 我個人的配置文件:
# 帳號密碼配置文件,/home/liwl/.liwl/deepin/scripts/cnblogs.json
# conblogs.json內容:
#{
#	"url":xxxx,
#	"user":xxxx,
#	"password":xxxx,
#}
# deepin分享博客成功后,發送一個系統通知,其icon圖片
# /home/liwl/.liwl/deepin/picture/cnblogs.png
#****************************************************************************#
if __name__ == "__main__":
    #腳本參數
    parser = OptionParser()
    parser.add_option("-f","--file",dest="filename")
    parser.add_option("-u","--upload",dest="image",action="append")
    (options,args) = parser.parse_args()

    #加載配置文件
    liwl_cnblogs = CnblogsAPI('/home/liwl/.liwl/deepin/scripts/cnblogs.json')

    #獲取markdown博客
    markdown_blog = options.filename
    if options.filename:
        if liwl_cnblogs.edit_post(markdown_blog):
            subprocess.run('notify-send -i /home/liwl/.liwl/deepin/picture/cnblogs.png "創建/更新博客,成功"',shell=True)
        else:
            subprocess.run('notify-send -i /home/liwl/.liwl/deepin/picture/cnblogs.png "創建/更新博客,失敗"',shell=True)

    #以下適合命令行發送
    #else:
        #subprocess.run('notify-send -i /home/liwl/.liwl/deepin/picture/cnblogs.png "未指定博客文件"',shell=True)
        

    #獲取多個圖片
    if options.image:
        for img in options.image + args:
            print(liwl_cnblogs.upload_image_get_url(img))
    #以下代碼適合命令行發送
    #else:
        #subprocess.run('notify-send -i /home/liwl/.liwl/deepin/picture/cnblogs.png "未指定(多個)圖片"',shell=True)

上面的代碼,保存到一個路徑下:/home/liwl/.liwl/deepin/scripts/send_to_cnblogs.py

注意賦予一個執行權限:chmod +x /home/liwl/.liwl/deepin/scripts/send_to_cnblogs.py

2.2 deepin配置右鍵發送

創建一個desktop文件:

sudo vim /usr/share/deepin/dde-file-manager/oem-menuextensions/deepin-send.desktop

內容如下:

[Desktop Entry]
Type=Application
Name=發布文檔到
Actions=SendTocnblogs;SendTonsccwx;SendTowiznote
X-DFM-MenuTypes=SingleFile
MimeType=text/markdown

[Desktop Action SendTocnblogs]
Name=博客園
Exec=python3 /home/liwl/.liwl/deepin/scripts/send_to_cnblogs.py --file %U
Icon=send-to

2.3 Typora配置上傳圖片

如下圖配置即可

需要注意的是,【上傳服務設定】-【命令】要寫腳本絕對路徑和參數,如下:

python3 /home/liwl/.liwl/deepin/scripts/send_to_cnblogs.py --upload

下面這張圖,就是我截圖之后,粘貼在typora,自動上傳的哦

image-20211208145559890

3. 原理分析

其實也沒啥原理,主要是以前沒有注意到metaWeblog.newMediaObject這個接口,這兩天研究了一下,發現這個接口,就把這個腳本重新修改了一下

簡單理解:xmlrpc是一個協議,python實現了這個協議接口

python2的協議接口為:xmlrpclib,python3的協議接口包為:xmlrpc.client

博客園允許你使用這個協議來使用他們提供的接口,而且有個前提,你需要在自己的博客設置里面啟用這個功能

博客設置——其他設置——勾選允許MetaWeblog博客客戶端訪問

Typora又恰好提供了使用命令或者腳本的方式來獲取圖片的url

所以,一切都是那么順其自然,挺幸運

本篇博客就是在deepin系統下,寫完了以后,右鍵發送到博客園的呢,右鍵

image-20211208152257579

發送成功后,deepin上方會有如下圖提示:

image-20211208150658598


最后還是強調,不要把博客平台當作圖床來用,否則后果自負


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM