Skip to content

Conversation

@pimbrouwers
Copy link
Member

@pimbrouwers pimbrouwers commented Mar 12, 2025

Proposal: Prefix-based HTML DSL for Falco.Markup

Problem Statement

Currently, Falco.Markup users need to use prefix notation (i.e., Elem.div, or self alias) for both the Elem and Attr modules. When the complexity of the markup increases, the level of noise created is substantial.

Proposed Solution

Full implementation can be found here.

Implement a unified DSL module with consistent prefix-based naming:

  • Single underscore (_) prefix for text elements (i.e., _text)
  • Single underscore (_) prefix for HTML elements (i.e., _div)
    • Element "text" shortcuts will also receive a trailing apostrophe to designate the mod (i.e., Text.h1 "here" becomes _h1' "here"
  • Single underscore (_) prefix and suffix for attributes (i.e., _class_)

Implementation Details

namespace Falco.Markup

[<AutoOpen>]
module Html =
    // Element aliases
    let inline _div attr content = Elem.div attr content
    let inline _span attr content = Elem.span attr content
    
    // Text aliases
    let _h1' content = Text.h1 content
    let _p' content = Text.p content

    // Attribute aliases
    let inline _class_ value = Attr.class' value
    let inline _id_ value = Attr.id value 

Benefits

  1. Visual "noise" reduction - Cleaner, more readable code
  2. Conflict avoidance - Prefixes prevent naming collisions
  3. Backward compatibility - Original modules remain unchanged

Example Usage

open Falco.Markup

let myComponent =
    _div [ _class_ "container" ] [
        _h1 [ _id_ "title" ] [ "Hello World" ]
        _p' "This is a paragraph"
    ]

Migration

No breaking changes - existing code continues to work while new code can adopt the prefixed approach.

@pimbrouwers pimbrouwers self-assigned this Mar 12, 2025
@pimbrouwers pimbrouwers added the enhancement New feature or request label Mar 12, 2025
@jkone27
Copy link

jkone27 commented Mar 14, 2025

why not just single letter modules and double ticked for reserved keywords? https://stackoverflow.com/questions/6639688/using-keywords-as-identifiers-in-f

let myComponent =
    m.div [ a.``class`` "container" ] [
        m.h1 [ a.id "title" ] [ "Hello World" ]
        m.p "This is a paragraph"
    ]

@pimbrouwers
Copy link
Member Author

why not just single letter modules and double ticked for reserved keywords? https://stackoverflow.com/questions/6639688/using-keywords-as-identifiers-in-f

let myComponent =
    m.div [ a.``class`` "container" ] [
        m.h1 [ a.id "title" ] [ "Hello World" ]
        m.p "This is a paragraph"
    ]

I appreciate the feedback! It's not a matter of the protected keywords, those are dealt with currently using single quote ticks (i.e., Attr.class') which is the style I prefer. The idea behind this, is to provide a more terse way to document complex HTML, and get away from the module prefixing altogether with backward compat.

@pimbrouwers
Copy link
Member Author

After careful consideration and refinement, I am confident in the implementation and its benefits. The prefix-based HTML DSL for Falco.Markup achieves the goals of reducing visual noise, avoiding naming conflicts, and maintaining backward compatibility.

The unified DSL module introduces consistent prefix-based naming conventions for elements, text shortcuts, and attributes, making code cleaner and more readable. The example usage demonstrates how this approach simplifies markup creation while preserving the flexibility of the original modules.

I believe this enhancement will significantly improve the developer experience for Falco.Markup users. As the PR has been open for some time and no further concerns have been raised, I am happy with the result and ready to move forward.

Thank you again for your support and collaboration!

@pimbrouwers pimbrouwers merged commit 91c3c46 into master Jun 26, 2025
1 check passed
@pimbrouwers pimbrouwers deleted the html-module branch June 26, 2025 14:55
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants