ocsigen / tyxml

Build valid HTML and SVG documents
https://ocsigen.org/tyxml/
Other
167 stars 62 forks source link

Tyxml.Html module does not follow Html_sigs.T #315

Open Chimrod opened 1 year ago

Chimrod commented 1 year ago

Hello,

I’m not sure of this issue, but when working with the functorial interface I had some error with this code:

module Make (HTML : Html_sigs.T) = struct end
module M = Make (Tyxml.Html)

which give an error in the compilation:

The module `Svg' is required but not provided

Is this intended ? It seems to come from the signature in the functorial interface which use destructive substitution (but I’m not sure how to undestand it in the case of modules):

and module Svg := Svg
Drup commented 1 year ago

Yes, this is intended, Html_sigs.T is an input signature, not supposed to be used to describe a concrete module. The right signature for an HTML module is Html_sigs.Make(...) (cf the tutorial for the functoria interface).

What are you actually trying to do ?

Chimrod commented 1 year ago

I'm trying to build a module type in order to declare a functor I could use with both tyxml and js_of_ocaml_tyxml

module Make (HTML : HTML) = struct
  let repr = HTML.div []
end

module JS_Builder = Make (Js_of_ocaml_tyxml.Tyxml_js)
module Server_Builder = Make (Tyxml.Html)

Using a signature such as module type HTML = Html_sigs.Make(Tyxml_xml)(Tyxml_svg).T is too high level gives type error when I want to link with Tyxml_js:

     ... In module Xml:
     Type declarations do not match:
       type event_handler = Xml.event_handler
     is not included in
       type event_handler = string
     The type
       event_handler = Js_of_ocaml.Dom_html.event Js_of_ocaml.Js.t -> bool
     is not equal to the type string

what is working for me is to rebuild the signature leaving the differents type abstract:

module type HTML =
  Html_sigs.T
    with type ('a, 'b) Xml.W.ft = 'a -> 'b
     and type 'a Xml.W.t = 'a
     and type 'a Xml.W.tlist = 'a list
     and type Xml.uri = string

but I was surprised to see an error with a missing Svg module.

Drup commented 1 year ago

Oh, I see, indeed, that is a good use case. What you should probably do is for Make to also take the Svg module, and to use with module Svg := Svg on the HTML signature.

Chimrod commented 1 year ago

Thanks for your answer ; it's good to hear that I'm not completly wrong !

Your answer is the solution of course, but I'm a bit hesitant to close the ticket : it took me time to figure exactly how to achieve what I wanted, and the ticket is a consequence of the questions I've had when trying to get a solution.

Do you think you can update the documentation with a word about this usage ?

Chimrod commented 1 year ago

To keep a track in the message, here is the functor signature:

module Make
    (SVG : Svg_sigs.T
             with type 'a Xml.W.t = 'a
              and type 'a Xml.W.tlist = 'a list
              and type Xml.uri = string)
    (HTML : Html_sigs.T with module Xml = SVG.Xml and module Svg := SVG) 
= struct 

end
Drup commented 1 year ago

I agree, it would be a good idea to add that somewhere in the documentation. I'm note quite sure where.

Note that you can use the NoWrap signature for "simple" cases (i.e., not the reactive stuff), which avoid restating some equalities.