Skip to content
Snippets Groups Projects
Commit 1334a3c8 authored by Ole Langbehn's avatar Ole Langbehn
Browse files

HOLI-3881 add fake mode for local development without secrets

parent 04f71dbf
No related branches found
No related tags found
No related merge requests found
export GEOAPIFY_API_KEY="" export GEOAPIFY_API_KEY=""
\ No newline at end of file
import { logger, LogSeverity } from "./logging.ts"; import { logger, LogSeverity } from "./logging.ts";
import { startServer } from "./server.ts"; import { DEFAULT_CACHE_ENABLED, DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE, DEFAULT_PORT, startServer } from "./server.ts";
const environment = Deno.env.get("ENVIRONMENT") || "development"; const environment = Deno.env.get("ENVIRONMENT") || "development";
...@@ -8,16 +8,29 @@ logger.setUpLogger( ...@@ -8,16 +8,29 @@ logger.setUpLogger(
environment === "development" ? LogSeverity.DEFAULT : LogSeverity.INFO, environment === "development" ? LogSeverity.DEFAULT : LogSeverity.INFO,
); );
const required = <T>(name: string, t?: T, fallback?: T): T => {
if (t === undefined && fallback === undefined) {
throw Error(`Environment variable "${name}" is required`);
} else {
return t !== undefined ? t : fallback!;
}
};
const serverConfigFromEnv = () => { const serverConfigFromEnv = () => {
const asNumber = (str?: string) => (str ? Number(str) : undefined); const asNumber = (str?: string) => (str ? Number(str) : undefined);
const asBoolean = (str?: string) => (str ? Boolean(str) : undefined); const asBoolean = (str?: string) => (str ? Boolean(str) : undefined);
const fake = asBoolean(Deno.env.get("FAKE")) || false // For local development. If set, the API returns dummy data
return { return {
port: asNumber(Deno.env.get("PORT")), port: required("PORT", asNumber(Deno.env.get("PORT")), DEFAULT_PORT),
cacheEnabled: asBoolean(Deno.env.get("CACHE_ENABLED")), cacheEnabled: required("CACHE_ENABLED", asBoolean(Deno.env.get("CACHE_ENABLED")), DEFAULT_CACHE_ENABLED),
cacheTtlMsPlacesAutocomplete: asNumber( cacheTtlMsPlacesAutocomplete: required("DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE", asNumber(Deno.env.get("DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE")), DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE),
Deno.env.get("DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE"), geoapifyApiKey: required(
"GEOAPIFY_API_KEY",
Deno.env.get("GEOAPIFY_API_KEY"),
fake ? 'dummy value' : undefined
), ),
geoapifyApiKey: Deno.env.get("GEOAPIFY_API_KEY"), fake
}; };
}; };
......
...@@ -32,7 +32,7 @@ const typeDefs = ` ...@@ -32,7 +32,7 @@ const typeDefs = `
type Query { type Query {
placesAutocomplete(text: String!, limit: Int, level: String): [Place]! placesAutocomplete(text: String!, limit: Int, level: String): [Place]!
placeDetails(id: String!): PlaceDetails! placeDetails(id: String!): PlaceDetails
} }
`; `;
...@@ -50,24 +50,23 @@ const createResolvers = (config: ServerConfig) => ({ ...@@ -50,24 +50,23 @@ const createResolvers = (config: ServerConfig) => ({
_parent: any, _parent: any,
parameters: PlacesAutocompleteParameters, parameters: PlacesAutocompleteParameters,
context: GraphQLContext, context: GraphQLContext,
) => ) => config.fake ? Promise.resolve([]) :
fetchPlaces( fetchPlaces(
parameters, parameters,
getLanguage(context.language), getLanguage(context.language),
config.geoapifyApiKey || "", config.geoapifyApiKey,
), ),
placeDetails: ( placeDetails: (
// deno-lint-ignore no-explicit-any // deno-lint-ignore no-explicit-any
_parent: any, _parent: any,
parameters: PlacesDetailsParameters, parameters: PlacesDetailsParameters,
context: GraphQLContext, context: GraphQLContext,
) => { ) => config.fake ? Promise.resolve(undefined) :
return fetchPlaceDetails( fetchPlaceDetails(
parameters, parameters,
getLanguage(context.language), getLanguage(context.language),
config.geoapifyApiKey || "", config.geoapifyApiKey,
); ),
},
}, },
}); });
...@@ -76,10 +75,11 @@ export const DEFAULT_CACHE_ENABLED = true; ...@@ -76,10 +75,11 @@ export const DEFAULT_CACHE_ENABLED = true;
export const DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE = 60_000 * 60 * 24; export const DEFAULT_CACHE_TTL_MS_GEOAPIFY_AUTOCOMPLETE = 60_000 * 60 * 24;
export interface ServerConfig { export interface ServerConfig {
port?: number; // default: 8003 port: number; // default: 8003
cacheEnabled?: boolean; // default: true cacheEnabled: boolean; // default: true
cacheTtlMsPlacesAutocomplete?: number; // default: 24 hours cacheTtlMsPlacesAutocomplete: number; // default: 24 hours
geoapifyApiKey?: string; geoapifyApiKey: string;
fake: boolean;
} }
export type GraphQLContext = { export type GraphQLContext = {
...@@ -94,7 +94,7 @@ export type GraphQLContext = { ...@@ -94,7 +94,7 @@ export type GraphQLContext = {
}; };
export const createGraphQLServer = (config: ServerConfig): GraphQLServer => { export const createGraphQLServer = (config: ServerConfig): GraphQLServer => {
const plugins = config.cacheEnabled || DEFAULT_CACHE_ENABLED const plugins = config.cacheEnabled
? [ ? [
useResponseCache({ useResponseCache({
// global cache per language, shared by all users // global cache per language, shared by all users
...@@ -133,13 +133,16 @@ export type GraphQLServer = any; ...@@ -133,13 +133,16 @@ export type GraphQLServer = any;
export const startServer = (config: ServerConfig): Promise<void> => { export const startServer = (config: ServerConfig): Promise<void> => {
const graphQLServer: GraphQLServer = createGraphQLServer(config); const graphQLServer: GraphQLServer = createGraphQLServer(config);
return serve(graphQLServer.handleRequest, { return serve(graphQLServer.handleRequest, {
port: config.port || DEFAULT_PORT, port: config.port,
onListen({ port, hostname }) { onListen({ port, hostname }) {
logger.info( logger.info(
`Server started at http://${ `Server started at http://${
hostname === "0.0.0.0" ? "localhost" : hostname hostname === "0.0.0.0" ? "localhost" : hostname
}:${port}/graphql`, }:${port}/graphql`,
); );
if(config.fake) {
logger.info(`Server is serving fake data due to FAKE env var set to true`)
}
}, },
}); });
}; };
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment