Skip to content

Instantly share code, notes, and snippets.

@holysugar
Created March 17, 2011 12:21
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save holysugar/874229 to your computer and use it in GitHub Desktop.
Save holysugar/874229 to your computer and use it in GitHub Desktop.
#!/usr/bin/ruby
# set ft=ruby ts=2 sts=2 sw=2 fileencoding=utf-8
path = "/Users/holy/work/test-git"
git = '/opt/local/bin/git'
########################
require 'open3'
require 'cgi'
class MyGit
class CommandError < StandardError; end
attr_reader :result, :error
def initialize(path, git_path = nil)
@path = path
@result = ''
@error = ''
@git = git_path || 'git'
end
def process_request(command, options = {})
Dir.chdir(@path)
case command
when 'status', 'diff', 'log', 'pull'
git(command)
when 'commit'
exec_git_commit(options["comment"])
when 'commit-push'
exec_git_commit(options["comment"], :push => true)
end
end
def git(command, *args)
line = "#{@git} #{command} #{args.join(' ')}"
stdin, stdout, stderr = *Open3.popen3(line)
stdin.close
result = "> #{line}\n#{stdout.read}\n"
@result += result
unless (error = stderr.read).empty?
@error = error
raise CommandError, error
end
end
private
def quote(string)
"'#{string.gsub("'") { "'\\''" }}'"
end
def exec_git_commit(comment, options = {})
comment ||= "auto commit."
git('add', '-A')
git('commit', '-m', quote(comment))
if options[:push]
git('pull', '--rebase')
git('push')
end
end
end
class GitCgi
class << self
def main(path, git = nil)
git = MyGit.new(path, git)
cgi = CGI.new
error = nil
@url = cgi.script_name
if command = cgi['c']
begin
git.process_request(command, cgi)
rescue MyGit::CommandError => e
end
end
cgi.out("text/html;charset=UTF-8") do
html_form do
html_result(git.result) + html_error(git.error)
end
end
end
def html_form
body = yield
commands = %w|status diff log pull commit commit-push|
<<-EOD
<html>
<head><title>Git CGI!</title></head>
<body>
<p>Please select command.</p>
<form action="#{@url}" method="POST">
<select name="c">
#{html_option(commands)}
</select>
Comment: <input type="text" size="80" name="comment" /><br />
<input type="submit" name="Exec git!" />
</form>
<hr />
<div class="result">
#{body}
</div>
</body>
EOD
end
def html_option(names)
names.map{|name|
name = CGI.escapeHTML(name)
%(<option value="#{name}">#{name}</option>)
}.join("\n")
end
def html_result(result)
return "" if result.empty?
<<-EOD
<p>Result</p>
<pre>#{CGI.escapeHTML result}</pre>
EOD
end
def html_error(result)
return "" if result.empty?
<<-EOD
<pre style="color:red">#{CGI.escapeHTML result}</pre>
EOD
end
end
end
GitCgi.main(path, git)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment