std.format spec conflict: docs say "follows Python rules" but std.jsonnet rejects booleans for numeric format codes

Open
#1,329 1 comment 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Assessment

Difficulty
4/5
Estimated time
3-5 days
Newbie friendliness
38/100
Issue type
Bug
Clarity
Mostly clear
Activity status
Quiet
Domain
compilers

Research direction

Start with the std.format documentation at the linked stdlib reference and the format_code helper in std.jsonnet, then compare the behavior described there with the examples in the issue. Review the linked sjsonnet PR for implementation context; done means the intended boolean behavior is decided and the documentation and reference implementation no longer conflict.

Written by the indexing model from the issue text.

Description

Summary

There is a conflict between the official documentation and the reference implementation (std.jsonnet) regarding how std.format handles boolean values with numeric format codes.

Documentation says

From https://jsonnet.org/ref/stdlib.html#std-format:

The string formatting follows the same rules as Python.

In Python, bool is a subclass of int, so all numeric format codes accept booleans:

>>> "%d" % True
'1'
>>> "%f" % True
'1.000000'
>>> "%x" % True
'1'
>>> "%s" % True
'True'

Reference implementation says

In std.jsonnet, the format_code helper explicitly checks:

if std.type(val) != 'number' then
  error 'Format required number at ' + i + ', got ' + std.type(val)

Since std.type(true) returns 'boolean' (not 'number'), all numeric format codes reject booleans:

std.format("%d", true)  → ERROR: "Format required number at 0, got boolean"
std.format("%f", true)  → ERROR
std.format("%x", true)  → ERROR

Only %s works: std.format("%s", true) → "true"

The conflict

Expression Python behavior (per docs) std.jsonnet behavior (per impl)
"%d" % true "1" ERROR
"%f" % true "1.000000" ERROR
"%x" % true "1" ERROR
"%s" % true "True" "true"

This causes confusion for implementors: should a compliant Jsonnet implementation follow the documented Python behavior (accept booleans) or the std.jsonnet implementation (reject booleans)?

Question

Which is the intended behavior?

  • (A) The documentation is correct — std.format should follow Python's rules and accept booleans for numeric codes (meaning std.jsonnet has a bug)
  • (B) The implementation is correct — std.format should reject booleans for numeric codes (meaning the documentation should be updated to remove the "follows Python" statement)

Context

This was discovered in sjsonnet where we initially implemented option (A) (following Python), then reverted to match std.jsonnet's behavior. See: https://github.com/databricks/sjsonnet/pull/1016

Dominant language
Jsonnet
Stars
7.6k
Forks
475
PR merge metrics
No merged PRs in 30d

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

More from google/jsonnet

All issues in google/jsonnet

Similar issues

More Compilers issues

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.