Skip to content
This repository has been archived by the owner on May 15, 2024. It is now read-only.

Commit

Permalink
feat(api): add NextJS 'GET' API endpoint for '/api/queries/topBlocked'
Browse files Browse the repository at this point in the history
  ## what
  - add 'GET' API endpoint for '/api/queries/topBlocked'

  ## how
  - Fetch data from upstream Pi-hole API

  ## why
  - This API endpoint will be used to fetch 'top blocked queries' data using Redux Toolkit Query

  ## where
  - ./src/pages/api/queries/topBlocked.ts

  ## usage
  • Loading branch information
Clumsy-Coder committed Aug 20, 2023
1 parent 69387fe commit 847be60
Showing 1 changed file with 97 additions and 0 deletions.
97 changes: 97 additions & 0 deletions src/pages/api/queries/topBlocked.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
import axios from 'axios';
import type { NextApiRequest, NextApiResponse } from 'next';

import { withSessionRoute } from '@lib/AuthSession';
import logger from '@utils/logger';
import { topItems as topItemsUrl } from '@utils/url/upstream';
import { ITopBlockedQueries, ITopItems } from '@utils/url/upstream.types';
import { getTopBlockedQueriesUrl as apiUrl } from '@utils/url/api';

/**
* Error message to return to the Requester
*/
interface ErrorMessage {
message: string;
}

/**
* API endpoint query parameters
*/
export interface IGetRequestData {
/**
* The number of entries to return
*
* @remarks defaults to 10
*/
numEntries?: number;
}

/**
* Summary 'formatted' data to return
*/
export type IGetTopBlockedQueriesResponseData = ITopBlockedQueries;

/**
* GET endpoint for /api/queries/topBlocked
*
* @remarks
* Returns forwarded destinations query data
*
* Must be authenticated
* @param req - HTTP request provided by NextJS
* @param res - HTTP response provided by NextJS
*/
const handleGetTopBlockedQueries = (
req: NextApiRequest,
res: NextApiResponse<IGetTopBlockedQueriesResponseData | ErrorMessage>,
) => {
const getLogger = logger.scope(apiUrl, 'GET');
const { ipAddress, port, password } = req.session.authSession;
const { numEntries = 10 } = req.query as IGetRequestData;

const requestUrl = `http://${ipAddress}:${port}/${topItemsUrl(numEntries)}&auth=${password}`;

axios
.get<ITopItems>(requestUrl)
.then((response) => {
getLogger.info('data obtained from upstream');
getLogger.debug(`data: `, response.data.top_ads);
res.status(200).json(response.data.top_ads);
getLogger.complete(`sending response`);
})
.catch((error) => {
getLogger.error(`error returned when sending HTTP request to '${requestUrl}'`);
res.status(500).json({ message: JSON.stringify(error) });
});
};

/**
* Default method to run when executing this http api endpoint
*
* @remarks
* HTTP API endpoint `/api/queries/topBlocked`
*
* @remarks
* HTTP method allowed: `GET`
*/
const requestHandler = (req: NextApiRequest, res: NextApiResponse) => {
const { method = '' } = req;

// limit which HTTP methods are allowed
switch (method) {
case 'GET': {
handleGetTopBlockedQueries(req, res);
break;
}
default: {
logger.error({
prefix: apiUrl,
message: `invalid HTTP method type '${method}'`,
});
res.setHeader('Allow', ['GET']);
res.status(405).end(`Method ${method} Not Allowed`);
}
}
};

export default withSessionRoute(requestHandler);

0 comments on commit 847be60

Please sign in to comment.