ginatra 3.0.1 → 4.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +18 -15
  3. data/.travis.yml +7 -6
  4. data/CONTRIBUTING.md +30 -0
  5. data/Gemfile +1 -9
  6. data/LICENSE.txt +30 -0
  7. data/README.md +63 -114
  8. data/Rakefile +10 -12
  9. data/bin/ginatra +79 -63
  10. data/config.ru +35 -3
  11. data/ginatra.gemspec +29 -18
  12. data/lib/ginatra.rb +161 -148
  13. data/lib/ginatra/config.rb +18 -121
  14. data/lib/ginatra/errors.rb +10 -0
  15. data/lib/ginatra/helpers.rb +154 -139
  16. data/lib/ginatra/repo.rb +67 -82
  17. data/lib/ginatra/repo_list.rb +25 -18
  18. data/lib/ginatra/repo_stats.rb +93 -0
  19. data/lib/ginatra/version.rb +4 -0
  20. data/lib/git/webby.rb +292 -0
  21. data/lib/git/webby/extensions.rb +10 -0
  22. data/lib/git/webby/http_backend.rb +177 -0
  23. data/lib/sinatra/partials.rb +1 -1
  24. data/public/css/application.css +6 -0
  25. data/public/css/custom.css +57 -0
  26. data/public/css/lib/bootstrap-responsive.min.css +9 -0
  27. data/public/css/lib/bootstrap.min.css +9 -0
  28. data/public/css/lib/highlight.css +209 -0
  29. data/public/img/glyphicons-halflings-white.png +0 -0
  30. data/public/img/glyphicons-halflings.png +0 -0
  31. data/public/img/spin.gif +0 -0
  32. data/public/js/application.js +5 -0
  33. data/public/js/custom.js +51 -0
  34. data/public/js/lib/bootstrap.min.js +6 -0
  35. data/public/js/lib/jquery.lazyload.min.js +2 -0
  36. data/public/js/lib/jquery.min.js +2 -0
  37. data/public/js/lib/jquery.pjax.js +739 -0
  38. data/repos/README.md +21 -8
  39. data/spec/ginatra/helpers_spec.rb +95 -0
  40. data/spec/ginatra/repo_list_spec.rb +66 -0
  41. data/spec/ginatra/repo_spec.rb +78 -0
  42. data/spec/ginatra/repo_stats_spec.rb +27 -0
  43. data/spec/ginatra_spec.rb +121 -0
  44. data/spec/spec_helper.rb +8 -17
  45. data/views/404.erb +18 -0
  46. data/views/500.erb +18 -0
  47. data/views/_footer.erb +7 -0
  48. data/views/_header.erb +12 -6
  49. data/views/_tree_nav.erb +53 -0
  50. data/views/atom.erb +32 -0
  51. data/views/blob.erb +27 -8
  52. data/views/commit.erb +95 -17
  53. data/views/empty_repo.erb +10 -0
  54. data/views/index.erb +27 -11
  55. data/views/layout.erb +16 -20
  56. data/views/log.erb +74 -54
  57. data/views/stats.erb +89 -0
  58. data/views/tree.erb +32 -20
  59. metadata +168 -94
  60. data/bin/ginatra-daemon +0 -87
  61. data/bin/ginatra-directory +0 -55
  62. data/bin/ginatra-server +0 -27
  63. data/bin/ginatra-setup +0 -28
  64. data/lib/ginatra/graph_commit.rb +0 -77
  65. data/public/img/add.png +0 -0
  66. data/public/img/diff.png +0 -0
  67. data/public/img/doc.png +0 -0
  68. data/public/img/rm.png +0 -0
  69. data/public/img/tree.png +0 -0
  70. data/public/src/branch-graph.js +0 -170
  71. data/public/src/colour.css +0 -86
  72. data/public/src/commit.css +0 -211
  73. data/public/src/ginatra.js +0 -7
  74. data/public/src/github.css +0 -129
  75. data/public/src/graph.css +0 -9
  76. data/public/src/highlight.pack.js +0 -1
  77. data/public/src/index.css +0 -92
  78. data/public/src/lists.css +0 -25
  79. data/public/src/raphael.js +0 -7
  80. data/public/src/reset.css +0 -49
  81. data/public/src/table.css +0 -33
  82. data/public/src/type.css +0 -30
  83. data/rackup.ru +0 -5
  84. data/spec/graph_commit_spec.rb +0 -54
  85. data/spec/repo_list_spec.rb +0 -84
  86. data/spec/repo_spec.rb +0 -61
  87. data/views/_actor_box.erb +0 -13
  88. data/views/_commit_info_box.erb +0 -27
  89. data/views/_tree_part.erb +0 -11
  90. data/views/atom.builder +0 -32
  91. data/views/graph.erb +0 -15
data/repos/README.md CHANGED
@@ -1,8 +1,21 @@
1
- From the top README:
2
-
3
- > To clone repositories so that Ginatra can see them, clone the repositories into `./repos/` - they will be served automatically. Use the `--bare` switch to both save space and make sure Ginatra can read them. If you rename them, make sure the directory ends in `.git'. For Example:
4
- >
5
- > cd repos
6
- > git clone --bare git://github.com/lenary/ginatra.git
7
- > git clone --bare git://github.com/mojombo/grit.git fun.git
8
-
1
+ To make Ginatra see repositories, put them into this directory. You can do this
2
+ by several ways:
3
+
4
+ 1. Clone repository here
5
+
6
+ git clone git://github.com/NARKOZ/ginatra.git
7
+
8
+ 2. Symlink repository into there
9
+
10
+ ln -s /path/to/repo repos/
11
+
12
+ 3. Copy repository here
13
+
14
+ cp -R /path/to/repo repos/
15
+
16
+ 4. Move repository here
17
+
18
+ mv -R /path/to/repo repos/
19
+
20
+ Run `ginatra --help` for additional command line help and see `config.yml` file
21
+ for available settings.
@@ -0,0 +1,95 @@
1
+ require 'spec_helper'
2
+
3
+ describe Ginatra::Helpers do
4
+ before { allow(Time).to receive(:now).and_return(Time.new(2012, 12, 25, 0, 0, 0, '+00:00')) }
5
+
6
+ let(:repo) { Ginatra::RepoList.find('test') }
7
+ let(:commit) { repo.commit('095955b') }
8
+
9
+ describe "#secure_mail" do
10
+ it "returns masked email" do
11
+ expect(secure_mail('eggscellent@example.com')).to eq('eggs...@example.com')
12
+ end
13
+ end
14
+
15
+ describe "#gravatar_image_tag" do
16
+ context "when options passed" do
17
+ it "returns a gravatar image tag with custom options" do
18
+ expect(
19
+ gravatar_image_tag('john@example.com', size: 100, alt: 'John', class: 'avatar')
20
+ ).to eq("<img src='https://secure.gravatar.com/avatar/d4c74594d841139328695756648b6bd6?s=100' alt='John' height='100' width='100' class='avatar'>")
21
+ end
22
+ end
23
+
24
+ context "when options not passed" do
25
+ it "returns a gravatar image tag with default options" do
26
+ expect(
27
+ gravatar_image_tag('john@example.com')
28
+ ).to eq("<img src='https://secure.gravatar.com/avatar/d4c74594d841139328695756648b6bd6?s=40' alt='john' height='40' width='40'>")
29
+ end
30
+ end
31
+ end
32
+
33
+ describe "#file_icon" do
34
+ context "symbolic link" do
35
+ it "returns icon share-alt" do
36
+ expect(file_icon(40960)).to eq("<span class='icon-share-alt'></span>")
37
+ end
38
+ end
39
+
40
+ context "executable file" do
41
+ it "returns icon asterisk" do
42
+ expect(file_icon(33261)).to eq("<span class='icon-asterisk'></span>")
43
+ end
44
+ end
45
+
46
+ context "non-executable file" do
47
+ it "returns icon file" do
48
+ expect(file_icon(33188)).to eq("<span class='icon-file'></span>")
49
+ end
50
+ end
51
+ end
52
+
53
+ describe "#nicetime" do
54
+ it "returns a time in nice format" do
55
+ expect(nicetime(Time.now)).to eq('Dec 25, 2012 &ndash; 00:00')
56
+ end
57
+ end
58
+
59
+ describe "#time_tag" do
60
+ it "returns a time in nice format" do
61
+ expect(
62
+ time_tag(Time.now)
63
+ ).to eq("<time datetime='2012-12-25T00:00:00+0000' title='2012-12-25 00:00:00'>December 25, 2012 00:00</time>")
64
+ end
65
+ end
66
+
67
+ describe "#patch_link" do
68
+ it "returns a link for a commit patch" do
69
+ expect(
70
+ patch_link(commit, 'test')
71
+ ).to eq("<a href='/test/commit/095955b6402c30ef24520bafdb8a8687df0a98d3.patch'>Download Patch</a>")
72
+ end
73
+ end
74
+
75
+ describe "#empty_description_hint_for" do
76
+ it "returns a hint for a repo with empty description" do
77
+ hint_text = "Edit `#{repo.path}description` file to set the repository description."
78
+ expect(empty_description_hint_for(repo)).to eq("<span class='icon-exclamation-sign' title='#{hint_text}'></span>")
79
+ end
80
+ end
81
+
82
+ describe "#atom_feed_url" do
83
+ context "when ref name passed" do
84
+ it "returns a link to repo reference atom feed" do
85
+ expect(atom_feed_url('test', 'master')).to eq("/test/master.atom")
86
+ end
87
+ end
88
+
89
+ context "when ref name not passed" do
90
+ it "returns a link to repo atom feed" do
91
+ expect(atom_feed_url('test')).to eq("/test.atom")
92
+ end
93
+ end
94
+ end
95
+ end
@@ -0,0 +1,66 @@
1
+ require 'spec_helper'
2
+
3
+ describe Ginatra::RepoList do
4
+ let(:repo) { Ginatra::RepoList.find('test') }
5
+ let(:repo_list) { Ginatra::RepoList.list }
6
+
7
+ it "is an array of 'Ginatra::Repo'" do
8
+ repo_list.each do |repo|
9
+ expect(repo).to be_an_instance_of(Ginatra::Repo)
10
+ end
11
+ end
12
+
13
+ it "contains the test repo" do
14
+ expect(repo_list).to include(repo)
15
+ end
16
+
17
+ it "has_repo? works for existing repo" do
18
+ expect(Ginatra::RepoList.instance.has_repo?('test')).to be true
19
+ end
20
+
21
+ it "has_repo? works for non-existant repo" do
22
+ expect(Ginatra::RepoList.instance.has_repo?('bad-test')).to be false
23
+ end
24
+
25
+ describe "New repos added to repo directory" do
26
+ before(:each) do
27
+ @new_repo_name = 'temp-new-repo'
28
+ @repo_dir = File.join(current_path, '..', 'repos')
29
+
30
+ FileUtils.cd(@repo_dir) do |repo_dir|
31
+ FileUtils.mkdir_p(@new_repo_name)
32
+ FileUtils.cd(@new_repo_name) do |new_repo_dir|
33
+ `git init`
34
+ end
35
+ end
36
+ end
37
+
38
+ it "should detect new repo after refresh" do
39
+ repo_list = Ginatra::RepoList.list # calling this should refresh the list
40
+ expect(Ginatra::RepoList.instance.has_repo?(@new_repo_name)).to be true
41
+
42
+ new_repo = Ginatra::RepoList.find(@new_repo_name)
43
+ expect(repo_list).to include(new_repo)
44
+ end
45
+
46
+ it "should detect when a repo has been removed after refresh" do
47
+ repo_list = Ginatra::RepoList.list # calling this should refresh the list
48
+ expect(Ginatra::RepoList.instance.has_repo?(@new_repo_name)).to be true
49
+
50
+ new_repo = Ginatra::RepoList.find(@new_repo_name)
51
+ expect(repo_list).to include(new_repo)
52
+
53
+ # remove the new repository from the file system
54
+ FileUtils.rm_rf File.join(@repo_dir, @new_repo_name), secure: true
55
+
56
+ repo_list = Ginatra::RepoList.list # refresh the repo list
57
+
58
+ expect(Ginatra::RepoList.instance.has_repo?(@new_repo_name)).to be false
59
+ expect(repo_list).to_not include(new_repo)
60
+ end
61
+
62
+ after(:each) do
63
+ FileUtils.rm_rf File.join(@repo_dir, @new_repo_name), secure: true
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,78 @@
1
+ require 'spec_helper'
2
+
3
+ describe Ginatra::Repo do
4
+ let(:repo) { Ginatra::RepoList.find('test') }
5
+
6
+ describe "repo" do
7
+ it "returns name" do
8
+ expect(repo.name).to eq("test")
9
+ end
10
+
11
+ it "returns param" do
12
+ expect(repo.param).to eq("test")
13
+ end
14
+
15
+ it "returns description" do
16
+ expect(repo.description).to eq("")
17
+ end
18
+ end
19
+
20
+ describe "#commit" do
21
+ it "returns commit by sha" do
22
+ commit = repo.commit '095955b'
23
+ expect(commit).to be_a_kind_of(Rugged::Commit)
24
+ expect(commit.oid).to eq('095955b6402c30ef24520bafdb8a8687df0a98d3')
25
+ end
26
+ end
27
+
28
+ describe "#commit_by_tag" do
29
+ it "returns commit by tag" do
30
+ commit = repo.commit_by_tag 'v0.0.3'
31
+ expect(commit).to be_a_kind_of(Rugged::Commit)
32
+ expect(commit.oid).to eq('0c386b293878fb5f69031a998d564ecb8c2fee4d')
33
+ end
34
+ end
35
+
36
+ describe "#commits" do
37
+ context "when branch exist" do
38
+ it "returns an array of commits" do
39
+ commits = repo.commits('master', 2)
40
+ expect(commits).to be_a_kind_of(Array)
41
+ expect(commits.size).to eq(2)
42
+ expect(commits.first.oid).to eq('095955b6402c30ef24520bafdb8a8687df0a98d3')
43
+ end
44
+ end
45
+
46
+ context "when branch not exist" do
47
+ it "raises Ginatra::InvalidRef" do
48
+ expect { repo.commits('404-branch') }.to raise_error(Ginatra::InvalidRef)
49
+ end
50
+ end
51
+ end
52
+
53
+ describe "#branches" do
54
+ it "returns an array of branches" do
55
+ branches = repo.branches
56
+ expect(branches).to be_a_kind_of(Array)
57
+ expect(branches.size).to eq(1)
58
+ expect(branches.first.name).to eq('master')
59
+ expect(branches.first.target.oid).to eq('095955b6402c30ef24520bafdb8a8687df0a98d3')
60
+ end
61
+ end
62
+
63
+ describe "#branches_with" do
64
+ it "returns an array of branches including commit" do
65
+ branches = repo.branches_with('095955b6402c30ef24520bafdb8a8687df0a98d3')
66
+ expect(branches).to be_a_kind_of(Array)
67
+ expect(branches.size).to eq(1)
68
+ expect(branches.first.name).to eq('master')
69
+ end
70
+ end
71
+
72
+ describe "#branch_exists?" do
73
+ it "checks existence of branch" do
74
+ expect(repo.branch_exists?('master')).to be true
75
+ expect(repo.branch_exists?('master-404')).to be false
76
+ end
77
+ end
78
+ end
@@ -0,0 +1,27 @@
1
+ require 'spec_helper'
2
+
3
+ describe Ginatra::RepoStats do
4
+ let(:repo) { Ginatra::RepoList.find('test') }
5
+ let(:repo_stats) { Ginatra::RepoStats.new(repo, 'master') }
6
+
7
+ it "#license" do
8
+ expect(repo_stats.license).to eq('MIT')
9
+ end
10
+
11
+ it "#commits_count" do
12
+ expect(repo_stats.commits_count).to eq(57)
13
+ end
14
+
15
+ it "#contributors" do
16
+ contributors = repo_stats.contributors
17
+ expect(contributors).to be_a_kind_of(Array)
18
+ expect(contributors.size).to eq(2)
19
+ expect(contributors.first).to eq(['atmos@atmos.org', { author: 'Corey Donohoe', commits_count: 55 }])
20
+ end
21
+
22
+ it "#created_at" do
23
+ created_at = repo_stats.created_at
24
+ expect(created_at).to be_a_kind_of(Time)
25
+ expect(created_at.to_s).to include('2009-03-04')
26
+ end
27
+ end
@@ -0,0 +1,121 @@
1
+ require 'spec_helper'
2
+
3
+ describe Ginatra::App do
4
+ describe "main page" do
5
+ it "returns http success" do
6
+ get '/'
7
+ expect(last_response.status).to eq(200)
8
+ end
9
+ end
10
+
11
+ describe "repo commits atom feed" do
12
+ it "returns http success" do
13
+ get '/test.atom'
14
+ expect(last_response.status).to eq(200)
15
+ end
16
+
17
+ it "returns application/xml" do
18
+ get '/test.atom'
19
+ expect(last_response.headers['Content-Type']).to match("application/xml.*")
20
+ end
21
+ end
22
+
23
+ describe "repo page" do
24
+ it "returns http success" do
25
+ get '/test'
26
+ expect(last_response.status).to eq(200)
27
+ end
28
+ end
29
+
30
+ describe "repo stats page" do
31
+ it "returns http success" do
32
+ get '/test/stats/master'
33
+ expect(last_response.status).to eq(200)
34
+ end
35
+ end
36
+
37
+ describe "branch commits atom feed" do
38
+ it "returns http success" do
39
+ get '/test/master.atom'
40
+ expect(last_response.status).to eq(200)
41
+ end
42
+
43
+ it "returns application/xml" do
44
+ get '/test/master.atom'
45
+ expect(last_response.headers['Content-Type']).to match("application/xml.*")
46
+ end
47
+ end
48
+
49
+ describe "repo branch page" do
50
+ it "returns http success" do
51
+ get '/test/master'
52
+ expect(last_response.status).to eq(200)
53
+ end
54
+ end
55
+
56
+ describe "repo commit patch" do
57
+ it "returns http success" do
58
+ get "/test/commit/095955b.patch"
59
+ expect(last_response.status).to eq(200)
60
+ end
61
+
62
+ it "returns text/plain" do
63
+ get "/test/commit/095955b.patch"
64
+ expect(last_response.headers['Content-Type']).to match("text/plain.*")
65
+ end
66
+ end
67
+
68
+ describe "repo commit page" do
69
+ it "returns http success" do
70
+ get "/test/commit/095955b"
71
+ expect(last_response.status).to eq(200)
72
+ end
73
+ end
74
+
75
+ describe "repo tag page" do
76
+ it "returns http success" do
77
+ get "/test/tag/v0.0.3"
78
+ expect(last_response.status).to eq(200)
79
+ end
80
+ end
81
+
82
+ describe "repo tree page" do
83
+ it "returns http success" do
84
+ get "/test/tree/master"
85
+ expect(last_response.status).to eq(200)
86
+ end
87
+ end
88
+
89
+ describe "repo tree page with path" do
90
+ it "returns http success" do
91
+ get "/test/tree/master/examples"
92
+ expect(last_response.status).to eq(200)
93
+ end
94
+ end
95
+
96
+ describe "repo blob page with path" do
97
+ it "returns http success" do
98
+ get '/test/blob/master/Gemfile'
99
+ expect(last_response.status).to eq(200)
100
+ end
101
+ end
102
+
103
+ describe "repo blob raw page" do
104
+ it "returns http success" do
105
+ get '/test/raw/master/Gemfile'
106
+ expect(last_response.status).to eq(200)
107
+ end
108
+
109
+ it "returns text/plain" do
110
+ get '/test/raw/master/Gemfile'
111
+ expect(last_response.headers['Content-Type']).to match("text/plain.*")
112
+ end
113
+ end
114
+
115
+ describe "repo log page" do
116
+ it "returns http success" do
117
+ get '/test/master/page/1'
118
+ expect(last_response.status).to eq(200)
119
+ end
120
+ end
121
+ end
data/spec/spec_helper.rb CHANGED
@@ -1,27 +1,18 @@
1
+ ENV['RACK_ENV'] = 'test'
1
2
 
2
- require 'bundler'
3
- Bundler.setup(:default, :test)
4
3
  require 'rspec'
5
4
  require 'ginatra'
6
- require 'webrat'
7
5
  require 'rack/test'
8
6
 
9
- Webrat.configure do |config|
10
- config.mode = :rack
7
+ def app
8
+ Ginatra::App
11
9
  end
12
10
 
13
- current_path = File.expand_path(File.dirname(__FILE__))
14
-
15
- Ginatra::App.set :environment, :test
16
- Ginatra::Config[:git_dirs] = ["#{current_path}/../repos/*"]
11
+ def current_path
12
+ File.expand_path File.dirname(__FILE__)
13
+ end
17
14
 
18
15
  RSpec.configure do |config|
19
- def app
20
- Ginatra::App
21
- end
22
-
23
- config.include(Rack::Test::Methods)
24
- config.include(Webrat::Methods)
25
- config.include(Webrat::Matchers)
16
+ config.include Rack::Test::Methods
17
+ config.include Ginatra::Helpers
26
18
  end
27
-