gitdocs 0.4.15 → 0.5.0.pre1
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.
- checksums.yaml +15 -0
- data/.gitignore +2 -1
- data/.travis.yml +8 -0
- data/CHANGELOG +13 -1
- data/README.md +17 -5
- data/Rakefile +2 -0
- data/bin/gitdocs +1 -1
- data/gitdocs.gemspec +8 -5
- data/lib/gitdocs.rb +2 -3
- data/lib/gitdocs/cli.rb +89 -45
- data/lib/gitdocs/configuration.rb +13 -12
- data/lib/gitdocs/docfile.rb +1 -1
- data/lib/gitdocs/manager.rb +35 -42
- data/lib/gitdocs/migration/001_create_shares.rb +3 -3
- data/lib/gitdocs/migration/002_add_remote_branch.rb +3 -3
- data/lib/gitdocs/migration/003_create_configs.rb +3 -3
- data/lib/gitdocs/migration/004_add_index_for_path.rb +3 -3
- data/lib/gitdocs/migration/005_add_start_web_frontend.rb +2 -2
- data/lib/gitdocs/migration/006_add_web_port_to_config.rb +2 -2
- data/lib/gitdocs/rendering.rb +1 -1
- data/lib/gitdocs/runner.rb +64 -50
- data/lib/gitdocs/server.rb +51 -27
- data/lib/gitdocs/version.rb +2 -2
- data/test/configuration_test.rb +13 -13
- data/test/runner_test.rb +13 -13
- data/test/test_helper.rb +24 -22
- metadata +34 -63
@@ -2,12 +2,12 @@ class CreateShares < ActiveRecord::Migration
|
|
2
2
|
def self.up
|
3
3
|
create_table :shares do |t|
|
4
4
|
t.column :path, :string
|
5
|
-
t.column :polling_interval, :double, :
|
6
|
-
t.column :notification, :boolean, :
|
5
|
+
t.column :polling_interval, :double, default: 15
|
6
|
+
t.column :notification, :boolean, default: true
|
7
7
|
end
|
8
8
|
end
|
9
9
|
|
10
10
|
def self.down
|
11
|
-
|
11
|
+
fail
|
12
12
|
end
|
13
13
|
end
|
@@ -1,10 +1,10 @@
|
|
1
1
|
class AddRemoteBranch < ActiveRecord::Migration
|
2
2
|
def self.up
|
3
|
-
add_column :shares, :remote_name, :string, :
|
4
|
-
add_column :shares, :branch_name, :string, :
|
3
|
+
add_column :shares, :remote_name, :string, default: 'origin'
|
4
|
+
add_column :shares, :branch_name, :string, default: 'master'
|
5
5
|
end
|
6
6
|
|
7
7
|
def self.down
|
8
|
-
|
8
|
+
fail
|
9
9
|
end
|
10
10
|
end
|
@@ -1,11 +1,11 @@
|
|
1
1
|
class CreateConfigs < ActiveRecord::Migration
|
2
2
|
def self.up
|
3
3
|
create_table :configs do |t|
|
4
|
-
t.column :load_browser_on_startup, :boolean, :
|
4
|
+
t.column :load_browser_on_startup, :boolean, default: true
|
5
5
|
end
|
6
6
|
end
|
7
7
|
|
8
8
|
def self.down
|
9
|
-
|
9
|
+
fail
|
10
10
|
end
|
11
|
-
end
|
11
|
+
end
|
@@ -1,10 +1,10 @@
|
|
1
1
|
class AddIndexForPath < ActiveRecord::Migration
|
2
2
|
def self.up
|
3
|
-
shares = Gitdocs::Configuration::Share.all.
|
3
|
+
shares = Gitdocs::Configuration::Share.all.reduce(Hash.new { |h, k| h[k] = [] }) { |h, s| h[s.path] << s; h }
|
4
4
|
shares.each do |path, shares|
|
5
5
|
shares.shift
|
6
6
|
shares.each(&:destroy) unless shares.empty?
|
7
7
|
end
|
8
|
-
add_index :shares, :path, :
|
8
|
+
add_index :shares, :path, unique: true
|
9
9
|
end
|
10
|
-
end
|
10
|
+
end
|
data/lib/gitdocs/rendering.rb
CHANGED
data/lib/gitdocs/runner.rb
CHANGED
@@ -4,11 +4,17 @@ module Gitdocs
|
|
4
4
|
|
5
5
|
attr_reader :root, :listener
|
6
6
|
|
7
|
+
def self.start_all(shares)
|
8
|
+
runners = shares.map { |share| Runner.new(share) }
|
9
|
+
runners.each(&:run)
|
10
|
+
runners
|
11
|
+
end
|
12
|
+
|
7
13
|
def initialize(share)
|
8
14
|
@share = share
|
9
|
-
@root = share.path.sub(%r{/+$},'') if share.path
|
15
|
+
@root = share.path.sub(%r{/+$}, '') if share.path
|
10
16
|
@polling_interval = share.polling_interval
|
11
|
-
@icon = File.expand_path(
|
17
|
+
@icon = File.expand_path('../../img/icon.png', __FILE__)
|
12
18
|
end
|
13
19
|
|
14
20
|
SearchResult = Struct.new(:file, :context)
|
@@ -17,7 +23,7 @@ module Gitdocs
|
|
17
23
|
|
18
24
|
results = []
|
19
25
|
if result_test = sh_string("git grep -i #{ShellTools.escape(term)}")
|
20
|
-
result_test.scan(/(.*?):([^\n]*)/) do |(file, context)|
|
26
|
+
result_test.scan(/(.*?):([^\n]*)/) do |(file, context)|
|
21
27
|
if result = results.find { |s| s.file == file }
|
22
28
|
result.context += ' ... ' + context
|
23
29
|
else
|
@@ -34,41 +40,41 @@ module Gitdocs
|
|
34
40
|
@show_notifications = @share.notification
|
35
41
|
@current_remote = @share.remote_name
|
36
42
|
@current_branch = @share.branch_name
|
37
|
-
@current_revision = sh_string(
|
43
|
+
@current_revision = sh_string('git rev-parse HEAD')
|
38
44
|
Guard::Notifier.turn_on if @show_notifications
|
39
45
|
|
40
46
|
mutex = Mutex.new
|
41
47
|
|
42
|
-
info(
|
48
|
+
info('Running gitdocs!', "Running gitdocs in `#{@root}'")
|
43
49
|
|
44
50
|
# Pull changes from remote repository
|
45
51
|
syncer = proc do
|
46
52
|
EM.defer(proc do
|
47
53
|
mutex.synchronize { sync_changes }
|
48
54
|
end, proc do
|
49
|
-
EM.add_timer(@polling_interval)
|
55
|
+
EM.add_timer(@polling_interval) do
|
50
56
|
syncer.call
|
51
|
-
|
57
|
+
end
|
52
58
|
end)
|
53
59
|
end
|
54
60
|
syncer.call
|
55
61
|
# Listen for changes in local repository
|
56
62
|
|
57
|
-
EM.defer(proc
|
58
|
-
listener = Guard::Listener.select_and_init(@root, :
|
59
|
-
listener.on_change
|
63
|
+
EM.defer(proc do
|
64
|
+
listener = Guard::Listener.select_and_init(@root, watch_all_modifications: true)
|
65
|
+
listener.on_change do |directories|
|
60
66
|
directories.uniq!
|
61
|
-
directories.delete_if {|d| d =~ /\/\.git/}
|
67
|
+
directories.delete_if { |d| d =~ /\/\.git/ }
|
62
68
|
unless directories.empty?
|
63
69
|
EM.next_tick do
|
64
|
-
EM.defer(proc
|
70
|
+
EM.defer(proc do
|
65
71
|
mutex.synchronize { push_changes }
|
66
|
-
|
72
|
+
end, proc {})
|
67
73
|
end
|
68
74
|
end
|
69
|
-
|
75
|
+
end
|
70
76
|
listener.start
|
71
|
-
|
77
|
+
end, proc { EM.stop_reactor })
|
72
78
|
end
|
73
79
|
|
74
80
|
def clear_state
|
@@ -80,36 +86,36 @@ module Gitdocs
|
|
80
86
|
if status.success?
|
81
87
|
changes = get_latest_changes
|
82
88
|
unless changes.empty?
|
83
|
-
author_list = changes.
|
89
|
+
author_list = changes.reduce(Hash.new { |h, k| h[k] = 0 }) { |h, c| h[c['author']] += 1; h }.to_a.sort { |a, b| b[1] <=> a[1] }.map { |(name, count)| "* #{name} (#{count} change#{count == 1 ? '' : 's'})" }.join("\n")
|
84
90
|
info("Updated with #{changes.size} change#{changes.size == 1 ? '' : 's'}", "In `#{@root}':\n#{author_list}")
|
85
91
|
end
|
86
92
|
push_changes
|
87
93
|
elsif out[/CONFLICT/]
|
88
|
-
conflicted_files = sh(
|
89
|
-
|
94
|
+
conflicted_files = sh('git ls-files -u --full-name -z').split("\0")
|
95
|
+
.reduce(Hash.new { |h, k| h[k] = [] }) do|h, line|
|
90
96
|
parts = line.split(/\t/)
|
91
97
|
h[parts.last] << parts.first.split(/ /)
|
92
98
|
h
|
93
|
-
|
94
|
-
warn(
|
99
|
+
end
|
100
|
+
warn('There were some conflicts', "#{conflicted_files.keys.map { |f| "* #{f}" }.join("\n")}")
|
95
101
|
conflicted_files.each do |conflict, ids|
|
96
102
|
conflict_start, conflict_end = conflict.scan(/(.*?)(|\.[^\.]+)$/).first
|
97
103
|
ids.each do |(mode, sha, id)|
|
98
|
-
author =
|
104
|
+
author = ' original' if id == '1'
|
99
105
|
system("cd #{@root} && git show :#{id}:#{conflict} > '#{conflict_start} (#{sha[0..6]}#{author})#{conflict_end}'")
|
100
106
|
end
|
101
|
-
system("cd #{@root} && git rm #{conflict}")
|
107
|
+
system("cd #{@root} && git rm #{conflict}") || fail
|
102
108
|
end
|
103
109
|
push_changes
|
104
|
-
elsif sh_string(
|
110
|
+
elsif sh_string('git remote').nil? # no remote to pull from
|
105
111
|
# Do nothing, no remote repo yet
|
106
112
|
else
|
107
|
-
error(
|
113
|
+
error('There was a problem synchronizing this gitdoc', "A problem occurred in #{@root}:\n#{out}")
|
108
114
|
end
|
109
115
|
end
|
110
116
|
|
111
117
|
def push_changes
|
112
|
-
message_file = File.expand_path(
|
118
|
+
message_file = File.expand_path('.gitmessage~', @root)
|
113
119
|
if File.exist? message_file
|
114
120
|
message = File.read message_file
|
115
121
|
File.delete message_file
|
@@ -118,7 +124,7 @@ module Gitdocs
|
|
118
124
|
end
|
119
125
|
sh 'find . -type d -regex ``./[^.].*'' -empty -exec touch \'{}/.gitignore\' \;'
|
120
126
|
sh 'git add .'
|
121
|
-
sh "git commit -a -m #{ShellTools.escape(message)}" unless sh(
|
127
|
+
sh "git commit -a -m #{ShellTools.escape(message)}" unless sh('git status -s').strip.empty?
|
122
128
|
if @current_revision.nil? || sh('git status')[/branch is ahead/]
|
123
129
|
out, code = sh_with_code("git push #{@current_remote} #{@current_branch}")
|
124
130
|
if code.success?
|
@@ -127,12 +133,19 @@ module Gitdocs
|
|
127
133
|
elsif @current_revision.nil?
|
128
134
|
# ignorable
|
129
135
|
elsif out[/\[rejected\]/]
|
130
|
-
warn("There was a conflict in #{@root}, retrying",
|
136
|
+
warn("There was a conflict in #{@root}, retrying", '')
|
131
137
|
else
|
132
138
|
error("BAD Could not push changes in #{@root}", out)
|
133
|
-
|
139
|
+
# TODO: need to add a status on shares so that the push problem can be
|
140
|
+
# displayed.
|
134
141
|
end
|
135
142
|
end
|
143
|
+
rescue
|
144
|
+
# Rescue any standard exceptions which come from the push related
|
145
|
+
# commands. This will prevent problems on a single share from killing
|
146
|
+
# the entire daemon.
|
147
|
+
error("Unexpected error pushing changes in #{@root}")
|
148
|
+
# TODO: get logging and/or put the error message into a status field in the database
|
136
149
|
end
|
137
150
|
|
138
151
|
def get_latest_changes
|
@@ -145,7 +158,7 @@ module Gitdocs
|
|
145
158
|
Yajl::Parser.new.parse(out) do |obj|
|
146
159
|
lines << obj
|
147
160
|
end
|
148
|
-
@current_revision = sh(
|
161
|
+
@current_revision = sh('git rev-parse HEAD').strip
|
149
162
|
lines
|
150
163
|
end
|
151
164
|
else
|
@@ -157,30 +170,28 @@ module Gitdocs
|
|
157
170
|
# Returns the list of files in a given directory
|
158
171
|
# dir_files("some/dir") => [<Docfile>, <Docfile>]
|
159
172
|
def dir_files(dir_path)
|
160
|
-
Dir[File.join(dir_path,
|
173
|
+
Dir[File.join(dir_path, '*')].to_a.map { |path| Docfile.new(path) }
|
161
174
|
end
|
162
175
|
|
163
176
|
# Returns file meta data based on relative file path
|
164
177
|
# file_meta("path/to/file")
|
165
178
|
# => { :author => "Nick", :size => 1000, :modified => ... }
|
166
179
|
def file_meta(file)
|
167
|
-
result = {}
|
168
180
|
file = file.gsub(%r{^/}, '')
|
169
181
|
full_path = File.expand_path(file, @root)
|
170
182
|
log_result = sh_string("git log --format='%aN|%ai' -n1 #{ShellTools.escape(file)}")
|
171
|
-
|
172
|
-
author, modified = log_result.split("|")
|
183
|
+
author, modified = log_result.split('|')
|
173
184
|
modified = Time.parse(modified.sub(' ', 'T')).utc.iso8601
|
174
185
|
size = if File.directory?(full_path)
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
186
|
+
Dir[File.join(full_path, '**', '*')].reduce(0) do |size, file|
|
187
|
+
File.symlink?(file) ? size : size += File.size(file)
|
188
|
+
end
|
189
|
+
else
|
190
|
+
File.symlink?(full_path) ? 0 : File.size(full_path)
|
191
|
+
end
|
181
192
|
size = -1 if size == 0 # A value of 0 breaks the table sort for some reason
|
182
|
-
|
183
|
-
|
193
|
+
|
194
|
+
{ author: author, size: size, modified: modified }
|
184
195
|
end
|
185
196
|
|
186
197
|
# Returns the revisions available for a particular file
|
@@ -189,9 +200,9 @@ module Gitdocs
|
|
189
200
|
file = file.gsub(%r{^/}, '')
|
190
201
|
output = sh_string("git log --format='%h|%s|%aN|%ai' -n100 #{ShellTools.escape(file)}")
|
191
202
|
output.to_s.split("\n").map do |log_result|
|
192
|
-
commit, subject, author, date = log_result.split(
|
203
|
+
commit, subject, author, date = log_result.split('|')
|
193
204
|
date = Time.parse(date.sub(' ', 'T')).utc.iso8601
|
194
|
-
{ :
|
205
|
+
{ commit: commit, subject: subject, author: author, date: date }
|
195
206
|
end
|
196
207
|
end
|
197
208
|
|
@@ -207,7 +218,7 @@ module Gitdocs
|
|
207
218
|
|
208
219
|
# Revert a file to a particular revision
|
209
220
|
def file_revert(file, ref)
|
210
|
-
if file_revisions(file).map {|r| r[:commit]}.include? ref
|
221
|
+
if file_revisions(file).map { |r| r[:commit] }.include? ref
|
211
222
|
file = file.gsub(%r{^/}, '')
|
212
223
|
full_path = File.expand_path(file, @root)
|
213
224
|
content = File.read(file_revision_at(file, ref))
|
@@ -216,38 +227,41 @@ module Gitdocs
|
|
216
227
|
end
|
217
228
|
|
218
229
|
def valid?
|
219
|
-
out, status = sh_with_code
|
230
|
+
out, status = sh_with_code 'git status'
|
220
231
|
@root.present? && status.success?
|
221
232
|
end
|
222
233
|
|
223
234
|
def warn(title, msg)
|
224
235
|
if @show_notifications
|
225
|
-
Guard::Notifier.notify(msg, :
|
236
|
+
Guard::Notifier.notify(msg, title: title)
|
226
237
|
else
|
227
238
|
Kernel.warn("#{title}: #{msg}")
|
228
239
|
end
|
240
|
+
rescue # Prevent StandardErrors from stopping the daemon.
|
229
241
|
end
|
230
242
|
|
231
243
|
def info(title, msg)
|
232
244
|
if @show_notifications
|
233
|
-
Guard::Notifier.notify(msg, :
|
245
|
+
Guard::Notifier.notify(msg, title: title, image: @icon)
|
234
246
|
else
|
235
247
|
puts("#{title}: #{msg}")
|
236
248
|
end
|
249
|
+
rescue # Prevent StandardErrors from stopping the daemon.
|
237
250
|
end
|
238
251
|
|
239
252
|
def error(title, msg)
|
240
253
|
if @show_notifications
|
241
|
-
Guard::Notifier.notify(msg, :
|
254
|
+
Guard::Notifier.notify(msg, title: title, image: :failure)
|
242
255
|
else
|
243
256
|
Kernel.warn("#{title}: #{msg}")
|
244
257
|
end
|
258
|
+
rescue # Prevent StandardErrors from stopping the daemon.
|
245
259
|
end
|
246
260
|
|
247
261
|
# sh_string("git config branch.`git branch | grep '^\*' | sed -e 's/\* //'`.remote", "origin")
|
248
|
-
def sh_string(cmd, default=nil)
|
262
|
+
def sh_string(cmd, default = nil)
|
249
263
|
val = sh(cmd).strip rescue nil
|
250
|
-
|
264
|
+
val.nil? || val.empty? ? default : val
|
251
265
|
end
|
252
266
|
|
253
267
|
# Run in shell, return both status and output
|
data/lib/gitdocs/server.rb
CHANGED
@@ -4,31 +4,33 @@ require 'coderay'
|
|
4
4
|
require 'uri'
|
5
5
|
require 'haml'
|
6
6
|
require 'mimetype_fu'
|
7
|
+
require 'launchy'
|
7
8
|
|
8
9
|
module Gitdocs
|
9
10
|
class Server
|
10
|
-
def initialize(manager, *gitdocs)
|
11
|
+
def initialize(manager, port = 8888, *gitdocs)
|
11
12
|
@manager = manager
|
13
|
+
@port = port.to_i
|
12
14
|
@gitdocs = gitdocs
|
13
15
|
end
|
14
16
|
|
15
|
-
def start
|
16
|
-
gds
|
17
|
+
def start
|
18
|
+
gds = @gitdocs
|
17
19
|
manager = @manager
|
18
20
|
Thin::Logging.debug = @manager.debug
|
19
|
-
Thin::Server.start('127.0.0.1', port) do
|
20
|
-
use Rack::Static, :
|
21
|
+
Thin::Server.start('127.0.0.1', @port) do
|
22
|
+
use Rack::Static, urls: ['/css', '/js', '/img', '/doc'], root: File.expand_path('../public', __FILE__)
|
21
23
|
use Rack::MethodOverride
|
22
24
|
run Renee {
|
23
25
|
if request.path_info == '/'
|
24
26
|
if manager.config.shares.size == 1
|
25
|
-
redirect!
|
27
|
+
redirect! '/0'
|
26
28
|
else
|
27
|
-
render!
|
29
|
+
render! 'home', layout: 'app', locals: { conf: manager.config, nav_state: 'home' }
|
28
30
|
end
|
29
31
|
else
|
30
32
|
path 'settings' do
|
31
|
-
get.render! 'settings', :
|
33
|
+
get.render! 'settings', layout: 'app', locals: { conf: manager.config, nav_state: 'settings' }
|
32
34
|
post do
|
33
35
|
shares = manager.config.shares
|
34
36
|
manager.config.global.update_attributes(request.POST['config'])
|
@@ -47,7 +49,7 @@ module Gitdocs
|
|
47
49
|
end
|
48
50
|
|
49
51
|
path('search').get do
|
50
|
-
render!
|
52
|
+
render! 'search', layout: 'app', locals: { conf: manager.config, results: manager.search(request.GET['q']), nav_state: nil }
|
51
53
|
end
|
52
54
|
|
53
55
|
path('shares') do
|
@@ -70,14 +72,13 @@ module Gitdocs
|
|
70
72
|
gd = gds[idx]
|
71
73
|
halt 404 if gd.nil?
|
72
74
|
file_path = URI.unescape(request.path_info)
|
73
|
-
file_ext = File.extname(file_path)
|
74
75
|
expanded_path = File.expand_path(".#{file_path}", gd.root)
|
75
|
-
message_file = File.expand_path(
|
76
|
+
message_file = File.expand_path('.gitmessage~', gd.root)
|
76
77
|
halt 400 unless expanded_path[/^#{Regexp.quote(gd.root)}/]
|
77
78
|
parent = File.dirname(file_path)
|
78
79
|
parent = '' if parent == '/'
|
79
80
|
parent = nil if parent == '.'
|
80
|
-
locals = {:
|
81
|
+
locals = { idx: idx, parent: parent, root: gd.root, file_path: expanded_path, nav_state: nil }
|
81
82
|
mime = File.mime_type?(File.open(expanded_path)) if File.file?(expanded_path)
|
82
83
|
mode = request.params['mode']
|
83
84
|
if mode == 'meta' # Meta
|
@@ -85,63 +86,86 @@ module Gitdocs
|
|
85
86
|
elsif mode == 'save' # Saving
|
86
87
|
File.open(expanded_path, 'w') { |f| f.print request.params['data'] }
|
87
88
|
File.open(message_file, 'w') { |f| f.print request.params['message'] } unless request.params['message'] == ''
|
88
|
-
redirect!
|
89
|
+
redirect! '/' + idx.to_s + file_path
|
89
90
|
elsif mode == 'upload' # Uploading
|
90
91
|
halt 404 unless file = request.params['file']
|
91
92
|
tempfile, filename = file[:tempfile], file[:filename]
|
92
93
|
FileUtils.mv(tempfile.path, File.expand_path(filename, expanded_path))
|
93
|
-
redirect!
|
94
|
+
redirect! '/' + idx.to_s + file_path + '/' + filename
|
94
95
|
elsif !File.exist?(expanded_path) && !request.params['dir'] # edit for non-existent file
|
95
96
|
FileUtils.mkdir_p(File.dirname(expanded_path))
|
96
97
|
FileUtils.touch(expanded_path)
|
97
|
-
redirect!
|
98
|
+
redirect! '/' + idx.to_s + file_path + '?mode=edit'
|
98
99
|
elsif !File.exist?(expanded_path) && request.params['dir'] # create directory
|
99
100
|
FileUtils.mkdir_p(expanded_path)
|
100
|
-
redirect!
|
101
|
+
redirect! '/' + idx.to_s + file_path
|
101
102
|
elsif File.directory?(expanded_path) # list directory
|
102
103
|
contents = gd.dir_files(expanded_path)
|
103
104
|
rendered_readme = nil
|
104
|
-
if readme = Dir[File.expand_path(
|
105
|
+
if readme = Dir[File.expand_path('README.{md}', expanded_path)].first
|
105
106
|
rendered_readme = '<h3>' + File.basename(readme) + '</h3><div class="tilt">' + render(readme) + '</div>'
|
106
107
|
end
|
107
|
-
render!
|
108
|
-
elsif mode ==
|
108
|
+
render! 'dir', layout: 'app', locals: locals.merge(contents: contents, rendered_readme: rendered_readme)
|
109
|
+
elsif mode == 'revisions' # list revisions
|
109
110
|
revisions = gd.file_revisions(file_path)
|
110
|
-
render!
|
111
|
-
elsif mode ==
|
111
|
+
render! 'revisions', layout: 'app', locals: locals.merge(revisions: revisions)
|
112
|
+
elsif mode == 'revert' # revert file
|
112
113
|
if revision = request.params['revision']
|
113
114
|
File.open(message_file, 'w') { |f| f.print "Reverting '#{file_path}' to #{revision}" }
|
114
115
|
gd.file_revert(file_path, revision)
|
115
116
|
end
|
116
|
-
redirect!
|
117
|
+
redirect! '/' + idx.to_s + file_path
|
117
118
|
elsif mode == 'delete' # delete file
|
118
119
|
FileUtils.rm(expanded_path)
|
119
|
-
redirect!
|
120
|
+
redirect! '/' + idx.to_s + parent
|
120
121
|
elsif mode == 'edit' && (mime.match(%r{text/}) || mime.match(%r{x-empty})) # edit file
|
121
122
|
contents = File.read(expanded_path)
|
122
|
-
render!
|
123
|
+
render! 'edit', layout: 'app', locals: locals.merge(contents: contents)
|
123
124
|
elsif mode != 'raw' # render file
|
124
125
|
revision = request.params['revision']
|
125
126
|
expanded_path = gd.file_revision_at(file_path, revision) if revision
|
126
127
|
begin # attempting to render file
|
127
128
|
contents = '<div class="tilt">' + render(expanded_path) + '</div>'
|
128
|
-
rescue RuntimeError
|
129
|
+
rescue RuntimeError # not tilt supported
|
129
130
|
contents = if mime.match(%r{text/})
|
130
131
|
'<pre class="CodeRay">' + CodeRay.scan_file(expanded_path).encode(:html) + '</pre>'
|
131
132
|
else
|
132
133
|
%|<embed class="inline-file" src="/#{idx}#{request.path_info}?mode=raw"></embed>|
|
133
134
|
end
|
134
135
|
end
|
135
|
-
render!
|
136
|
+
render! 'file', layout: 'app', locals: locals.merge(contents: contents)
|
136
137
|
else # other file
|
137
138
|
run! Rack::File.new(gd.root)
|
138
139
|
end
|
139
140
|
end
|
140
141
|
end
|
141
142
|
}.setup {
|
142
|
-
views_path File.expand_path(
|
143
|
+
views_path File.expand_path('../views', __FILE__)
|
143
144
|
}
|
144
145
|
end
|
145
146
|
end
|
147
|
+
|
148
|
+
def wait_for_start_and_open(restarting)
|
149
|
+
wait_for_web_server = proc do
|
150
|
+
i = 0
|
151
|
+
begin
|
152
|
+
TCPSocket.open('127.0.0.1', @port).close
|
153
|
+
@manager.log('Web server running!')
|
154
|
+
if !restarting && @manager.config.global.load_browser_on_startup
|
155
|
+
Launchy.open("http://localhost:#{@port}/")
|
156
|
+
end
|
157
|
+
rescue Errno::ECONNREFUSED
|
158
|
+
sleep 0.2
|
159
|
+
i += 1
|
160
|
+
if i <= 20
|
161
|
+
@manager.log('Retrying web server loop...')
|
162
|
+
retry
|
163
|
+
else
|
164
|
+
@manager.log('Web server failed to start')
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|
168
|
+
EM.defer(wait_for_web_server)
|
169
|
+
end
|
146
170
|
end
|
147
171
|
end
|