private int AddHostingPlan(string name, int serverId)
		{
			try
			{
				Log.WriteStart("Adding hosting plan");
				// gather form info
				HostingPlanInfo plan = new HostingPlanInfo();
				plan.UserId = 1;
				plan.PlanId = 0;
				plan.IsAddon = false;
				plan.PlanName = name;
				plan.PlanDescription = "";
				plan.Available = true; // always available

				plan.SetupPrice = 0;
				plan.RecurringPrice = 0;
				plan.RecurrenceLength = 1;
				plan.RecurrenceUnit = 2; // month

				plan.PackageId = 0;
				plan.ServerId = serverId;
				List<HostingPlanGroupInfo> groups = new List<HostingPlanGroupInfo>();
				List<HostingPlanQuotaInfo> quotas = new List<HostingPlanQuotaInfo>();

				DataSet ds = ES.Services.Packages.GetHostingPlanQuotas(-1, 0, serverId);

				foreach (DataRow groupRow in ds.Tables[0].Rows)
				{
					bool enabled = (bool)groupRow["ParentEnabled"];
					if (!enabled)
						continue; // disabled group

					int groupId = (int)groupRow["GroupId"]; ;

					HostingPlanGroupInfo group = new HostingPlanGroupInfo();
					group.GroupId = groupId;
					group.Enabled = true;
					group.GroupName = Convert.ToString(groupRow["GroupName"]);
					group.CalculateDiskSpace = (bool)groupRow["CalculateDiskSpace"];
					group.CalculateBandwidth = (bool)groupRow["CalculateBandwidth"];
					groups.Add(group);

					DataView dvQuotas = new DataView(ds.Tables[1], "GroupID=" + group.GroupId.ToString(), "", DataViewRowState.CurrentRows);
					List<HostingPlanQuotaInfo> groupQuotas = GetGroupQuotas(groupId, dvQuotas);
					quotas.AddRange(groupQuotas);
				}

				plan.Groups = groups.ToArray();
				plan.Quotas = quotas.ToArray();

				// Add Web Deploy publishing support if enabled by default
				if (Utils.IsWebDeployInstalled())
				{
					var resGroupWeb = Array.Find(plan.Groups, x => x.GroupName.Equals(ResourceGroups.Web, StringComparison.OrdinalIgnoreCase));
					//
					if (resGroupWeb != null)
					{
						EnableRemoteManagementQuota(quotas, new DataView(ds.Tables[1], String.Format("GroupID = {0}", resGroupWeb.GroupId), "", DataViewRowState.CurrentRows));
					}
				}

				int planId = ES.Services.Packages.AddHostingPlan(plan);
				if (planId > 0)
				{
					Log.WriteEnd("Added hosting plan");
				}
				else
				{
					Log.WriteError(string.Format("Enterprise Server error: {0}", planId));
				}
				return planId;
			}
			catch (Exception ex)
			{
				if (!Utils.IsThreadAbortException(ex))
					Log.WriteError("Hosting plan configuration error", ex);
				return -1;
			}
		}
		private int AddHostingPlan(string name, int serverId)
		{
			try
			{
				Log.WriteStart("Adding hosting plan");
				// gather form info
				HostingPlanInfo plan = new HostingPlanInfo();
				plan.UserId = 1;
				plan.PlanId = 0;
				plan.IsAddon = false;
				plan.PlanName = name;
				plan.PlanDescription = "";
				plan.Available = true; // always available

				plan.SetupPrice = 0;
				plan.RecurringPrice = 0;
				plan.RecurrenceLength = 1;
				plan.RecurrenceUnit = 2; // month

				plan.PackageId = 0;
				plan.ServerId = serverId;
				List<HostingPlanGroupInfo> groups = new List<HostingPlanGroupInfo>();
				List<HostingPlanQuotaInfo> quotas = new List<HostingPlanQuotaInfo>();

				DataSet ds = ES.Services.Packages.GetHostingPlanQuotas(-1, 0, serverId);

				foreach (DataRow groupRow in ds.Tables[0].Rows)
				{
					bool enabled = (bool)groupRow["ParentEnabled"];
					if (!enabled)
						continue; // disabled group

					int groupId = (int)groupRow["GroupId"]; ;

					HostingPlanGroupInfo group = new HostingPlanGroupInfo();
					group.GroupId = groupId;
					group.Enabled = true;
					group.CalculateDiskSpace = (bool)groupRow["CalculateDiskSpace"];
					group.CalculateBandwidth = (bool)groupRow["CalculateBandwidth"];
					groups.Add(group);

					DataView dvQuotas = new DataView(ds.Tables[1], "GroupID=" + group.GroupId.ToString(), "", DataViewRowState.CurrentRows);
					List<HostingPlanQuotaInfo> groupQuotas = GetGroupQuotas(groupId, dvQuotas);
					quotas.AddRange(groupQuotas);

				}

				plan.Groups = groups.ToArray();
				plan.Quotas = quotas.ToArray();

				int planId = ES.Services.Packages.AddHostingPlan(plan);
				if (planId > 0)
				{
					Log.WriteEnd("Added hosting plan");
				}
				else
				{
					Log.WriteError(string.Format("Enterprise Server error: {0}", planId));
				}
				return planId;
			}
			catch (Exception ex)
			{
				if (!Utils.IsThreadAbortException(ex))
					Log.WriteError("Hosting plan configuration error", ex);
				return -1;
			}
		}
        public static KeyValueBunch GetHostingPlansQuotas(int resellerId, int planId)
        {
            KeyValueBunch hpQuotas = new KeyValueBunch();

            //
            ES.SecurityContext.SetThreadPrincipal(resellerId);
            //
            ES.HostingPlanContext ctx = ES.PackageController.GetHostingPlanContext(planId);
            //
            if (ctx != null)
            {
                //
                ES.QuotaValueInfo[] quotasArray = ctx.QuotasArray;
                //
                for (int i = 0; i < ctx.GroupsArray.Length; i++)
                {
                    //
                    ES.HostingPlanGroupInfo group = ctx.GroupsArray[i];
                    //
                    if (group.Enabled)
                    {
                        //
                        List <string> planQuota = new List <string>();
                        //
                        foreach (ES.QuotaValueInfo quota in quotasArray)
                        {
                            //
                            if (quota.QuotaName.StartsWith(group.GroupName))
                            {
                                // boolean quota
                                if (quota.QuotaTypeId == 1)
                                {
                                    // only enabled quotas will be displayed
                                    if (quota.QuotaAllocatedValue == 1)
                                    {
                                        planQuota.Add(quota.QuotaName + "=Enabled");
                                    }
                                }
                                // numeric
                                else
                                {
                                    if (quota.QuotaAllocatedValue > 0)
                                    {
                                        planQuota.Add(quota.QuotaName + "=" + quota.QuotaAllocatedValue);
                                    }
                                    else if (quota.QuotaAllocatedValue == -1)
                                    {
                                        planQuota.Add(quota.QuotaName + "=Unlimited");
                                    }
                                }
                            }
                        }
                        // only filled-up groups are allowed to display
                        if (planQuota.Count > 0)
                        {
                            hpQuotas[group.GroupName] = String.Join(",", planQuota.ToArray());
                        }
                    }
                }
            }
            //
            return(hpQuotas);
        }
        public void CollectFormData()
        {
            groups = new List<HostingPlanGroupInfo>();
            quotas = new List<HostingPlanQuotaInfo>();

            // gather info
            foreach (RepeaterItem item in dlGroups.Items)
            {
                Literal litGroupId = (Literal)item.FindControl("groupId");
                CheckBox chkEnabled = (CheckBox)item.FindControl("chkEnabled");
                CheckBox chkCountDiskspace = (CheckBox)item.FindControl("chkCountDiskspace");
                CheckBox chkCountBandwidth = (CheckBox)item.FindControl("chkCountBandwidth");

                if (!chkEnabled.Checked)
                    continue; // disabled group

                HostingPlanGroupInfo group = new HostingPlanGroupInfo();
                group.GroupId = Utils.ParseInt(litGroupId.Text, 0);
                group.Enabled = chkEnabled.Checked;
                group.CalculateDiskSpace = chkCountDiskspace.Checked;
                group.CalculateBandwidth = chkCountBandwidth.Checked;
                groups.Add(group);

                // iterate quotas
                DataList dlQuotas = (DataList)item.FindControl("dlQuotas");
                foreach (DataListItem quotaItem in dlQuotas.Items)
                {
                    QuotaEditor quotaEditor = (QuotaEditor)quotaItem.FindControl("quotaEditor");
                 
                    HostingPlanQuotaInfo quota = new HostingPlanQuotaInfo();
                    quota.QuotaId = quotaEditor.QuotaId;
                    quota.QuotaValue = quotaEditor.QuotaValue;
                    quotas.Add(quota);
                }
            }
        }
        public static HostingPlanContext GetHostingPlanContext(int planId)
        {
            HostingPlanContext context = new HostingPlanContext();

            // load hosting plan
            context.HostingPlan = GetHostingPlan(planId);
            if (context.HostingPlan == null)
                return null;

            // load groups and quotas
            DataSet ds = GetHostingPlanQuotas(0, planId, 0);

            List<HostingPlanGroupInfo> groups = new List<HostingPlanGroupInfo>();
            foreach (DataRow dr in ds.Tables[0].Rows)
            {
                HostingPlanGroupInfo group = new HostingPlanGroupInfo();
                group.GroupId = (int)dr["GroupID"];
                group.GroupName = (string)dr["GroupName"];

                bool enabled = (bool)dr["Enabled"];
                group.Enabled = enabled;
                group.CalculateBandwidth = (bool)dr["CalculateBandwidth"];
                group.CalculateDiskSpace = (bool)dr["CalculateDiskSpace"];

                if (enabled)
                {
                    groups.Add(group);
                    context.Groups.Add(group.GroupName, group);
                }
            }

            List<QuotaValueInfo> quotas = new List<QuotaValueInfo>();
            foreach (DataRow dr in ds.Tables[1].Rows)
            {
                QuotaValueInfo quota = new QuotaValueInfo();
                quota.QuotaId = (int)dr["QuotaId"];
                quota.GroupId = (int)dr["GroupId"];
                quota.QuotaName = (string)dr["QuotaName"];
                quota.QuotaTypeId = (int)dr["QuotaTypeId"];
                quota.QuotaAllocatedValue = (int)dr["QuotaValue"];
                quotas.Add(quota);
                context.Quotas.Add(quota.QuotaName, quota);
            }

            context.GroupsArray = groups.ToArray();
            context.QuotasArray = quotas.ToArray();

            return context;
        }
        public static PackageContext GetPackageContext(int packageId)
        {
            PackageContext context = new PackageContext();

            // load package
            context.Package = GetPackage(packageId);
            if (context.Package == null)
                return null;

            // load groups and quotas
            DataSet ds = GetPackageQuotas(packageId);

            List<HostingPlanGroupInfo> groups = new List<HostingPlanGroupInfo>();
            foreach (DataRow dr in ds.Tables[0].Rows)
            {
                HostingPlanGroupInfo group = new HostingPlanGroupInfo();
                group.GroupId = (int)dr["GroupID"];
                group.GroupName = (string)dr["GroupName"];
                group.Enabled = true;
                group.CalculateBandwidth = (bool)dr["CalculateBandwidth"];
                group.CalculateDiskSpace = (bool)dr["CalculateDiskSpace"];
                groups.Add(group);
                context.Groups.Add(group.GroupName, group);
            }

            List<QuotaValueInfo> quotas = new List<QuotaValueInfo>();
            foreach (DataRow dr in ds.Tables[1].Rows)
            {
                QuotaValueInfo quota = new QuotaValueInfo();
                quota.QuotaId = (int)dr["QuotaId"];
                quota.GroupId = (int)dr["GroupId"];
                quota.QuotaName = (string)dr["QuotaName"];
                quota.QuotaTypeId = (int)dr["QuotaTypeId"];
                quota.QuotaAllocatedValue = (int)dr["QuotaValue"];
                quota.QuotaUsedValue = (int)dr["QuotaUsedValue"];
                quota.QuotaExhausted = (packageId < 2) || (quota.QuotaAllocatedValue != -1 && quota.QuotaUsedValue >= quota.QuotaAllocatedValue);
                quotas.Add(quota);
                context.Quotas.Add(quota.QuotaName, quota);
            }

            context.GroupsArray = groups.ToArray();
            context.QuotasArray = quotas.ToArray();

            return context;
        }
        private static string BuildPlanQuotasXml(HostingPlanGroupInfo[] groups, HostingPlanQuotaInfo[] quotas)
        {
            // build xml
            /*
            XML Format:

            <plan>
                <groups>
	                <group id="16" enabled="1" calculateDiskSpace="1" calculateBandwidth="1"/>
                </groups>
                <quotas>
	                <quota id="2" value="2"/>
                </quotas>
            </plan>

            */

            if (groups == null || quotas == null)
                return null;

            XmlDocument doc = new XmlDocument();
            XmlElement nodePlan = doc.CreateElement("plan");

            XmlElement nodeGroups = doc.CreateElement("groups");
            nodePlan.AppendChild(nodeGroups);
            XmlElement nodeQuotas = doc.CreateElement("quotas");
            nodePlan.AppendChild(nodeQuotas);

            // groups
            if (groups != null)
            {
                foreach (HostingPlanGroupInfo group in groups)
                {
                    XmlElement nodeGroup = doc.CreateElement("group");
                    nodeGroups.AppendChild(nodeGroup);
                    nodeGroup.SetAttribute("id", group.GroupId.ToString());
                    nodeGroup.SetAttribute("enabled", group.Enabled ? "1" : "0");
                    nodeGroup.SetAttribute("calculateDiskSpace", group.CalculateDiskSpace ? "1" : "0");
                    nodeGroup.SetAttribute("calculateBandwidth", group.CalculateBandwidth ? "1" : "0");
                }
            }

            // quotas
            if (quotas != null)
            {
                foreach (HostingPlanQuotaInfo quota in quotas)
                {
                    XmlElement nodeQuota = doc.CreateElement("quota");
                    nodeQuotas.AppendChild(nodeQuota);
                    nodeQuota.SetAttribute("id", quota.QuotaId.ToString());
                    nodeQuota.SetAttribute("value", quota.QuotaValue.ToString());
                }
            }

            return nodePlan.OuterXml;
        }