Zaid-Ajaj / Feliz

A fresh retake of the React API in Fable and a collection of high-quality components to build React applications in F#, optimized for happiness
https://zaid-ajaj.github.io/Feliz/
MIT License
534 stars 78 forks source link

Report incompatible Fable version from Feliz.CompilerPlugins #539

Open MangelMaxime opened 1 year ago

MangelMaxime commented 1 year ago

If user use Feliz.CompilerPlugins v2, with Fable 3 there is no compilation error.

Only a runtime one from React about invalid hook usage.

Is it possible detect Fable version and make the compilations fails if it is invalid?

@alfonsogarciacaro

Zaid-Ajaj commented 1 year ago

If user use Feliz.CompilerPlugins v2, with Fable 3 there is no compilation error.

Something like this?

#if FABLE_COMPILER_3
failwith "Detected Fable v3 compiler using Feliz v2.0.0. Please upgrade Fable to latest v4"
#endif
MangelMaxime commented 1 year ago

I would prefer a compilation error than a runtime error but that's already a plus.

And it also assume that the user don't install Feliz.CompilerPlugins alone but always through Felizwhich should be ok to assume I think.

In the plugin, there is actually a Fable minimum version set but not sure if it does something or not:

https://github.com/Zaid-Ajaj/Feliz/blob/b8feba427f3a45661a0a118a65a1b782462662f6/Feliz.CompilerPlugins/Hook.fs#L6-L9

Zaid-Ajaj commented 1 year ago

@MangelMaxime I think the FableMinimumVersion doesn't do much now because 4.0.0 doesn't account for theta-018 prerelease versions

MangelMaxime commented 1 year ago

There is a check against FableMinimumVersion in Fable source code:

https://github.com/fable-compiler/Fable/blob/8c0767d4426c697e04421194ab1d265bfd8e597e/src/Fable.Transforms/Global/Compiler.fs#L163-L176

        member com.ApplyPlugin<'Plugin, 'Input when 'Plugin :> PluginAttribute>(plugins: Map<_,_>, atts: Fable.Attribute seq, input: 'Input, transform) =
            if Map.isEmpty plugins then input
            else
                // Reverse attributes so plugins closer to member/type are applied first
                (input, Seq.rev atts) ||> Seq.fold (fun input att ->
                    match Map.tryFind att.Entity plugins with
                    | None -> input
                    | Some plugin ->
                        let pluginInstance = System.Activator.CreateInstance(plugin, List.toArray att.ConstructorArgs) :?> 'Plugin
                        if not(expectedVersionMatchesActual pluginInstance.FableMinimumVersion Literals.VERSION) then
                            failwithf "Plugin %s expects v%s but currently running Fable v%s"
                                        plugin.FullName pluginInstance.FableMinimumVersion Literals.VERSION
                        let helper = com.ToPluginHelper()
                        transform pluginInstance helper input)

I will try to look if the check is actually doing something or if there is an bug in it.