Skip to content

Commit

Permalink
dialects: allow embedded dots in extensions
Browse files Browse the repository at this point in the history
Signed-off-by: Nicolás Ojeda Bär <n.oje.bar@gmail.com>
  • Loading branch information
nojb committed May 24, 2023
1 parent fb2d63a commit cfed06c
Show file tree
Hide file tree
Showing 13 changed files with 72 additions and 16 deletions.
3 changes: 3 additions & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ Unreleased
- Add additional metadata to the traces provided by `--trace-file` whenever
`--trace-extended` is passed (#7778, @rleshchinskiy)

- Extensions used in `(dialect)` can include embedded dots (e.g., `cppo.ml`) for
versions of the Dune language 3.8 and later. (#7782, @nojb)

3.8.0 (2023-05-23)
------------------

Expand Down
5 changes: 3 additions & 2 deletions doc/dune-files.rst
Original file line number Diff line number Diff line change
Expand Up @@ -75,9 +75,10 @@ dialect

Specify the file extension used for this dialect.

The extension string must not contain any dots and be unique in a given
The extension string must not start with a dot and be unique in a given
project (so that a given extension can be mapped back to a
corresponding dialect).
corresponding dialect). In Dune 3.8 and later, the extension string may
contain embedded dots (e.g., `cppo.ml`).

This field is required.

Expand Down
14 changes: 7 additions & 7 deletions src/dune_rules/dialect.ml
Original file line number Diff line number Diff line change
Expand Up @@ -70,19 +70,19 @@ let encode { name; file_kinds } =
let decode =
let open Dune_lang.Decoder in
let kind kind =
let+ loc, extension = field "extension" (located string)
let+ loc, extension = field "extension" (located extension)
and+ preprocess = field_o "preprocess" (located Action.decode_dune_file)
and+ format =
field_o "format"
(map
~f:(fun (loc, x) -> (loc, x, []))
(located Action.decode_dune_file))
in
let extension =
if String.contains extension '.' then
User_error.raise ~loc [ Pp.textf "extension must not contain '.'" ];
"." ^ extension
in
and+ syntax_ver = Syntax.get_exn Stanza.syntax in
let ver = (3, 9) in
(if syntax_ver < ver && Option.is_some (String.index_from extension 1 '.')
then
let what = "the possibility of defining extensions with embedded dots" in
Syntax.Error.since loc Stanza.syntax ver ~what);
{ File_kind.kind; extension; preprocess; format }
in
fields
Expand Down
7 changes: 1 addition & 6 deletions src/dune_rules/melange/melange_stanzas.ml
Original file line number Diff line number Diff line change
Expand Up @@ -24,12 +24,7 @@ module Emit = struct
let implicit_alias = Alias.Name.of_string "melange"

let decode =
let extension_field =
let+ loc, extension = located string in
if String.is_prefix ~prefix:"." extension then
User_error.raise ~loc [ Pp.textf "extension must not start with '.'" ];
"." ^ extension
in
let extension_field = extension in
let module_systems =
let module_system =
enum [ ("es6", Melange.Module_system.Es6); ("commonjs", CommonJs) ]
Expand Down
6 changes: 6 additions & 0 deletions src/dune_sexp/decoder.ml
Original file line number Diff line number Diff line change
Expand Up @@ -343,6 +343,12 @@ let filename =
[ Pp.textf "'.' and '..' are not valid filenames" ]
| fn -> fn)

let extension =
plain_string (fun ~loc s ->
if String.is_prefix ~prefix:"." s then
User_error.raise ~loc [ Pp.textf "extension must not start with '.'" ];
"." ^ s)

let relative_file =
plain_string (fun ~loc fn ->
if Filename.is_relative fn then fn
Expand Down
4 changes: 4 additions & 0 deletions src/dune_sexp/decoder.mli
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,10 @@ val plain_string : (loc:Loc.t -> string -> 'a) -> 'a t
(** A valid filename, i.e. a string other than "." or ".." *)
val filename : Filename.t t

(** An extension: a string not starting with ".". The value returned by the
parser is prefixed with ".". *)
val extension : string t

(** A relative filename *)
val relative_file : string t

Expand Down
2 changes: 1 addition & 1 deletion test/blackbox-tests/test-cases/dialects/bad3.t/run.t
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,5 @@
File "dune-project", line 5, characters 28-32:
5 | (implementation (extension .foo))
^^^^
Error: extension must not contain '.'
Error: extension must not start with '.'
[1]
2 changes: 2 additions & 0 deletions test/blackbox-tests/test-cases/dialects/dots.t/cppo.ml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
let () =
print_endline {|print_endline "Hello, World"|}
11 changes: 11 additions & 0 deletions test/blackbox-tests/test-cases/dialects/dots.t/dune
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
(executable
(name main)
(modules main))

(executable
(name cppo)
(modules cppo))

(rule
(alias show)
(action (cat main.cppo.ml.ml)))
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
(dialect
(name cppo)
(implementation
(extension cppo.ml)
(preprocess (run ./cppo.exe %{input-file})))
(interface
(extension cppo.mli)
(preprocess (run ./cppo.exe %{input-file}))))
Empty file.
Empty file.
26 changes: 26 additions & 0 deletions test/blackbox-tests/test-cases/dialects/dots.t/run.t
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
Test the (dialect ...) stanza inside the `dune-project` file.

$ { echo '(lang dune 3.8)'; cat dune-project.in; } >dune-project

$ dune build --display short
File "dune-project", line 5, characters 13-20:
5 | (extension cppo.ml)
^^^^^^^
Error: the possibility of defining extensions with embedded dots is only
available since version 3.9 of the dune language. Please update your
dune-project file to have (lang dune 3.9).
[1]

$ { echo '(lang dune 3.9)'; cat dune-project.in; } >dune-project

$ dune build --display short
ocamlc .cppo.eobjs/byte/dune__exe__Cppo.{cmi,cmti}
ocamlc .main.eobjs/byte/dune__exe__Main.{cmi,cmti}
ocamlopt .cppo.eobjs/native/dune__exe__Cppo.{cmx,o}
ocamlopt cppo.exe
cppo main.cppo.ml.ml
ocamlopt .main.eobjs/native/dune__exe__Main.{cmx,o}
ocamlopt main.exe

$ dune build @show
print_endline "Hello, World"

0 comments on commit cfed06c

Please sign in to comment.