Skip to content

Commit

Permalink
project start: create server http with endpoint main
Browse files Browse the repository at this point in the history
- create structure of folders
- add contrllers, services, and routes
  • Loading branch information
EdixonAlberto committed Jan 5, 2023
0 parents commit 760917e
Show file tree
Hide file tree
Showing 10 changed files with 594 additions and 0 deletions.
Empty file added .gitignore
Empty file.
8 changes: 8 additions & 0 deletions .vscode/extensions.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"recommendations": [
"denoland.vscode-deno",
"rangav.vscode-thunder-client",
"dzannotti.vscode-babel-coloring",
"xabikos.javascriptsnippets"
]
}
9 changes: 9 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"deno.enable": true,
"editor.formatOnSave": true,
"[typescript]": {
"editor.defaultFormatter": "denoland.vscode-deno"
},
"deno.config": "./deno.jsonc",
"discord.enabled": true
}
19 changes: 19 additions & 0 deletions deno.jsonc
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
{
"tasks": {
"dev": "deno run --watch --allow-net src/main.ts"
},
"fmt": {
"files": {
"include": [
"src/"
]
},
"options": {
"useTabs": true,
"lineWidth": 120,
"indentWidth": 2,
"singleQuote": true,
"proseWrap": "preserve"
}
}
}
427 changes: 427 additions & 0 deletions deno.lock

Large diffs are not rendered by default.

65 changes: 65 additions & 0 deletions src/controllers/jobs.controller.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
import { Context } from 'https://deno.land/x/[email protected]/mod.ts';
import { ScraperService } from '../services/Scraper.service.ts';

export async function getJobs(ctx: Context): Promise<void> {
const scraper = new ScraperService('https://www.getonbrd.com');
const $ = await scraper.execute('/empleos/programacion');

const jobsResultList = $(
'body #right-col .main-container ul.sgb-results-list>div',
);

const jobs = $(jobsResultList).map((_i, el) => {
let elCheerio = $(el);
elCheerio = elCheerio.children('a');

const elInfo = elCheerio
.children('.gb-results-list__main')
.children('.gb-results-list__info');

// const logo = elCheerio
// .children('.gb-results-list__main')
// .children('.gb-results-list__avatar')
// .children('img.gb-results-list__img')
// .attr('src');

const title: string = elInfo
.children('.gb-results-list__title')
.children('strong')
.text();

const [role, time]: string[] = elInfo
.children('.gb-results-list__title')
.children('span')
.text()
.split('|')
.map((t) => t.trim());

const textInfo: string = elInfo
.children('div')
.text();

const [companyName, ...locations]: string[] = textInfo
.split('\n')
.filter((t) => t);

const location = locations
.filter((_t, i) => i > 0)
.join(' ');

const url: string = elCheerio.attr('href') || '';

return {
title,
role,
time,
companyName,
location,
url,
};
}).toArray();

ctx.response.body = {
jobs,
};
}
9 changes: 9 additions & 0 deletions src/main.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import { Server } from './services/Server.service.ts';

try {
const server = new Server();

server.run();
} catch (error) {
console.log((error as Error).message);
}
8 changes: 8 additions & 0 deletions src/routes/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import { Router } from 'https://deno.land/x/[email protected]/mod.ts';
import { getJobs } from '../controllers/jobs.controller.ts';

const router = new Router();

router.get('/jobs', getJobs);

export const routes = router.routes();
17 changes: 17 additions & 0 deletions src/services/Scraper.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import { CheerioAPI, load } from 'https://esm.sh/[email protected]';

export class ScraperService {
private baseUrl: string;

constructor(baseUrl: string) {
this.baseUrl = baseUrl;
}

public async execute(path: string): Promise<CheerioAPI> {
const pathname: string = path.startsWith('/') ? path : `/${path}`;
const response = await fetch(this.baseUrl + pathname);
const html: string = await response.text();
const $ = load(html);
return $;
}
}
32 changes: 32 additions & 0 deletions src/services/Server.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import { Application } from 'https://deno.land/x/[email protected]/mod.ts';
import { routes } from '../routes/index.ts';

export class Server {
private readonly app = new Application();

constructor() {
this.middlewares();
this.routes();
}

private middlewares() {
// Asegurar que todas las peticiones empiecen por "/api"
this.app.use(async (ctx, next) => {
const path: string[] = ctx.request.url.pathname.split('/');
if (path[1] === 'api') {
ctx.request.url.pathname = `${path[0]}/${path[2]}`;
await next();
}
});
}

private routes(): void {
this.app.use(routes);
}

public run(): void {
const port = 8000;
this.app.listen({ hostname: '0.0.0.0', port });
console.log(`Sever listening on port ${port}`);
}
}

0 comments on commit 760917e

Please sign in to comment.