All files / src/worker env.ts

82.35% Statements 28/34
57.69% Branches 15/26
100% Functions 13/13
82.35% Lines 28/34

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111            6x                             211x           6x       42x     86x       80x       6x   6x       42x   42x       42x       163x   163x 1x     162x       28x 28x 28x   28x 28x                           70x       42x 42x 42x 42x                   6x 6x     6x    
import { TypedEnv } from './types'
import { InvalidVariableError, MissingVariableError } from './errors'
import { isRegion, Region } from './fingerprint/region'
import { RuleActionUnion } from './fingerprint/ruleset'
import { isLogLevel, LogLevel } from '../shared/types'
 
const defaults = {
  FP_CDN_HOST: 'fpcdn.io',
  FP_INGRESS_BASE_HOST: 'api.fpjs.io',
  PROTECTED_APIS: [],
  IDENTIFICATION_PAGE_URLS: [],
  FP_RULESET_ID: '',
  FP_FAILURE_FALLBACK_ACTION: {
    type: 'block',
    status_code: 403,
    body: '',
    headers: [],
  },
} satisfies Partial<TypedEnv>
 
function assertVariableIsSet(env: TypedEnv, key: keyof TypedEnv) {
  Iif (!env[key]) {
    throw new MissingVariableError(key)
  }
}
 
export function getCDNHost(env: TypedEnv) {
  return env.FP_CDN_HOST || defaults.FP_CDN_HOST
}
 
export function getIngressBaseHost(env: TypedEnv) {
  return env.FP_INGRESS_BASE_HOST || defaults.FP_INGRESS_BASE_HOST
}
export function getProtectedApis(env: TypedEnv) {
  return env.PROTECTED_APIS ?? defaults.PROTECTED_APIS
}
 
export function getIdentificationPageUrls(env: TypedEnv) {
  return env.IDENTIFICATION_PAGE_URLS ?? defaults.IDENTIFICATION_PAGE_URLS
}
 
export function getPublicKey(env: TypedEnv) {
  assertVariableIsSet(env, 'FP_PUBLIC_KEY')
 
  return env.FP_PUBLIC_KEY
}
 
export function getSecretKey(env: TypedEnv) {
  assertVariableIsSet(env, 'FP_SECRET_KEY')
 
  return env.FP_SECRET_KEY
}
 
export function getRulesetId(env: TypedEnv) {
  return env.FP_RULESET_ID || ''
}
 
export function getRoutePrefix(env: TypedEnv) {
  assertVariableIsSet(env, 'WORKER_ROUTE_PREFIX')
 
  if (env.WORKER_ROUTE_PREFIX.startsWith('/')) {
    throw new InvalidVariableError('WORKER_ROUTE_PREFIX', 'must not start with slash')
  }
 
  return env.WORKER_ROUTE_PREFIX
}
 
export function getFallbackRuleAction(env: TypedEnv): RuleActionUnion {
  const rule = env.FP_FAILURE_FALLBACK_ACTION
  Eif (rule) {
    const result = RuleActionUnion.safeParse(rule)
 
    Eif (result.success) {
      return result.data
    }
 
    console.warn(`Invalid rule action provided`, result.error, 'Fallback to block action.')
  }
 
  return defaults.FP_FAILURE_FALLBACK_ACTION
}
 
/**
 * Determines if the current environment is in monitor mode.
 * If that's the case, the worker will still perform necessary identification requests, but won't perform any ruleset enforcement.
 */
export function isMonitorMode(env: TypedEnv) {
  return !env.FP_RULESET_ID
}
 
export function getFpRegion(env: TypedEnv): Region {
  const region = env.FP_REGION
  Eif (region) {
    Eif (isRegion(region)) {
      return region
    }
 
    console.warn(`Invalid region provided: ${region}. Using default region: us`)
  }
 
  return 'us'
}
 
export function getFpLogLevel(env: TypedEnv): LogLevel {
  const level = env.FP_LOG_LEVEL
  Iif (level && isLogLevel(level)) {
    return level
  }
  return 'error'
}