Skip to main content
Advertisement

1.4 Hello World

3 Ways to Run JavaScript

There are three main ways to run JavaScript code.


Method 1: Inline Script

Write <script> tags directly inside an HTML file.

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Hello World</title>
</head>
<body>
<h1 id="greeting">Hello!</h1>

<script>
// Inline JavaScript
console.log("Hello, World!");

// DOM manipulation
const h1 = document.getElementById('greeting');
h1.textContent = 'Hello, JavaScript!';
h1.style.color = 'blue';
</script>
</body>
</html>

Pros: Quick testing without separate files Cons: HTML becomes complex with long code, no caching


Method 2: External Script File

Separate JavaScript code into its own .js file.

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Hello World</title>
</head>
<body>
<h1 id="greeting">Hello!</h1>
<button id="btn">Click me</button>

<!-- Load external script -->
<script src="app.js" defer></script>
</body>
</html>
// app.js
console.log("External script loaded!");

const greeting = document.getElementById('greeting');
const btn = document.getElementById('btn');

btn.addEventListener('click', () => {
greeting.textContent = 'Button clicked!';
});

Pros: Code separation, browser caching, reusable Cons: Additional HTTP request (mitigated by caching)


Method 3: Run with Node.js

Execute with the node command in terminal.

// hello.js
console.log("Hello, World!");
console.log("Node.js version:", process.version);

const name = "JavaScript";
console.log(`Hello, ${name}!`);
# Run
node hello.js

# Output
# Hello, World!
# Node.js version: v20.11.0
# Hello, JavaScript!

<script> Tag Position and defer/async

The position and attributes of <script> tags significantly affect page loading performance.

<head>
<!-- Problem: HTML parsing stops, downloads/executes script, then resumes -->
<!-- DOM not ready yet, so document.getElementById returns null -->
<script src="app.js"></script>
</head>

Just before </body> (Traditional method)

<body>
<!-- HTML content -->
<h1>Hello</h1>

<!-- Runs after DOM is ready -->
<script src="app.js"></script>
</body>
<head>
<!-- Downloads in parallel with HTML parsing, executes after HTML parsing completes -->
<!-- Executes just before DOMContentLoaded event -->
<script src="app.js" defer></script>
</head>
  • Doesn't block HTML parsing
  • Order guaranteed for multiple scripts
  • Runs before DOMContentLoaded event

async attribute

<head>
<!-- Downloads in parallel, executes immediately when done (pauses parsing) -->
<script src="analytics.js" async></script>
</head>
  • Executes immediately when download completes (briefly pauses HTML parsing)
  • Order not guaranteed for multiple scripts
  • Best for independent scripts that don't depend on other scripts/DOM

Complete console Methods Guide

console.log('Regular message');
console.info('Info message');
console.warn('Warning message');
console.error('Error message');
console.debug('Debug message');

// Styled output (browser)
console.log('%cStyled text', 'color: blue; font-size: 20px; font-weight: bold');

// Table display
const users = [
{ id: 1, name: 'Alice', score: 85 },
{ id: 2, name: 'Bob', score: 92 },
];
console.table(users);

// Time measurement
console.time('sort time');
const arr = Array.from({ length: 100000 }, () => Math.random());
arr.sort((a, b) => a - b);
console.timeEnd('sort time');

// Grouping
console.group('User Processing');
console.log('Validating name...');
console.log('Validating email...');
console.groupEnd();

// Conditional output
console.assert(1 === 2, '1 and 2 are different');

Hello World with ES Modules

// greet.js
export function greet(name) {
return `Hello, ${name}!`;
}

export const DEFAULT_NAME = 'World';
// main.js
import { greet, DEFAULT_NAME } from './greet.js';

console.log(greet(DEFAULT_NAME)); // Hello, World!
console.log(greet('JavaScript')); // Hello, JavaScript!
<!-- index.html - type="module" required -->
<script type="module" src="main.js"></script>

Pro Tips

Use the Debugger Instead of console.log

// Instead of this
console.log('Value:', someComplexObject);

// This is better: set breakpoint with debugger keyword
debugger; // Execution pauses here when DevTools is open

Remove console in Production

// vite.config.js
export default {
build: {
minify: 'terser',
terserOptions: {
compress: {
drop_console: true, // Remove console.* in production
drop_debugger: true,
},
},
},
};
Advertisement