···4848 let v = String.sub s (i + 1) (String.length s - i - 1) in
4949 (h, Some v)
50505151+let auto_commit ~sys ~reporepo ~op =
5252+ match
5353+ Oi.Source.Reporepo.commit_dirty ~sys ~path:reporepo
5454+ ~msg:(Fmt.str "oi repo %s" op) ()
5555+ with
5656+ | [] -> ()
5757+ | files ->
5858+ Fmt.pr " committed %d file(s) to reporepo HEAD@." (List.length files)
5959+5160let parse_handle_version s =
5261 match String.index_opt s '=' with
5362 | None -> (s, None)
···493502 unavailable@."
494503 summary.total summary.kept summary.rewrote
495504 (List.length summary.unavailable)
496496- end
505505+ end;
506506+ auto_commit ~sys ~reporepo ~op:(Fmt.str "add %s" handle)
497507 in
498508 let handle =
499509 Arg.(
···621631 (fun (pkg, reason) ->
622632 Fmt.pr " %a %s: %s@." Oi.Style.warn_string "unavailable" pkg reason)
623633 summary.unavailable
624624- end
634634+ end;
635635+ auto_commit ~sys ~reporepo ~op:(Fmt.str "bump %s" handle)
625636626637 let cmd =
627638 let run () reporepo reporepo_url handle_opt all url ref_ toolchain
···794805 (fun t -> match parse_group t with [] -> None | g -> Some g)
795806 pkgs
796807 in
797797- match
808808+ (match
798809 Oi.Source.Reporepo.bump ~fs ~sys ~path:reporepo ~handle
799810 ~root_packages:groups ()
800811 with
···805816 (if List.length e.root_packages = 1 then "y" else "ies")
806817 | `Unchanged e ->
807818 Fmt.pr "No change: %s.%s already has that root-packages list.@."
808808- e.handle e.version
819819+ e.handle e.version);
820820+ auto_commit ~sys ~reporepo ~op:(Fmt.str "set-roots %s" handle)
809821 in
810822 let handle =
811823 Arg.(
···875887 Oi.Source.Reporepo.remove ~fs ~path:reporepo ~handle ?version ();
876888 Fmt.pr "Removed %s%s from %s@." handle
877889 (match version with None -> " (all versions)" | Some v -> "." ^ v)
878878- reporepo
890890+ reporepo;
891891+ auto_commit ~sys ~reporepo
892892+ ~op:
893893+ (Fmt.str "remove %s%s" handle
894894+ (match version with None -> "" | Some v -> "." ^ v))
879895 in
880896 let handle_spec =
881897 Arg.(
+31-13
lib/oi/pipeline.ml
···466466 m "depext check: %d pkg(s) declare matching depexts, union = %d"
467467 (List.length entries)
468468 (OpamSysPkg.Set.cardinal all));
469469- (* Defensive nudge for the case where source packages exist but
470470- declare no depexts active for this platform. Common on macOS
471471- when the package's opam file only declares Linux distros, or
472472- when the homebrew filter clause is missing. The build may
473473- still need system libraries (gmp, openssl, pkg-config, …);
474474- we emit a one-liner so the user isn't blindsided by a
475475- low-level [./configure] failure with no prior warning. *)
476476- if OpamSysPkg.Set.is_empty all && conf.os = "macos" then
477477- Say.warn
478478- "no system depexts matched for %d source package(s) on macOS. If \
479479- the build fails with missing headers (gmp.h, openssl/ssl.h, …), \
480480- install them with: brew install <pkg>"
481481- (List.length source_pkgs);
469469+ (* Per-layer nudge for source packages that declare no active
470470+ depexts on this platform. Compute the set of pkgs WITH active
471471+ depexts and subtract from [source_pkgs] to find the silent
472472+ ones. The build may still need system libraries (gmp,
473473+ openssl, pkg-config, …) and we'd rather warn upfront than
474474+ surface a [./configure] failure mid-build. *)
475475+ let with_depexts =
476476+ List.fold_left
477477+ (fun acc e -> OpamPackage.Set.add e.Depexts.pkg acc)
478478+ OpamPackage.Set.empty entries
479479+ in
480480+ let without_depexts =
481481+ List.filter
482482+ (fun p -> not (OpamPackage.Set.mem p with_depexts))
483483+ source_pkgs
484484+ in
485485+ (match without_depexts with
486486+ | [] -> ()
487487+ | pkgs ->
488488+ let names =
489489+ pkgs
490490+ |> List.map (fun p ->
491491+ OpamPackage.Name.to_string (OpamPackage.name p))
492492+ |> List.sort_uniq String.compare
493493+ |> String.concat ", "
494494+ in
495495+ Say.warn
496496+ "no %s depexts declared for source build(s): %s. If the build \
497497+ fails with missing headers, install the relevant system \
498498+ packages."
499499+ conf.os names);
482500 if not (OpamSysPkg.Set.is_empty all) then (
483501 let st = Depexts.status all in
484502 Log.info (fun m ->
+18-5
lib/oi/source.ml
···243243 (git_at_out ~sys ~path [ "rev-list"; "--count"; base ^ ".." ^ head ])
244244 with _ -> 0
245245246246- let push ?(on_step_start = fun _ _ -> ()) ~sys ~path () =
246246+ let commit_dirty ~sys ~path ~msg () =
247247 assert_clone path;
248248 let porcelain = git_at_out ~sys ~path [ "status"; "--porcelain" ] in
249249 let dirty_paths =
···252252 if String.length line < 4 then None
253253 else Some (String.sub line 3 (String.length line - 3)))
254254 in
255255+ if dirty_paths = [] then []
256256+ else begin
257257+ git_at ~sys ~path [ "add"; "-A" ];
258258+ git_at_inherit ~sys ~path [ "commit"; "-m"; msg ];
259259+ dirty_paths
260260+ end
261261+262262+ let push ?(on_step_start = fun _ _ -> ()) ~sys ~path () =
255263 on_step_start 1 "commit local changes";
256264 let commit_step =
265265+ let porcelain = git_at_out ~sys ~path [ "status"; "--porcelain" ] in
266266+ let dirty_paths =
267267+ porcelain |> String.split_on_char '\n'
268268+ |> List.filter_map (fun line ->
269269+ if String.length line < 4 then None
270270+ else Some (String.sub line 3 (String.length line - 3)))
271271+ in
257272 if dirty_paths = [] then Step_commit { files = [] }
258258- else begin
259259- git_at ~sys ~path [ "add"; "-A" ];
273273+ else
260274 let summary =
261275 if List.length dirty_paths = 1 then List.hd dirty_paths
262276 else Fmt.str "%d files" (List.length dirty_paths)
···269283 summary
270284 (String.concat "\n" (List.map (fun p -> " " ^ p) dirty_paths))
271285 in
272272- git_at_inherit ~sys ~path [ "commit"; "-m"; msg ];
286286+ let _ = commit_dirty ~sys ~path ~msg () in
273287 Step_commit { files = dirty_paths }
274274- end
275288 in
276289 on_step_start 2 "pull --rebase from upstream";
277290 let head_before = git_at_out ~sys ~path [ "rev-parse"; "HEAD" ] in
+7
lib/oi/source.mli
···248248 (** Stage and commit any uncommitted changes, [git pull --rebase] to bring in
249249 upstream history, then [git push] if local is ahead. *)
250250251251+ val commit_dirty :
252252+ sys:D10.Sysops.t -> path:string -> msg:string -> unit -> string list
253253+ (** Stage and commit any uncommitted changes in the reporepo at [path] with
254254+ commit message [msg]. Returns the list of files that were committed (empty
255255+ when the working tree is already clean, and no commit is created in that
256256+ case). *)
257257+251258 val add :
252259 fs:Eio.Fs.dir_ty Eio.Path.t ->
253260 sys:D10.Sysops.t ->