Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

console.json #222

Open
wmelton opened this issue Feb 20, 2023 · 11 comments
Open

console.json #222

wmelton opened this issue Feb 20, 2023 · 11 comments

Comments

@wmelton
Copy link

wmelton commented Feb 20, 2023

The vast majority of data transmission in today's javascript ecosystem happens via JSON serialized objects. For node.js developers, serializing objects to inspect them is a mainstay of iterative debugging.

However, as many, many objects are nested, being able to easily inspect the entire object in the console is cumbersome.

console.log(JSON.stringify(<serializable>, null, 2)) has been coded more times in my career than I ever want to count lol.

Given the fact that JSON is ubiquitous in 2023, that JS is object-based by default (meaning the majority of object structures are JSON-serializable), and that it would just be insanely useful, helpful to developers, I want to propose that the whatwg console standard be extended to include console.json

In an ideal world, calling console.json() would perform a similar duty as console.log(JSON.stringify(<serializable>, null, 2)) but with a lot less syntax.

An argument to pretty print or not would seem reasonable. If for verbosity sake an argument to limit the depth of iteration was desired, that would be a reasonable argument/ask in my mind.

Otherwise this seems like a straight-forward and immensely helpful standard extension, especially for node.js developers.

@terinjokes
Copy link
Collaborator

There is already a similar console.dir, which is specified as logging the first parameter as a generic JavaScript object. The agents I've tested with have a means of copying as JSON.

@wmelton
Copy link
Author

wmelton commented Feb 21, 2023

@terinjokes Yeah console.dir isn't a reasonable solution and its not purpose built for the problem most developers are trying to solve when they want to inspect an object.

Example:

(async () => {
  const deepObject = {
    a: {
      b: {
        c: {
          d: {
            e: {
              f: {
                g: {
                  foo: 'bar',
                  array: [1, 2, 3, 4, 5],
                },
              },
            },
          },
        },
      },
    },
  }
  console.dir(deepObject)
})()

Outputs: { a: { b: { c: [Object] } } } which is the problem. I want to see what's in there.

Of course, you can pass the compact flag as false if pretty print is the problem:

{
  a: {
    b: {
      c: [Object]
    }
  }
}

However, much of the object is still obfuscated. Okay, so console.dir then gives us the depth flag. Well, let's look at that:

// console.dir(deepObject, {compact: false, depth: 4})
{
  a: {
    b: {
      c: {
        d: {
          e: [Object]
        }
      }
    }
  }
}

Boo, still [Object]. Well thats because I didn't specify depth far enough. Sigh. Okay lets guess some more about the right depth:

// console.dir(deepObject, {compact: false, depth: 7})
{
  a: {
    b: {
      c: {
        d: {
          e: {
            f: {
              g: {
                foo: 'bar',
                array: [Array]
              }
            }
          }
        }
      }
    }
  }
}

Bollocks! I can see the lower keys now, but still not the values. Of course, I can try again with another depth that will show what array is, but if array was say an array of nested objects, then I'm just iterating and fighting with console.dir to let me easily inspect this thing 🔥 quickly 🔥

Proposed Improvements in console.json

  • Purpose built. This means developers intuitively know what calling console.json on an object will likely do.

  • depth flag as an optional limiter, rather than an optional expander(as it is in console.dir). By default, console.json would unfurl the entire object like console.log(JSON.stringify(<serializable>)) would.

    • As shown above the depth flag with console.dir is not useful when dealing with data structures you aren't familiar with (perhaps a larger object from an API response). It does not aid in rapid introspection. It results in a frustrating iterative guessing game on the right depth to see the whole object... which is the problem my proposal is trying to solve to begin with.
  • pretty defaults to true for maximum readability.

@terinjokes
Copy link
Collaborator

terinjokes commented Feb 21, 2023

When I run your top example in Firefox, I get the following, which I believe is the requested behavior?

{
  "a": {
    "b": {
      "c": {
        "d": {
          "e": {
            "f": {
              "g": {
                "foo": "bar",
                "array": [
                  1,
                  2,
                  3,
                  4,
                  5
                ]
              }
            }
          }
        }
      }
    }
  }
}

I would expect dir to be the same as what you're asking for with json.

@wmelton
Copy link
Author

wmelton commented Feb 21, 2023

Otherwise this seems like a straight-forward and immensely helpful standard extension, especially for node.js developers.

While it's wonderful that a vendor browser used by 7% of the world does the legwork to expand it automatically, Chrome (77% of global usage) however, does not auto unfurl. They have their own built-in dev tools that make you walk the prototype tree:
image

Additionally, backend js developers are a huge segment of the development community today. Unfortunately, the node.js team will not implement this behavior unless whatwg's standard implements it first, which is why I am here. I opened a PR to implement this in node.js core and they sent me here. The examples I provided are from node, but as mentioned, Chrome does not perform as you showed from FireFox(which again, is only 7% of users globally as of this year).

@terinjokes
Copy link
Collaborator

terinjokes commented Feb 21, 2023

How console methods render is implementation defined. This specification defines dir as rendering a generic Javascript object, and Node.js can certainly (and probably should) implement that as a JSON or JSON-like encoding. But that's their call to make.

@paulirish
Copy link

Browser consoles are interactive, where's node's console emits non-interactive text to stdout..

It does seem like the proposed solution is to work around node's default depth (and lack of interactivity)... I've left a reply on nodejs/node#46689

@wmelton
Copy link
Author

wmelton commented Feb 21, 2023

@paulirish agreed, browser consoles are always going to have vendor specific implementations on this stuff.

I originally opened this discussion as a thread in node.js since browsers weren't really what I had in mind from the start.

I was told by that team to come here, so thats why I'm here lol.

Thanks for commenting on the original thread.

@domfarolino
Copy link
Member

I was told by that team to come here, so thats why I'm here lol.

Unfortunately I don't think there is too much here that's actionable since as Terin mentioned, this is very much implementation-specific territory. That is, if we were to spec console.json, it would be subject to the same implementation-specific liberties that the spec gives for other APIs. Given that I don't see much of a path forward, I might recommend closing this issue.

@wmelton
Copy link
Author

wmelton commented Mar 30, 2023

@domfarolino for me, I still think that it should be considered more significantly.

In 2023, JSON is a first class citizen with a nearly unmatched ubiquity in the web-development world.

While there are of course vendor specific details and implementation-specific liberties in the console spec, console.dir does not achieve the same goal as console.json.

To tackle the browser implementation-specific objection head-on, I would argue that in heavy debug cycles, being able to stringify an object directly to JSON via (console.json(<serializable)) in the developer console would be immensely useful far and above what console.dir achieves because of the interoperability and usability of getting data in to JSON quickly and easily for use in other dev tools.

Further, I would argue that console.json has no implementation-specific considerations or liberties since JSON is well defined by RFC-8259, and, unlike console.dir, the output format is fixed: its a string, as defined by it's RFC.

This simplifies and removes ambiguity about browser-specific implementations since JSON is a string, and since auto-magic object tree structuring in browser UIs generally exists already, there would be no reason for browsers to implement console.json in any other fashion than to print the serializable object to the console in its string form.

The suite of console.* functions are largely utility functions anyhow, meant to help, assist, and improve the developer experience. console.json would bolster that value proposition, improve developer experience, and also provide a pathway for backend js projects (like node) to implement it as well.

Thanks again for your consideration on this topic.

@terinjokes
Copy link
Collaborator

I think this would be better resolved by working with your user-agent to provide the options you want to for console.dir, rather than requiring one specific encoding. I have concerns around serialization and transmission requirements needed in remote debugging scenarios, and console.dir allows agents to use other structures more suitable for their environments (eg, Nyxt might use lists or cons).

@wmelton
Copy link
Author

wmelton commented Jun 9, 2023

@terinjokes On the browser side, I hear ya. The challenge is, the node.js team follows your standard strictly (which is why they sent me here). So this is not an issue I feel necessarily needs to be addressed for browser-based development where use-agent is in play, but about the downstream subscribers to this standard like node.js.

Maybe if you know anyone on the node.js team, you can let them know these types of deviations are anticipated in contexts where we are dealing with a specific applications implementation of the standard?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

4 participants