repobrowse 0.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 (43) hide show
  1. checksums.yaml +7 -0
  2. data/.gitattributes +5 -0
  3. data/.gitignore +3 -0
  4. data/COPYING +661 -0
  5. data/GNUmakefile +38 -0
  6. data/MANIFEST +42 -0
  7. data/README +35 -0
  8. data/lib/repobrowse.rb +7 -0
  9. data/lib/repobrowse/app.rb +60 -0
  10. data/lib/repobrowse/config.rb +66 -0
  11. data/lib/repobrowse/error.rb +21 -0
  12. data/lib/repobrowse/escape.rb +28 -0
  13. data/lib/repobrowse/git.rb +71 -0
  14. data/lib/repobrowse/git_atom.rb +109 -0
  15. data/lib/repobrowse/git_commit_html.rb +320 -0
  16. data/lib/repobrowse/git_disambiguate.rb +21 -0
  17. data/lib/repobrowse/git_http_backend.rb +109 -0
  18. data/lib/repobrowse/git_log.rb +4 -0
  19. data/lib/repobrowse/git_patch.rb +55 -0
  20. data/lib/repobrowse/git_raw.rb +50 -0
  21. data/lib/repobrowse/git_raw_tree_html.rb +50 -0
  22. data/lib/repobrowse/git_show.rb +32 -0
  23. data/lib/repobrowse/git_src.rb +37 -0
  24. data/lib/repobrowse/git_src_blob_html.rb +89 -0
  25. data/lib/repobrowse/git_src_tree_html.rb +118 -0
  26. data/lib/repobrowse/html.rb +66 -0
  27. data/lib/repobrowse/limit_rd.rb +86 -0
  28. data/lib/repobrowse/pipe_body.rb +25 -0
  29. data/lib/repobrowse/repo.rb +21 -0
  30. data/lib/repobrowse/static.rb +96 -0
  31. data/repobrowse.gemspec +29 -0
  32. data/test/covshow.rb +30 -0
  33. data/test/git.fast-import-data +101 -0
  34. data/test/helper.rb +182 -0
  35. data/test/test_config.rb +29 -0
  36. data/test/test_git.rb +15 -0
  37. data/test/test_git_atom.rb +27 -0
  38. data/test/test_git_clone.rb +73 -0
  39. data/test/test_git_patch.rb +44 -0
  40. data/test/test_git_raw_tree_html.rb +34 -0
  41. data/test/test_git_show.rb +17 -0
  42. data/test/test_html.rb +23 -0
  43. metadata +139 -0
@@ -0,0 +1,29 @@
1
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
2
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
3
+ # frozen_string_literal: true
4
+ require_relative 'helper'
5
+
6
+ class TestConfig < Test::Unit::TestCase
7
+ def test_load_hash
8
+ config = {
9
+ 'repo.git.path' => '/path/to/git.git',
10
+ 'repo.repobrowse.path' => '/path/to/repobrowse.git',
11
+ }
12
+ config = Repobrowse::Config.new(config)
13
+ assert_instance_of Repobrowse::Config, config
14
+ end
15
+
16
+ def test_load_file
17
+ cfg = Tempfile.new('git-config')
18
+ cfg.write <<''
19
+ [repo "git"]
20
+ email = a@example.com
21
+ email = b@example.com
22
+ path = /path/to/nowhere
23
+
24
+ cfg.flush
25
+ cfg = Repobrowse::Config.new(cfg.path)
26
+ assert_equal %w(a@example.com b@example.com),
27
+ cfg.instance_variable_get(:@raw)['repo.git.email']
28
+ end
29
+ end
@@ -0,0 +1,15 @@
1
+ # -*- encoding: binary -*-
2
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
3
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
4
+ # frozen_string_literal: true
5
+ require_relative 'helper'
6
+ require 'repobrowse/git'
7
+
8
+ class TestGit < Test::Unit::TestCase
9
+ def test_unquote
10
+ g = Repobrowse::Git.new('/dev/null')
11
+ assert_equal "foo\nbar", g.git_unquote('"foo\\nbar"'), 'unquoted newline'
12
+ assert_equal "Eléanor", g.git_unquote('"El\\303\\251anor"'),
13
+ 'unquoted octal'
14
+ end
15
+ end
@@ -0,0 +1,27 @@
1
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
2
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
3
+ # frozen_string_literal: true
4
+ require_relative 'helper'
5
+ require 'rss'
6
+
7
+ class TestGitAtom < Test::Unit::TestCase
8
+ def test_git_atom
9
+ git_tmp_repo do |tmp_dir, git_dir|
10
+ s, h, b = req('GET', "/tmp/atom/master")
11
+ assert_equal 'application/atom+xml', h['Content-Type']
12
+ assert_equal 200, s.to_i
13
+ str = body_string(b)
14
+ feed = RSS::Parser.parse(str)
15
+ assert_kind_of RSS::Atom::Feed, feed
16
+ assert_predicate feed, :valid?
17
+
18
+ s, h, _ = req('GET', "/tmp/atom/master:non/existent")
19
+ assert h['Content-Type'], 'whatever type is fine for now'
20
+ assert_equal 404, s.to_i
21
+
22
+ s, h, _ = req('GET', "/tmp/atom/master:dir/")
23
+ assert_equal 302, s.to_i
24
+ assert_match %r{\Ahttp://[^/]+/tmp/atom/master:dir\z}, h['Location']
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,73 @@
1
+ # -*- encoding: binary -*-
2
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
3
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
4
+ # frozen_string_literal: true
5
+ require_relative 'helper'
6
+
7
+ class TestClone < Test::Unit::TestCase
8
+ def test_clone
9
+ git_tmp_repo do |tmp_dir, git_dir|
10
+ rack_server(@app) do |logq, host, port|
11
+ url = "http://#{host}:#{port}/tmp"
12
+ dst = "#{tmp_dir}/dst"
13
+
14
+ assert system(*%W(git clone -q #{url} #{dst})),
15
+ 'smart clone works'
16
+ FileUtils.rm_rf(dst)
17
+
18
+ assert system(*%W(git --git-dir=#{git_dir} update-server-info)),
19
+ 'enable dumb clones'
20
+
21
+ env = { 'GIT_SMART_HTTP' => '0' }
22
+ assert system(env, *%W(git clone -q #{url} #{dst})),
23
+ 'dumb clone works'
24
+ FileUtils.rm_rf(dst)
25
+
26
+ assert system(*%W(git --git-dir=#{git_dir} repack -adq)), 'repack'
27
+ assert system(env, *%W(git clone -q #{url} #{dst})),
28
+ 'dumb clone works after packing'
29
+
30
+ packs = Dir["#{git_dir}/objects/pack/*.pack"]
31
+ if packs[0] =~ %r{(/objects/pack/[^\.]+\.pack)\z}
32
+ require 'net/http'
33
+ Net::HTTP.start(host, port) do |http|
34
+ path = -"/tmp#$1"
35
+ res = http.request(Net::HTTP::Get.new(path))
36
+ pack = File.open(packs[0], 'rb', &:read)
37
+ size = pack.size
38
+ assert_equal pack, res.body
39
+ assert_equal 200, res.code.to_i
40
+
41
+ req = Net::HTTP::Get.new(path, 'Range' => 'bytes=5-46')
42
+ res = http.request(req)
43
+ assert_equal 206, res.code.to_i
44
+ assert_equal "bytes 5-46/#{size}", res['Content-Range']
45
+ assert_equal pack[5..46], res.body
46
+ assert_equal 'application/x-git-packed-objects', res['Content-Type']
47
+
48
+ req = Net::HTTP::Get.new(path, 'Range' => 'bytes=5-')
49
+ res = http.request(req)
50
+ assert_equal 206, res.code.to_i
51
+ last = size - 1
52
+ assert_equal "bytes 5-#{last}/#{size}", res['Content-Range']
53
+ assert_equal pack[5..-1], res.body
54
+
55
+ req = Net::HTTP::Get.new(path, 'Range' => 'bytes=-1')
56
+ res = http.request(req)
57
+ assert_equal 206, res.code.to_i
58
+ assert_equal "bytes #{last}-#{last}/#{size}", res['Content-Range']
59
+ assert_equal pack[-1], res.body
60
+
61
+ req = Net::HTTP::Get.new(path, 'Range' => 'bytes=0-0')
62
+ res = http.request(req)
63
+ assert_equal 206, res.code.to_i
64
+ assert_equal "bytes 0-0/#{size}", res['Content-Range']
65
+ assert_equal pack[0], res.body
66
+ end
67
+ else
68
+ warn "no packs? #{packs.inspect}"
69
+ end
70
+ end
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,44 @@
1
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
2
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
3
+ # frozen_string_literal: true
4
+ require_relative 'helper'
5
+
6
+ class TestGitPatch < Test::Unit::TestCase
7
+ def test_git_patch
8
+ git_tmp_repo do |tmp_dir, git_dir|
9
+ g = Repobrowse::Git.new(git_dir)
10
+ cmt = g.rugged.rev_parse('HEAD')
11
+ cmt = cmt.oid
12
+ assert_match %r{\A[a-f0-9]{40}\z}, cmt
13
+ status, headers, body = req('GET', "/tmp/#{cmt}.patch")
14
+ assert headers.delete('Expires'), 'Expires exists'
15
+ orig = [ status, headers ].freeze
16
+ assert_equal 200, status.to_i
17
+ assert_equal 'text/plain; charset=UTF-8', headers['Content-Type']
18
+ assert_equal %Q{inline; filename="#{cmt}.patch"},
19
+ headers['Content-Disposition']
20
+ str = body_string(body)
21
+ assert_match %r{\AFrom #{cmt} }, str
22
+
23
+ patch = str.split("\n")
24
+ sig = patch.pop
25
+ assert(sig.sub!(/format-patch /, 'format-patch --no-signature '))
26
+ assert_equal '-- ', patch.pop
27
+ sig_out = IO.popen(sig, chdir: git_dir, &:read)
28
+ sig_out = sig_out.split("\n")
29
+ assert_equal patch, sig_out, 'sig used to regenerate the patch'
30
+
31
+ status, headers, body = req('GET', "/tmp/#{cmt[0,16]}.patch")
32
+ assert_equal 302, status, 'redirected to full commit URL'
33
+ assert_match %r{://[^/]+/tmp/#{cmt}\.patch\z}, headers['Location']
34
+
35
+ res = req('HEAD', "/tmp/#{cmt}.patch")
36
+ assert res[1].delete('Expires'), 'Expires exists'
37
+ assert_equal '', body_string(res.pop), 'HEAD gives empty body'
38
+ assert_equal orig, res, 'HEAD works'
39
+
40
+ res = req('GET', "/tmp/#{'0' * 40}.patch")
41
+ assert_equal 404, res[0].to_i
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,34 @@
1
+ # -*- encoding: binary -*-
2
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
3
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
4
+ # frozen_string_literal: true
5
+ require_relative 'helper'
6
+ require 'repobrowse/git_raw_tree_html'
7
+
8
+ class TestGitRawTreeHTML < Test::Unit::TestCase
9
+ def test_foo
10
+ git_tmp_repo do |tmp_dir, git_dir|
11
+ g = Repobrowse::Git.new(git_dir)
12
+ rgd = g.rugged
13
+ re = %r{<li><a\nhref="[^"]+">([^<]+)</a></li>}
14
+
15
+ tree = rgd.rev_parse('HEAD:')
16
+ foo = Repobrowse::GitRawTreeHTML.new(tree, 'HEAD', nil)
17
+ s = +''
18
+ foo.each { |buf| s << buf }
19
+ cmd = %W(git --git-dir=#{git_dir} ls-tree -z --name-only HEAD:)
20
+ dir = IO.popen(cmd, 'rb') { |rd| rd.readlines("\0", chomp: true) }
21
+ assert_equal dir, s.scan(re).flatten!
22
+ foo.close
23
+
24
+ tree = rgd.rev_parse('HEAD:dir')
25
+ foo = Repobrowse::GitRawTreeHTML.new(tree, 'HEAD', 'dir')
26
+ s = +''
27
+ foo.each { |buf| s << buf }
28
+ cmd = %W(git --git-dir=#{git_dir} ls-tree -z --name-only HEAD:dir)
29
+ dir = IO.popen(cmd, 'rb') { |rd| rd.readlines("\0", chomp: true) }
30
+ assert_equal [ '../', dir ].flatten!, s.scan(re).flatten!
31
+ foo.close
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,17 @@
1
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
2
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
3
+ # frozen_string_literal: true
4
+ require_relative 'helper'
5
+
6
+ class TestGitShow < Test::Unit::TestCase
7
+ def test_git_show
8
+ git_tmp_repo do |tmp_dir, git_dir|
9
+ g = Repobrowse::Git.new(git_dir)
10
+ cmt = g.rugged.rev_parse_oid('HEAD')
11
+ assert_match %r{\A[a-f0-9]{40}\z}, cmt
12
+ status, _, body = req('GET', "/tmp/#{cmt}")
13
+ assert_equal 200, status.to_i
14
+ tidy_check(body)
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,23 @@
1
+ # -*- encoding: binary -*-
2
+ # Copyright (C) 2017-2018 all contributors <repobrowse-public@80x24.org>
3
+ # License: AGPL-3.0+ <https://www.gnu.org/licenses/agpl-3.0.txt>
4
+ # frozen_string_literal: false
5
+ require_relative 'helper'
6
+ require 'repobrowse/html'
7
+
8
+ class TestHtml < Test::Unit::TestCase
9
+ def test_attr
10
+ html = Repobrowse::HTML.new
11
+ ary = [ 'Hello/World.pm', 'Zcat', 'hello world.c', 'Eléanor', '$at',
12
+ 'hello_world'
13
+ ]
14
+ ary.each do |s|
15
+ attr = html.to_anchor(-s)
16
+ assert_not_same s, attr
17
+ assert_match %r{\A[a-zA-Z][\w:\.]+\z}, attr
18
+ assert_equal %Q("#{attr}"), attr.encode(xml: :attr),
19
+ 'no need to encode again'
20
+ assert_equal s, html.from_anchor(-attr)
21
+ end
22
+ end
23
+ end
metadata ADDED
@@ -0,0 +1,139 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: repobrowse
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.0
5
+ platform: ruby
6
+ authors:
7
+ - repobrowse hackers
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2018-07-15 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: test-unit
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '3.0'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '3.0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: roda
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '3.3'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '3.3'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rugged
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '0.24'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '0.24'
55
+ description: |-
56
+ A repository browser with only basic HTML and text; free of
57
+ images and JavaScript. It is intended as a companion to
58
+ public-inbox[1] but may be used on its own. It only supports
59
+ git for now, but support for other Free Software version control
60
+ systems may happen.
61
+ email: repobrowse-public@80x24.org
62
+ executables: []
63
+ extensions: []
64
+ extra_rdoc_files: []
65
+ files:
66
+ - ".gitattributes"
67
+ - ".gitignore"
68
+ - COPYING
69
+ - GNUmakefile
70
+ - MANIFEST
71
+ - README
72
+ - lib/repobrowse.rb
73
+ - lib/repobrowse/app.rb
74
+ - lib/repobrowse/config.rb
75
+ - lib/repobrowse/error.rb
76
+ - lib/repobrowse/escape.rb
77
+ - lib/repobrowse/git.rb
78
+ - lib/repobrowse/git_atom.rb
79
+ - lib/repobrowse/git_commit_html.rb
80
+ - lib/repobrowse/git_disambiguate.rb
81
+ - lib/repobrowse/git_http_backend.rb
82
+ - lib/repobrowse/git_log.rb
83
+ - lib/repobrowse/git_patch.rb
84
+ - lib/repobrowse/git_raw.rb
85
+ - lib/repobrowse/git_raw_tree_html.rb
86
+ - lib/repobrowse/git_show.rb
87
+ - lib/repobrowse/git_src.rb
88
+ - lib/repobrowse/git_src_blob_html.rb
89
+ - lib/repobrowse/git_src_tree_html.rb
90
+ - lib/repobrowse/html.rb
91
+ - lib/repobrowse/limit_rd.rb
92
+ - lib/repobrowse/pipe_body.rb
93
+ - lib/repobrowse/repo.rb
94
+ - lib/repobrowse/static.rb
95
+ - repobrowse.gemspec
96
+ - test/covshow.rb
97
+ - test/git.fast-import-data
98
+ - test/helper.rb
99
+ - test/test_config.rb
100
+ - test/test_git.rb
101
+ - test/test_git_atom.rb
102
+ - test/test_git_clone.rb
103
+ - test/test_git_patch.rb
104
+ - test/test_git_raw_tree_html.rb
105
+ - test/test_git_show.rb
106
+ - test/test_html.rb
107
+ homepage: https://80x24.org/repobrowse/
108
+ licenses:
109
+ - AGPL-3.0+
110
+ metadata: {}
111
+ post_install_message:
112
+ rdoc_options: []
113
+ require_paths:
114
+ - lib
115
+ required_ruby_version: !ruby/object:Gem::Requirement
116
+ requirements:
117
+ - - ">="
118
+ - !ruby/object:Gem::Version
119
+ version: '2.3'
120
+ required_rubygems_version: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
125
+ requirements: []
126
+ rubyforge_project:
127
+ rubygems_version: 2.7.7
128
+ signing_key:
129
+ specification_version: 4
130
+ summary: repobrowse - old-fashioned repository browser
131
+ test_files:
132
+ - test/test_html.rb
133
+ - test/test_git_patch.rb
134
+ - test/test_git_show.rb
135
+ - test/test_git_clone.rb
136
+ - test/test_config.rb
137
+ - test/test_git_raw_tree_html.rb
138
+ - test/test_git.rb
139
+ - test/test_git_atom.rb