values.ts 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202
  1. import { z } from "zod";
  2. // ServiceString is a string value in a service that can be read-only or editable
  3. export const serviceStringValidator = z.object({
  4. readOnly: z.boolean(),
  5. value: z.string(),
  6. });
  7. export type ServiceString = z.infer<typeof serviceStringValidator>;
  8. // ServiceNumber is a number value in a service that can be read-only or editable
  9. export const serviceNumberValidator = z.object({
  10. readOnly: z.boolean(),
  11. value: z.coerce.number(),
  12. });
  13. export type ServiceNumber = z.infer<typeof serviceNumberValidator>;
  14. // ServiceBoolean is a boolean value in a service that can be read-only or editable
  15. export const serviceBooleanValidator = z.object({
  16. readOnly: z.boolean(),
  17. value: z.boolean(),
  18. });
  19. export type ServiceBoolean = z.infer<typeof serviceBooleanValidator>;
  20. // ServiceArray is an array of ServiceStrings
  21. const serviceArrayValidator = z.array(
  22. z.object({
  23. key: z.string(),
  24. value: serviceStringValidator,
  25. })
  26. );
  27. export type ServiceArray = z.infer<typeof serviceArrayValidator>;
  28. const getNumericValue = (
  29. defaultValue: number,
  30. overrideValue?: number,
  31. validAsZero = false
  32. ) => {
  33. if (!overrideValue) {
  34. return defaultValue;
  35. }
  36. if (!validAsZero && overrideValue === 0) {
  37. return defaultValue;
  38. }
  39. return overrideValue;
  40. };
  41. // ServiceField is a helper to create a ServiceString, ServiceNumber, or ServiceBoolean
  42. export const ServiceField = {
  43. string: (defaultValue: string, overrideValue?: string): ServiceString => {
  44. return {
  45. readOnly: !!overrideValue,
  46. value: overrideValue ?? defaultValue,
  47. };
  48. },
  49. number: (
  50. defaultValue: number,
  51. overrideValue?: number,
  52. validAsZero = false
  53. ): ServiceNumber => {
  54. return {
  55. readOnly: !!overrideValue || (validAsZero && overrideValue === 0),
  56. value: getNumericValue(defaultValue, overrideValue, validAsZero),
  57. };
  58. },
  59. boolean: (
  60. defaultValue?: boolean,
  61. overrideValue?: boolean
  62. ): ServiceBoolean => {
  63. return {
  64. readOnly: typeof overrideValue === "boolean",
  65. value: overrideValue ?? defaultValue ?? false,
  66. };
  67. },
  68. };
  69. // Autoscaling
  70. export const autoscalingValidator = z.object({
  71. enabled: serviceBooleanValidator,
  72. minInstances: serviceNumberValidator.optional(),
  73. maxInstances: serviceNumberValidator.optional(),
  74. cpuThresholdPercent: serviceNumberValidator.optional(),
  75. memoryThresholdPercent: serviceNumberValidator.optional(),
  76. });
  77. export type ClientAutoscaling = z.infer<typeof autoscalingValidator>;
  78. export type SerializedAutoscaling = {
  79. enabled: boolean;
  80. minInstances?: number;
  81. maxInstances?: number;
  82. cpuThresholdPercent?: number;
  83. memoryThresholdPercent?: number;
  84. };
  85. export function serializeAutoscaling({
  86. autoscaling,
  87. }: {
  88. autoscaling?: ClientAutoscaling;
  89. }): SerializedAutoscaling | undefined {
  90. return (
  91. autoscaling && {
  92. enabled: autoscaling.enabled.value,
  93. minInstances: autoscaling.minInstances?.value,
  94. maxInstances: autoscaling.maxInstances?.value,
  95. cpuThresholdPercent: autoscaling.cpuThresholdPercent?.value,
  96. memoryThresholdPercent: autoscaling.memoryThresholdPercent?.value,
  97. }
  98. );
  99. }
  100. export function deserializeAutoscaling({
  101. autoscaling,
  102. override,
  103. setDefaults,
  104. }: {
  105. autoscaling?: SerializedAutoscaling;
  106. override?: SerializedAutoscaling;
  107. setDefaults: boolean;
  108. }): ClientAutoscaling | undefined {
  109. return (
  110. autoscaling ? {
  111. enabled: ServiceField.boolean(autoscaling.enabled, override?.enabled),
  112. minInstances: autoscaling.minInstances
  113. ? ServiceField.number(autoscaling.minInstances, override?.minInstances)
  114. : ServiceField.number(1, undefined),
  115. maxInstances: autoscaling.maxInstances
  116. ? ServiceField.number(autoscaling.maxInstances, override?.maxInstances)
  117. : ServiceField.number(10, undefined),
  118. cpuThresholdPercent: autoscaling.cpuThresholdPercent
  119. ? ServiceField.number(
  120. autoscaling.cpuThresholdPercent,
  121. override?.cpuThresholdPercent
  122. )
  123. : ServiceField.number(50, undefined),
  124. memoryThresholdPercent: autoscaling.memoryThresholdPercent
  125. ? ServiceField.number(
  126. autoscaling.memoryThresholdPercent,
  127. override?.memoryThresholdPercent
  128. )
  129. : ServiceField.number(50, undefined),
  130. } : (setDefaults ? {
  131. enabled: ServiceField.boolean(false, undefined),
  132. minInstances: ServiceField.number(1, undefined),
  133. maxInstances: ServiceField.number(10, undefined),
  134. cpuThresholdPercent: ServiceField.number(50, undefined),
  135. memoryThresholdPercent: ServiceField.number(50, undefined),
  136. } : undefined )
  137. );
  138. }
  139. // Health Check
  140. export const healthcheckValidator = z.object({
  141. enabled: serviceBooleanValidator,
  142. httpPath: serviceStringValidator.optional(),
  143. });
  144. export type ClientHealthCheck = z.infer<typeof healthcheckValidator>;
  145. export type SerializedHealthcheck = {
  146. enabled: boolean;
  147. httpPath?: string;
  148. };
  149. export function serializeHealth({
  150. health,
  151. }: {
  152. health?: ClientHealthCheck;
  153. }): SerializedHealthcheck | undefined {
  154. return (
  155. health && {
  156. enabled: health.enabled.value,
  157. httpPath: health.httpPath?.value,
  158. }
  159. );
  160. }
  161. export function deserializeHealthCheck({
  162. health,
  163. override,
  164. setDefaults,
  165. }: {
  166. health?: SerializedHealthcheck;
  167. override?: SerializedHealthcheck;
  168. setDefaults: boolean;
  169. }): ClientHealthCheck | undefined {
  170. return (
  171. health ? {
  172. enabled: ServiceField.boolean(health.enabled, override?.enabled),
  173. httpPath: health.httpPath
  174. ? ServiceField.string(health.httpPath, override?.httpPath)
  175. : ServiceField.string("", undefined),
  176. } : (setDefaults ? {
  177. enabled: ServiceField.boolean(false, undefined),
  178. httpPath: ServiceField.string("", undefined),
  179. } : undefined)
  180. );
  181. }
  182. // Domains
  183. export const domainsValidator = z.array(
  184. z.object({
  185. name: serviceStringValidator,
  186. })
  187. );
  188. export type ClientDomains = z.infer<typeof domainsValidator>;