UNPKG

@cocalc/server

Version:

CoCalc server functionality: functions used by either the hub and the next.js server

108 lines 4.62 kB
"use strict"; /* * This file is part of CoCalc: Copyright © 2020 Sagemath, Inc. * License: AGPLv3 s.t. "Commons Clause" – see LICENSE.md for details */ Object.defineProperty(exports, "__esModule", { value: true }); exports.getProductId = void 0; const site_license_1 = require("@cocalc/util/consts/site-license"); const timecalcs_1 = require("@cocalc/util/stripe/timecalcs"); const dedicated_1 = require("@cocalc/util/upgrades/dedicated"); // When we change pricing, the products in stripe will already // exist with old prices (often grandfathered) so we may want to // instead change the version so new products get created // automatically. // 20220406: version "1" after discovering an unintentional volume discount, // skewing the unit price per "product" in stripe. // 20220425: keeping version "1" when introducing "boost" (appending an uppercase "B") // and dedicated resources (they are explicitly listed and define their own "stripeID") // i.e. starting with "dVW" or "dD", which is distinct from starting with "a[idle]" // 20220601: price increases, due to inflation, etc. const VERSION = 2; function getProductId(info) { /* We generate a unique identifier that represents the parameters of the purchase. The following parameters determine what "product" they are purchasing: - custom_uptime (until 2022-02: custom_always_running) - custom_cpu - custom_dedicated_cpu - custom_disk - custom_member - custom_ram - custom_dedicated_ram - period: subscription or set number of days We encode these in a string which serves to identify the product. */ function period() { if (info.type === "disk") throw new Error("disk do not have a period"); if (info.subscription == "no") { return (0, timecalcs_1.getDays)(info).toString(); } else { return "0"; // 0 means "subscription" -- same product for all types of subscription billing; } } // this is backwards compatible: short: 0, always_running: 1, ... function idleTimeout() { if (info.type !== "quota") throw new Error("idle_timeout only for quota"); switch (info.custom_uptime) { case "short": return 0; case "always_running": return 1; default: return 1 + site_license_1.LicenseIdleTimeoutsKeysOrdered.indexOf(info.custom_uptime); } } const type = info.type; const pid = [`license_`]; switch (type) { case "quota": pid.push(...[ `a${idleTimeout()}`, `b${info.user == "business" ? 1 : 0}`, `c${info.custom_cpu}`, `d${info.custom_disk}`, `m${info.custom_member ? 1 : 0}`, `p${period()}`, `r${info.custom_ram}`, ]); if (info.custom_dedicated_ram) { pid.push(`y${info.custom_dedicated_ram}`); } if (info.custom_dedicated_cpu) { pid.push(`z${Math.round(10 * info.custom_dedicated_cpu)}`); } // boost licenses have the same price as corresponding regular licenses, but their user visible title/description is different! if (info.boost === true) { pid.push("B"); } break; // this makes also sure to only purchase a known disk (nothing made up) case "disk": if (typeof info.dedicated_disk === "boolean") { throw new Error(`didicated_disk configuration must be an object!`); } const disk = dedicated_1.PRICES.disks[(0, dedicated_1.getDedicatedDiskKey)(info.dedicated_disk)]; if (disk == null) { throw new Error("no disk found – should never happen!"); } pid.push(disk.stripeID); break; // we make sure only known VMs can be bought (and later we check if the price matches as well) case "vm": const vm = dedicated_1.PRICES.vms[info.dedicated_vm.machine]; if (vm == null) { throw new Error(`VM of type ${info.dedicated_vm.machine} not found`); } pid.push(vm.stripeID); break; default: throw new Error(`Product ID: unknown type ${type}`); } pid.push(`_v${VERSION}`); return pid.join(""); } exports.getProductId = getProductId; //# sourceMappingURL=product-id.js.map