Nixify and start frontend update
This commit is contained in:
139
frontend/src/js/api.ts
Normal file
139
frontend/src/js/api.ts
Normal file
@@ -0,0 +1,139 @@
|
||||
import { randUserName, randPastDate, randIp, randPassword, randUuid, randNumber } from '@ngneat/falso';
|
||||
|
||||
export interface LoginAttempt {
|
||||
readonly date: string;
|
||||
readonly remoteIP: string;
|
||||
readonly username: string;
|
||||
readonly password: string;
|
||||
readonly sshClientVersion: string;
|
||||
readonly connectionUUID: string;
|
||||
readonly country: string;
|
||||
}
|
||||
|
||||
export interface TotalStats {
|
||||
readonly password: number;
|
||||
readonly username: number;
|
||||
readonly ip: number;
|
||||
readonly country: number;
|
||||
readonly attempts: number;
|
||||
}
|
||||
|
||||
export interface StatsResult {
|
||||
name: string;
|
||||
count: number;
|
||||
}
|
||||
|
||||
export interface ApiaryAPI {
|
||||
live(fn: (a: LoginAttempt) => void): void;
|
||||
stats(statsType: string, limit: number): Promise<StatsResult[]>;
|
||||
query(queryType: string, query: string): Promise<LoginAttempt[]>;
|
||||
totals(): Promise<TotalStats>;
|
||||
}
|
||||
|
||||
function fakeLoginAttempt(): LoginAttempt {
|
||||
return {
|
||||
date: randPastDate().toISOString(),
|
||||
remoteIP: randIp().toString(),
|
||||
username: randUserName().toString(),
|
||||
password: randPassword().toString(),
|
||||
sshClientVersion: '1.0',
|
||||
connectionUUID: randUuid().toString(),
|
||||
country: 'NO'
|
||||
}
|
||||
}
|
||||
|
||||
export class DummyApiaryAPIClient implements ApiaryAPI {
|
||||
live(fn: (a: LoginAttempt) => void): () => void {
|
||||
const interval = setInterval(() => {
|
||||
let a = fakeLoginAttempt();
|
||||
fn(a);
|
||||
}, 1000);
|
||||
|
||||
return () => { clearInterval(interval) }
|
||||
}
|
||||
async stats(_type: string, limit: number): Promise<StatsResult[]> {
|
||||
const stats = Array.from({ length: limit }, () => {
|
||||
return { name: randUserName().toString(), count: randNumber().valueOf() }
|
||||
});
|
||||
return Promise.resolve(stats);
|
||||
}
|
||||
async query(_type: string, _query: string): Promise<LoginAttempt[]> {
|
||||
const attempts = Array.from({ length: 10 }, () => {
|
||||
return fakeLoginAttempt();
|
||||
})
|
||||
return Promise.resolve(attempts);
|
||||
}
|
||||
|
||||
async totals(): Promise<TotalStats> {
|
||||
return Promise.resolve({ password: 1, username: 1, ip: 1, country: 1, attempts: 1 })
|
||||
}
|
||||
}
|
||||
|
||||
export class ApiaryAPIClient implements ApiaryAPI {
|
||||
live(fn: (a: LoginAttempt) => void): () => void {
|
||||
const es = new EventSource('/api/stream');
|
||||
const updateFn = (ev: MessageEvent<string>) => {
|
||||
const attempt: LoginAttempt = JSON.parse(ev.data);
|
||||
fn(attempt);
|
||||
};
|
||||
es.addEventListener('message', updateFn)
|
||||
|
||||
return () => {
|
||||
es.removeEventListener('message', updateFn);
|
||||
es.close();
|
||||
}
|
||||
}
|
||||
async stats(statsType: string, limit: number): Promise<StatsResult[]> {
|
||||
const resp = await fetch(`/api/stats?type=${statsType}&limit=${limit}`)
|
||||
if (!resp.ok) {
|
||||
throw new Error('Failed to fetch query')
|
||||
}
|
||||
const data: StatsResult[] | null = await resp.json()
|
||||
if (!data) {
|
||||
return []
|
||||
}
|
||||
return data
|
||||
}
|
||||
async query(queryType: string, query: string): Promise<LoginAttempt[]> {
|
||||
const resp = await fetch(`/api/query?type=${queryType}&query=${query}`)
|
||||
if (!resp.ok) {
|
||||
throw new Error('Failed to fetch query')
|
||||
}
|
||||
const data: LoginAttempt[] = await resp.json()
|
||||
|
||||
return data
|
||||
}
|
||||
|
||||
async totals(): Promise<TotalStats> {
|
||||
let password: number = -1
|
||||
let username: number = -1
|
||||
let ip: number = -1
|
||||
let attempts: number = -1
|
||||
let country: number = -1
|
||||
|
||||
const resp = await fetch('/api/stats?type=total')
|
||||
const data: Array<StatsResult> = await resp.json()
|
||||
|
||||
for (const stat of data) {
|
||||
switch (stat.name) {
|
||||
case 'UniquePasswords':
|
||||
password = stat.count
|
||||
break
|
||||
case 'UniqueUsernames':
|
||||
username = stat.count
|
||||
break
|
||||
case 'UniqueIPs':
|
||||
ip = stat.count
|
||||
break
|
||||
case 'TotalLoginAttempts':
|
||||
attempts = stat.count
|
||||
break
|
||||
case 'UniqueCountries':
|
||||
country = stat.count
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return { password, username, ip, attempts, country }
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user