grim-reaper 1.0.29
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 +7 -0
- data/README.md +511 -0
- data/bin/grim +397 -0
- data/docs/AI_MACHINE_LEARNING.md +373 -0
- data/docs/BACKUP_RECOVERY.md +477 -0
- data/docs/CLOUD_DISTRIBUTED_SYSTEMS.md +502 -0
- data/docs/DEVELOPMENT_TOOLS_INFRASTRUCTURE.md +547 -0
- data/docs/PERFORMANCE_OPTIMIZATION.md +515 -0
- data/docs/SECURITY_COMPLIANCE.md +535 -0
- data/docs/SYSTEM_MAINTENANCE_OPERATIONS.md +520 -0
- data/docs/SYSTEM_MONITORING_HEALTH.md +502 -0
- data/docs/TESTING_QUALITY_ASSURANCE.md +526 -0
- data/docs/WEB_SERVICES_APIS.md +573 -0
- data/lib/grim_reaper/core.rb +130 -0
- data/lib/grim_reaper/go_module.rb +151 -0
- data/lib/grim_reaper/installer.rb +485 -0
- data/lib/grim_reaper/python_module.rb +172 -0
- data/lib/grim_reaper/security_module.rb +180 -0
- data/lib/grim_reaper/shell_module.rb +156 -0
- data/lib/grim_reaper/version.rb +5 -0
- data/lib/grim_reaper.rb +41 -0
- metadata +247 -0
@@ -0,0 +1,151 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "open3"
|
4
|
+
|
5
|
+
module GrimReaper
|
6
|
+
# Go module wrapper for go_grim operations
|
7
|
+
class GoModule
|
8
|
+
attr_reader :config, :grim_root
|
9
|
+
|
10
|
+
def initialize(config, grim_root)
|
11
|
+
@config = config
|
12
|
+
@grim_root = grim_root
|
13
|
+
end
|
14
|
+
|
15
|
+
def execute(command, *args)
|
16
|
+
case command
|
17
|
+
when "compress"
|
18
|
+
execute_compress(*args)
|
19
|
+
when "decompress"
|
20
|
+
execute_decompress(*args)
|
21
|
+
when "build"
|
22
|
+
execute_build(*args)
|
23
|
+
when "test"
|
24
|
+
execute_test(*args)
|
25
|
+
when "benchmark"
|
26
|
+
execute_benchmark(*args)
|
27
|
+
else
|
28
|
+
execute_generic(command, *args)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
def status
|
33
|
+
{
|
34
|
+
status: "ready",
|
35
|
+
module: "go",
|
36
|
+
available_commands: %w[compress decompress build test benchmark],
|
37
|
+
grim_root: @grim_root
|
38
|
+
}
|
39
|
+
end
|
40
|
+
|
41
|
+
private
|
42
|
+
|
43
|
+
def execute_compress(*args)
|
44
|
+
binary_path = File.join(@grim_root, "go_grim", "build", "grim-compression")
|
45
|
+
|
46
|
+
if File.exist?(binary_path)
|
47
|
+
stdout, stderr, status = Open3.capture3(binary_path, "-input", *args, chdir: @grim_root)
|
48
|
+
{
|
49
|
+
command: "compress",
|
50
|
+
args: args,
|
51
|
+
stdout: stdout,
|
52
|
+
stderr: stderr,
|
53
|
+
success: status.success?,
|
54
|
+
module: "go"
|
55
|
+
}
|
56
|
+
else
|
57
|
+
{ error: "Go compression binary not found", module: "go" }
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
def execute_decompress(*args)
|
62
|
+
binary_path = File.join(@grim_root, "go_grim", "build", "grim-compression")
|
63
|
+
|
64
|
+
if File.exist?(binary_path)
|
65
|
+
stdout, stderr, status = Open3.capture3(binary_path, "-decompress", *args, chdir: @grim_root)
|
66
|
+
{
|
67
|
+
command: "decompress",
|
68
|
+
args: args,
|
69
|
+
stdout: stdout,
|
70
|
+
stderr: stderr,
|
71
|
+
success: status.success?,
|
72
|
+
module: "go"
|
73
|
+
}
|
74
|
+
else
|
75
|
+
{ error: "Go compression binary not found", module: "go" }
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
def execute_build(*args)
|
80
|
+
go_path = File.join(@grim_root, "go_grim")
|
81
|
+
|
82
|
+
if Dir.exist?(go_path)
|
83
|
+
stdout, stderr, status = Open3.capture3("go", "build", "-o", "build/grim-compression", ".", chdir: go_path)
|
84
|
+
{
|
85
|
+
command: "build",
|
86
|
+
args: args,
|
87
|
+
stdout: stdout,
|
88
|
+
stderr: stderr,
|
89
|
+
success: status.success?,
|
90
|
+
module: "go"
|
91
|
+
}
|
92
|
+
else
|
93
|
+
{ error: "Go source directory not found", module: "go" }
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
def execute_test(*args)
|
98
|
+
go_path = File.join(@grim_root, "go_grim")
|
99
|
+
|
100
|
+
if Dir.exist?(go_path)
|
101
|
+
stdout, stderr, status = Open3.capture3("go", "test", *args, chdir: go_path)
|
102
|
+
{
|
103
|
+
command: "test",
|
104
|
+
args: args,
|
105
|
+
stdout: stdout,
|
106
|
+
stderr: stderr,
|
107
|
+
success: status.success?,
|
108
|
+
module: "go"
|
109
|
+
}
|
110
|
+
else
|
111
|
+
{ error: "Go source directory not found", module: "go" }
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
def execute_benchmark(*args)
|
116
|
+
go_path = File.join(@grim_root, "go_grim")
|
117
|
+
|
118
|
+
if Dir.exist?(go_path)
|
119
|
+
stdout, stderr, status = Open3.capture3("go", "test", "-bench=.", *args, chdir: go_path)
|
120
|
+
{
|
121
|
+
command: "benchmark",
|
122
|
+
args: args,
|
123
|
+
stdout: stdout,
|
124
|
+
stderr: stderr,
|
125
|
+
success: status.success?,
|
126
|
+
module: "go"
|
127
|
+
}
|
128
|
+
else
|
129
|
+
{ error: "Go source directory not found", module: "go" }
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
133
|
+
def execute_generic(command, *args)
|
134
|
+
binary_path = File.join(@grim_root, "go_grim", "build", "grim-#{command}")
|
135
|
+
|
136
|
+
if File.exist?(binary_path)
|
137
|
+
stdout, stderr, status = Open3.capture3(binary_path, *args, chdir: @grim_root)
|
138
|
+
{
|
139
|
+
command: command,
|
140
|
+
args: args,
|
141
|
+
stdout: stdout,
|
142
|
+
stderr: stderr,
|
143
|
+
success: status.success?,
|
144
|
+
module: "go"
|
145
|
+
}
|
146
|
+
else
|
147
|
+
{ error: "Go binary not found: grim-#{command}", module: "go" }
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
end
|
@@ -0,0 +1,485 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "open3"
|
4
|
+
require "fileutils"
|
5
|
+
|
6
|
+
module GrimReaper
|
7
|
+
# Ruby-specific installer and dependency manager
|
8
|
+
class Installer
|
9
|
+
attr_reader :grim_root, :backup_dir, :install_dir
|
10
|
+
|
11
|
+
def initialize
|
12
|
+
@grim_root = find_grim_root
|
13
|
+
@backup_dir = ENV["HOME"] + "/.graveyard"
|
14
|
+
@install_dir = ENV["HOME"] + "/reaper"
|
15
|
+
end
|
16
|
+
|
17
|
+
# Find Grim Reaper root directory
|
18
|
+
def find_grim_root
|
19
|
+
# Try to find from current directory
|
20
|
+
current_dir = Dir.pwd
|
21
|
+
10.times do
|
22
|
+
if File.exist?(File.join(current_dir, "throne", "grim_throne.sh")) ||
|
23
|
+
File.exist?(File.join(current_dir, "throne", "rb_grim_throne.sh")) ||
|
24
|
+
File.exist?(File.join(current_dir, "tsk_flask", "grim_admin_server.py"))
|
25
|
+
return current_dir
|
26
|
+
end
|
27
|
+
|
28
|
+
parent_dir = File.dirname(current_dir)
|
29
|
+
break if parent_dir == current_dir
|
30
|
+
current_dir = parent_dir
|
31
|
+
end
|
32
|
+
|
33
|
+
# Try common installation paths
|
34
|
+
possible_paths = [
|
35
|
+
ENV["HOME"] + "/reaper",
|
36
|
+
ENV["HOME"] + "/.reaper",
|
37
|
+
"/root/reaper",
|
38
|
+
"/root/.reaper",
|
39
|
+
"/usr/local/reaper",
|
40
|
+
"/usr/share/reaper",
|
41
|
+
Dir.pwd
|
42
|
+
]
|
43
|
+
|
44
|
+
possible_paths.each do |path|
|
45
|
+
if Dir.exist?(path) && (
|
46
|
+
File.exist?(File.join(path, "throne", "grim_throne.sh")) ||
|
47
|
+
File.exist?(File.join(path, "throne", "rb_grim_throne.sh")) ||
|
48
|
+
File.exist?(File.join(path, "tsk_flask", "grim_admin_server.py"))
|
49
|
+
)
|
50
|
+
return path
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
raise Error, "Could not find Grim Reaper root directory"
|
55
|
+
end
|
56
|
+
|
57
|
+
# Setup complete Grim Reaper environment (like npm/pip packages)
|
58
|
+
def setup_complete_environment
|
59
|
+
puts "🗡️ Setting up complete Grim Reaper environment..."
|
60
|
+
|
61
|
+
# Setup Ruby environment
|
62
|
+
setup_ruby_environment
|
63
|
+
|
64
|
+
# Install Python components
|
65
|
+
install_python_components
|
66
|
+
|
67
|
+
# Install Go components
|
68
|
+
install_go_components
|
69
|
+
|
70
|
+
# Install Shell components
|
71
|
+
install_shell_components
|
72
|
+
|
73
|
+
# Install Scythe components
|
74
|
+
install_scythe_components
|
75
|
+
|
76
|
+
# Create necessary directories
|
77
|
+
create_directories
|
78
|
+
|
79
|
+
# Setup environment file
|
80
|
+
setup_environment_file
|
81
|
+
|
82
|
+
puts "✅ Complete Grim Reaper environment setup finished"
|
83
|
+
end
|
84
|
+
|
85
|
+
# Setup Ruby environment
|
86
|
+
def setup_ruby_environment
|
87
|
+
puts "💎 Setting up Ruby environment..."
|
88
|
+
|
89
|
+
# Check Ruby version
|
90
|
+
check_ruby_version
|
91
|
+
|
92
|
+
# Install Bundler if not present
|
93
|
+
install_bundler
|
94
|
+
|
95
|
+
# Install common Ruby gems
|
96
|
+
install_ruby_gems
|
97
|
+
|
98
|
+
# Setup RVM/rbenv if available
|
99
|
+
setup_ruby_version_manager
|
100
|
+
|
101
|
+
puts "✅ Ruby environment setup complete"
|
102
|
+
end
|
103
|
+
|
104
|
+
# Install Python components (like pip package)
|
105
|
+
def install_python_components
|
106
|
+
puts "🐍 Installing Python components..."
|
107
|
+
|
108
|
+
# Check if Python is available
|
109
|
+
unless system("python3 --version > /dev/null 2>&1")
|
110
|
+
puts "⚠️ Python3 not found, skipping Python components"
|
111
|
+
return
|
112
|
+
end
|
113
|
+
|
114
|
+
# Install pip if not available
|
115
|
+
unless system("pip3 --version > /dev/null 2>&1")
|
116
|
+
puts "📦 Installing pip3..."
|
117
|
+
unless system("apt-get update && apt-get install -y python3-pip") ||
|
118
|
+
system("yum install -y python3-pip")
|
119
|
+
puts "⚠️ Could not install pip3"
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
# Install Python dependencies
|
124
|
+
python_packages = %w[flask requests psutil cryptography]
|
125
|
+
python_packages.each do |package|
|
126
|
+
unless system("pip3 list | grep -q #{package}")
|
127
|
+
puts "📦 Installing Python package: #{package}"
|
128
|
+
unless system("pip3 install #{package}")
|
129
|
+
puts "⚠️ Failed to install #{package}"
|
130
|
+
end
|
131
|
+
end
|
132
|
+
end
|
133
|
+
|
134
|
+
# Create Python virtual environment if needed
|
135
|
+
venv_path = File.join(@grim_root, "py_grim", "venv")
|
136
|
+
unless Dir.exist?(venv_path)
|
137
|
+
puts "🐍 Creating Python virtual environment..."
|
138
|
+
unless system("python3 -m venv #{venv_path}")
|
139
|
+
puts "⚠️ Failed to create virtual environment"
|
140
|
+
end
|
141
|
+
end
|
142
|
+
|
143
|
+
puts "✅ Python components setup complete"
|
144
|
+
end
|
145
|
+
|
146
|
+
# Install Go components
|
147
|
+
def install_go_components
|
148
|
+
puts "🐹 Installing Go components..."
|
149
|
+
|
150
|
+
# Check if Go is available
|
151
|
+
unless system("go version > /dev/null 2>&1")
|
152
|
+
puts "📦 Installing Go..."
|
153
|
+
unless system("apt-get update && apt-get install -y golang-go") ||
|
154
|
+
system("yum install -y golang")
|
155
|
+
puts "⚠️ Could not install Go"
|
156
|
+
end
|
157
|
+
return
|
158
|
+
end
|
159
|
+
|
160
|
+
# Create Go build directory
|
161
|
+
go_build_dir = File.join(@grim_root, "go_grim", "build")
|
162
|
+
FileUtils.mkdir_p(go_build_dir) unless Dir.exist?(go_build_dir)
|
163
|
+
|
164
|
+
# Build Go binaries if source exists
|
165
|
+
go_src_dir = File.join(@grim_root, "go_grim")
|
166
|
+
if Dir.exist?(go_src_dir) && File.exist?(File.join(go_src_dir, "go.mod"))
|
167
|
+
puts "🐹 Building Go binaries..."
|
168
|
+
Dir.chdir(go_src_dir) do
|
169
|
+
unless system("go mod tidy")
|
170
|
+
puts "⚠️ Failed to tidy Go modules"
|
171
|
+
end
|
172
|
+
unless system("go build -o build/grim-compression .")
|
173
|
+
puts "⚠️ Failed to build Go binary"
|
174
|
+
end
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
puts "✅ Go components setup complete"
|
179
|
+
end
|
180
|
+
|
181
|
+
# Install Shell components
|
182
|
+
def install_shell_components
|
183
|
+
puts "🐚 Installing Shell components..."
|
184
|
+
|
185
|
+
# Make shell scripts executable
|
186
|
+
shell_scripts = [
|
187
|
+
"sh_grim/backup.sh",
|
188
|
+
"sh_grim/restore.sh",
|
189
|
+
"sh_grim/monitor.sh",
|
190
|
+
"sh_grim/scan.sh",
|
191
|
+
"sh_grim/security.sh",
|
192
|
+
"throne/grim_throne.sh",
|
193
|
+
"throne/rb_grim_throne.sh"
|
194
|
+
]
|
195
|
+
|
196
|
+
shell_scripts.each do |script|
|
197
|
+
script_path = File.join(@grim_root, script)
|
198
|
+
if File.exist?(script_path)
|
199
|
+
File.chmod(0o755, script_path)
|
200
|
+
puts "🔧 Made executable: #{script}"
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
# Install system dependencies
|
205
|
+
system_deps = %w[rsync tar gzip bzip2 xz-utils]
|
206
|
+
system_deps.each do |dep|
|
207
|
+
unless system("which #{dep} > /dev/null 2>&1")
|
208
|
+
puts "📦 Installing system dependency: #{dep}"
|
209
|
+
unless system("apt-get update && apt-get install -y #{dep}") ||
|
210
|
+
system("yum install -y #{dep}")
|
211
|
+
puts "⚠️ Could not install #{dep}"
|
212
|
+
end
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
216
|
+
puts "✅ Shell components setup complete"
|
217
|
+
end
|
218
|
+
|
219
|
+
# Install Scythe components
|
220
|
+
def install_scythe_components
|
221
|
+
puts "🗡️ Installing Scythe components..."
|
222
|
+
|
223
|
+
# Check if scythe directory exists
|
224
|
+
scythe_dir = File.join(@grim_root, "scythe")
|
225
|
+
unless Dir.exist?(scythe_dir)
|
226
|
+
puts "⚠️ Scythe directory not found, creating..."
|
227
|
+
FileUtils.mkdir_p(scythe_dir)
|
228
|
+
end
|
229
|
+
|
230
|
+
# Install Python dependencies for scythe
|
231
|
+
if system("python3 --version > /dev/null 2>&1")
|
232
|
+
scythe_packages = %w[flask requests cryptography psutil]
|
233
|
+
scythe_packages.each do |package|
|
234
|
+
unless system("pip3 list | grep -q #{package}")
|
235
|
+
puts "📦 Installing Scythe dependency: #{package}"
|
236
|
+
unless system("pip3 install #{package}")
|
237
|
+
puts "⚠️ Failed to install #{package}"
|
238
|
+
end
|
239
|
+
end
|
240
|
+
end
|
241
|
+
end
|
242
|
+
|
243
|
+
puts "✅ Scythe components setup complete"
|
244
|
+
end
|
245
|
+
|
246
|
+
# Check Ruby version
|
247
|
+
def check_ruby_version
|
248
|
+
ruby_version = `ruby -e "puts RUBY_VERSION"`.strip
|
249
|
+
puts "💎 Ruby Version: #{ruby_version}"
|
250
|
+
|
251
|
+
major, minor = ruby_version.split(".").map(&:to_i)
|
252
|
+
if major < 2 || (major == 2 && minor < 7)
|
253
|
+
raise Error, "Ruby 2.7+ required, found #{ruby_version}"
|
254
|
+
end
|
255
|
+
end
|
256
|
+
|
257
|
+
# Install Bundler
|
258
|
+
def install_bundler
|
259
|
+
unless system("gem list bundler -i > /dev/null 2>&1")
|
260
|
+
puts "📦 Installing Bundler..."
|
261
|
+
unless system("gem install bundler")
|
262
|
+
raise Error, "Failed to install Bundler"
|
263
|
+
end
|
264
|
+
end
|
265
|
+
end
|
266
|
+
|
267
|
+
# Install common Ruby gems
|
268
|
+
def install_ruby_gems
|
269
|
+
gems = %w[rake rspec rubocop yard reek brakeman bundle-audit]
|
270
|
+
|
271
|
+
gems.each do |gem_name|
|
272
|
+
unless system("gem list #{gem_name} -i > /dev/null 2>&1")
|
273
|
+
puts "📦 Installing #{gem_name}..."
|
274
|
+
unless system("gem install #{gem_name}")
|
275
|
+
warn "Failed to install #{gem_name}"
|
276
|
+
end
|
277
|
+
end
|
278
|
+
end
|
279
|
+
end
|
280
|
+
|
281
|
+
# Setup Ruby version manager
|
282
|
+
def setup_ruby_version_manager
|
283
|
+
if system("which rvm > /dev/null 2>&1")
|
284
|
+
puts "🔄 RVM detected, setting up..."
|
285
|
+
system("rvm use --default")
|
286
|
+
elsif system("which rbenv > /dev/null 2>&1")
|
287
|
+
puts "🔄 rbenv detected, setting up..."
|
288
|
+
system("rbenv rehash")
|
289
|
+
end
|
290
|
+
end
|
291
|
+
|
292
|
+
# Setup .scythe directory structure
|
293
|
+
def setup_scythe_directories
|
294
|
+
puts "🗡️ Setting up .scythe directory structure..."
|
295
|
+
|
296
|
+
scythe_dir = File.join(@grim_root, ".graveyard", ".rip", ".scythe")
|
297
|
+
|
298
|
+
# Create main scythe directories
|
299
|
+
scythe_subdirs = [
|
300
|
+
"config",
|
301
|
+
"db",
|
302
|
+
"logs",
|
303
|
+
"run",
|
304
|
+
"integrations"
|
305
|
+
]
|
306
|
+
|
307
|
+
scythe_subdirs.each do |subdir|
|
308
|
+
dir_path = File.join(scythe_dir, subdir)
|
309
|
+
FileUtils.mkdir_p(dir_path) unless Dir.exist?(dir_path)
|
310
|
+
end
|
311
|
+
|
312
|
+
# Create log subdirectories
|
313
|
+
log_subdirs = ["orchestration", "components", "integrations", "security"]
|
314
|
+
log_subdirs.each do |subdir|
|
315
|
+
dir_path = File.join(scythe_dir, "logs", subdir)
|
316
|
+
FileUtils.mkdir_p(dir_path) unless Dir.exist?(dir_path)
|
317
|
+
end
|
318
|
+
|
319
|
+
# Create integration subdirectories
|
320
|
+
integration_subdirs = ["discovered", "configs", "scripts"]
|
321
|
+
integration_subdirs.each do |subdir|
|
322
|
+
dir_path = File.join(scythe_dir, "integrations", subdir)
|
323
|
+
FileUtils.mkdir_p(dir_path) unless Dir.exist?(dir_path)
|
324
|
+
end
|
325
|
+
|
326
|
+
# Create scythe configuration file
|
327
|
+
config_file = File.join(scythe_dir, "config", "scythe.yaml")
|
328
|
+
unless File.exist?(config_file)
|
329
|
+
config_content = <<~CONFIG
|
330
|
+
# Scythe Configuration
|
331
|
+
# Central orchestrator settings for Grim Reaper System
|
332
|
+
|
333
|
+
scythe:
|
334
|
+
version: "1.0.5"
|
335
|
+
install_date: #{Time.now.iso8601}
|
336
|
+
|
337
|
+
database:
|
338
|
+
path: "../db/scythe.db"
|
339
|
+
auto_backup: true
|
340
|
+
backup_interval: "24h"
|
341
|
+
|
342
|
+
logging:
|
343
|
+
level: "info"
|
344
|
+
path: "../logs"
|
345
|
+
max_size: "100MB"
|
346
|
+
max_files: 10
|
347
|
+
|
348
|
+
orchestration:
|
349
|
+
enabled: true
|
350
|
+
heartbeat_interval: "30s"
|
351
|
+
max_concurrent_jobs: 5
|
352
|
+
|
353
|
+
integrations:
|
354
|
+
enabled: true
|
355
|
+
scan_interval: "5m"
|
356
|
+
auto_discover: true
|
357
|
+
|
358
|
+
security:
|
359
|
+
encryption: true
|
360
|
+
key_rotation: "30d"
|
361
|
+
audit_logs: true
|
362
|
+
CONFIG
|
363
|
+
|
364
|
+
File.write(config_file, config_content)
|
365
|
+
puts "✅ Created scythe configuration: #{config_file}"
|
366
|
+
end
|
367
|
+
|
368
|
+
# Try to run the universal setup script if available
|
369
|
+
setup_script = File.join(@grim_root, "scripts", "setup_scythe_dirs.sh")
|
370
|
+
if File.exist?(setup_script)
|
371
|
+
begin
|
372
|
+
system("bash '#{setup_script}' setup '#{@grim_root}' auto")
|
373
|
+
puts "✅ Initialized scythe database"
|
374
|
+
rescue
|
375
|
+
puts "⚠️ Could not initialize scythe database - basic structure created"
|
376
|
+
end
|
377
|
+
end
|
378
|
+
|
379
|
+
puts "✅ .scythe directory structure created at: #{scythe_dir}"
|
380
|
+
end
|
381
|
+
|
382
|
+
# Create necessary directories
|
383
|
+
def create_directories
|
384
|
+
# Setup .scythe structure first
|
385
|
+
setup_scythe_directories
|
386
|
+
|
387
|
+
dirs = [
|
388
|
+
File.join(@grim_root, "logs"),
|
389
|
+
File.join(@grim_root, "cache"),
|
390
|
+
@backup_dir,
|
391
|
+
File.join(@grim_root, "temp"),
|
392
|
+
File.join(@grim_root, "py_grim", "venv"),
|
393
|
+
File.join(@grim_root, "go_grim", "build"),
|
394
|
+
File.join(@grim_root, "scythe", "logs")
|
395
|
+
]
|
396
|
+
|
397
|
+
dirs.each do |dir|
|
398
|
+
FileUtils.mkdir_p(dir) unless Dir.exist?(dir)
|
399
|
+
puts "📁 Created directory: #{dir}"
|
400
|
+
end
|
401
|
+
end
|
402
|
+
|
403
|
+
# Setup environment file
|
404
|
+
def setup_environment_file
|
405
|
+
env_file = File.join(@grim_root, ".env")
|
406
|
+
scythe_dir = File.join(@grim_root, ".graveyard", ".rip", ".scythe")
|
407
|
+
env_content = <<~ENV
|
408
|
+
# Grim Reaper Environment Configuration
|
409
|
+
GRIM_ROOT=#{@grim_root}
|
410
|
+
SCYTHE_DIR=#{scythe_dir}
|
411
|
+
GRIM_BACKUP_DIR=#{@backup_dir}
|
412
|
+
GRIM_HOME=#{@install_dir}
|
413
|
+
GRIM_RUBY_VERSION=#{`ruby -e "puts RUBY_VERSION"`.strip}
|
414
|
+
GRIM_PYTHON_VERSION=#{`python3 --version 2>/dev/null | cut -d' ' -f2` || 'Not installed'}
|
415
|
+
GRIM_GO_VERSION=#{`go version 2>/dev/null | cut -d' ' -f3` || 'Not installed'}
|
416
|
+
ENV
|
417
|
+
|
418
|
+
File.write(env_file, env_content)
|
419
|
+
puts "📄 Created environment file: #{env_file}"
|
420
|
+
end
|
421
|
+
|
422
|
+
# Verify installation
|
423
|
+
def verify_installation
|
424
|
+
puts "🔍 Verifying installation..."
|
425
|
+
|
426
|
+
checks = [
|
427
|
+
{ name: "Ruby", check: -> { system("ruby --version > /dev/null 2>&1") } },
|
428
|
+
{ name: "Bundler", check: -> { system("bundle --version > /dev/null 2>&1") } },
|
429
|
+
{ name: "Python3", check: -> { system("python3 --version > /dev/null 2>&1") } },
|
430
|
+
{ name: "Go", check: -> { system("go version > /dev/null 2>&1") } },
|
431
|
+
{ name: "Grim Root", check: -> { Dir.exist?(@grim_root) } },
|
432
|
+
{ name: "Ruby Throne", check: -> { File.exist?(File.join(@grim_root, "throne", "rb_grim_throne.sh")) } },
|
433
|
+
{ name: "Python Throne", check: -> { File.exist?(File.join(@grim_root, "throne", "py_grim_throne.sh")) } },
|
434
|
+
{ name: "Go Throne", check: -> { File.exist?(File.join(@grim_root, "throne", "go_grim_throne.sh")) } },
|
435
|
+
{ name: "Shell Throne", check: -> { File.exist?(File.join(@grim_root, "throne", "sh_grim_throne.sh")) } },
|
436
|
+
{ name: "Backup Directory", check: -> { Dir.exist?(@backup_dir) } }
|
437
|
+
]
|
438
|
+
|
439
|
+
checks.each do |check|
|
440
|
+
if check[:check].call
|
441
|
+
puts "✅ #{check[:name]}: OK"
|
442
|
+
else
|
443
|
+
puts "❌ #{check[:name]}: FAILED"
|
444
|
+
end
|
445
|
+
end
|
446
|
+
end
|
447
|
+
|
448
|
+
# Get installation status
|
449
|
+
def status
|
450
|
+
{
|
451
|
+
ruby_version: `ruby -e "puts RUBY_VERSION"`.strip,
|
452
|
+
bundler_version: `bundle --version 2>/dev/null`.strip,
|
453
|
+
python_version: `python3 --version 2>/dev/null | cut -d' ' -f2` || 'Not installed',
|
454
|
+
go_version: `go version 2>/dev/null | cut -d' ' -f3` || 'Not installed',
|
455
|
+
grim_root: @grim_root,
|
456
|
+
backup_dir: @backup_dir,
|
457
|
+
install_dir: @install_dir,
|
458
|
+
ruby_throne_exists: File.exist?(File.join(@grim_root, "throne", "rb_grim_throne.sh")),
|
459
|
+
python_throne_exists: File.exist?(File.join(@grim_root, "throne", "py_grim_throne.sh")),
|
460
|
+
go_throne_exists: File.exist?(File.join(@grim_root, "throne", "go_grim_throne.sh")),
|
461
|
+
shell_throne_exists: File.exist?(File.join(@grim_root, "throne", "sh_grim_throne.sh")),
|
462
|
+
backup_dir_exists: Dir.exist?(@backup_dir)
|
463
|
+
}
|
464
|
+
end
|
465
|
+
|
466
|
+
# Cleanup temporary files
|
467
|
+
def cleanup
|
468
|
+
temp_dir = File.join(@grim_root, "temp")
|
469
|
+
if Dir.exist?(temp_dir)
|
470
|
+
FileUtils.rm_rf(temp_dir)
|
471
|
+
puts "🧹 Cleaned temporary directory"
|
472
|
+
end
|
473
|
+
end
|
474
|
+
|
475
|
+
# Post-install hook
|
476
|
+
def self.post_install
|
477
|
+
new.setup_complete_environment
|
478
|
+
end
|
479
|
+
|
480
|
+
# Post-update hook
|
481
|
+
def self.post_update
|
482
|
+
new.verify_installation
|
483
|
+
end
|
484
|
+
end
|
485
|
+
end
|