Skip to content

Document component attribute value semantics more clearly #10

@tormnator

Description

@tormnator

Is your feature request or improvement related to a problem?

Yes.

Component attribute syntax in Nue is currently harder to understand than it should be, especially for new users passing values into components.

The current docs do not clearly explain the behavioral differences between:

  • label="value"
  • :label="value"
  • :label="{ value }"
  • :label="'value'"

This makes it difficult to know when Nue is treating something as:

  • a literal string
  • an expression lookup
  • interpolation syntax
  • component-only data
  • a rendered DOM attribute

There also appears to be at least one misleading example in the docs.

Solution you'd like

Document component attribute value semantics explicitly.

At minimum, the docs should explain:

  • regular attributes vs colon attributes
  • literal strings vs expressions
  • the difference between label="value" and :label="'value'"
  • the difference between :label="value" and :label="{ value }"
  • that colon attributes are component data props and are not rendered to the DOM
  • that regular attributes are also rendered into the DOM
  • that bare values in colon attributes are expressions, not literal strings
  • that numeric literals like :count="12" work because they are valid expressions
  • that string literals in colon attributes must be written as actual string expressions

It would also help to state clearly whether this behavior is shared across HTML and DHTML component usage, or whether there are any differences.

Problem summary

From current implementation and observed behavior:

  1. Regular attributes like label="value" behave as literal attribute values.
  2. Regular attributes are also available as component data.
  3. Regular attributes are rendered into the DOM.
  4. Colon attributes are treated as expressions.
  5. Colon attributes are passed as component data and are not rendered into the DOM.
  6. A bare colon value like :label="value" is interpreted as an identifier lookup, not the string "value".
  7. Numeric literals like :count="12" work because 12 is a valid expression.
  8. A string literal in a colon attribute must be written as a quoted expression, for example :label="'value'".

This behavior seems internally consistent, but it is not explained clearly enough in the docs.

Concrete docs problem

Under Components in packages/www/docs/html-syntax.md, the docs currently show:

<product-card :name="Coffee" :price="12"/>

That example is misleading for name.

Based on actual behavior, :name="Coffee" does not pass the literal string Coffee; it attempts to resolve a variable named Coffee.

So this example is only half-correct:

  • :price="12" works because 12 is a numeric literal expression
  • :name="Coffee" does not work as a string literal

If the intention is to pass a literal string, the example should instead use something like:

<product-card :name="'Coffee'" :price="12"/>

or, if DOM output is acceptable:

<product-card name="Coffee" :price="12"/>

Suggested examples to document

Literal attribute value

<badge label="New"/>
  • passes the literal string New
  • also renders label="New" into the DOM

Data-only variable prop

<badge :label="label"/>
  • resolves label from the current expression scope
  • passes it into the component as data
  • does not render label into the DOM

Interpolation-style expression

<badge :label="{ label }"/>
  • also resolves from the current expression scope
  • useful to compare with :label="label" so readers understand that both are expression forms

Data-only literal string

<badge :label="'New'"/>
  • passes the literal string New
  • does not render label into the DOM

Suggested documentation locations

1. packages/www/docs/html-syntax.md

This seems like the most important place.

Under the existing Components section, add a short subsection such as:

  • Passing component props
  • Regular attributes vs colon attributes
  • Literal strings vs expressions

This section should also fix the current :name="Coffee" example.

2. packages/www/docs/interactive-components.md

This file should explain prop-passing syntax in the context of real component use.

The current Template data section is already near this topic, but it would benefit from clarifying:

  • what component data is ambient vs explicitly passed
  • how to pass page/template values into components
  • how literal strings differ from expression props

3. packages/www/docs/template-data.md

Probably not the main place for the syntax explanation, but it may benefit from a short cross-reference so readers can distinguish:

  • where values come from
  • how values are passed into components

Alternatives you've considered

1. Only fix the misleading example

That would help, but it would not address the broader confusion around regular attributes, colon attributes, literals, and expressions.

2. Leave the behavior implicit

This is the current situation, but it makes common component prop usage harder to learn than necessary.

Additional context

This seems primarily like a documentation issue.

The current behavior appears internally consistent. The missing piece is a clear explanation of the rules where component usage is introduced.

If there are any intentional differences between HTML and DHTML component usage for attribute semantics, those should also be documented explicitly.

Metadata

Metadata

Assignees

No one assigned

    Labels

    documentationImprovements or additions to documentationenhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions