blastr 0.0.6 → 0.0.7
Sign up to get free protection for your applications and to get access to all the features.
- data/History.txt +4 -0
- data/Manifest.txt +4 -0
- data/README.rdoc +10 -1
- data/lib/blastr.rb +20 -44
- data/lib/people/people.rb +22 -0
- data/lib/scm/git.rb +24 -18
- data/lib/scm/scm.rb +22 -2
- data/lib/scm/svn.rb +3 -1
- data/test/test_git_log_entry.rb +30 -0
- data/test/test_git_revision.rb +35 -0
- data/test/test_svn_revision.rb +23 -0
- metadata +8 -1
data/History.txt
CHANGED
data/Manifest.txt
CHANGED
@@ -5,6 +5,7 @@ README.rdoc
|
|
5
5
|
Rakefile
|
6
6
|
bin/blastr
|
7
7
|
lib/blastr.rb
|
8
|
+
lib/people/people.rb
|
8
9
|
lib/scm/git.rb
|
9
10
|
lib/scm/scm.rb
|
10
11
|
lib/scm/svn.rb
|
@@ -12,5 +13,8 @@ lib/tts/tts.rb
|
|
12
13
|
script/console
|
13
14
|
script/destroy
|
14
15
|
script/generate
|
16
|
+
test/test_git_log_entry.rb
|
17
|
+
test/test_git_revision.rb
|
15
18
|
test/test_helper.rb
|
19
|
+
test/test_svn_revision.rb
|
16
20
|
test/test_tts.rb
|
data/README.rdoc
CHANGED
@@ -8,7 +8,16 @@ Blastr observes a version control repository for commits and makes audible annou
|
|
8
8
|
|
9
9
|
== FEATURES/PROBLEMS:
|
10
10
|
|
11
|
-
|
11
|
+
Blastr watches for incoming commits to a source repository and voices the commit
|
12
|
+
messages out loud.
|
13
|
+
|
14
|
+
The supported version control systems include:
|
15
|
+
* Subversion (http://subversion.tigris.org)
|
16
|
+
* Git (http://git-scm.com)
|
17
|
+
|
18
|
+
The supported operating systems (for running Blastr) include:
|
19
|
+
* Mac OS X
|
20
|
+
* Linux (requires the 'espeak' or 'festival' text-to-speech utility)
|
12
21
|
|
13
22
|
== SYNOPSIS:
|
14
23
|
|
data/lib/blastr.rb
CHANGED
@@ -1,52 +1,40 @@
|
|
1
1
|
$:.unshift(File.dirname(__FILE__)) unless
|
2
2
|
$:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
|
3
3
|
|
4
|
-
require 'yaml'
|
5
|
-
require 'scm/git.rb'
|
6
|
-
require 'scm/svn.rb'
|
7
|
-
require 'tts/tts.rb'
|
8
|
-
|
9
4
|
module Blastr
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
if File.file?(PEOPLE_FILE)
|
16
|
-
yaml = YAML.load_file(PEOPLE_FILE)
|
17
|
-
return yaml unless yaml == false
|
18
|
-
end
|
19
|
-
{ }
|
20
|
-
end
|
5
|
+
require 'scm/scm.rb'
|
6
|
+
require 'tts/tts.rb'
|
7
|
+
require 'people/people.rb'
|
8
|
+
|
9
|
+
VERSION = '0.0.7'
|
21
10
|
|
22
|
-
def self.full_name_of(username)
|
23
|
-
people[username] ||= username
|
24
|
-
end
|
25
|
-
end
|
26
|
-
|
27
11
|
class Process
|
28
12
|
def initialize(args=[])
|
29
13
|
scm_url = ARGV[0]
|
30
|
-
@scm = Blastr.
|
14
|
+
@scm = Blastr::SourceControl.implementation_for(scm_url)
|
31
15
|
@since_revision = @scm.as_revision(ARGV[1]) if ARGV.size > 1
|
32
16
|
@since_revision = @scm.latest_revision unless ARGV.size > 1
|
33
17
|
end
|
34
18
|
|
19
|
+
def run
|
20
|
+
puts "Polling #{@scm.name} commits since revision #{@since_revision}..."
|
21
|
+
while true
|
22
|
+
announce_new_commits
|
23
|
+
sleep 30
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
35
27
|
def announce(commit)
|
36
28
|
puts "[#{commit.revision}] Commit by #{commit.author}: #{commit.comment}"
|
37
|
-
Blastr::TTS.speak("Commit by #{
|
29
|
+
Blastr::TTS.speak("Commit by #{People.full_name_of(commit.author)}: #{commit.comment}")
|
38
30
|
end
|
39
31
|
|
40
|
-
def
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
announce(commit)
|
46
|
-
@since_revision = commit.revision
|
47
|
-
end
|
32
|
+
def announce_new_commits
|
33
|
+
@scm.commits_since(@since_revision.to_s).each do |commit|
|
34
|
+
if @since_revision.before?(commit.revision)
|
35
|
+
announce(commit)
|
36
|
+
@since_revision = commit.revision
|
48
37
|
end
|
49
|
-
sleep 30
|
50
38
|
end
|
51
39
|
end
|
52
40
|
end
|
@@ -58,16 +46,4 @@ module Blastr
|
|
58
46
|
temp_dir
|
59
47
|
end
|
60
48
|
|
61
|
-
def Blastr::scm_implementations
|
62
|
-
[ Blastr::Subversion, Blastr::Git ]
|
63
|
-
end
|
64
|
-
|
65
|
-
def Blastr::scm(url)
|
66
|
-
scm_implementations.each do |impl|
|
67
|
-
if impl.understands_url?(url)
|
68
|
-
return impl.new(url)
|
69
|
-
end
|
70
|
-
end
|
71
|
-
raise "No SCM implementation found that would understand #{url}"
|
72
|
-
end
|
73
49
|
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'yaml'
|
2
|
+
|
3
|
+
module Blastr
|
4
|
+
class People
|
5
|
+
PEOPLE_FILE = File.expand_path("~/.blastr/people")
|
6
|
+
CONFIG_HELP_MESSAGE = ""
|
7
|
+
|
8
|
+
puts CONFIG_HELP_MESSAGE unless File.file?(PEOPLE_FILE)
|
9
|
+
|
10
|
+
def self.people
|
11
|
+
if File.file?(PEOPLE_FILE)
|
12
|
+
yaml = YAML.load_file(PEOPLE_FILE)
|
13
|
+
return yaml unless yaml == false
|
14
|
+
end
|
15
|
+
{ }
|
16
|
+
end
|
17
|
+
|
18
|
+
def self.full_name_of(username)
|
19
|
+
people[username] ||= username
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
data/lib/scm/git.rb
CHANGED
@@ -2,8 +2,8 @@ require 'rubygems'
|
|
2
2
|
require 'git'
|
3
3
|
require 'blastr/scm.rb'
|
4
4
|
|
5
|
-
module Blastr
|
6
|
-
|
5
|
+
module Blastr::SourceControl
|
6
|
+
|
7
7
|
class GitLogEntry < LogEntry
|
8
8
|
def initialize(commit)
|
9
9
|
@revision = GitRevision.new(commit.sha, commit.date)
|
@@ -15,7 +15,7 @@ module Blastr
|
|
15
15
|
class GitRevision
|
16
16
|
attr_accessor :name, :date
|
17
17
|
|
18
|
-
def initialize(name, date =
|
18
|
+
def initialize(name, date = Time.now)
|
19
19
|
@name = name
|
20
20
|
@date = date
|
21
21
|
end
|
@@ -45,13 +45,13 @@ module Blastr
|
|
45
45
|
|
46
46
|
def as_revision(arg)
|
47
47
|
raise "Invalid revision: #{arg}" unless arg =~ /^(HEAD(~\d+)?)|([\d\w:-]+)$/
|
48
|
-
|
48
|
+
obj = nil
|
49
|
+
with_clone do |clone|
|
50
|
+
obj = clone.object(arg.to_s)
|
51
|
+
end
|
52
|
+
GitRevision.new(obj.sha, obj.date)
|
49
53
|
end
|
50
54
|
|
51
|
-
def understands_url?(url)
|
52
|
-
url.index("git://") == 0
|
53
|
-
end
|
54
|
-
|
55
55
|
def latest_revision
|
56
56
|
commits = commits_since(as_revision("HEAD~5"))
|
57
57
|
return as_revision("HEAD") unless commits.size > 0
|
@@ -59,19 +59,25 @@ module Blastr
|
|
59
59
|
end
|
60
60
|
|
61
61
|
def commits_since(revision)
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
commits
|
66
|
-
@clone.log.between(revision.to_s).each do |commit|
|
67
|
-
commits << GitLogEntry.new(commit)
|
68
|
-
end
|
69
|
-
return commits.reverse
|
62
|
+
with_clone do |clone|
|
63
|
+
commits = []
|
64
|
+
clone.log.between(revision.to_s).each do |commit|
|
65
|
+
commits << GitLogEntry.new(commit)
|
70
66
|
end
|
71
|
-
|
72
|
-
FileUtils.remove_dir(@clone.dir, :force => true)
|
67
|
+
return commits.reverse
|
73
68
|
end
|
74
69
|
end
|
70
|
+
|
71
|
+
private
|
72
|
+
def with_clone
|
73
|
+
clone = ::Git.clone(@git_url, Blastr::temp_dir)
|
74
|
+
clone.chdir do
|
75
|
+
yield clone
|
76
|
+
end
|
77
|
+
FileUtils.remove_dir(clone.dir, :force => true)
|
78
|
+
end
|
75
79
|
end
|
76
80
|
|
77
81
|
end
|
82
|
+
|
83
|
+
Blastr::SourceControl.register_implementation(Blastr::SourceControl::Git)
|
data/lib/scm/scm.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
|
-
module Blastr
|
1
|
+
module Blastr::SourceControl
|
2
|
+
|
2
3
|
class LogEntry
|
3
4
|
attr_accessor :revision, :author, :comment
|
4
5
|
def initialize(revision, author, comment)
|
@@ -10,4 +11,23 @@ module Blastr
|
|
10
11
|
"revision #{@revision} by #{@author}: #{@comment}"
|
11
12
|
end
|
12
13
|
end
|
13
|
-
|
14
|
+
|
15
|
+
def self.implementation_for(url)
|
16
|
+
IMPLEMENTATIONS.each do |impl|
|
17
|
+
if impl.understands_url?(url)
|
18
|
+
return impl.new(url)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
raise "No SCM implementation found that would understand #{url}"
|
22
|
+
end
|
23
|
+
|
24
|
+
IMPLEMENTATIONS = []
|
25
|
+
|
26
|
+
def self.register_implementation(implementation)
|
27
|
+
IMPLEMENTATIONS << implementation unless IMPLEMENTATIONS.include?(implementation)
|
28
|
+
end
|
29
|
+
|
30
|
+
end
|
31
|
+
|
32
|
+
require File.dirname(__FILE__) + '/svn.rb'
|
33
|
+
require File.dirname(__FILE__) + '/git.rb'
|
data/lib/scm/svn.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
require 'fileutils'
|
2
2
|
require 'blastr/scm.rb'
|
3
3
|
|
4
|
-
module Blastr
|
4
|
+
module Blastr::SourceControl
|
5
5
|
|
6
6
|
class SubversionRevision
|
7
7
|
attr_accessor :name
|
@@ -80,3 +80,5 @@ module Blastr
|
|
80
80
|
end
|
81
81
|
|
82
82
|
end
|
83
|
+
|
84
|
+
Blastr::SourceControl.register_implementation(Blastr::SourceControl::Subversion)
|
@@ -0,0 +1,30 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
|
3
|
+
class TestGitLogEntry < Test::Unit::TestCase
|
4
|
+
|
5
|
+
COMMIT_HASH = "db4ace1c9ba6add9a2b08c153367e2b379f8fb4c"
|
6
|
+
COMMIT_DATE = Time.now
|
7
|
+
COMMIT_AUTHOR = "johndoe"
|
8
|
+
COMMIT_MESSAGE = "o hai"
|
9
|
+
|
10
|
+
class FakeAuthor
|
11
|
+
def initialize(name); @name = name; end
|
12
|
+
def name; @name; end
|
13
|
+
end
|
14
|
+
|
15
|
+
class FakeCommit
|
16
|
+
def sha; COMMIT_HASH; end
|
17
|
+
def date; COMMIT_DATE; end
|
18
|
+
def author; FakeAuthor.new(COMMIT_AUTHOR); end
|
19
|
+
def message; COMMIT_MESSAGE; end
|
20
|
+
end
|
21
|
+
|
22
|
+
def test_initialization
|
23
|
+
entry = Blastr::SourceControl::GitLogEntry.new(FakeCommit.new)
|
24
|
+
assert_equal Blastr::SourceControl::GitRevision, entry.revision.class
|
25
|
+
assert_equal COMMIT_HASH, entry.revision.to_s
|
26
|
+
assert_equal COMMIT_DATE, entry.revision.date
|
27
|
+
assert_equal COMMIT_AUTHOR, entry.author
|
28
|
+
assert_equal COMMIT_MESSAGE, entry.comment
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
|
3
|
+
class TestGitRevision < Test::Unit::TestCase
|
4
|
+
|
5
|
+
SAMPLE_SHA = "db4ace1c9ba6add9a2b08c153367e2b379f8fb4c"
|
6
|
+
|
7
|
+
def setup
|
8
|
+
@revision_with_date = Blastr::SourceControl::GitRevision.new(SAMPLE_SHA, Time.now - 100)
|
9
|
+
@revision_without_date = Blastr::SourceControl::GitRevision.new(SAMPLE_SHA)
|
10
|
+
end
|
11
|
+
|
12
|
+
def test_to_s
|
13
|
+
assert @revision_without_date.to_s == SAMPLE_SHA
|
14
|
+
assert @revision_with_date.to_s == SAMPLE_SHA
|
15
|
+
end
|
16
|
+
|
17
|
+
def test_before_comparison_between_dated_revisions
|
18
|
+
later_revision = Blastr::SourceControl::GitRevision.new(SAMPLE_SHA, @revision_with_date.date + 1)
|
19
|
+
assert @revision_with_date.before?(later_revision) == true
|
20
|
+
assert later_revision.before?(@revision_with_date) == false
|
21
|
+
end
|
22
|
+
|
23
|
+
def test_revision_defaults_its_date_to_now
|
24
|
+
assert @revision_with_date.before?(@revision_without_date) == true
|
25
|
+
assert @revision_without_date.before?(@revision_with_date) == false
|
26
|
+
end
|
27
|
+
|
28
|
+
def test_before_comparison_with_HEAD
|
29
|
+
head = Blastr::SourceControl::GitRevision.new("HEAD")
|
30
|
+
[@revision_with_date, @revision_without_date].each do |any_revision|
|
31
|
+
assert any_revision.before?(head) == true
|
32
|
+
assert head.before?(any_revision) == false
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper.rb'
|
2
|
+
|
3
|
+
class TestSubversionRevision < Test::Unit::TestCase
|
4
|
+
|
5
|
+
def test_to_s
|
6
|
+
rev = Blastr::SourceControl::SubversionRevision.new("123")
|
7
|
+
assert rev.to_s == "123"
|
8
|
+
end
|
9
|
+
|
10
|
+
def test_before_comparison_between_revisions
|
11
|
+
rev123 = Blastr::SourceControl::SubversionRevision.new("123")
|
12
|
+
rev456 = Blastr::SourceControl::SubversionRevision.new("456")
|
13
|
+
assert rev123.before?(rev456) == true
|
14
|
+
assert rev456.before?(rev123) == false
|
15
|
+
end
|
16
|
+
|
17
|
+
def test_before_comparison_with_HEAD
|
18
|
+
rev = Blastr::SourceControl::SubversionRevision.new("100")
|
19
|
+
head = Blastr::SourceControl::SubversionRevision.new("HEAD")
|
20
|
+
assert rev.before?(head) == true
|
21
|
+
assert head.before?(rev) == false
|
22
|
+
end
|
23
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: blastr
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Lasse Koskela
|
@@ -62,6 +62,7 @@ files:
|
|
62
62
|
- Rakefile
|
63
63
|
- bin/blastr
|
64
64
|
- lib/blastr.rb
|
65
|
+
- lib/people/people.rb
|
65
66
|
- lib/scm/git.rb
|
66
67
|
- lib/scm/scm.rb
|
67
68
|
- lib/scm/svn.rb
|
@@ -69,7 +70,10 @@ files:
|
|
69
70
|
- script/console
|
70
71
|
- script/destroy
|
71
72
|
- script/generate
|
73
|
+
- test/test_git_log_entry.rb
|
74
|
+
- test/test_git_revision.rb
|
72
75
|
- test/test_helper.rb
|
76
|
+
- test/test_svn_revision.rb
|
73
77
|
- test/test_tts.rb
|
74
78
|
has_rdoc: true
|
75
79
|
homepage: http://blastr.rubyforge.org
|
@@ -99,5 +103,8 @@ signing_key:
|
|
99
103
|
specification_version: 2
|
100
104
|
summary: Blastr observes a version control repository for commits and makes audible announcements out of the commit messages
|
101
105
|
test_files:
|
106
|
+
- test/test_git_log_entry.rb
|
107
|
+
- test/test_git_revision.rb
|
102
108
|
- test/test_helper.rb
|
109
|
+
- test/test_svn_revision.rb
|
103
110
|
- test/test_tts.rb
|