open Goaljobs
-(* Repo dir, etc. *)
-let fedora_dir = Sys.getenv "HOME" // "d/fedora"
-let fedora_repo pkg branch = fedora_dir // pkg // branch
-let fedora_specfile pkg branch =
- sprintf "%s/%s.spec" (fedora_repo pkg branch) pkg
+open Config
(* Get the current version of a package. *)
let fedora_verrel pkg branch =
try ignore (String.find str substr); true
with Invalid_string -> false
-(* Check if a Koji (completed successfully) build exists. *)
(* Not helped by the fact that the 'koji' tool actively
* resists automation: RHBZ#760924.
*)
-let koji_build_exists =
- let state_complete = contains_substring "State: COMPLETE" in
- let state_other = contains_substring "State: " in
+
+(* XXX koji_build_state verrel: If you do a build and it fails, then
+ * do another build without bumping the release field, 'koji buildinfo'
+ * seems to always return the failed build, at least until the second
+ * build completes. This means the code below fails. Unclear how it
+ * can be fixed, but best to always bump the release to avoid the
+ * problem.
+ *)
+
+(* Get build state. *)
+let rec koji_build_state verrel =
+ fst (koji_build_state_task verrel)
+
+(* Get build state and task ID. *)
+and koji_build_state_task =
+ let state = Pcre.regexp "State: (\\w+)" in
+ let task_id = Pcre.regexp "Task: (\\d+)" in
let no_such_build = contains_substring "No such build" in
fun verrel ->
- (* Once a build is known to be complete, memoize it. *)
+ (* For speed, if a build is complete memoize it. *)
let key = sprintf "koji_build_complete_%s" verrel in
if memory_exists key then
- true
+ `Complete, None
else (
- let rec loop () =
- let out = shout "timeout 120 koji buildinfo %s 2>&1 ||:" verrel in
- if state_complete out then
- true
- else if state_other out then
- false
- else if no_such_build out then
- false
- else (
- eprintf "%s\n" out;
- eprintf "koji_build_exists: unknown output\nretrying ...\n%!";
- loop ()
- )
- in
- let r = loop () in
- memory_set key "1";
- r
+ let out = shout "timeout 120 koji buildinfo %s 2>&1 ||:" verrel in
+ if no_such_build out then
+ `No_such_build, None
+ else (
+ let state =
+ try
+ let subs = Pcre.exec ~rex:state out in
+ match Pcre.get_substring subs 1 with
+ | "BUILDING" -> `Building
+ | "COMPLETE" -> `Complete
+ | "DELETED" -> `Deleted
+ | "FAILED" -> `Failed
+ | "CANCELED" -> `Canceled
+ | sub ->
+ failwith (sprintf "koji_build_state_task: %s: unknown build state '%s'"
+ verrel sub)
+ with
+ Not_found ->
+ failwith (sprintf "koji_build_state_task: %s: no build state found"
+ verrel) in
+ let task =
+ try
+ let subs = Pcre.exec ~rex:task_id out in
+ Some (int_of_string (Pcre.get_substring subs 1))
+ with
+ Not_found -> None in
+
+ if state == `Complete then
+ memory_set key "1";
+
+ state, task
+ )
)
(* Perform a Koji build and wait until it finishes. If it fails,
contains_substring "Name or service not known" in
let completed_successfully = contains_substring "completed successfully" in
let failed = contains_substring "FAILED" in
- fun pkg branch ->
+ fun ?(wait = true) ?side_tag pkg branch ->
let repodir = fedora_repo pkg branch in
- let out = shout "cd %s && fedpkg build 2>&1 ||:" repodir in
- let task_id =
- try
- let subs = Pcre.exec ~rex:created_task out in
- int_of_string (Pcre.get_substring subs 1)
- with Not_found ->
- failwith "could not find task ID in fedpkg build output" in
- let rec loop out =
- if name_or_service_not_known out then (
- let out =
- shout "cd %s && koji watch-task %d 2>&1 ||:" repodir task_id in
- loop out
- )
- else if completed_successfully out then
- ()
- else if failed out then (
- eprintf "%s\n%!" out;
- failwith "koji build failed"
- )
- else
- failwith (sprintf "koji_build: unknown output: %s" out)
+ let out =
+ shout "
+ cd %s
+ fedpkg build%s%s 2>&1
+ " repodir
+ (if not wait then " --nowait" else "")
+ (match side_tag with None -> "" | Some t -> " --target " ^ t)
in
- loop out
+ if not wait then (
+ (* Just check the task was created. *)
+ if not (Pcre.pmatch ~rex:created_task out) then (
+ failwith "fedpkg build: build failed to start"
+ )
+ ) else (
+ let task_id =
+ try
+ let subs = Pcre.exec ~rex:created_task out in
+ int_of_string (Pcre.get_substring subs 1)
+ with Not_found ->
+ failwith "could not find task ID in fedpkg build output" in
+ let rec loop out =
+ if name_or_service_not_known out then (
+ let out =
+ shout "cd %s && koji watch-task %d 2>&1 ||:" repodir task_id in
+ loop out
+ )
+ else if completed_successfully out then
+ ()
+ else if failed out then (
+ failwith "koji build failed"
+ )
+ else
+ failwith (sprintf "koji_build: unknown output: %s" out)
+ in
+ loop out
+ )
let koji_wait_repo =
let successfully_waited = contains_substring "Successfully waited" in