JavaScript, a language of freedom, where creativity knows no bounds 😆
Let's channel this creativity with JSDoc for clarity and guidance 🤓
# CHAPTER 1
Facilitating Onboarding
Accelerates the onboarding process for new developers, enabling them to grasp the functionality and architecture of large-scale JavaScript projects rapidly.
Enhancing Team Collaboration
Fosters better understanding and collaboration within development teams.
Sustainable Development
Supports long-term project sustainability by making the codebase more navigable and easier to maintain, even as team members change over time.
# CHAPTER 1
// Normal Javascript Comment 1
/* Normal Javascript Comment 2 */
/**
JSDoc containing two asterisks
*/
# PRESENTING CODE
# CHAPTER 1
@
and are followed by a newline, except for the last block tag in a comment.@
and are enclosed in curly braces {}
. Use a backslash \
to escape curly braces within the tag text. Newlines are not required after inline tags./**
* @type {number}
*/
var FOO = 1
/**
* @const {number}
*/
const FOO = 1
/**
* @type {Array<string>}
*/
const colours = ['red', 'blue', 'green']
# JSDoc cheatsheet
/**
* This is a function.
*
* @param {string} n - A string param
* @param {string} [o] - A optional string param
* @param {string} [d=DefaultValue] - A optional string param
* @return {string} A good string
*
* @example
*
* foo('hello')
*/
function foo(n, o, d) {
return n
}
# JSDoc cheatsheet
# JSDoc cheatsheet
/**
* A song
* @typedef {Object} Song
* @property {string} title - The title
* @property {string} artist - The artist
* @property {number} year - The year
*/
/**
* Plays a song
* @param {Song} song - The {@link Song} to be played
*/
function play(song) {}
# JSDoc cheatsheet
/**
* A song
* @typedef {{
* title: string,
* artist: string,
* year: number
* }} Song
*/
/**
* Plays a song
* @param {Song} song - The {@link Song} to be played
*/
function play(song) {}
# JSDoc cheatsheet
/**
* @typedef {import('./Foo').default} Bar
*/
/**
* @param {Bar} x
*/
function test(x) {}
# JSDoc cheatsheet
/**
* Adds two numbers
* @param {number} a - The first number
* @param {number} b - The second number
*/
function add(a, b) {
return a + b;
}
/**
* @param {number} a - The first number
* @param {number} b - The second number
* @description Adds two numbers
*/
function add(a, b) {
return a + b;
}
# JSDoc cheatsheet
// The @param tag is used to specify the name (required),
// type, and description of a function's parameter.
// The syntax is:
// @param {Type} Name - Description.
// The parameter type can be a native JavaScript type,
// and expressions can be used to indicate if a parameter
// is non-nullable or an array.
/**
* Greets a user
* @param {string} name - The user's name
*/
function sayHello(name) {
alert('Hello ' + name);
}
# JSDoc cheatsheet
// The @returns tag is used to describe
// the value that a function returns.
//
// The syntax is:
// @returns {Type} Description.
/**
* Adds two numbers
* @param {number} a - The first number
* @param {number} b - The second number
* @returns {number} The sum of numbers a and b
*/
function add(a, b) {
return a + b;
}
# JSDoc cheatsheet
/**
* Divides two numbers
* @param {number} a - The numerator
* @param {number} b - The denominator, must not be 0
* @throws {Error} If the denominator is 0,
* an error is thrown indicating division by zero
* is not allowed.
* @returns {number} The result of the division a / b
*/
function divide(a, b) {
if (b === 0) {
throw new Error('Division by zero is not allowed.');
}
return a / b;
}
# JSDoc cheatsheet
/**
* Fetches data from a URL asynchronously
* @async
* @param {string} url - The URL to fetch data from
* @returns {Promise<Object>} A promise resolving to
* the data fetched from the URL
*/
async function fetchData(url) {
const response = await fetch(url);
return response.json();
}
# JSDoc cheatsheet
/**
* Possible title for this talk
* @type {string}
* @author Exiliot [exiliot@example.com]
*/
const talkTitle = "Demystifying JSDoc"
# JSDoc cheatsheet
/**
* Sums of the square of two numbers a**2 + b**2
* @example <caption>How to use the sumSquares function</caption>
* // returns 13
* sumSquares(2, 3)
* @example
* // returns 41
* sumSquares(4, 5)
* // Typing the function
* @param {number} a - The first number
* @param {number} b - The second number
* @returns {Number} Returns the sum of the squares
* */
const sumSquares = function(a, b){
return a**2 + b**2
}
# JSDoc cheatsheet
/**
* @version 1.0.0
* @type {number}
**/
const meaningOfLife = 42
# JSDoc cheatsheet
/**
* How to use the link tags
* Also see the {@link https://jsdoc.app/tags-inline-link.html official docs} for more information
* @tutorial getting-started
**/
function myFunction (){
}
# JSDoc cheatsheet
/**
* Represents a greeting component that displays a welcome message.
*
* @component
* @param {Object} props - The properties passed to the component.
* @param {string} props.name - The name of the person to greet.
* @returns {JSX.Element} A greeting message wrapped in a <div>.
*/
const Greeting = ({ name }) => <div>Hello, {name}!</div>;
# JSDoc cheatsheet
import React from 'react';
/**
* @typedef Props
* @prop {React.ReactNode} title
* @prop {React.ReactNode} [desc]
* @prop {React.ReactNode} [selectFlightPrompt]
* @prop {()=>void} [onLogin]
*/
/**
* @param {Props} props
*/
const InflowHeader = ({ title, desc, selectFlightPrompt, onLogin }) => (
...
);
# JSDoc cheatsheet
/**
* @typedef Props
* @prop {any} resource
*/
/**
* @typedef State
* @prop {boolean} isDrawerOpen
*/
# JSDoc cheatsheet
/**
* @extends Component<Props, State>
*/
class SampleContainer extends Component {
/** @type {State} */
state = {
isDrawerOpen: false,
};
constructor(props){
super(props);
}
render() {
return <>...</>;
}
}
# JSDoc cheatsheet
/**
* Custom hook for managing and toggling boolean state.
*
* @returns {[boolean, () => void]} Current state and
* a function to toggle the state.
*
* @example
* const [isOpen, toggleOpen] = useToggle(false);
*/
const useToggle = (initialState = false) => {
const [state, setState] = useState(initialState);
const toggle = () => setState(!state);
return [state, toggle];
};
# JSDoc cheatsheet
/**
* Custom hook for managing and toggling boolean state.
*
* @typedef {Object} HookResult - The result of the hook.
* @property {boolean} state - The current boolean state.
* @property {Function} toggle - Function to toggle the
* state.
*
* @param {boolean} [initialState=false] - The initial state.
* @returns {HookResult} Current state and a function to
* toggle the state.
*/
const useToggle = (initialState = false) => {
const [state, setState] = useState(initialState);
const toggle = () => setState(!state);
return [state, toggle];
};
# JSDoc cheatsheet
# JSDOC + IntelliSense
# JSDOC + IntelliSense
JSDoc and TypeScript both solve the problems with writing and maintaining plain JavaScript code.
However, they used different approaches, which have their benefits and drawbacks.
Flexibility & Compatability
JSDoc being just JS comments, means it could be added to any JS codebase regardless of the language version, and it is not tied to a compiler like TypeScript is.
Code Annotation
JSDoc could be used for more than just type checking. It could be used to add more documentation, describe how functions work, and generate a documentationwebsite, all providing value to enhance code maintainability and understanding.
No Compilation Step
TypeScript requires compilation to change the TypeScript code into JS so the engine can understand it, while JSDoc does not require any other step as they are just "comments", which is supported feature of JS itself.
# CHAPTER 2
Stronger Static Typing
TypeScript provides a strong model for types and catches these errors at compile time. Unlike JSDoc, where these typing end in the code itself and isn't enforced.
Type Inference
TypeScript can infer the type from its value. This helps reduce explicit type annotations and makes the codebase less verbose.
Transpilation
TypeScript can adopt the latest and future features of the JS language with its polyfill feature. It effectively transpiles these codes down to understandable versions for browsers that would not have support for the features yet.
# CHAPTER 2
// TypeScript
function stringsStringStrings(p1: string, p2?: string, p3?: string, p4 = "test"): string {
// ...
}
// JSDoc
/**
* @param {string} p1
* @param {string=} p2
* @param {string} [p3]
* @param {string} [p4="test"]
* @return {string}
*/
function stringsStringStrings(p1, p2, p3, p4) {
// ...
}
# PRESENTING CODE
const thing = document.querySelector('#my-element')
addStuff(thing); // Error: type undefined is not assignable to type Thing
// or
const data = await fetch('https://my-url.dev');
return data.results // error: data is possibly undefined
// TypeScript
const thing = document.querySelector('#my-element')
addStuff(thing!); // although probably don't do this
addStuff(thing as Thing) // still not great but it works
// JSDoc
const thing = document.querySelector('#my-element')
addStuff(
// thing is definitely defined by this point, see line 120
// @ts-ignore-next-line
thing
);
# PRESENTING CODE
# PRESENTING CODE
# PRESENTING CODE
# PRESENTING CODE