Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 7 additions & 3 deletions apps/api/src/app/app.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
Patch,
Post,
Put,
Query,
Res,
UseInterceptors,
} from '@nestjs/common';
Expand Down Expand Up @@ -59,7 +60,10 @@ export class AppController {
@ApiResponse({ status: 200, description: 'Result Report for All the Health Check Services' })
async checkHealth() {
return this.healthCheckService.check([
async () => this.http.pingCheck('RabbitMQ', 'http://localhost:15672/'),
async () => this.http.pingCheck(
"RabbitMQ",
this.configService.get("RABBITMQ_HEALTH_URL")
),
async () => this.http.pingCheck('Basic Check', 'http://localhost:3333/api'),
async () => this.redisIndicator.checkHealth('Redis', { type: 'redis', client: this.redis, timeout: 500 }),
async () => this.prismaIndicator.isHealthy('Db'),
Expand Down Expand Up @@ -90,8 +94,8 @@ export class AppController {
@Get('/:hashid')
@ApiOperation({ summary: 'Redirect Links' })
@ApiResponse({ status: 301, description: 'will be redirected to the specified link'})
async redirect(@Param('hashid') hashid: string, @Res() res) {
const reRouteURL: string = await this.appService.redirect(hashid);
async redirect(@Param('hashid') hashid: string, @Query() queryParams: Record<string, string | string[]>, @Res() res) {
const reRouteURL: string = await this.appService.redirect(hashid, queryParams);
this.clickServiceClient
.send('onClick', {
hashid: hashid,
Expand Down
27 changes: 27 additions & 0 deletions apps/api/src/app/app.service.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,11 @@ import { RedisService } from 'nestjs-redis';
import { AppService } from './app.service';
import { PrismaService } from './prisma.service';
import { TelemetryService } from './telemetry/telemetry.service';
import { Link } from './app.interface';

describe('AppService', () => {
let service: AppService;
let prisma: PrismaService;
let mockRedisSet;

const mockRedis = {
Expand Down Expand Up @@ -90,11 +92,36 @@ describe('AppService', () => {
.compile();

service = module.get<AppService>(AppService);
prisma = module.get<PrismaService>(PrismaService);
});

it('should be defined', () => {
expect(service).toBeDefined();
});

it("should return url with query params appended to it", async () => {
const url = "https://google.com";
const hashId = "1";
const queryParams = {
hello: "1234",
world: "5678",
};

const link: Link = {
id: "1",
user: null,
tags: [],
clicks: 0,
url: url,
hashid: +hashId,
project: null,
customHashId: null,
};

prisma.link.findMany = jest.fn().mockResolvedValueOnce([link]);

expect(await service.redirect(hashId, queryParams)).toBe(
`${url}?hello=1234&world=5678`
);
});
});
31 changes: 25 additions & 6 deletions apps/api/src/app/app.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ export class AppService {
});
}

async redirect(hashid: string): Promise<string> {
async redirect(hashid: string, queryParams?: Record<string, string | string[]>): Promise<string> {
return this.prisma.link.findMany({
where: {
OR: [
Expand All @@ -122,20 +122,39 @@ export class AppService {
take: 1
})
.then(response => {
const url = response[0].url
let url = response[0].url
const params = response[0].params
const ret = [];

this.updateClicks(response[0].hashid.toString());

if(params == null){
return url;
}else {
if(params != null){
Object.keys(params).forEach(function(d) {
ret.push(encodeURIComponent(d) + '=' + encodeURIComponent(params[d]));
})
return `${url}?${ret.join('&')}` || '';
url = `${url}?${ret.join('&')}` || '';
}

if (queryParams && Object.keys(queryParams).length) {
if (params == null) {
url += "?";
} else {
url += "&";
}
const qparams = [];
Object.keys(queryParams).forEach((d: string) => {
if (Array.isArray(queryParams[d])) {
(queryParams[d] as string[]).forEach(val => {
qparams.push(encodeURIComponent(d) + "=" + encodeURIComponent(val));
});
} else {
qparams.push(encodeURIComponent(d) + "=" + encodeURIComponent(queryParams[d] as string));
}
});
url += qparams.join("&") || "";
}

return url;
})
.catch(err => {
this.telemetryService.sendEvent(this.configService.get<string>('POSTHOG_DISTINCT_KEY'), "Exception in getLinkFromHashIdOrCustomHashId query", {error: err.message})
Expand Down
4 changes: 3 additions & 1 deletion sample.env
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,13 @@ POSTHOG_BATCH_SIZE=20
POSTHOG_FLUSH_INTERVAL=10000
CLICK_BACKUP_CRON='* * 1 * * *'

RABBITMQ_HEALTH_URL=http://localhost:15672/

# This was inserted by `prisma init`:
# Environment variables declared in this file are automatically made available to Prisma.
# See the documentation for more detail: https://pris.ly/d/prisma-schema#accessing-environment-variables-from-the-schema

# Prisma supports the native connection string format for PostgreSQL, MySQL, SQLite, SQL Server, MongoDB and CockroachDB (Preview).
# See the documentation for all the connection string options: https://pris.ly/d/connection-strings

DATABASE_URL="postgresql://postgres:yoursupersecret@localhost:5432/shortdb?schema=public"
DATABASE_URL="postgresql://postgres:yoursupersecret@localhost:5432/shortdb?schema=public"