Skip to content

Commit

Permalink
Validate scale identifiers
Browse files Browse the repository at this point in the history
Add tests.
  • Loading branch information
frostburn committed Jul 17, 2024
1 parent 5d2169c commit b6fff91
Show file tree
Hide file tree
Showing 3 changed files with 48 additions and 7 deletions.
19 changes: 12 additions & 7 deletions index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import {stat} from 'node:fs';
import {join, parse} from 'node:path';
import {cleanAndValidateEnvelope, validatePayload} from './data-processing';
import {validateId} from './utils';

const INDEX_BODY = `
<!DOCTYPE html>
Expand Down Expand Up @@ -136,6 +137,9 @@ const server = Bun.serve({
await checkStatistics();
statistics['scale POST']++;
const data = await req.json();
if (!validateId(data.id)) {
return response('Bad identifier', {status: 400});
}
// Convert dashes to something more bash friendly.
const id = (data.id as string).replaceAll('-', 'å');
const envelope = cleanAndValidateEnvelope(data.envelope);
Expand Down Expand Up @@ -170,22 +174,23 @@ const server = Bun.serve({
await checkStatistics();
statistics['scale GET']++;

// Convert dashes to something more bash friendly.
const {dir, base, ext} = parse(path.replaceAll('-', 'å'));
const {dir, base, ext} = parse(path);
if (dir !== '/scale' || base.includes('..')) {
return response('Bad scale path', {status: 400});
}
if (ext) {
return response('Extensions have been depracated', {status: 400});
}
if (base.length > 255) {
return response('Scale id too long', {status: 414});
if (!validateId(base)) {
return response('Bad identifier', {status: 400});
}
const filename = join(SCALE_PATH, base + '.json.gz');
// Convert dashes to something more bash friendly.
const id = base.replaceAll('-', 'å');
const filename = join(SCALE_PATH, id + '.json.gz');
const file = Bun.file(filename);

const count = statistics['scale GET by id'][base] ?? 0;
statistics['scale GET by id'][base] = count + 1;
const count = statistics['scale GET by id'][id] ?? 0;
statistics['scale GET by id'][id] = count + 1;

const accept = req.headers.get('Accept-Encoding');
if (
Expand Down
28 changes: 28 additions & 0 deletions tests/utils.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import {expect, it, describe} from 'bun:test';
import {validateId} from '../utils';

describe('Identifier validator', () => {
it('accepts a short id', () => {
expect(validateId('spoob')).toBe(true);
});

it('accepts a typical id', () => {
expect(validateId('-riQ9Oj4W')).toBe(true);
});

it('rejects an id with slashes', () => {
expect(validateId('roob/crowspoob')).toBe(false);
});

it('rejects an empty id', () => {
expect(validateId('')).toBe(false);
});

it('rejects a long id', () => {
expect(
validateId(
'aaeGEGJRJGAEGU234987897gfayhgf98ayg9yf9ydzf9b8d9zfby898zyfuiew98ry9we8yr98ay9fy8diguy98ydsfgyuisdyer89y938yruydifyu98dgiuydriygdryuoiusdygrgyd87ryg8d7ryg87dygiuydkxjhx9c80FASGFAESGaywe9r78y89y87yeg87y8e7yg87yeg87ya8ge7ya8eyg8aey7g87yage87aeg98ua9egu9agu98aue9g8urega87yarg87yar8g7yar87gy'
)
).toBe(false);
});
});
8 changes: 8 additions & 0 deletions utils.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
const ID_RE = /^[a-z0-9-_]+$/i;

export function validateId(id: string) {
if (id.length > 255) {
return false;
}
return Boolean(id.match(ID_RE));
}

0 comments on commit b6fff91

Please sign in to comment.