This content originally appeared on DEV Community and was authored by Manoj Gohel
PASETO (Platform-Agnostic Security Tokens) is a modern alternative to JWT (JSON Web Tokens) that focuses on security and simplicity. Here’s an example of how to use PASETO for token-based authentication in JavaScript.
Setup
-
Install the necessary libraries:
- Use the
paseto.js
library for PASETO. - For simplicity, we’ll use
Node.js
andExpress
to demonstrate a server-side implementation.
- Use the
npm install paseto express body-parser
- Create the server:
// server.js
const express = require('express');
const bodyParser = require('body-parser');
const { V4 } = require('paseto');
const { generateKeyPair } = require('paseto/dist/lib/crypto/pair');
const app = express();
const port = 3000;
app.use(bodyParser.json());
let privateKey;
let publicKey;
(async () => {
const keyPair = await generateKeyPair('v4.public');
privateKey = keyPair.secretKey;
publicKey = keyPair.publicKey;
})();
// Middleware to verify PASETO token
const authenticateToken = async (req, res, next) => {
const token = req.header('Authorization').replace('Bearer ', '');
try {
const payload = await V4.verify(token, publicKey);
req.user = payload;
next();
} catch (err) {
res.status(401).send('Unauthorized');
}
};
// Login route to generate PASETO token
app.post('/login', async (req, res) => {
const { username, password } = req.body;
// Replace with your own user verification logic
if (username === 'admin' && password === 'password') {
const token = await V4.sign({ username }, privateKey, { expiresIn: '1h' });
res.json({ token });
} else {
res.status(401).send('Invalid credentials');
}
});
// Protected route
app.get('/protected', authenticateToken, (req, res) => {
res.json({ message: 'This is a protected route', user: req.user });
});
app.listen(port, () => {
console.log(`Server running at http://localhost:${port}`);
});
Explanation
-
Key Pair Generation:
- The server generates a key pair for signing and verifying PASETO tokens using
generateKeyPair('v4.public')
.
- The server generates a key pair for signing and verifying PASETO tokens using
-
Login Route:
- The
/login
route verifies the username and password. - If valid, it generates a PASETO token using
V4.sign
and sends it to the client.
- The
-
Authentication Middleware:
- The
authenticateToken
middleware extracts the token from theAuthorization
header. - It verifies the token using
V4.verify
and attaches the payload to thereq.user
object.
- The
-
Protected Route:
- The
/protected
route uses theauthenticateToken
middleware to ensure only authenticated users can access it.
- The
Client-Side Example
Here is a simple client-side example using fetch:
<!DOCTYPE html>
<html>
<head>
<title>PASETO Authentication</title>
</head>
<body>
<h1>PASETO Authentication Example</h1>
<button id="loginButton">Login</button>
<button id="protectedButton">Access Protected Route</button>
<script>
document.getElementById('loginButton').addEventListener('click', async () => {
const response = await fetch('http://localhost:3000/login', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ username: 'admin', password: 'password' })
});
const data = await response.json();
localStorage.setItem('token', data.token);
alert('Logged in and token stored in local storage');
});
document.getElementById('protectedButton').addEventListener('click', async () => {
const token = localStorage.getItem('token');
const response = await fetch('http://localhost:3000/protected', {
method: 'GET',
headers: {
'Authorization': `Bearer ${token}`
}
});
const data = await response.json();
alert(JSON.stringify(data));
});
</script>
</body>
</html>
Explanation
-
Login Button:
- Sends a POST request to the
/login
endpoint with the username and password. - Stores the received token in
localStorage
.
- Sends a POST request to the
-
Protected Button:
- Sends a GET request to the
/protected
endpoint with the token in theAuthorization
header. - Displays the response data.
- Sends a GET request to the
This example demonstrates how to use PASETO for token-based authentication in a simple Node.js application with client-side interaction.
This content originally appeared on DEV Community and was authored by Manoj Gohel