import React, { useState, useEffect } from "react";
import ReactGA from 'react-ga4';
import theme from "../theme.jsx";
import countries from "../components/Countries.jsx";
import {
Box,
Paper,
Typography,
Divider,
Button,
Grid,
Card,
Dialog,
DialogTitle,
DialogContent,
TextField,
InputAdornment,
IconButton,
Chip,
Checkbox,
Tooltip,
Slider,
DialogActions,
CardContent,
ButtonGroup,
DialogContentText,
ToggleButton,
ToggleButtonGroup,
} from "@mui/material";
import { useNavigate, Link } from "react-router-dom";
import { Autocomplete } from "@mui/material";
import { toast } from "react-toastify"
import {
Cached as CachedIcon,
ContentCopy as ContentCopyIcon,
Draw as DrawIcon,
Close as CloseIcon,
Done as DoneIcon,
Clear as ClearIcon,
AddTask as AddTaskIcon,
} from "@mui/icons-material";
import { typecost, typecost_single, } from "../views/HandlePaymentNew.jsx";
import { handlePayasyougo } from "../views/HandlePaymentNew.jsx"
import Billing from "./Billing.jsx";
const LicencePopup = (props) => {
const { globalUrl, userdata, serverside, billingInfo, stripeKey, setModalOpen, isScale, isLoggedIn, isMobile, selectedOrganization, isCloud } = props;
//const alert = useAlert();
let navigate = useNavigate();
const [selectedDealModalOpen, setSelectedDealModalOpen] = React.useState(false);
const [dealList, setDealList] = React.useState([]);
const [dealName, setDealName] = React.useState("");
const [dealAddress, setDealAddress] = React.useState("");
const [dealType, setDealType] = React.useState("MSSP");
const [dealCountry, setDealCountry] = React.useState("United States");
const [dealCurrency, setDealCurrency] = React.useState("USD");
const [dealStatus, setDealStatus] = React.useState("initiated");
const [dealValue, setDealValue] = React.useState("");
const [dealDiscount, setDealDiscount] = React.useState("");
const [dealerror, setDealerror] = React.useState("");
const [variant, setVariant] = useState(0)
const [shuffleVariant, setShuffleVariant] = useState(isCloud ? 0 : 1)
const [BillingEmail, setBillingEmail] = useState(selectedOrganization?.Billing?.Email);
const [openChangeEmailBox, setOpenChangeEmailBox] = useState(false);
// const parsedFields = maxFields === undefined ? 300 : maxFields
const initialShuffleVariant = isCloud ? 0 : 1;
const [paymentType, setPaymentType] = useState(0)
const [currentPrice, setCurrentPrice] = useState(129)
const [isLoaded, setIsLoaded] = useState(false)
const [errorMessage, setErrorMessage] = useState("")
const [highlight, setHighlight] = useState(false)
// Cloud
const [calculatedApps, setCalculatedApps] = useState(600)
const [calculatedCost, setCalculatedCost] = useState("$600")
const [selectedValue, setSelectedValue] = useState(100)
useEffect(() => {
if(selectedOrganization?.Billing?.Email !== BillingEmail) {
setBillingEmail(selectedOrganization?.Billing?.Email);
}
}, [selectedOrganization])
// Onprem
const [calculatedCores, setCalculatedCores] = useState('600')
const [onpremSelectedValue, setOnpremSelectedValue] = useState(8)
const [billingCycle, setBillingCycle] = useState("annual")
const [scaleValue, setScaleValue] = useState(
new URLSearchParams(window.location.search).get("app_runs") ||
(userdata?.app_execution_limit / 1000) + 50 || 10
);
useEffect(() => {
setScaleValue((userdata?.app_execution_limit / 1000) + 50 || 10)
}, [userdata])
const getPrice = (basePrice) => {
return Math.round(billingCycle === "annual" ? basePrice * 0.9 : basePrice); // 10% discount for annual
};
const stripe = typeof window === 'undefined' || window.location === undefined ? "" : props.stripeKey === undefined ? "" : window.Stripe ? window.Stripe(props.stripeKey) : ""
// Handle slider change for Scale plan
const handleScaleChange = (event, newValue) => {
setScaleValue(newValue);
// Add app runs to URL query params
const urlSearchParams = new URLSearchParams(window.location.search);
urlSearchParams.set("app_runs", newValue); // Convert to actual app runs (k to actual number)
const newUrl = `${window.location.pathname}?${urlSearchParams.toString()}`;
window.history.replaceState({}, "", newUrl);
};
// Handle billing cycle change
const handleBillingCycleChange = (event, newValue) => {
if (newValue !== null) {
setBillingCycle(newValue);
if(isCloud){
ReactGA.event({
category: 'Billingpage',
action: 'Billing Cycle Changed',
label: `${billingCycle} -> ${newValue}`,
});
}
// Add billing cycle to URL query params
const urlSearchParams = new URLSearchParams(window.location.search);
urlSearchParams.set("billing_cycle", newValue);
const newUrl = `${
window.location.pathname
}?${urlSearchParams.toString()}`;
window.history.replaceState({}, "", newUrl);
}
};
const payasyougo = "Pay as you go"
const paperStyle = {
padding: 20,
paddingBottom: 30,
borderRadius: theme.palette?.borderRadius,
height: "100%"
}
billingInfo.subscription = {
"active": true,
"name": userdata?.app_execution_limit === 10000 ? "10,000 App Runs" : "2,000 App Runs",
"price": "Free",
"currency": "Free",
"currency_text": "",
"interval": "",
"description": "Pay as you go",
"features": [
"Community Support",
`Includes ${userdata?.app_execution_limit === 10000 ? "10,000" : "2,000"} app run/month for free. `,
"Get all 2500+ Apps and 10 Workflows",
"Invite up to 5 users"
],
"limit": userdata?.app_execution_limit === 10000 ? 10000 : 2000,
}
const sendSignatureRequest = (subscription) => {
const url = `${globalUrl}/api/v1/orgs/${selectedOrganization.id}`;
fetch(url, {
body: JSON.stringify({
org_id: selectedOrganization.id,
subscription: subscription,
}),
mode: "cors",
method: "POST",
credentials: "include",
crossDomain: true,
withCredentials: true,
headers: {
"Content-Type": "application/json; charset=utf-8",
},
})
.then((response) => {
if (response.status !== 200) {
console.log("Error in response");
}
return response.json();
})
.then((responseJson) => {
console.log("Response from signature request: ", responseJson);
})
.catch((error) => {
console.log("Error: ", error);
})
}
const SubscriptionObject = (props) => {
const { globalUrl, index, userdata, serverside, billingInfo, stripeKey, selectedOrganization, handleGetOrg, subscription, highlight, } = props;
const [signatureOpen, setSignatureOpen] = React.useState(false);
const [tosChecked, setTosChecked] = React.useState(subscription.eula_signed)
const [hovered, setHovered] = React.useState(false)
const [newBillingEmail, setNewBillingEmail] = useState('');
var top_text = "Starter Plan"
// if (subscription.limit === undefined && subscription.level === undefined || subscription.level === null || subscription.level === 0) {
// subscription.name = "Enterprise"
// subscription.currency_text = "$"
// subscription.price = subscription.level * 180
// subscription.limit = subscription.level * 100000
// subscription.interval = subscription.recurrence
// subscription.features = [
// "Includes " + subscription.limit + " app runs/month. ",
// "Multi-Tenancy and Region-Selection",
// "And all other features from /pricing",
// ]
// }
// if (userdata?.app_execution_limit >= 300000) {
// subscription.name = "Enterprise"
// subscription.currency_text = "$"
// subscription.price = typecost_single
// subscription.limit = userdata?.app_execution_limit
// subscription.interval = "app run / month"
// subscription.features = [
// "Includes " + (userdata?.app_execution_limit/1000) + "K app runs/month. ",
// "Multi-Tenancy and Region-Selection",
// "And all other features from /pricing",
// ]
// }
var newPaperstyle = JSON.parse(JSON.stringify(paperStyle))
if (subscription.name === "Enterprise" && subscription.active === true) {
top_text = "Enterprise Plan"
// newPaperstyle.border = "1px solid #f85a3e"
}
var showSupport = false
if (subscription.name.includes("default")) {
top_text = "Custom Contract"
// newPaperstyle.border = "1px solid #f85a3e"
showSupport = true
}
if (subscription.name.includes("App Run Units")) {
top_text = "Scale Plan"
showSupport = true
}
if (subscription.name.includes("Open Source")) {
top_text = "Open Source"
showSupport = true
}
if (subscription.name.includes("Scale")) {
top_text = "Scale access"
}
if (highlight === true) {
// Add an "Upgrade now" button
// newPaperstyle.border = "1px solid #f85a3e"
}
const handleClickOpen = () => {
setOpenChangeEmailBox(true);
};
const HandleChangeBillingEmail = (orgId) => {
const email = newBillingEmail;
const emailPattern = /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,6}$/;
if (!emailPattern.test(email)) {
toast("Please enter a valid email address");
return;
} else {
setNewBillingEmail(email);
}
toast("Updating billing email. Please Wait")
const data = {
org_id: orgId,
email: newBillingEmail,
billing: {
email: newBillingEmail,
},
};
const url = `${globalUrl}/api/v1/orgs/${orgId}/billing`;
fetch(url, {
method: "POST",
body: JSON.stringify(data),
credentials: "include",
headers: {
"Content-Type": "application/json",
},
})
.then((response) => {
if (response.status !== 200) {
console.log("Bad status code in get org:", response.status);
}
return response.json();
}).then((responseJson) => {
if (responseJson.success === true) {
toast.success("Successfully updated billing email");
setBillingEmail(newBillingEmail);
setOpenChangeEmailBox(false);
} else {
toast.error("Failed to update billing email. Please try again.");
}
})
.catch((error) => {
console.log("Error getting org:", error);
});
}
return (
: null}
{isCloud && highlight === true && top_text !== "Starter Plan" ?
{subscription.features !== undefined && subscription.features !== null ?
subscription.features.map((feature, index) => {
var parsedFeature = feature
if (feature.includes("Documentation: ")) {
parsedFeature =
Documentation to get started
}
if (feature.includes("Worker License: ")) {
const fieldId = "webhook_uri_field_" + index
parsedFeature =