Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Promisification #169

Open
wants to merge 11 commits into
base: master
Choose a base branch
from
Open

Promisification #169

wants to merge 11 commits into from

Conversation

srnec
Copy link
Contributor

@srnec srnec commented Jul 1, 2020

  • added new eslint rules & better configured existing eslint rules
  • extracted OCR related logic into separate service class (can be reused in future for other restaurant parsers)
  • added promise with timeout utility function (basically it adds the way to time out promises)
  • extracted HTML scraping logic into its own service class (to extract logic into its own class and it will ease unit testing in future)
  • promisification - getting rid of callbacks in favor of promises (mainly in MenuFetcher)
  • refactored Config - it is no longer needed to instantiate it, it can be imported from anywhere

Next time I want to check for better options in debugging, watching (realtime reload) etc.

/**
* Here add new restaurant for given location
*/
const restaurants: RestaurantMap = new Map([
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

extracted here the restaurant config in order to better type it + contributors have it easily accessible and separated from other configuration

]]
])
}
export const config: IConfig = {
Copy link
Contributor Author

@srnec srnec Jul 1, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks to moving from Class to constant this config doesn't need to be instantiated (like it was in app.ts) and another benefit is that it can be imported and referenced by any other file/class/service.

@@ -0,0 +1,20 @@
export async function promiseWithTimeout<T>(timeoutMs: number, promise: () => Promise<T>): Promise<T> {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Handy thing that will handle timeouts when promise is executed... it is used to time out the parsing operation when it takes too long.

import { config } from "../config";

export class HtmlScraperService {
static async scrape(url: string): Promise<string> {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I extracted logic for scraping into this service. Its sole purpose is for given URL return the scraped data.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suggest injecting config through ctor, otherwise this in untestable (unmockable)


export type DocumentType = "pdf" | "image" | "encoded";

export class OcrService {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar to HtmlScraperService... extracted logic for OCR stuff into this service... now it can be better unit tested and also reused for other parsers.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

similar suggestion 😄

@srnec srnec requested a review from yohny July 1, 2020 21:58

constructor(private readonly _config: IConfig, private readonly _cache: NodeCache) { }
private readonly cache = new NodeCache({ checkperiod: (config.cache.expirationTime / 2) });
private readonly pendingTasks = new Map<string, Promise<IMenuItem[]>>();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this goes against dependency injection, now the dependencies (config and cache) are created by MenuFetcher itself, which hides them from outside world and makes maintenenc and unittesting harder (if we would have some unittests for MenuFetcher 😄 ) - I suggest injecting those dependencies through ctor as it was originally

import { config } from "../config";

export class HtmlScraperService {
static async scrape(url: string): Promise<string> {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suggest injecting config through ctor, otherwise this in untestable (unmockable)


export type DocumentType = "pdf" | "image" | "encoded";

export class OcrService {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

similar suggestion 😄

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants