From 00fb5b7327a52eb77a01a929976241a6fe17521d Mon Sep 17 00:00:00 2001 From: Anil Madhavapeddy Date: Mon, 8 Jul 2019 16:56:03 +0100 Subject: [PATCH] do opam file generation in the same order as `opam lint` The logic for the field order used by `opam lint --normalise` is in opam-file and not opam-file-format. This is too much to vendor, so this commit hardcodes the field order based on the opam-file logic. It won't change very often upstream so this shouldn't impose too much of a maintenance overhead. Closes #2290 Signed-off-by: Anil Madhavapeddy --- dune-build-info.opam | 38 +++--- dune.opam | 14 +-- src/opam_create.ml | 6 +- src/opam_file.ml | 52 ++++++++ src/opam_file.mli | 2 + .../test-cases/dune-project-meta/run.t | 113 ++++++++++++++++++ .../test-fields-with-tmpl/dune-project | 60 ++++++++++ .../github-unix.opam.template | 1 + .../github.opam.template | 1 + 9 files changed, 260 insertions(+), 27 deletions(-) create mode 100644 test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/dune-project create mode 100644 test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github-unix.opam.template create mode 100644 test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github.opam.template diff --git a/dune-build-info.opam b/dune-build-info.opam index e6abec158e1..32092c06d4b 100644 --- a/dune-build-info.opam +++ b/dune-build-info.opam @@ -1,5 +1,24 @@ # This file is generated by dune, edit dune-project instead opam-version: "2.0" +synopsis: "Embed build informations inside executable" +description: """ +The build-info library allows to access information about how the +executable was built, such as the version of the project at which it +was built or the list of statically linked libraries with their +versions. It supports reporting the version from the version control +system during development to get an precise reference of when the +executable was built. +""" +maintainer: ["Jane Street Group, LLC "] +authors: ["Jane Street Group, LLC "] +license: "MIT" +homepage: "https://github.com/ocaml/dune" +doc: "https://dune.readthedocs.io/" +bug-reports: "https://github.com/ocaml/dune/issues" +depends: [ + "ocaml" {>= "4.02"} + "dune" {>= "1.11"} +] build: [ ["dune" "subst"] {pinned} [ @@ -14,23 +33,4 @@ build: [ "@doc" {with-doc} ] ] -maintainer: ["Jane Street Group, LLC "] -authors: ["Jane Street Group, LLC "] -bug-reports: "https://github.com/ocaml/dune/issues" -homepage: "https://github.com/ocaml/dune" -doc: "https://dune.readthedocs.io/" -license: "MIT" dev-repo: "git+https://github.com/ocaml/dune.git" -synopsis: "Embed build informations inside executable" -description: """ -The build-info library allows to access information about how the -executable was built, such as the version of the project at which it -was built or the list of statically linked libraries with their -versions. It supports reporting the version from the version control -system during development to get an precise reference of when the -executable was built. -""" -depends: [ - "ocaml" {>= "4.02"} - "dune" {>= "1.11"} -] diff --git a/dune.opam b/dune.opam index c17f4183e3e..6d79315663d 100644 --- a/dune.opam +++ b/dune.opam @@ -1,12 +1,5 @@ # This file is generated by dune, edit dune-project instead opam-version: "2.0" -maintainer: ["Jane Street Group, LLC "] -authors: ["Jane Street Group, LLC "] -bug-reports: "https://github.com/ocaml/dune/issues" -homepage: "https://github.com/ocaml/dune" -doc: "https://dune.readthedocs.io/" -license: "MIT" -dev-repo: "git+https://github.com/ocaml/dune.git" synopsis: "Fast, portable and opinionated build system" description: """ @@ -27,6 +20,12 @@ several opam roots/switches simultaneously. This helps maintaining packages across several versions of OCaml and gives cross-compilation for free. """ +maintainer: ["Jane Street Group, LLC "] +authors: ["Jane Street Group, LLC "] +license: "MIT" +homepage: "https://github.com/ocaml/dune" +doc: "https://dune.readthedocs.io/" +bug-reports: "https://github.com/ocaml/dune/issues" depends: [ "ocaml" {>= "4.02"} "base-unix" @@ -37,6 +36,7 @@ conflicts: [ "odoc" {< "1.3.0"} "dune-release" {< "1.3.0"} ] +dev-repo: "git+https://github.com/ocaml/dune.git" build: [ # opam 2 sets OPAM_SWITCH_PREFIX, so we don't need a hardcoded path ["ocaml" "configure.ml" "--libdir" lib] {opam-version < "2"} diff --git a/src/opam_create.ml b/src/opam_create.ml index 26227e48197..15b5cfe0df7 100644 --- a/src/opam_create.ml +++ b/src/opam_create.ml @@ -97,7 +97,11 @@ let opam_fields project (package : Package.t) = ; "build", default_build_command project ] in - List.concat + let sort_fields l = + if Dune_project.dune_version project < (1, 11) then l + else Opam_file.Create.normalise_field_order l + in + sort_fields @@ List.concat [ fields ; list_fields ; optional_fields diff --git a/src/opam_file.ml b/src/opam_file.ml index 04ccc7eff2f..b3b22ff2935 100644 --- a/src/opam_file.ml +++ b/src/opam_file.ml @@ -87,6 +87,58 @@ module Create = struct let list f xs = List (nopos, List.map ~f xs) let string_list xs = list string xs + let normalise_field_order vars = + let normal_field_order = [ + (* Extracted from opam/src/format/opamFile.ml *) + "opam-version"; + "name"; + "version"; + "synopsis"; + "description"; + "maintainer"; + "authors"; + "author"; + "license"; + "tags"; + "homepage"; + "doc"; + "bug-reports"; + "depends"; + "depopts"; + "conflicts"; + "conflict-class"; + "available"; + "flags"; + "setenv"; + "build"; + "run-test"; + "install"; + "remove"; + "substs"; + "patches"; + "build-env"; + "features"; + "messages"; + "post-messages"; + "depexts"; + "libraries"; + "syntax"; + "dev-repo"; + "pin-depends"; + "extra-files" ] + in + let standard_fields = + List.filter_map normal_field_order ~f:(fun field -> + Option.map (List.assoc vars field) + ~f:(fun v -> field, v)) + in + let extra_fields = + List.filter_map vars ~f:(fun (name,v) -> + if List.mem ~set:normal_field_order name then None + else Some (name,v)) + in + standard_fields @ extra_fields + let of_bindings vars ~file = let file_contents = List.map vars ~f:(fun (var, value) -> diff --git a/src/opam_file.mli b/src/opam_file.mli index 24566676608..fa9d9106a99 100644 --- a/src/opam_file.mli +++ b/src/opam_file.mli @@ -36,5 +36,7 @@ module Create : sig val string_list : string list -> value + val normalise_field_order : (string * value) list -> (string * value) list + val of_bindings : (string * value) list -> file:Path.t -> t end diff --git a/test/blackbox-tests/test-cases/dune-project-meta/run.t b/test/blackbox-tests/test-cases/dune-project-meta/run.t index 29dc4e08283..fe9cc05e730 100644 --- a/test/blackbox-tests/test-cases/dune-project-meta/run.t +++ b/test/blackbox-tests/test-cases/dune-project-meta/run.t @@ -169,3 +169,116 @@ Generation of opam files with lang dune >= 1.11 "@doc" {with-doc} ] ] + + +Templates should also be respected with extension fields, in this +case "x-foo": + + $ dune build @install --root test-fields-with-tmpl --auto-promote + Entering directory 'test-fields-with-tmpl' + $ cat test-fields-with-tmpl/github.opam + # This file is generated by dune, edit dune-project instead + opam-version: "2.0" + synopsis: "GitHub APIv3 OCaml library" + description: """ + This library provides an OCaml interface to the + [GitHub APIv3](https://developer.github.com/v3/) (JSON). + + It is compatible with [MirageOS](https://mirage.io) and also compiles to pure + JavaScript via [js_of_ocaml](http://ocsigen.org/js_of_ocaml).""" + maintainer: ["Anil Madhavapeddy "] + authors: [ + "Anil Madhavapeddy" + "David Sheets" + "Andy Ray" + "Jeff Hammerbacher" + "Thomas Gazagnaire" + "Rudi Grinberg" + "Qi Li" + "Jeremy Yallop" + "Dave Tucker" + ] + license: "MIT" + homepage: "https://github.com/mirage/ocaml-github" + doc: "https://mirage.github.io/ocaml-github/" + bug-reports: "https://github.com/mirage/ocaml-github/issues" + depends: [ + "ocaml" {>= "4.03.0"} + "uri" {>= "1.9.0"} + "cohttp" {>= "0.99.0"} + "cohttp-lwt" {>= "0.99"} + "lwt" {>= "2.4.4"} + "atdgen" {>= "2.0.0"} + "yojson" {>= "1.6.0"} + "stringext" + ] + build: [ + ["dune" "subst"] {pinned} + [ + "dune" + "build" + "-p" + name + "-j" + jobs + "@install" + "@runtest" {with-test} + "@doc" {with-doc} + ] + ] + dev-repo: "git+https://github.com/mirage/ocaml-github.git" + x-foo: "an extension field" + +And this file should contains a "libraries" field at the end. +It is not sorted since its in a template, which always comes at +the end. + + $ cat test-fields-with-tmpl/github-unix.opam + # This file is generated by dune, edit dune-project instead + opam-version: "2.0" + synopsis: "GitHub APIv3 Unix library" + description: """ + This library provides an OCaml interface to the [GitHub APIv3](https://developer.github.com/v3/) + (JSON). This package installs the Unix (Lwt) version.""" + maintainer: ["Anil Madhavapeddy "] + authors: [ + "Anil Madhavapeddy" + "David Sheets" + "Andy Ray" + "Jeff Hammerbacher" + "Thomas Gazagnaire" + "Rudi Grinberg" + "Qi Li" + "Jeremy Yallop" + "Dave Tucker" + ] + license: "MIT" + homepage: "https://github.com/mirage/ocaml-github" + doc: "https://mirage.github.io/ocaml-github/" + bug-reports: "https://github.com/mirage/ocaml-github/issues" + depends: [ + "ocaml" {>= "4.03.0"} + "github" {= version} + "cohttp" {>= "0.99.0"} + "cohttp-lwt-unix" {>= "0.99.0"} + "stringext" + "lambda-term" {>= "2.0"} + "cmdliner" {>= "0.9.8"} + "base-unix" + ] + build: [ + ["dune" "subst"] {pinned} + [ + "dune" + "build" + "-p" + name + "-j" + jobs + "@install" + "@runtest" {with-test} + "@doc" {with-doc} + ] + ] + dev-repo: "git+https://github.com/mirage/ocaml-github.git" + libraries: [ "github_unix" ] diff --git a/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/dune-project b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/dune-project new file mode 100644 index 00000000000..a18cfb4d389 --- /dev/null +++ b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/dune-project @@ -0,0 +1,60 @@ +(lang dune 1.11) +(name github) + +(generate_opam_files true) + +(license MIT) +(maintainers "Anil Madhavapeddy ") +(authors "Anil Madhavapeddy" "David Sheets" "Andy Ray" + "Jeff Hammerbacher" "Thomas Gazagnaire" "Rudi Grinberg" + "Qi Li" "Jeremy Yallop" "Dave Tucker") +(source (github mirage/ocaml-github)) +(documentation "https://mirage.github.io/ocaml-github/") + +(package + (name github) + (tags (org:mirage org:xapi-project git)) + (depends + (ocaml (>= 4.03.0)) + (uri (>= 1.9.0)) + (cohttp (>= 0.99.0)) + (cohttp-lwt (>= 0.99)) + (lwt (>= 2.4.4)) + (atdgen (>= 2.0.0)) + (yojson (>= 1.6.0)) + stringext) + (synopsis "GitHub APIv3 OCaml library") + (description "This library provides an OCaml interface to the +[GitHub APIv3](https://developer.github.com/v3/) (JSON). + +It is compatible with [MirageOS](https://mirage.io) and also compiles to pure +JavaScript via [js_of_ocaml](http://ocsigen.org/js_of_ocaml).")) + +(package + (name github-jsoo) + (tags (org:mirage org:xapi-project git)) + (depends + (ocaml (>= 4.03.0)) + (github (= :version)) + (cohttp (>= 0.99.0)) + (cohttp-lwt-jsoo (>= 0.99.0)) + (js_of_ocaml-lwt (>= 3.4.0))) + (synopsis "GitHub APIv3 JavaScript library") + (description "This library provides an OCaml interface to the [GitHub APIv3](https://developer.github.com/v3/) +(JSON). This library installs the JavaScript version, which uses [js_of_ocaml](http://ocsigen.org/js_of_ocaml).")) + +(package + (name github-unix) + (tags (org:mirage org:xapi-project git)) + (depends + (ocaml (>= 4.03.0)) + (github (= :version)) + (cohttp (>= 0.99.0)) + (cohttp-lwt-unix (>= 0.99.0)) + stringext + (lambda-term (>= 2.0)) + (cmdliner (>= 0.9.8)) + base-unix) + (synopsis "GitHub APIv3 Unix library") + (description "This library provides an OCaml interface to the [GitHub APIv3](https://developer.github.com/v3/) +(JSON). This package installs the Unix (Lwt) version.")) diff --git a/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github-unix.opam.template b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github-unix.opam.template new file mode 100644 index 00000000000..b0d9b53176e --- /dev/null +++ b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github-unix.opam.template @@ -0,0 +1 @@ +libraries: [ "github_unix" ] diff --git a/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github.opam.template b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github.opam.template new file mode 100644 index 00000000000..2acd5090a14 --- /dev/null +++ b/test/blackbox-tests/test-cases/dune-project-meta/test-fields-with-tmpl/github.opam.template @@ -0,0 +1 @@ +x-foo: "an extension field"