ラベル python の投稿を表示しています。 すべての投稿を表示
ラベル python の投稿を表示しています。 すべての投稿を表示

2011-01-13

20 minutes blogging trail [2011-01-12 Wed]

今日もこのブログに書くことを考えながら過ごす20分の時間をスタートさせました。 例によってネタは「org-modeからblogger.comへ投稿できる」ということですが。

使っている道具を紹介します。

  • org-blogger.el
  • org2blogger.el
  • get-direct-url-in-picasa.py
  • getalbumid.py
  • upload-image-to-blogger-in-picasa.py

です。 なお、これらのpythonスクリプトは

  • gdata ライブラリ?

が先にインストールされてないと動作しません。 ま、インストールしたと言うことで。

使うための用意

まずは、albumidを取得して、次のアップロードに備えます。この作業は初回のみでOKです。 毎回行う必要はありません。

#!/usr/bin/python
import sys
import gdata.photos.service

#usage: in command.com like winXP, 
# > python get_albmid.py| nkf -s
# use "nkf -Wsd", if needed.

args = sys.argv
#args.pop(0)
email = "your@gmail.com"
password = "it's a nuts"
username='default'

gd_client = gdata.photos.service.PhotosService()
gd_client.email = email
gd_client.password = password
gd_client.source = 'exampleCo-exampleApp-1'
gd_client.ProgrammaticLogin()

albums = gd_client.GetUserFeed(user=username)
for album in albums.entry:
  print 'id:[%s] title:[%s] number of photos: %s' % (album.gphoto_id.text, album.title.text, album.numphotos.text)

を実行すると、

>get_albumid.py
id:[5555555555555555555] title:[Windows Live Writer] number of photos: 2
id:[1234567890123456789] title:[Chemical-X] number of photos: 18

というIDの数字と、アルバムのタイトルが出てきました。 アルバムは、picasa内で確認できるアルバムの数と同じです。

そして、特定のアルバムに画像を追加したいときに、この album id :1234567890123456789 (自分の"Chemical-X"なら) を次に使います。

画像の有無をチェック・無ければアップロード

ここで得たalbum id を使って、そのアルバムに画像を追加したいとします。

bloggerに執筆するときにはそれらをひとまとまりにしたい

というのが良くある考え方だと思います。 その時、 get-direct-url-in-picasa.pyをつかって、picasa上にその画像の有無を調べます。 画像があれば、picasa上のファイルへのdirect linkが得られるはずです。 もしpicasa上にその画像が無いと判断したら、 upload-image-to-blogger-in-picasa.pyをつかって、 最初に得たalbum id を指定して、画像をアップロードします。 そしてその画像のpicasa上でのdirect linkをget-direct-url-in-picasa.pyで得ます。

まずはget-direct-url-in-picasa.py の内容です。

#!/usr/bin/python2.5
# return the direct link (URL) of picture in picasa.

import sys # for argv
import gdata.photos.service
import gdata.media
import gdata.geo

argvs = sys.argv
argc = len(argvs)
if (argc != 3 ):
    print 'Usage: # python %s AlbumName FileName' % argvs[0]
    quit()

albumname = argvs[1]
filename = argvs[2]
album_id="1234567890123456789" # the albm_id fo "Chemical-X" was given by get_albumid.py

gd_client = gdata.photos.service.PhotosService()
gd_client.email = 'changeme@gmail.com'     # Set your Picasaweb e-mail address...
gd_client.password = 'secret word'  # ... and password
gd_client.source = 'api-sample-google-com'
gd_client.ProgrammaticLogin()



album_url = '/data/feed/api/user/%s/albumid/%s' % ('default', album_id)
photos = gd_client.GetFeed('/data/feed/api/user/%s/albumid/%s?kind=photo' % ('default', album_id))
for photo in photos.entry:
    if photo.title.text == filename :
        print photo.content.src,

続いて、upload-image-to-blogger-in-picasa.py の内容です。

#!/usr/bin/python2.5
# return the direct link (URL) of picture in picasa.

import sys # for argv
import gdata.photos.service
import gdata.media
import gdata.geo

argvs = sys.argv
argc = len(argvs)
if (argc != 2 ):
    print 'Usage: # python %s FileName' % argvs[0]
    quit()

filename = argvs[1]


gd_client = gdata.photos.service.PhotosService()
gd_client.email = 'changeme@gmail.com'     # Set your Picasaweb e-mail address...
gd_client.password = 'secret password'  # ... and password
gd_client.source = 'upload-image-to-blogger-in-picasa'
gd_client.ProgrammaticLogin()
album_id="1234567890123456789" # the albm_id fo "Chemical-X" was given by get_albumid.py


album_url = '/data/feed/api/user/%s/albumid/%s' % ('default', album_id)
photo = gd_client.InsertPhotoSimple(album_url, filename, filename, filename, content_type='image/png')
print photo.content.src,

これで、画像がもともとpicasa上にあってもなくてもどちらの場合だったとしても、 処理後には、picasa上のurlを取得できたことになります。

それを使って、org2blogger.elでは、エクスポートしたhtml無いでの画像リンク先を変更するという作業を行います。 以下、org2blogger.el.

(setq get-url-script-name "pathto/org2blogger/get-direct-url-in-picasa.py")
(setq upload-image-script-name "pathto/elisp/org2blogger/upload-image-to-blogger-in-picasa.py")
(setq image-file-path "l:/0mine/org/images/")
(setq blog-name "Chemical-X")
(setq albumid "1234567890123456789") ; given by get_albumid.py for "Chemical-X")

(defun replace-links-with-upload-image-url ()
  (interactive)
  (while (re-search-forward "^<img src=\"images/\\(.*\.png\\)\"  alt=\"\\(.*\.png\\)\" />" nil t)
      (setq local-image-file-name (buffer-substring-no-properties (match-beginning 1) (match-end 1)))

      ;check the blog already has the image file or not.
      (setq uploaded-img-url 
            (chomp (get-uploaded-img-url get-url-script-name blog-name local-image-file-name)))
      (message "Match file name: %s" uploaded-img-url)
      (if (string-equal uploaded-img-url "")
                                        ;if the blog does not have the image, upload the image firstly, and receive the URL.
                                        ;if the blog has the image, just receive the URL.
          (progn
            ;upload image file-name
            ;get uploaded file name (direct URL) again.

            (setq uploaded-img-url
                  (shell-command-to-string (concat upload-image-script-name " " image-file-path local-image-file-name)))
            (message "uploaded-img-url:%s" uploaded-img-url)
;           (setq uploaded-img-url 
;                 (chomp (get-uploaded-img-url get-url-script-name blog-name local-image-file-name)))
            )
        )

      ;replace the line with htmlized-img-url string.
      ;Delete line
      ;The equivalent of ‘kill-line’ (‘C-k’) but without kill ring side effects:
      (delete-region (line-beginning-position) (line-end-position))

      (insert (htmlized-img-url uploaded-img-url))
      )
;  (message "matched string: %s" match-string)
)


(defun get-uploaded-img-url (script-name blog-name file-name)
      (shell-command-to-string (concat script-name " "
                                       blog-name " "
                                        file-name)))


(defun chomp (str)
      "Chomp leading and tailing whitespace from STR."
      (let ((s (if (symbolp str) (symbol-name str) str)))
        (replace-regexp-in-string "\\(^[[:space:]\n]*\\|[[:space:]\n]*$\\)" "" s)))

(defun htmlized-img-url (uploaded-img-url)
  (concat "<a "
          "onblur=\"try {parent.deselectBloggerImageGracefully();} catch(e) {}\" "
          "href=\"" uploaded-img-url "\">"
          "<img "
          "style=\"display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px;\" "
          "src=\"" uploaded-img-url "\" "
          "border=\"0\" "
          "alt=\"\" "
          "/>"
          "</a>"
          )
  )

置換し終わったhtmlをorg-googlecl.elのorg-googlecl-blog関数を使ってblogger.comへ投稿します。 org-modeで書いたテキスト内で、

M-x org-googlecl-blog

してみてください。 世界が変わって見えましたか?

終わりに

これで画像を含むorg-mode の文章も、全自動でblogger.comへ投稿できるようになりました。 org-mode でblogger.comへ投稿するすてきなemacsライフを。

35分かかりましたね。まぁ、いいや。 このシリーズはこれでおしまいです。

2011-01-12

20 minutes blogging trial [2011-01-11 Tue]

昨夜遅くに申し訳程度の更新をしました。 org-modeで書いたエントリをblogger.comへ投稿するブログ投稿機能が一通り揃いました。

コードやスクリプト達が実際にしてくれるのは、以下の事柄です。 処理を、リストと図に並べて記します。 (図は昨日投稿したものです)

https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgYMaYRKvRc8yMcLWwZ69kRjuLEbswWSTBpKUDYtB1mIvlMlz_UZiLKOOZ98ZW927ILJLatgj6VKDBpeRMdNwu2HrhbHk3m5SxstldCzHHmNtwDmu4CcpKkO8QQpnRWK-UtimeW_Wy00_k/

Blog posting procedure from org-mode with some scripts.

  1. org形式をhtml形式へ変換して出力する
  2. orgファイル内で、ditaa, dot, src内で記述した画像ファイル(png)を生成する
  3. 指定されたたローカルのアドレスを、picasa上のアドレスに置換する
    1. imgタグで指定した(ローカルにある)ファイル名がpicasaのアルバム内にあるかを確認する
      1. アルバム内に該当するファイルが見つからなければ、アップロードする
    2. 3.1. で確認されたpicasa内のURLを取得する
  4. blogger.comに3.の内容を投稿する

これを説明しようとエントリを書いてみたのですが、この時点で既に25分経っています。

アルバム内で目的のファイルがあるかの確認には、pythonスクリプトを使いました。 スクリプト作成には ミドルスペックを低負荷で: ☆BloGTK補完計画 を、ほとんどそのまま流用させてもらいました。

picasa apiにdirect linkを得る関数がありました。 あと、アルバムを指定するときに、album idを取得する事も参考にしました。

30分越えてしまいました。 時間があっという間に過ぎました。

2011-01-10

20 minutes blogging trial [2011-01-09 Sun]

blogger.com 経由でアップロードした画像ファイルの direct link が取得できました。 googleclはwindows版でのコンパイル済みのモノを使っていたので、開発待ちという状況でした。 python の gdata を取ってきて、ドキュメントを見ていくと、 (画素数を指定されていない)オリジナル画像のURLは photo.content.srcで出力されることが分かりました。 こんな感じです。

picasa-direct-url.pyの内容。

#!/usr/bin/python2.5

import gdata.photos.service
import gdata.media
import gdata.geo

gd_client = gdata.photos.service.PhotosService()
gd_client.email = 'change.me@gmail.com'     # Set your Picasaweb e-mail address...
gd_client.password = 'change.your.password'  # ... and password
gd_client.source = 'api-sample-google-com'
gd_client.ProgrammaticLogin()

albums = gd_client.GetUserFeed()
for album in albums.entry:
  print 'Album: %s (%s)' % (album.title.text, album.numphotos.text)

  photos = gd_client.GetFeed('/data/feed/api/user/default/albumid/%s?kind=photo' % (album.gphoto_id.text))
  for photo in photos.entry:
      print 'Photo:', photo.title.text, '\n', photo.content.src

これを起動すると、

path/to/gdata-2.0.13/samples>picasa-direct-url.py
Album: Chemical-X (16)
(snip)
Photo: conventional-way-converting-html2blogger.png
https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjSujdlSS4LJQKZX_vHVzmqgV6_mXcuTGzzL6wdL09XHVRm0SzBuPM8DO4U2XL5knR4yRxU8InB10WoxAA7Lxpuo9Oi0NQNZvskO9c11n3xzMKOhy812WtTy74yhFvR17BkM3li_GBG7eo/
al-way-converting-html2blogger.png
(snip)

長いURLが出力されています。

これで、org-modeでのテキスト作成->emacsからblogger.comへの自動投稿 への道が更に開けそうです。 画像も対応してblogger.comに自動投稿してくれたらそれはとても便利になります。

ただ、org-googlecl.elのみを利用するかというと、それはちょっと分かりません。 現状のorg-googlecl.elで文字列を送る機能を実装して、 画像を挿入したいときには、そのdirect-link のURLを api で取得、それをelispでhtmlのAタグまで整形。 この方法が、一番感性が早そうです。

googleclに画像を含めたポスト機能を求めるのは結構時間が必要になりそうです。 org-mode内でorg-babelを使って生成した画像を含めて、googlclが全部をポストするには、今の情報では足りなさそうだからです。 直リンクするためのアドレスを取得しなければいけません。 その機能をgoogleclが作られるのを待つしかないわけです。 googlecl wikiで探しても、希望は一件のみで、それに対応するチケットが切られていない用です。

Comment by gialloporpora, Jul 23, 2010

Is it possible to have an option to print the url-direct after posting an image on Picasa? I would like to see the direct link to the image that I have posted, better if I could select output format (html, BBCode) to embeed it. Another thing, is it possible to accept also URL (remote images) as input, not only local images?

Sandro

残念なことに何も反応がありません。

ですので、google apiが用意されていて、gdataで操作できるなら、自分で直接やった方が早そうです。 何が知りたいかはもう分かっているわけですから。 phthonはほとんどいじったことがありませんが、まぁ、何とかなるでしょう。。

最初に想像したこと、

XMLのやりとり全てをelispで書いて実現する

という悪夢の様な状況1と比べれば、よっぽど楽になりそうです。

python勉強時間確保の優先順位が上がりました。 楽しいことを勉強できるのは最高に幸せな時間です。

今日はemacsとblogger.comとの周りの状況を説明するのに、35分もかかってしまいました。 20minじゃないですよね。 全然時間が足りませんでした。

Footnotes:

1 atom-blogger.elというライブラリがあります。2006年に公開されております。詳しくは@ Blogger 投稿用の Emacs パッケージをご覧下さい。

Related Posts: