Fork me on GitHub

2011/10/17


このエントリーをはてなブックマークに追加
以前、「jekyllで始める簡単ブログ」という記事を書いたのですが
Big Sky :: Jekyllで始める簡単ブログ

GithubのユーザページでJekyllが使われる様になりました。 GitHub Pages Upgraded to Jekyll 0.5.0 - GitHub I just released Jek...

http://mattn.kaoriya.net/software/lang/ruby/20090409185248.htm
octopressというのを使うともっと簡単に出来る事が分かった。
Octopress

Octopress is a framework designed by Brandon Mathis for Jekyll , the blog aware static site generato...

http://octopress.org
imathis/octopress - GitHub

What is Octopress? Octopress is Jekyll blogging at its finest. Octopress sports a clean responsive t...

https://github.com/imathis/octopress
以下簡単な手順を示す。
このgithubリポジトリは基本的に、1ブログに対して1つcloneする。cloneしたら
# rake install
する。octopressをシステムにインストールのではなく、このブログ用リポジトリにsassテーマをキャッシュさせる為の設定を行うだけなので安心してやって貰ってok。
次にgithubにブログを作るのであれば
# rake setup_github_pages
を実行し、読み取り書き込み権限のあるgit URLを貼り付けて完了。
Windowsの場合はちょっとここで修正が必要で、config.rbとかRakefileに変なパスが書かれているので直す。実際にはpublic/c:/path/to/public...みたいなフルパスが重なっているはずなのでpublic...に直せばok。
これについては時間があったらパッチ書いてpull requestを送るつもり。

さて、これでブログを書く準備が出来ました。簡単すぎますね!

試しにsource/_posts/2011-10-17-github-jekyll.mkdというmarkdownのファイルを作ります。中身は以前ご紹介した内容と変わりませんが、ocotopressは幾らか拡張プラグインが入っているので色んな書き方が出来ます。
例えばgist tagプラグインを使って
---
layout: post
title: "githubとjekyllとoctopressで作るブログ"
date: 2011-07-03 5:59
comments: true
categories:
---
便利すぎる...

{% gist 1292428 %}
こう書いて
# rake gen_deploy
すると
githubとjekyllとoctopressで作るブログ - ギッハブる日記

Recent Posts githubとjekyllとoctopressで作るブログ Github Repos Status updating... @mattn on Github Latest T...

http://mattn.github.com/blog/blog/2011/07/03/github-jekyll/
こんな記事が出来上がります。dateはファイル名じゃなくてdateの方が(設定されていれば)優先されるみたいですね。以後は記事を書いてrake den_deployするだけの簡単なお仕事です。
他にも、imageタグや、haml形式入力、html5 videoタグなど、色んなプラグインがあります。また、sassフォルダ内にあるsassファイルを弄れば簡単しかも柔軟なCSSを吐き出せます。
なお、_config.xmlを弄ってタイトルやサブタイトル、githubアカウント、twitterアカウントなんかを設定すると上述の様なサイトが簡単に出来上がります。
# ----------------------- #
#      Main Configs       #
# ----------------------- #

url: http://mattn.github.com/blog
title: "ギッハブる日記"
subtitle: ギッハブで作る開発日誌
author: mattn

気をつけておいて欲しいのは、github/jekyllはCGIで動いている訳じゃなくて、octopressが静的コンテンツを生成しているので、記事をアップする環境に依存する事。まぁここはbundleを使っているのでOSさえ変わらなければ大丈夫かと思います。Windowsからでも既述の様な修正を入れれば使えています。無料のgithubで簡単にしかもモダンなブログサイトを作りたい方は、一考してみてはどうでしょうか。
Posted at 21:01 in ソフトウェア::lang::ruby
Tagged as: github, jekyll, octopress
Bookmarks: add to hatena add to hatena | add to delicious.com | add to livedoor.clip add to livedoor.clip

2009/06/24


このエントリーをはてなブックマークに追加
これはgithubじゃなくても使えるかも
Gitはトランスポート層が選択出来るのは知っていたけど、まさかこんな書き方出来るとは思ってなかった。
以前、こんな記事書きましたが
github.comへのSSH接続にはホスト名"ssh.github.com"、ポート"443"に接続する様に設定します。※このssh.github.comが味噌です。

github.comへのSSH接続にはホスト名"ssh.github.com"、ポート"443"に接続する様に設定します。 ※このssh.github.comが味噌です。

http://mattn.kaoriya.net/software/20081029172540.htm
これ以下の1行で出来る事が分かりました。
# git clone ssh://git@ssh.github.com:443/my-name/my-repo.git
ssh.github.comに443ポートでSSHプロトコルを喋るよ!っていう指定になります。これでcloneしたワーキングツリーでは、以前書いた記事の様にpullはpublic clone、pushはowner cloneというやり方ではなくowner cloneといてpullしている為 .ssh/config ファイルを修正したり
# git remote add origin git@github.com:my-name/my-repo.git
する事もなくいきなりpush出来るになります。
こりゃいいわ。

Version Control with Git Version Control with Git
Jon Loeliger
Oreilly & Associates Inc / ¥ 2,364 (2009-06)
 
発送可能時間:通常1~3週間以内に発送

Posted at 10:33 in ソフトウェア
Tagged as: github, ssh
Bookmarks: add to hatena add to hatena | add to delicious.com | add to livedoor.clip add to livedoor.clip

2009/06/18


このエントリーをはてなブックマークに追加
WindowsではGrowl For Windowsとそれが使っているプロトコルGNTPにより、Windowsでもアイコンを使ったGrowlアプリケーションの開発が可能になりました。その一つにmiyagawaさんが作ったgithub growlerのGNTP版でもあるyet another github growlerというのも作りました。
これでMac, Windowsでのgithub growlerがある事になるのですが、Linuxにありません。Linuxにはアイコンが表示できてGNTPプロトコルを喋るGrowlシステムがありません。
そこで以前から使っていた、Growlネットワークプロトコル(Growlネットワークプロトコルはアイコンが出せません)をサポートしているmumblesというGrowlシステムを調べて見たところ、内部ではpythonでDBusによるプロセス間通信を行っている事が分かりました。
mumbles-project.org

a plugin driven, modern notification system for Gnome

http://www.mumbles-project.org/
さらにそのDBusインタフェース上ではアイコン表示をサポートしていた為、これは!と思いGitHubのGrowlアプリケーションを作ってみました。
まず、DBusで通信する為のプラグインを作成します。
DBusでメソッドが呼ばれると、MumblesPluginクラスに渡されるMumblesNotifyオブジェクトのalertメソッドを呼び出します。
全体のソースは以下の様になります。
from MumblesPlugin import *
import dbus
import gnomevfs
import os
import urllib

class GithubMumbles(MumblesPlugin):
  plugin_name = 'GithubMumbles'
  dbus_interface = 'com.github.DBus'
  dbus_path = '/com/github/DBus'
  icons = {'github' : 'github.png'}
  __url = None

  def __init__(self, mumbles_notify, session_bus):
    self.signal_config = {
      'Notify': self.Notify,
      'NotifyNum': self.NotifyNum
    }
    MumblesPlugin.__init__(self, mumbles_notify, session_bus)
    self.add_click_handler(self.onClick)

  def NotifyNum(self, num):
    self.__url = 'http://github.com/'
    icon = self.get_icon('github')
    title = 'Github'
    msg = str(num)+' new messages!'
    self.mumbles_notify.alert(self.plugin_name, title, msg, icon)

  def Notify(self, link, author, text):
    self.__url = link
    path = os.path.join(PLUGIN_DIR_USER, 'icons', 'github-%s' % author)
    if os.path.exists(path):
      self.icons[author] = 'github-%s' % author
      icon = self.get_icon(author)
    else:
      icon = self.get_icon('github')
    self.mumbles_notify.alert(self.plugin_name, author, text, icon)

  def onClick(self, widget, event, plugin_name):
    if event.button == 3:
      self.mumbles_notify.close(widget.window)
    else:
      self.open_url(self.__url)

  def open_url(self, url):
    mime_type = gnomevfs.get_mime_type(url)
    application = gnomevfs.mime_get_default_application(mime_type)
    os.system(application[2] + ' "' + url + '" &')
インタフェースはリンク、作者、本文のみとしました。これをegg形式にビルドしてmumblesのpluginフォルダに置くと、上記のインタフェース呼び出しによりGrowlが表示されます。
MumblesPluginにはget_iconメソッドが用意されており、これにはアイコン名称を渡す事になります。実際にはplugin/iconsというフォルダにある名称のファイルが使用されるので、今回の仕組としてはgithubフィードのチェッカースクリプトでアイコンをplugin/iconsフォルダに格納させ、それを使用してプラグイン側が使用するという形になっています。プラグイン側でアイコンを取って来ても良いのですがアイコンをダウンロードしている最中はGrowlが固まってしまう為、今回の様な作りとなっています。
次にチェッカースクリプトですが以下の様なコードになります。
#!/usr/bin/env python

UPDATE_INTERVAL=1000 # 10 minutes
MAX_NOTIFICATIONS = 40
DEBUG = True
##################################################

import os
import sys
import time
import getopt
import rfc822
import calendar
import urllib
import feedparser
import dbus
import dbus.service
from dbus.mainloop.glib import DBusGMainLoop
import gobject
from BeautifulSoup import BeautifulSoup
from pit import Pit

GITHUB_DBUS_INTERFACE = 'com.github.DBus'
GITHUB_DBUS_PATH = '/com/github/DBus'

config = Pit.get('github.com', {'require': {
    'user'  : 'user id on github.com',
    'token' : 'user token on github.com'
    }})

class Usage(Exception):
  def __init__(self, msg=None):
    app = sys.argv[0]
    if msg != 'help':
        self.msg = app+': Invalid options. Try --help for usage details.'
    else:
      self.msg = app+": DBus notifications on new github messages.\n"

class GithubCheck(dbus.service.Object):
  def __init__(self):
    session_bus = dbus.SessionBus()
    bus_name = dbus.service.BusName(GITHUB_DBUS_INTERFACE, bus=session_bus)
    dbus.service.Object.__init__(self, bus_name, GITHUB_DBUS_PATH)

    self.interval = UPDATE_INTERVAL
    self.notifyLimit = MAX_NOTIFICATIONS
    self.debug = DEBUG

    self.lastCheck = None
    self.minInterval = 60000 # 1 minute min refresh interval

    if self.interval < self.minInterval:
      print "Warning: Cannot check github more often than once a minute! Using default of 1 minute."
      self.interval = self.minInterval
    self._check()

  @dbus.service.signal(dbus_interface=GITHUB_DBUS_INTERFACE, signature='sss')
  def Notify(self, link, author, text):
    pass

  @dbus.service.signal(dbus_interface=GITHUB_DBUS_INTERFACE, signature='i')
  def NotifyNum(self, num):
    pass

  def _check(self):
    if self.debug:
      if self.lastCheck:
        print "checking feed (newer than %s):" %(self.lastCheck)
      else:
        print "checking feed:"
    try:
      items = feedparser.parse("http://github.com/%s.private.atom/?token=%s" % (config['user'], config['token']))['entries']
    except Exception, e:
      items = []

    if self.lastCheck:
      lastCheck = calendar.timegm(time.localtime(calendar.timegm(rfc822.parsedate(self.lastCheck))))
      for item in items:
        if calendar.timegm(item.published_parsed) < lastCheck:
          items.remove(item)

    self.lastCheck = rfc822.formatdate()
    num_notifications = len(items)

    if num_notifications > MAX_NOTIFICATIONS:
      if self.debug:
        print "%s new entries\n" %(num_notifications)
      self.NotifyNum(num_notifications)
    elif num_notifications < 0:
      if self.debug:
        print "no new entries\n"
    else:
      for item in items:
        path = os.path.join(os.path.expanduser('~'), '.mumbles', 'plugins', 'icons', 'github-%s' % item['author'])
        if not os.path.exists(path):
          html = urllib.urlopen('http://github.com/%s' % item['author']).read()
          soup = BeautifulSoup(html)
          img = soup.findAll('div', {'class':'identity'})[0].find('img')['src']
          img = img.replace("?s=50&", "?s=30&");
          urllib.urlretrieve(img, path)
        self.Notify(item['link'], item['author'], item['title'])
        time.sleep(6)
    gobject.timeout_add(self.interval,self._check)

if __name__ == '__main__':
  DBusGMainLoop(set_as_default=True)
  try:
    try:
      opts, args = getopt.getopt(
        sys.argv[1:], "hp", ["help"])
    except getopt.GetoptError:
      raise Usage()

    for o, a in opts:
      if o in ("-h", "--help"):
        raise Usage('help')
      else:
        raise Usage()
  except Usage, err:
    print >> sys.stderr, err.msg
    sys.exit(2)

  t = GithubCheck()
  try:
    loop = gobject.MainLoop()
    loop.run()
  except KeyboardInterrupt:
    print "githubcheck shut down..."
  except Exception, ex:
    print "Exception in githubcheck: %s" %(ex)
だらだらとしたコードですが、大体分かってもらえるかと思います。pitを使っているので初回起動のみユーザとトークンをエディタで入力する必要があります。トークンはGitHubのダッシュボードにあるRSSアイコンのリンク先URLに含まれています。

実行してしばらくすると以下の様な画面が表示されます。
mumbles-github-growler
これで快適になりました。
github上で全てのソースを公開しています。
mattn's mumbles-github-growler at master - GitHub

github growler using mumbles plugin and checker script.

http://github.com/mattn/mumbles-github-growler/tree/master
よろしければどうぞ。
Posted at 22:12 in ソフトウェア::lang::python
Tagged as: github, growl, mumbles
Bookmarks: add to hatena add to hatena | add to delicious.com | add to livedoor.clip add to livedoor.clip

2009/02/27


このエントリーをはてなブックマークに追加
# git clone http://github.com/miyagawa/remedie.git
got d46438302f839f85631e2953c09a6c653833b390
walk d46438302f839f85631e2953c09a6c653833b390
got 17cbee3478c5a25cb4ffbfe3c4f935afdcae02d0
...
walk 04834c0931dfff5fe33a59693d54cb997cbcd095
walk eed0c0c2b3ac58cd2f7e288577b2dd2372523824
walk c3f3a024dbf154c0f9212f13810aabcbbb2a254c
error: Unable to find ab991c530b3e603384fde59a0fe243b954a3131c under http://github.com/miyagawa/remedie.git
Cannot obtain needed blob ab991c530b3e603384fde59a0fe243b954a3131c
while processing commit c3f3a024dbf154c0f9212f13810aabcbbb2a254c.
fatal: Fetch failed.
とすると、エラーが出てたのですが直った様です。
Using HTTP to access github repos / Repo issues / Discussion Area - GitHub Support

github stuff

This should be fixed now. Sorry about that!


http://support.github.com/discussions/repos/25-using-http-to-access-github-repos
ビール飲んでる様に見えるけど、ちゃんと働いてくれました。
github++
Posted at 11:29 in ソフトウェア
Tagged as: git, github
Bookmarks: add to hatena add to hatena | add to delicious.com | add to livedoor.clip add to livedoor.clip