forked from cstrahan/bundix
-
-
Notifications
You must be signed in to change notification settings - Fork 55
/
commandline.rb
169 lines (140 loc) · 4.37 KB
/
commandline.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
require 'optparse'
require 'tmpdir'
require 'tempfile'
require 'pathname'
require_relative '../bundix'
require_relative 'shell_nix_context'
class Bundix
class CommandLine
DEFAULT_OPTIONS = {
ruby: 'ruby',
bundle_pack_path: 'vendor/bundle',
gemfile: 'Gemfile',
lockfile: 'Gemfile.lock',
gemset: 'gemset.nix',
project: File.basename(Dir.pwd)
}
def self.run
self.new.run
end
def initialize
@options = DEFAULT_OPTIONS.clone
end
attr_accessor :options
def run
parse_options
handle_magic
handle_lock
handle_init
gemset = build_gemset
save_gemset(gemset)
end
def parse_options
op = OptionParser.new do |o|
o.on '-m', '--magic', 'lock, pack, and write dependencies' do
options[:magic] = true
end
o.on "--ruby=#{options[:ruby]}", 'ruby version to use for magic and init, defaults to latest' do |value|
options[:ruby] = value
end
o.on "--bundle-pack-path=#{options[:bundle_pack_path]}", "path to pack the magic" do |value|
options[:bundle_pack_path] = value
end
o.on '-i', '--init', "initialize a new shell.nix for nix-shell (won't overwrite old ones)" do
options[:init] = true
end
o.on "--gemset=#{options[:gemset]}", 'path to the gemset.nix' do |value|
options[:gemset] = File.expand_path(value)
end
o.on "--lockfile=#{options[:lockfile]}", 'path to the Gemfile.lock' do |value|
options[:lockfile] = File.expand_path(value)
end
o.on "--gemfile=#{options[:gemfile]}", 'path to the Gemfile' do |value|
options[:gemfile] = File.expand_path(value)
end
o.on '-d', '--dependencies', 'include gem dependencies (deprecated)' do
warn '--dependencies/-d is deprecated because'
warn 'dependencies will always be fetched'
end
o.on '-q', '--quiet', 'only output errors' do
options[:quiet] = true
end
o.on '-l', '--lock', 'generate Gemfile.lock first' do
options[:lock] = true
end
o.on '-v', '--version', 'show the version of bundix' do
puts Bundix::VERSION
exit
end
o.on '--env', 'show the environment in bundix' do
system('env')
exit
end
end
op.parse!
$VERBOSE = !options[:quiet]
options
end
def handle_magic
ENV['BUNDLE_GEMFILE'] = options[:gemfile]
if options[:magic]
fail unless system(
Bundix::NIX_SHELL, '-p', options[:ruby],
"bundler.override { ruby = #{options[:ruby]}; }",
"--command", "bundle lock --lockfile=#{options[:lockfile]}")
fail unless system(
Bundix::NIX_SHELL, '-p', options[:ruby],
"bundler.override { ruby = #{options[:ruby]}; }",
"--command", "bundle pack --all --path #{options[:bundle_pack_path]}")
end
end
def shell_nix_context
ShellNixContext.from_hash(options)
end
def shell_nix_string
tmpl = ERB.new(File.read(File.expand_path('../../template/shell-nix.erb', __dir__)))
tmpl.result(shell_nix_context.bind)
end
def handle_init
if options[:init]
if File.file?('shell.nix')
warn "won't override existing shell.nix but here is what it'd look like:"
puts shell_nix_string
else
File.write('shell.nix', shell_nix_string)
end
end
end
def handle_lock
if options[:lock]
lock = !File.file?(options[:lockfile])
lock ||= File.mtime(options[:gemfile]) > File.mtime(options[:lockfile])
if lock
ENV.delete('BUNDLE_PATH')
ENV.delete('BUNDLE_FROZEN')
ENV.delete('BUNDLE_BIN_PATH')
system('bundle', 'lock')
fail 'bundle lock failed' unless $?.success?
end
end
end
def build_gemset
Bundix.new(options).convert
end
def object2nix(obj)
Nixer.serialize(obj)
end
def save_gemset(gemset)
tempfile = Tempfile.new('gemset.nix', encoding: 'UTF-8')
begin
tempfile.write(object2nix(gemset))
tempfile.flush
FileUtils.cp(tempfile.path, options[:gemset])
FileUtils.chmod(0644, options[:gemset])
ensure
tempfile.close!
tempfile.unlink
end
end
end
end