config.go 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708
  1. package config
  2. import (
  3. "errors"
  4. "flag"
  5. "fmt"
  6. "math"
  7. "os"
  8. "regexp"
  9. "runtime"
  10. log "github.com/sirupsen/logrus"
  11. "github.com/imgproxy/imgproxy/v3/config/configurators"
  12. "github.com/imgproxy/imgproxy/v3/imagetype"
  13. "github.com/imgproxy/imgproxy/v3/version"
  14. )
  15. var (
  16. Network string
  17. Bind string
  18. ReadTimeout int
  19. WriteTimeout int
  20. KeepAliveTimeout int
  21. ClientKeepAliveTimeout int
  22. DownloadTimeout int
  23. Concurrency int
  24. RequestsQueueSize int
  25. MaxClients int
  26. TTL int
  27. CacheControlPassthrough bool
  28. SetCanonicalHeader bool
  29. SoReuseport bool
  30. PathPrefix string
  31. MaxSrcResolution int
  32. MaxSrcFileSize int
  33. MaxAnimationFrames int
  34. MaxAnimationFrameResolution int
  35. MaxSvgCheckBytes int
  36. MaxRedirects int
  37. AllowSecurityOptions bool
  38. JpegProgressive bool
  39. PngInterlaced bool
  40. PngQuantize bool
  41. PngQuantizationColors int
  42. AvifSpeed int
  43. Quality int
  44. FormatQuality map[imagetype.Type]int
  45. StripMetadata bool
  46. KeepCopyright bool
  47. StripColorProfile bool
  48. AutoRotate bool
  49. EnforceThumbnail bool
  50. ReturnAttachment bool
  51. SvgFixUnsupported bool
  52. EnableWebpDetection bool
  53. EnforceWebp bool
  54. EnableAvifDetection bool
  55. EnforceAvif bool
  56. EnableClientHints bool
  57. PreferredFormats []imagetype.Type
  58. SkipProcessingFormats []imagetype.Type
  59. UseLinearColorspace bool
  60. DisableShrinkOnLoad bool
  61. Keys [][]byte
  62. Salts [][]byte
  63. SignatureSize int
  64. Secret string
  65. AllowOrigin string
  66. UserAgent string
  67. IgnoreSslVerification bool
  68. DevelopmentErrorsMode bool
  69. AllowedSources []*regexp.Regexp
  70. SanitizeSvg bool
  71. CookiePassthrough bool
  72. CookieBaseURL string
  73. LocalFileSystemRoot string
  74. S3Enabled bool
  75. S3Region string
  76. S3Endpoint string
  77. GCSEnabled bool
  78. GCSKey string
  79. GCSEndpoint string
  80. ABSEnabled bool
  81. ABSName string
  82. ABSKey string
  83. ABSEndpoint string
  84. SwiftEnabled bool
  85. SwiftUsername string
  86. SwiftAPIKey string
  87. SwiftAuthURL string
  88. SwiftDomain string
  89. SwiftTenant string
  90. SwiftAuthVersion int
  91. SwiftConnectTimeoutSeconds int
  92. SwiftTimeoutSeconds int
  93. ETagEnabled bool
  94. ETagBuster string
  95. BaseURL string
  96. Presets []string
  97. OnlyPresets bool
  98. WatermarkData string
  99. WatermarkPath string
  100. WatermarkURL string
  101. WatermarkOpacity float64
  102. FallbackImageData string
  103. FallbackImagePath string
  104. FallbackImageURL string
  105. FallbackImageHTTPCode int
  106. FallbackImageTTL int
  107. DataDogEnable bool
  108. DataDogEnableMetrics bool
  109. NewRelicAppName string
  110. NewRelicKey string
  111. NewRelicLabels map[string]string
  112. PrometheusBind string
  113. PrometheusNamespace string
  114. OpenTelemetryEndpoint string
  115. OpenTelemetryProtocol string
  116. OpenTelemetryServiceName string
  117. OpenTelemetryEnableMetrics bool
  118. OpenTelemetryServerCert string
  119. OpenTelemetryClientCert string
  120. OpenTelemetryClientKey string
  121. OpenTelemetryGRPCInsecure bool
  122. OpenTelemetryPropagators []string
  123. OpenTelemetryTraceIDGenerator string
  124. OpenTelemetryConnectionTimeout int
  125. CloudWatchServiceName string
  126. CloudWatchNamespace string
  127. CloudWatchRegion string
  128. BugsnagKey string
  129. BugsnagStage string
  130. HoneybadgerKey string
  131. HoneybadgerEnv string
  132. SentryDSN string
  133. SentryEnvironment string
  134. SentryRelease string
  135. AirbrakeProjecID int
  136. AirbrakeProjecKey string
  137. AirbrakeEnv string
  138. ReportDownloadingErrors bool
  139. EnableDebugHeaders bool
  140. FreeMemoryInterval int
  141. DownloadBufferSize int
  142. BufferPoolCalibrationThreshold int
  143. HealthCheckPath string
  144. )
  145. var (
  146. keyPath string
  147. saltPath string
  148. presetsPath string
  149. )
  150. func init() {
  151. Reset()
  152. flag.StringVar(&keyPath, "keypath", "", "path of the file with hex-encoded key")
  153. flag.StringVar(&saltPath, "saltpath", "", "path of the file with hex-encoded salt")
  154. flag.StringVar(&presetsPath, "presets", "", "path of the file with presets")
  155. }
  156. func Reset() {
  157. Network = "tcp"
  158. Bind = ":8080"
  159. ReadTimeout = 10
  160. WriteTimeout = 10
  161. KeepAliveTimeout = 10
  162. ClientKeepAliveTimeout = 90
  163. DownloadTimeout = 5
  164. Concurrency = runtime.GOMAXPROCS(0) * 2
  165. RequestsQueueSize = 0
  166. MaxClients = 2048
  167. TTL = 31536000
  168. CacheControlPassthrough = false
  169. SetCanonicalHeader = false
  170. SoReuseport = false
  171. PathPrefix = ""
  172. MaxSrcResolution = 16800000
  173. MaxSrcFileSize = 0
  174. MaxAnimationFrames = 1
  175. MaxAnimationFrameResolution = 0
  176. MaxSvgCheckBytes = 32 * 1024
  177. MaxRedirects = 10
  178. AllowSecurityOptions = false
  179. JpegProgressive = false
  180. PngInterlaced = false
  181. PngQuantize = false
  182. PngQuantizationColors = 256
  183. AvifSpeed = 8
  184. Quality = 80
  185. FormatQuality = map[imagetype.Type]int{imagetype.AVIF: 65}
  186. StripMetadata = true
  187. KeepCopyright = true
  188. StripColorProfile = true
  189. AutoRotate = true
  190. EnforceThumbnail = false
  191. ReturnAttachment = false
  192. SvgFixUnsupported = false
  193. EnableWebpDetection = false
  194. EnforceWebp = false
  195. EnableAvifDetection = false
  196. EnforceAvif = false
  197. EnableClientHints = false
  198. PreferredFormats = []imagetype.Type{
  199. imagetype.JPEG,
  200. imagetype.PNG,
  201. imagetype.GIF,
  202. }
  203. SkipProcessingFormats = make([]imagetype.Type, 0)
  204. UseLinearColorspace = false
  205. DisableShrinkOnLoad = false
  206. Keys = make([][]byte, 0)
  207. Salts = make([][]byte, 0)
  208. SignatureSize = 32
  209. Secret = ""
  210. AllowOrigin = ""
  211. UserAgent = fmt.Sprintf("imgproxy/%s", version.Version())
  212. IgnoreSslVerification = false
  213. DevelopmentErrorsMode = false
  214. AllowedSources = make([]*regexp.Regexp, 0)
  215. SanitizeSvg = true
  216. CookiePassthrough = false
  217. CookieBaseURL = ""
  218. LocalFileSystemRoot = ""
  219. S3Enabled = false
  220. S3Region = ""
  221. S3Endpoint = ""
  222. GCSEnabled = false
  223. GCSKey = ""
  224. ABSEnabled = false
  225. ABSName = ""
  226. ABSKey = ""
  227. ABSEndpoint = ""
  228. SwiftEnabled = false
  229. SwiftUsername = ""
  230. SwiftAPIKey = ""
  231. SwiftAuthURL = ""
  232. SwiftAuthVersion = 0
  233. SwiftTenant = ""
  234. SwiftDomain = ""
  235. SwiftConnectTimeoutSeconds = 10
  236. SwiftTimeoutSeconds = 60
  237. ETagEnabled = false
  238. ETagBuster = ""
  239. BaseURL = ""
  240. Presets = make([]string, 0)
  241. OnlyPresets = false
  242. WatermarkData = ""
  243. WatermarkPath = ""
  244. WatermarkURL = ""
  245. WatermarkOpacity = 1
  246. FallbackImageData = ""
  247. FallbackImagePath = ""
  248. FallbackImageURL = ""
  249. FallbackImageHTTPCode = 200
  250. FallbackImageTTL = 0
  251. DataDogEnable = false
  252. NewRelicAppName = ""
  253. NewRelicKey = ""
  254. NewRelicLabels = make(map[string]string)
  255. PrometheusBind = ""
  256. PrometheusNamespace = ""
  257. OpenTelemetryEndpoint = ""
  258. OpenTelemetryProtocol = "grpc"
  259. OpenTelemetryServiceName = "imgproxy"
  260. OpenTelemetryEnableMetrics = false
  261. OpenTelemetryServerCert = ""
  262. OpenTelemetryClientCert = ""
  263. OpenTelemetryClientKey = ""
  264. OpenTelemetryGRPCInsecure = true
  265. OpenTelemetryPropagators = make([]string, 0)
  266. OpenTelemetryTraceIDGenerator = "xray"
  267. OpenTelemetryConnectionTimeout = 5
  268. CloudWatchServiceName = ""
  269. CloudWatchNamespace = "imgproxy"
  270. CloudWatchRegion = ""
  271. BugsnagKey = ""
  272. BugsnagStage = "production"
  273. HoneybadgerKey = ""
  274. HoneybadgerEnv = "production"
  275. SentryDSN = ""
  276. SentryEnvironment = "production"
  277. SentryRelease = fmt.Sprintf("imgproxy@%s", version.Version())
  278. AirbrakeProjecID = 0
  279. AirbrakeProjecKey = ""
  280. AirbrakeEnv = "production"
  281. ReportDownloadingErrors = true
  282. EnableDebugHeaders = false
  283. FreeMemoryInterval = 10
  284. DownloadBufferSize = 0
  285. BufferPoolCalibrationThreshold = 1024
  286. HealthCheckPath = ""
  287. }
  288. func Configure() error {
  289. if port := os.Getenv("PORT"); len(port) > 0 {
  290. Bind = fmt.Sprintf(":%s", port)
  291. }
  292. configurators.String(&Network, "IMGPROXY_NETWORK")
  293. configurators.String(&Bind, "IMGPROXY_BIND")
  294. configurators.Int(&ReadTimeout, "IMGPROXY_READ_TIMEOUT")
  295. configurators.Int(&WriteTimeout, "IMGPROXY_WRITE_TIMEOUT")
  296. configurators.Int(&KeepAliveTimeout, "IMGPROXY_KEEP_ALIVE_TIMEOUT")
  297. configurators.Int(&ClientKeepAliveTimeout, "IMGPROXY_CLIENT_KEEP_ALIVE_TIMEOUT")
  298. configurators.Int(&DownloadTimeout, "IMGPROXY_DOWNLOAD_TIMEOUT")
  299. configurators.Int(&Concurrency, "IMGPROXY_CONCURRENCY")
  300. configurators.Int(&RequestsQueueSize, "IMGPROXY_REQUESTS_QUEUE_SIZE")
  301. configurators.Int(&MaxClients, "IMGPROXY_MAX_CLIENTS")
  302. configurators.Int(&TTL, "IMGPROXY_TTL")
  303. configurators.Bool(&CacheControlPassthrough, "IMGPROXY_CACHE_CONTROL_PASSTHROUGH")
  304. configurators.Bool(&SetCanonicalHeader, "IMGPROXY_SET_CANONICAL_HEADER")
  305. configurators.Bool(&SoReuseport, "IMGPROXY_SO_REUSEPORT")
  306. configurators.String(&PathPrefix, "IMGPROXY_PATH_PREFIX")
  307. configurators.MegaInt(&MaxSrcResolution, "IMGPROXY_MAX_SRC_RESOLUTION")
  308. configurators.Int(&MaxSrcFileSize, "IMGPROXY_MAX_SRC_FILE_SIZE")
  309. configurators.Int(&MaxSvgCheckBytes, "IMGPROXY_MAX_SVG_CHECK_BYTES")
  310. configurators.Int(&MaxAnimationFrames, "IMGPROXY_MAX_ANIMATION_FRAMES")
  311. configurators.MegaInt(&MaxAnimationFrameResolution, "IMGPROXY_MAX_ANIMATION_FRAME_RESOLUTION")
  312. configurators.Int(&MaxRedirects, "IMGPROXY_MAX_REDIRECTS")
  313. configurators.Patterns(&AllowedSources, "IMGPROXY_ALLOWED_SOURCES")
  314. configurators.Bool(&SanitizeSvg, "IMGPROXY_SANITIZE_SVG")
  315. configurators.Bool(&AllowSecurityOptions, "IMGPROXY_ALLOW_SECURITY_OPTIONS")
  316. configurators.Bool(&JpegProgressive, "IMGPROXY_JPEG_PROGRESSIVE")
  317. configurators.Bool(&PngInterlaced, "IMGPROXY_PNG_INTERLACED")
  318. configurators.Bool(&PngQuantize, "IMGPROXY_PNG_QUANTIZE")
  319. configurators.Int(&PngQuantizationColors, "IMGPROXY_PNG_QUANTIZATION_COLORS")
  320. configurators.Int(&AvifSpeed, "IMGPROXY_AVIF_SPEED")
  321. configurators.Int(&Quality, "IMGPROXY_QUALITY")
  322. if err := configurators.ImageTypesQuality(FormatQuality, "IMGPROXY_FORMAT_QUALITY"); err != nil {
  323. return err
  324. }
  325. configurators.Bool(&StripMetadata, "IMGPROXY_STRIP_METADATA")
  326. configurators.Bool(&KeepCopyright, "IMGPROXY_KEEP_COPYRIGHT")
  327. configurators.Bool(&StripColorProfile, "IMGPROXY_STRIP_COLOR_PROFILE")
  328. configurators.Bool(&AutoRotate, "IMGPROXY_AUTO_ROTATE")
  329. configurators.Bool(&EnforceThumbnail, "IMGPROXY_ENFORCE_THUMBNAIL")
  330. configurators.Bool(&ReturnAttachment, "IMGPROXY_RETURN_ATTACHMENT")
  331. configurators.Bool(&SvgFixUnsupported, "IMGPROXY_SVG_FIX_UNSUPPORTED")
  332. configurators.Bool(&EnableWebpDetection, "IMGPROXY_ENABLE_WEBP_DETECTION")
  333. configurators.Bool(&EnforceWebp, "IMGPROXY_ENFORCE_WEBP")
  334. configurators.Bool(&EnableAvifDetection, "IMGPROXY_ENABLE_AVIF_DETECTION")
  335. configurators.Bool(&EnforceAvif, "IMGPROXY_ENFORCE_AVIF")
  336. configurators.Bool(&EnableClientHints, "IMGPROXY_ENABLE_CLIENT_HINTS")
  337. configurators.String(&HealthCheckPath, "IMGPROXY_HEALTH_CHECK_PATH")
  338. if err := configurators.ImageTypes(&PreferredFormats, "IMGPROXY_PREFERRED_FORMATS"); err != nil {
  339. return err
  340. }
  341. if err := configurators.ImageTypes(&SkipProcessingFormats, "IMGPROXY_SKIP_PROCESSING_FORMATS"); err != nil {
  342. return err
  343. }
  344. configurators.Bool(&UseLinearColorspace, "IMGPROXY_USE_LINEAR_COLORSPACE")
  345. configurators.Bool(&DisableShrinkOnLoad, "IMGPROXY_DISABLE_SHRINK_ON_LOAD")
  346. if err := configurators.HexSlice(&Keys, "IMGPROXY_KEY"); err != nil {
  347. return err
  348. }
  349. if err := configurators.HexSlice(&Salts, "IMGPROXY_SALT"); err != nil {
  350. return err
  351. }
  352. configurators.Int(&SignatureSize, "IMGPROXY_SIGNATURE_SIZE")
  353. if err := configurators.HexSliceFile(&Keys, keyPath); err != nil {
  354. return err
  355. }
  356. if err := configurators.HexSliceFile(&Salts, saltPath); err != nil {
  357. return err
  358. }
  359. configurators.String(&Secret, "IMGPROXY_SECRET")
  360. configurators.String(&AllowOrigin, "IMGPROXY_ALLOW_ORIGIN")
  361. configurators.String(&UserAgent, "IMGPROXY_USER_AGENT")
  362. configurators.Bool(&IgnoreSslVerification, "IMGPROXY_IGNORE_SSL_VERIFICATION")
  363. configurators.Bool(&DevelopmentErrorsMode, "IMGPROXY_DEVELOPMENT_ERRORS_MODE")
  364. configurators.Bool(&CookiePassthrough, "IMGPROXY_COOKIE_PASSTHROUGH")
  365. configurators.String(&CookieBaseURL, "IMGPROXY_COOKIE_BASE_URL")
  366. configurators.String(&LocalFileSystemRoot, "IMGPROXY_LOCAL_FILESYSTEM_ROOT")
  367. configurators.Bool(&S3Enabled, "IMGPROXY_USE_S3")
  368. configurators.String(&S3Region, "IMGPROXY_S3_REGION")
  369. configurators.String(&S3Endpoint, "IMGPROXY_S3_ENDPOINT")
  370. configurators.Bool(&GCSEnabled, "IMGPROXY_USE_GCS")
  371. configurators.String(&GCSKey, "IMGPROXY_GCS_KEY")
  372. configurators.String(&GCSEndpoint, "IMGPROXY_GCS_ENDPOINT")
  373. configurators.Bool(&ABSEnabled, "IMGPROXY_USE_ABS")
  374. configurators.String(&ABSName, "IMGPROXY_ABS_NAME")
  375. configurators.String(&ABSKey, "IMGPROXY_ABS_KEY")
  376. configurators.String(&ABSEndpoint, "IMGPROXY_ABS_ENDPOINT")
  377. configurators.Bool(&SwiftEnabled, "IMGPROXY_USE_SWIFT")
  378. configurators.String(&SwiftUsername, "IMGPROXY_SWIFT_USERNAME")
  379. configurators.String(&SwiftAPIKey, "IMGPROXY_SWIFT_API_KEY")
  380. configurators.String(&SwiftAuthURL, "IMGPROXY_SWIFT_AUTH_URL")
  381. configurators.String(&SwiftDomain, "IMGPROXY_SWIFT_DOMAIN")
  382. configurators.String(&SwiftTenant, "IMGPROXY_SWIFT_TENANT")
  383. configurators.Int(&SwiftConnectTimeoutSeconds, "IMGPROXY_SWIFT_CONNECT_TIMEOUT_SECONDS")
  384. configurators.Int(&SwiftTimeoutSeconds, "IMGPROXY_SWIFT_TIMEOUT_SECONDS")
  385. configurators.Bool(&ETagEnabled, "IMGPROXY_USE_ETAG")
  386. configurators.String(&ETagBuster, "IMGPROXY_ETAG_BUSTER")
  387. configurators.String(&BaseURL, "IMGPROXY_BASE_URL")
  388. configurators.StringSlice(&Presets, "IMGPROXY_PRESETS")
  389. if err := configurators.StringSliceFile(&Presets, presetsPath); err != nil {
  390. return err
  391. }
  392. configurators.Bool(&OnlyPresets, "IMGPROXY_ONLY_PRESETS")
  393. configurators.String(&WatermarkData, "IMGPROXY_WATERMARK_DATA")
  394. configurators.String(&WatermarkPath, "IMGPROXY_WATERMARK_PATH")
  395. configurators.String(&WatermarkURL, "IMGPROXY_WATERMARK_URL")
  396. configurators.Float(&WatermarkOpacity, "IMGPROXY_WATERMARK_OPACITY")
  397. configurators.String(&FallbackImageData, "IMGPROXY_FALLBACK_IMAGE_DATA")
  398. configurators.String(&FallbackImagePath, "IMGPROXY_FALLBACK_IMAGE_PATH")
  399. configurators.String(&FallbackImageURL, "IMGPROXY_FALLBACK_IMAGE_URL")
  400. configurators.Int(&FallbackImageHTTPCode, "IMGPROXY_FALLBACK_IMAGE_HTTP_CODE")
  401. configurators.Int(&FallbackImageTTL, "IMGPROXY_FALLBACK_IMAGE_TTL")
  402. configurators.Bool(&DataDogEnable, "IMGPROXY_DATADOG_ENABLE")
  403. configurators.Bool(&DataDogEnableMetrics, "IMGPROXY_DATADOG_ENABLE_ADDITIONAL_METRICS")
  404. configurators.String(&NewRelicAppName, "IMGPROXY_NEW_RELIC_APP_NAME")
  405. configurators.String(&NewRelicKey, "IMGPROXY_NEW_RELIC_KEY")
  406. configurators.StringMap(&NewRelicLabels, "IMGPROXY_NEW_RELIC_LABELS")
  407. configurators.String(&PrometheusBind, "IMGPROXY_PROMETHEUS_BIND")
  408. configurators.String(&PrometheusNamespace, "IMGPROXY_PROMETHEUS_NAMESPACE")
  409. configurators.String(&OpenTelemetryEndpoint, "IMGPROXY_OPEN_TELEMETRY_ENDPOINT")
  410. configurators.String(&OpenTelemetryProtocol, "IMGPROXY_OPEN_TELEMETRY_PROTOCOL")
  411. configurators.String(&OpenTelemetryServiceName, "IMGPROXY_OPEN_TELEMETRY_SERVICE_NAME")
  412. configurators.Bool(&OpenTelemetryEnableMetrics, "IMGPROXY_OPEN_TELEMETRY_ENABLE_METRICS")
  413. configurators.String(&OpenTelemetryServerCert, "IMGPROXY_OPEN_TELEMETRY_SERVER_CERT")
  414. configurators.String(&OpenTelemetryClientCert, "IMGPROXY_OPEN_TELEMETRY_CLIENT_CERT")
  415. configurators.String(&OpenTelemetryClientKey, "IMGPROXY_OPEN_TELEMETRY_CLIENT_KEY")
  416. configurators.Bool(&OpenTelemetryGRPCInsecure, "IMGPROXY_OPEN_TELEMETRY_GRPC_INSECURE")
  417. configurators.StringSlice(&OpenTelemetryPropagators, "IMGPROXY_OPEN_TELEMETRY_PROPAGATORS")
  418. configurators.String(&OpenTelemetryTraceIDGenerator, "IMGPROXY_OPEN_TELEMETRY_TRACE_ID_GENERATOR")
  419. configurators.Int(&OpenTelemetryConnectionTimeout, "IMGPROXY_OPEN_TELEMETRY_CONNECTION_TIMEOUT")
  420. configurators.String(&CloudWatchServiceName, "IMGPROXY_CLOUD_WATCH_SERVICE_NAME")
  421. configurators.String(&CloudWatchNamespace, "IMGPROXY_CLOUD_WATCH_NAMESPACE")
  422. configurators.String(&CloudWatchRegion, "IMGPROXY_CLOUD_WATCH_REGION")
  423. configurators.String(&BugsnagKey, "IMGPROXY_BUGSNAG_KEY")
  424. configurators.String(&BugsnagStage, "IMGPROXY_BUGSNAG_STAGE")
  425. configurators.String(&HoneybadgerKey, "IMGPROXY_HONEYBADGER_KEY")
  426. configurators.String(&HoneybadgerEnv, "IMGPROXY_HONEYBADGER_ENV")
  427. configurators.String(&SentryDSN, "IMGPROXY_SENTRY_DSN")
  428. configurators.String(&SentryEnvironment, "IMGPROXY_SENTRY_ENVIRONMENT")
  429. configurators.String(&SentryRelease, "IMGPROXY_SENTRY_RELEASE")
  430. configurators.Int(&AirbrakeProjecID, "IMGPROXY_AIRBRAKE_PROJECT_ID")
  431. configurators.String(&AirbrakeProjecKey, "IMGPROXY_AIRBRAKE_PROJECT_KEY")
  432. configurators.String(&AirbrakeEnv, "IMGPROXY_AIRBRAKE_ENVIRONMENT")
  433. configurators.Bool(&ReportDownloadingErrors, "IMGPROXY_REPORT_DOWNLOADING_ERRORS")
  434. configurators.Bool(&EnableDebugHeaders, "IMGPROXY_ENABLE_DEBUG_HEADERS")
  435. configurators.Int(&FreeMemoryInterval, "IMGPROXY_FREE_MEMORY_INTERVAL")
  436. configurators.Int(&DownloadBufferSize, "IMGPROXY_DOWNLOAD_BUFFER_SIZE")
  437. configurators.Int(&BufferPoolCalibrationThreshold, "IMGPROXY_BUFFER_POOL_CALIBRATION_THRESHOLD")
  438. if len(Keys) != len(Salts) {
  439. return fmt.Errorf("Number of keys and number of salts should be equal. Keys: %d, salts: %d", len(Keys), len(Salts))
  440. }
  441. if len(Keys) == 0 {
  442. log.Warning("No keys defined, so signature checking is disabled")
  443. }
  444. if len(Salts) == 0 {
  445. log.Warning("No salts defined, so signature checking is disabled")
  446. }
  447. if SignatureSize < 1 || SignatureSize > 32 {
  448. return fmt.Errorf("Signature size should be within 1 and 32, now - %d\n", SignatureSize)
  449. }
  450. if len(Bind) == 0 {
  451. return errors.New("Bind address is not defined")
  452. }
  453. if ReadTimeout <= 0 {
  454. return fmt.Errorf("Read timeout should be greater than 0, now - %d\n", ReadTimeout)
  455. }
  456. if WriteTimeout <= 0 {
  457. return fmt.Errorf("Write timeout should be greater than 0, now - %d\n", WriteTimeout)
  458. }
  459. if KeepAliveTimeout < 0 {
  460. return fmt.Errorf("KeepAlive timeout should be greater than or equal to 0, now - %d\n", KeepAliveTimeout)
  461. }
  462. if ClientKeepAliveTimeout < 0 {
  463. return fmt.Errorf("Client KeepAlive timeout should be greater than or equal to 0, now - %d\n", ClientKeepAliveTimeout)
  464. }
  465. if DownloadTimeout <= 0 {
  466. return fmt.Errorf("Download timeout should be greater than 0, now - %d\n", DownloadTimeout)
  467. }
  468. if Concurrency <= 0 {
  469. return fmt.Errorf("Concurrency should be greater than 0, now - %d\n", Concurrency)
  470. }
  471. if RequestsQueueSize < 0 {
  472. return fmt.Errorf("Requests queue size should be greater than or equal 0, now - %d\n", RequestsQueueSize)
  473. }
  474. if MaxClients < 0 {
  475. return fmt.Errorf("Concurrency should be greater than or equal 0, now - %d\n", MaxClients)
  476. }
  477. if TTL <= 0 {
  478. return fmt.Errorf("TTL should be greater than 0, now - %d\n", TTL)
  479. }
  480. if MaxSrcResolution <= 0 {
  481. return fmt.Errorf("Max src resolution should be greater than 0, now - %d\n", MaxSrcResolution)
  482. }
  483. if MaxSrcFileSize < 0 {
  484. return fmt.Errorf("Max src file size should be greater than or equal to 0, now - %d\n", MaxSrcFileSize)
  485. }
  486. if MaxAnimationFrames <= 0 {
  487. return fmt.Errorf("Max animation frames should be greater than 0, now - %d\n", MaxAnimationFrames)
  488. }
  489. if PngQuantizationColors < 2 {
  490. return fmt.Errorf("Png quantization colors should be greater than 1, now - %d\n", PngQuantizationColors)
  491. } else if PngQuantizationColors > 256 {
  492. return fmt.Errorf("Png quantization colors can't be greater than 256, now - %d\n", PngQuantizationColors)
  493. }
  494. if AvifSpeed < 0 {
  495. return fmt.Errorf("Avif speed should be greater than 0, now - %d\n", AvifSpeed)
  496. } else if AvifSpeed > 8 {
  497. return fmt.Errorf("Avif speed can't be greater than 8, now - %d\n", AvifSpeed)
  498. }
  499. if Quality <= 0 {
  500. return fmt.Errorf("Quality should be greater than 0, now - %d\n", Quality)
  501. } else if Quality > 100 {
  502. return fmt.Errorf("Quality can't be greater than 100, now - %d\n", Quality)
  503. }
  504. if len(PreferredFormats) == 0 {
  505. return errors.New("At least one preferred format should be specified")
  506. }
  507. if IgnoreSslVerification {
  508. log.Warning("Ignoring SSL verification is very unsafe")
  509. }
  510. if LocalFileSystemRoot != "" {
  511. stat, err := os.Stat(LocalFileSystemRoot)
  512. if err != nil {
  513. return fmt.Errorf("Cannot use local directory: %s", err)
  514. }
  515. if !stat.IsDir() {
  516. return errors.New("Cannot use local directory: not a directory")
  517. }
  518. if LocalFileSystemRoot == "/" {
  519. log.Warning("Exposing root via IMGPROXY_LOCAL_FILESYSTEM_ROOT is unsafe")
  520. }
  521. }
  522. if _, ok := os.LookupEnv("IMGPROXY_USE_GCS"); !ok && len(GCSKey) > 0 {
  523. log.Warning("Set IMGPROXY_USE_GCS to true since it may be required by future versions to enable GCS support")
  524. GCSEnabled = true
  525. }
  526. if WatermarkOpacity <= 0 {
  527. return errors.New("Watermark opacity should be greater than 0")
  528. } else if WatermarkOpacity > 1 {
  529. return errors.New("Watermark opacity should be less than or equal to 1")
  530. }
  531. if FallbackImageHTTPCode < 100 || FallbackImageHTTPCode > 599 {
  532. return errors.New("Fallback image HTTP code should be between 100 and 599")
  533. }
  534. if len(PrometheusBind) > 0 && PrometheusBind == Bind {
  535. return errors.New("Can't use the same binding for the main server and Prometheus")
  536. }
  537. if OpenTelemetryConnectionTimeout < 1 {
  538. return errors.New("OpenTelemetry connection timeout should be greater than zero")
  539. }
  540. if FreeMemoryInterval <= 0 {
  541. return errors.New("Free memory interval should be greater than zero")
  542. }
  543. if DownloadBufferSize < 0 {
  544. return errors.New("Download buffer size should be greater than or equal to 0")
  545. } else if DownloadBufferSize > math.MaxInt32 {
  546. return fmt.Errorf("Download buffer size can't be greater than %d", math.MaxInt32)
  547. }
  548. if BufferPoolCalibrationThreshold < 64 {
  549. return errors.New("Buffer pool calibration threshold should be greater than or equal to 64")
  550. }
  551. return nil
  552. }