const crypto = require('crypto');
const fs = require('fs');
const path = require('path');
// Generate a key pair for this example
const { privateKey, publicKey } = crypto.generateKeyPairSync('rsa', {
modulusLength: 2048,
publicKeyEncoding: {
type: 'spki',
format: 'pem'
},
privateKeyEncoding: {
type: 'pkcs8',
format: 'pem'
}
});
// File to sign and verify
const filePath = 'example_file.txt';
const signaturePath = 'example_file.sig';
// Function to sign a file
function signFile(filePath, privateKey, algorithm = 'SHA256') {
return new Promise((resolve, reject) => {
const sign = crypto.createSign(algorithm);
const stream = fs.createReadStream(filePath);
stream.on('data', (data) => {
sign.update(data);
});
stream.on('end', () => {
const signature = sign.sign(privateKey, 'hex');
resolve(signature);
});
stream.on('error', (error) => {
reject(error);
});
});
}
// Function to verify a file
function verifyFile(filePath, publicKey, signature, algorithm = 'SHA256') {
return new Promise((resolve, reject) => {
const verify = crypto.createVerify(algorithm);
const stream = fs.createReadStream(filePath);
stream.on('data', (data) => {
verify.update(data);
});
stream.on('end', () => {
const isValid = verify.verify(publicKey, signature, 'hex');
resolve(isValid);
});
stream.on('error', (error) => {
reject(error);
});
});
}
// Create a test file if it doesn't exist
if (!fs.existsSync(filePath)) {
const content = 'This is a test file for signature verification.\n'.repeat(100);
fs.writeFileSync(filePath, content);
console.log(`Created test file: ${filePath}`);
}
// Main function
async function main() {
try {
// Sign the file
console.log('Signing file...');
const signature = await signFile(filePath, privateKey);
// Save the signature for later verification
fs.writeFileSync(signaturePath, signature);
console.log(`Signature saved to: ${signaturePath}`);
// Verify the file with the saved signature
console.log('Verifying file...');
const isValid = await verifyFile(filePath, publicKey, signature);
console.log('Is signature valid?', isValid);
// Tamper with the file and try to verify again
console.log('\nTampering with file...');
fs.appendFileSync(filePath, '\nThis line was added after signing!');
try {
const isTamperedValid = await verifyFile(filePath, publicKey, signature);
console.log('Is tampered file valid?', isTamperedValid);
} catch (error) {
console.log('Error verifying tampered file:', error.message);
}
} catch (error) {
console.error('Error:', error.message);
}
}
// Run the example
main();