dbuenzli / fpath

File paths for OCaml
http://erratique.ch/software/fpath
ISC License
26 stars 10 forks source link

Dedicated (sub)module for punctuation-based symbols (//, /, etc.) #19

Open mjambon opened 1 year ago

mjambon commented 1 year ago

What I want:

Usage:

open Fpath.Operators

...

let abs_dir ?(cwd = Unix.getcwd () |> Fpath.v) path =
  cwd // path |> Fpath.parent

If I'm not missing an operator, the signature of the submodule would be:

module Operators : sig
  val (/) : t -> string -> t
  val (//) : t -> Fpath.t -> t
  val (+) : t -> ext -> t
  val (-+) : t -> ext -> t
end

I like the long name Operators because it makes it clear to the reader of the code that this is probably where the exotic operators come from. Since it's only meant to be used as open Fpath.Operators or let open Fpath.Operators in, it's not that frequent and doesn't need to be extremely short.

On a related note, we're experimenting with the prefix operator !! which would make !!file an alias for (Fpath.to_string file). I can make a dedicated issue or PR once I'm convinced it's a good idea.

dbuenzli commented 1 year ago

If anything it will be Syntax but I'm not convinced in providing this. All the uses of the operators should be quite localized, so it's meant to be used with the Fpath.() notation:

let abs_dir ?(cwd = Unix.getcwd () |> Fpath.v) path =
  Fpath.(cwd // path) |> Fpath.parent
mjambon commented 1 year ago

Good point. In this case, I think I'd rather write this:

let abs_dir ?(cwd = Unix.getcwd () |> Fpath.v) path =
  Fpath.append cwd path |> Fpath.parent

(we don't have to worry about whether Fpath.cwd or Fpath.path exist)

An alternative is to let users define their own module that provides operators. This is what we're doing right now in semgrep. It's not a huge deal because it's a large application and we already have our own custom "standard library". It's more annoying in small projects where I'd go with let (//) = Fpath.append at the beginning of each module where it's used.

Earlier, I mentioned that we use !! as an alias for Fpath.to_string because we use it widely, more so than the other operators and really makes the code lighter in my opinion. Here's an example:

open Fpath.Syntax

...
if Sys.file_exists !!file then (
  ...
)

Compare with

if Sys.file_exists Fpath.(!!file) then (
  ...
)