dx-spec icon indicating copy to clipboard operation
dx-spec copied to clipboard

Type syntax

Open tmcw opened this issue 7 years ago • 2 comments

There are essentially 3 type syntaxes at play:

  • JSDoc
  • TypeScript
  • Flow

documentation.js supports JSDoc and Flow, but as we've painfully discovered, JSDoc and Flow are very different. The ideal solution here would be:

  • No new type syntax
  • Wide range of supported types
  • Consistent meaning even in codebases with more than one type of types.

I think that one good approach is:

  • In Flow files, interpret 'documentation types' as Flow syntax, and in TypeScript, the same. In normal javascript files, the default should be Flow.
  • Drop JSDoc support. It has no value-add.

tmcw avatar Sep 28 '17 03:09 tmcw

It's probably easiest just to copy the basic jsdoc structure. I would make all the tags match Flow/TypeScript as much as possible, and the type syntax should be identical to Flow/TS.

/**
 * A function.
 * @typeParam T {Object} description
 * @param value {number | T} description
 * @return {T} description
 */
function method(value) {
  // ...
}

Then it's just a question for how to create things like type aliases, namespaces, and enums:

type Foo = number;

namespace Bar {
  export function fn() {}
}

enum a {
  // ...
}

Also, the type syntax for objects can get a bit weird:

It's currently like this:

/**
 * A function.
 * @param options {Object} description
 * @param options.foo {number} description
 * @param options.bar {string} description
 */

You could make it like Flow/TS:

/**
 * A function.
 * @param options {{ foo: number, bar: string }} description
 */

But then how do you document the individual properties, you'd immediately need to create a type alias of some sort.

There's always the possibility to use Flow's inline comment type syntax:

// description
function method(options /*: { foo: number, bar: string } */) {...}

/*::
// description
type Options = {
  // description
  foo: number,
  // description
  bar: string,
};
*/

// description
function method(options /*: Options */) {...}

The win you'd get there is that you'd have a type checker ready to validate these types, existing documentation and community, and it'd be easier to move to Flow or TypeScript from this syntax than from JSDocs.

That being said, a lot of people don't really like this syntax and might not like it over the jsdocs-style syntax.

jamiebuilds avatar Oct 12 '17 23:10 jamiebuilds

I think another feature of the ideal solution would be that, when documenting flow or typescript code, you don't have to explicitly write type names in documentation comments when they're available from the type system. E.g.:

/**
 * @param x I shouldn't have to write {number} here.
 */
function method(x: number) {
}

anandthakker avatar Oct 13 '17 12:10 anandthakker