@@ -17,6 +17,7 @@ local notify = log.notify
1717--- @field repo ? string
1818--- @field mode ? string
1919--- @field vertical ? boolean
20+ --- @field untracked ? boolean
2021
2122--- @class diffs.ReviewCommandParseResult
2223--- @field spec diffs.ReviewSpec
@@ -28,6 +29,7 @@ local notify = log.notify
2829--- @field repo_root string
2930--- @field mode string ?
3031--- @field vertical boolean
32+ --- @field untracked boolean
3133--- @field display string
3234--- @field exec_args string[]
3335
@@ -179,17 +181,28 @@ function M.parse_command_args(args)
179181 local tokens = split_args (args )
180182 local layout = ' unified'
181183 local has_layout = false
182-
183- while tokens [1 ] and tokens [1 ]:match (' ^%+%+layout=' ) do
184- if has_layout then
185- return nil , ' repeated ++layout option'
186- end
187- local value = tokens [1 ]:match (' ^%+%+layout=(.+)$' )
188- if value ~= ' unified' and value ~= ' stacked' and value ~= ' split' then
189- return nil , ' unsupported layout ' .. tostring (value )
184+ local untracked = nil
185+ local has_untracked = false
186+
187+ while tokens [1 ] and (tokens [1 ]:match (' ^%+%+layout=' ) or tokens [1 ] == ' ++nountracked' ) do
188+ local token = tokens [1 ]
189+ if token :match (' ^%+%+layout=' ) then
190+ if has_layout then
191+ return nil , ' repeated ++layout option'
192+ end
193+ local value = token :match (' ^%+%+layout=(.+)$' )
194+ if value ~= ' unified' and value ~= ' stacked' and value ~= ' split' then
195+ return nil , ' unsupported layout ' .. tostring (value )
196+ end
197+ has_layout = true
198+ layout = value
199+ else
200+ if has_untracked then
201+ return nil , ' repeated ++nountracked option'
202+ end
203+ has_untracked = true
204+ untracked = false
190205 end
191- has_layout = true
192- layout = value
193206 table.remove (tokens , 1 )
194207 end
195208
@@ -201,6 +214,9 @@ function M.parse_command_args(args)
201214 if not spec then
202215 return nil , err
203216 end
217+ if has_untracked then
218+ spec .untracked = untracked
219+ end
204220
205221 return {
206222 spec = spec ,
@@ -231,6 +247,9 @@ function M.normalize(spec, repo_root_override)
231247 if spec .vertical ~= nil and type (spec .vertical ) ~= ' boolean' then
232248 error (' diffs: review.vertical must be a boolean' )
233249 end
250+ if spec .untracked ~= nil and type (spec .untracked ) ~= ' boolean' then
251+ error (' diffs: review.untracked must be a boolean' )
252+ end
234253
235254 local repo_root = repo_root_override or resolve_repo_root (spec .repo )
236255 if not repo_root then
@@ -278,12 +297,18 @@ function M.normalize(spec, repo_root_override)
278297 return nil , ref_err
279298 end
280299
300+ local untracked = true
301+ if spec .untracked ~= nil then
302+ untracked = spec .untracked
303+ end
304+
281305 return {
282306 base = base ,
283307 target = target ,
284308 repo_root = repo_root ,
285309 mode = mode ,
286310 vertical = spec .vertical or false ,
311+ untracked = untracked ,
287312 display = display ,
288313 exec_args = exec_args ,
289314 },
@@ -575,36 +600,38 @@ local function run_current_state(review, deps)
575600 lines = unstaged_rendered ,
576601 }, unstaged_specs , state )
577602
578- local untracked , untracked_err = untracked_paths (review )
579- if not untracked then
580- return nil ,
581- untracked_err ~= ' ' and untracked_err or ' git ls-files failed for review Untracked section' ,
582- nil
583- end
584- local untracked_lines = {}
585- local untracked_specs = {}
586- for _ , path in ipairs (untracked ) do
587- if is_untracked_binary (review .repo_root , path ) then
588- dbg (' skipping binary untracked %s' , path )
589- else
590- local spec = diffspec .index_to_worktree (path )
591- local rendered , render_err = render .file (spec , review .repo_root )
592- if rendered then
593- for _ , line in ipairs (rendered ) do
594- untracked_lines [# untracked_lines + 1 ] = line
603+ if review .untracked then
604+ local untracked , untracked_err = untracked_paths (review )
605+ if not untracked then
606+ return nil ,
607+ untracked_err ~= ' ' and untracked_err or ' git ls-files failed for review Untracked section' ,
608+ nil
609+ end
610+ local untracked_lines = {}
611+ local untracked_specs = {}
612+ for _ , path in ipairs (untracked ) do
613+ if is_untracked_binary (review .repo_root , path ) then
614+ dbg (' skipping binary untracked %s' , path )
615+ else
616+ local spec = diffspec .index_to_worktree (path )
617+ local rendered , render_err = render .file (spec , review .repo_root )
618+ if rendered then
619+ for _ , line in ipairs (rendered ) do
620+ untracked_lines [# untracked_lines + 1 ] = line
621+ end
622+ untracked_specs [path ] = spec
623+ elseif render_err then
624+ dbg (' skipping untracked %s: %s' , path , render_err )
595625 end
596- untracked_specs [path ] = spec
597- elseif render_err then
598- dbg (' skipping untracked %s: %s' , path , render_err )
599626 end
600627 end
628+ append_section (lines , {
629+ id = ' untracked' ,
630+ label = ' Untracked' ,
631+ description = ' empty -> worktree' ,
632+ lines = untracked_lines ,
633+ }, untracked_specs , state )
601634 end
602- append_section (lines , {
603- id = ' untracked' ,
604- label = ' Untracked' ,
605- description = ' empty -> worktree' ,
606- lines = untracked_lines ,
607- }, untracked_specs , state )
608635
609636 return lines ,
610637 nil ,
@@ -779,12 +806,14 @@ function M.open(spec, deps)
779806 base = review .base ,
780807 target = review .target ,
781808 mode = review .mode ,
809+ untracked = review .untracked ,
782810 }),
783811 rail_style = deps .rail_style ,
784812 vars = {
785813 diffs_review_base = review .base ,
786814 diffs_review_target = review .target ,
787815 diffs_review_mode = review .mode ,
816+ diffs_review_untracked = review .untracked ,
788817 },
789818 })
790819
@@ -847,13 +876,15 @@ function M.reload(bufnr, repo_root, path, deps)
847876 local stored_base = get_buf_var (bufnr , ' diffs_review_base' )
848877 local stored_target = get_buf_var (bufnr , ' diffs_review_target' )
849878 local stored_mode = get_buf_var (bufnr , ' diffs_review_mode' )
879+ local stored_untracked = get_buf_var (bufnr , ' diffs_review_untracked' )
850880
851881 local review_spec
852882 if stored_base then
853883 review_spec = {
854884 base = stored_base ,
855885 target = stored_target ,
856886 mode = stored_mode ,
887+ untracked = stored_untracked ,
857888 }
858889 else
859890 local parse_err
0 commit comments