rubyn 0.1.0 → 0.1.1
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
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: da809f272fcbe6c989b0a09ff5917f4aa91db8b345dd29b85d2229bfe2227421
|
|
4
|
+
data.tar.gz: 78a8fb3249fb87a9696d73f8d4622e9421dd0d4254732eb292cb4e9f11c07f59
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 1ca7d13fd823a0089510cb255ed082ee1213beb066c435374013848305102ecb95bf14b5b31f285da9029a1cc84a0071a8925a772348c7626254f38317f78980
|
|
7
|
+
data.tar.gz: b9a529dea633b3e2ab4ee0a92b6cb7dec54c8466a4458de65365498a14a13e06b795c7c1b6a0896d85ab135ce8f9700ebb7c1b11d23d58b4670774d4c89c4695
|
|
@@ -59,19 +59,26 @@ module Rubyn
|
|
|
59
59
|
def extract_file_blocks(response)
|
|
60
60
|
blocks = []
|
|
61
61
|
|
|
62
|
-
#
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
62
|
+
# Split response around code blocks, keeping surrounding text for path detection
|
|
63
|
+
parts = response.split(/(```ruby\n.*?```)/m)
|
|
64
|
+
|
|
65
|
+
parts.each_with_index do |part, i|
|
|
66
|
+
next unless part.start_with?("```ruby\n")
|
|
67
|
+
|
|
68
|
+
code = part.sub(/\A```ruby\n/, "").sub(/```\z/, "")
|
|
69
|
+
preceding_text = i > 0 ? parts[i - 1] : ""
|
|
70
|
+
|
|
71
|
+
# Strategy 1: Path in bold header above code block
|
|
72
|
+
# **New file: app/services/foo.rb** or **app/services/foo.rb**
|
|
73
|
+
path = preceding_text.match(/\*\*(?:New file:\s*|Modified:\s*)?([a-zA-Z0-9_\/\.\-]+\.rb)\*\*/i)&.dig(1)
|
|
74
|
+
|
|
75
|
+
# Strategy 2: Path as backtick-wrapped line above code block
|
|
76
|
+
path ||= preceding_text.match(/`([a-zA-Z0-9_\/\.\-]+\.rb)`\s*\z/)&.dig(1)
|
|
77
|
+
|
|
78
|
+
# Strategy 3: Path as comment on first line inside code block
|
|
79
|
+
path ||= code.lines.first&.strip&.match(/^#\s*([a-zA-Z0-9_\/\.\-]+\.rb)/)&.dig(1)
|
|
70
80
|
|
|
71
|
-
|
|
72
|
-
if blocks.empty?
|
|
73
|
-
code_match = response.match(/```ruby\n(.*?)```/m)
|
|
74
|
-
blocks << { tag: nil, path: nil, code: code_match[1] } if code_match
|
|
81
|
+
blocks << { path: path, code: code }
|
|
75
82
|
end
|
|
76
83
|
|
|
77
84
|
blocks
|
|
@@ -103,8 +110,9 @@ module Rubyn
|
|
|
103
110
|
formatter.newline
|
|
104
111
|
formatter.info("This refactor produces #{file_blocks.length} file(s):")
|
|
105
112
|
file_blocks.each do |block|
|
|
106
|
-
label = block[:tag] == "NEW" ? "NEW" : "MODIFIED"
|
|
107
113
|
path = block[:path] || file
|
|
114
|
+
is_new = path != file && !path.end_with?("/#{file}") && !file.end_with?("/#{path}")
|
|
115
|
+
label = is_new ? "NEW" : "MODIFIED"
|
|
108
116
|
formatter.info(" [#{label}] #{path}")
|
|
109
117
|
end
|
|
110
118
|
|
|
@@ -129,8 +137,9 @@ module Rubyn
|
|
|
129
137
|
|
|
130
138
|
def apply_selected_blocks(file, original, file_blocks, formatter)
|
|
131
139
|
file_blocks.each do |block|
|
|
132
|
-
label = block[:tag] == "NEW" ? "NEW" : "MODIFIED"
|
|
133
140
|
path = block[:path] || file
|
|
141
|
+
is_new = path != file && !path.end_with?("/#{file}") && !file.end_with?("/#{path}")
|
|
142
|
+
label = is_new ? "NEW" : "MODIFIED"
|
|
134
143
|
print " Apply [#{label}] #{path}? (y/n/diff) "
|
|
135
144
|
choice = $stdin.gets&.strip&.downcase
|
|
136
145
|
|
|
@@ -138,7 +147,7 @@ module Rubyn
|
|
|
138
147
|
when "y"
|
|
139
148
|
write_block(file, block, formatter)
|
|
140
149
|
when "diff"
|
|
141
|
-
existing =
|
|
150
|
+
existing = is_new ? "" : File.read(resolve_path(file, block))
|
|
142
151
|
Rubyn::Output::DiffRenderer.render(original: existing, modified: block[:code])
|
|
143
152
|
print " Apply? (y/n) "
|
|
144
153
|
if $stdin.gets&.strip&.downcase == "y"
|
|
@@ -293,22 +293,24 @@
|
|
|
293
293
|
|
|
294
294
|
// Build the file-to-code mapping
|
|
295
295
|
// Headers and code blocks are in the same order — zip them together
|
|
296
|
+
// Determine NEW vs MODIFIED by comparing path against the original file
|
|
296
297
|
var fileChanges = codeBlocks.map(function(code, i) {
|
|
297
298
|
var header = fileHeaders[i];
|
|
299
|
+
var path = header ? header.path : file;
|
|
300
|
+
var isNew = path !== file && !path.endsWith("/" + file) && !file.endsWith("/" + path);
|
|
298
301
|
return {
|
|
299
|
-
path:
|
|
300
|
-
|
|
302
|
+
path: path,
|
|
303
|
+
isNew: isNew,
|
|
301
304
|
code: code
|
|
302
305
|
};
|
|
303
306
|
});
|
|
304
307
|
|
|
305
|
-
// Show each code block with its file path
|
|
308
|
+
// Show each code block with its file path and NEW badge if applicable
|
|
306
309
|
fileChanges.forEach(function(change, i) {
|
|
307
310
|
html += '<div class="rubyn-code-block">';
|
|
308
311
|
html += '<div class="rubyn-code-block-header">';
|
|
309
|
-
if (change.
|
|
310
|
-
|
|
311
|
-
html += '<span class="rubyn-file-tag ' + tagClass + '">' + change.tag + '</span>';
|
|
312
|
+
if (change.isNew) {
|
|
313
|
+
html += '<span class="rubyn-file-tag rubyn-tag-new">NEW</span>';
|
|
312
314
|
}
|
|
313
315
|
html += '<span class="rubyn-tool-filepath">' + escapeHtml(change.path) + '</span>';
|
|
314
316
|
html += '<div class="rubyn-code-block-actions">';
|
|
@@ -478,14 +480,34 @@
|
|
|
478
480
|
|
|
479
481
|
function extractFileHeaders(text) {
|
|
480
482
|
var headers = [];
|
|
483
|
+
var parts = text.split(/(```ruby\n[\s\S]*?```)/g);
|
|
481
484
|
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
var
|
|
488
|
-
|
|
485
|
+
for (var i = 0; i < parts.length; i++) {
|
|
486
|
+
if (parts[i].indexOf("```ruby\n") !== 0) continue;
|
|
487
|
+
|
|
488
|
+
var code = parts[i].replace(/^```ruby\n/, "").replace(/```$/, "");
|
|
489
|
+
var preceding = i > 0 ? parts[i - 1] : "";
|
|
490
|
+
var path = null;
|
|
491
|
+
|
|
492
|
+
// Strategy 1: Bold header above code block
|
|
493
|
+
// **New file: path.rb** or **path.rb**
|
|
494
|
+
var boldMatch = preceding.match(/\*\*(?:New file:\s*|Modified:\s*)?([a-zA-Z0-9_\/\.\-]+\.rb)\*\*/i);
|
|
495
|
+
if (boldMatch) path = boldMatch[1];
|
|
496
|
+
|
|
497
|
+
// Strategy 2: Backtick-wrapped path above code block
|
|
498
|
+
if (!path) {
|
|
499
|
+
var tickMatch = preceding.match(/`([a-zA-Z0-9_\/\.\-]+\.rb)`\s*$/);
|
|
500
|
+
if (tickMatch) path = tickMatch[1];
|
|
501
|
+
}
|
|
502
|
+
|
|
503
|
+
// Strategy 3: Path as comment on first line inside code block
|
|
504
|
+
if (!path) {
|
|
505
|
+
var firstLine = code.split("\n")[0].trim();
|
|
506
|
+
var commentMatch = firstLine.match(/^#\s*([a-zA-Z0-9_\/\.\-]+\.rb)/);
|
|
507
|
+
if (commentMatch) path = commentMatch[1];
|
|
508
|
+
}
|
|
509
|
+
|
|
510
|
+
headers.push({ path: path });
|
|
489
511
|
}
|
|
490
512
|
|
|
491
513
|
return headers;
|
data/lib/rubyn/version.rb
CHANGED