diff --git a/app/db/crud.py b/app/db/crud.py
@@ -185,6 +185,7 @@ def update_host(db: Session, db_host: InboundHost, host: InboundHostModify):
db_host.fingerprint = host.fingerprint
db_host.fragment = host.fragment.model_dump() if host.fragment else None
db_host.mux = host.mux
+ db_host.is_disabled = host.is_disabled
db.commit()
db.refresh(db_host)
return db_host
diff --git a/app/utils/share.py b/app/utils/share.py
@@ -235,6 +235,8 @@ def generate_user_configs(
hosts = crud.get_inbound_hosts(db, inb_id)
for host in hosts:
+ if host.is_disabled:
+ continue
host_snis = host.sni.split(",") if host.sni else []
sni_list = host_snis or inbound["sni"]
if sni_list:
diff --git a/dashboard/src/features/subscription-settings/form/fields/shuffle-configs.tsx b/dashboard/src/components/form-fields/checkbox.tsx
rename from dashboard/src/features/subscription-settings/form/fields/shuffle-configs.tsx
rename to dashboard/src/components/form-fields/checkbox.tsx
@@ -6,15 +6,13 @@ import {
FormControl,
} from "@marzneshin/components";
import { useFormContext } from "react-hook-form";
-import { useTranslation } from "react-i18next";
-export const ShuffleConfigsField = () => {
- const { t } = useTranslation()
+export const CheckboxField = ({ name, label }: { name: string, label: string }) => {
const form = useFormContext();
return (
<FormField
control={form.control}
- name="shuffle_configs"
+ name={name}
render={({ field }) => (
<FormItem className="flex flex-row items-start space-x-3 space-y-0 rounded-md py-2">
<FormControl>
@@ -25,7 +23,7 @@ export const ShuffleConfigsField = () => {
</FormControl>
<div className="space-y-1 leading-none">
<FormLabel>
- {t("page.settings.subscription-settings.shuffle-configs")}
+ {label}
</FormLabel>
</div>
</FormItem>
diff --git a/dashboard/src/features/users/components/form-fields/date.tsx b/dashboard/src/components/form-fields/date.tsx
rename from dashboard/src/features/users/components/form-fields/date.tsx
rename to dashboard/src/components/form-fields/date.tsx
diff --git a/dashboard/src/components/form-fields/index.ts b/dashboard/src/components/form-fields/index.ts
@@ -0,0 +1,2 @@
+export * from "./date";
+export * from "./checkbox";
diff --git a/dashboard/src/components/index.ts b/dashboard/src/components/index.ts
@@ -19,3 +19,4 @@ export * from "./boolean-pill";
export * from "./info-table";
export * from "./skeletons";
export * from "./no-propogation-button";
+export * from "./form-fields";
diff --git a/dashboard/src/features/hosts/dialogs/mutation/fields/is-disabled.tsx b/dashboard/src/features/hosts/dialogs/mutation/fields/is-disabled.tsx
@@ -0,0 +1,22 @@
+import { Switch, FormField, FormControl, FormItem } from "@marzneshin/components";
+import { useFormContext } from "react-hook-form";
+
+export const IsDisabled = () => {
+ const form = useFormContext();
+ return (
+ <FormField
+ control={form.control}
+ name="is_disabled"
+ render={({ field }) => (
+ <FormItem>
+ <FormControl>
+ <Switch
+ checked={!field.value}
+ onCheckedChange={(checked) => field.onChange(!checked)}
+ />
+ </FormControl>
+ </FormItem>
+ )}
+ />
+ )
+}
diff --git a/dashboard/src/features/hosts/dialogs/mutation/fields/remark.tsx b/dashboard/src/features/hosts/dialogs/mutation/fields/remark.tsx
@@ -13,6 +13,7 @@ import { PopoverGuide } from '@marzneshin/features/hosts';
import { useFormContext } from "react-hook-form";
import { useTranslation } from "react-i18next";
import { InfoIcon } from 'lucide-react';
+import { IsDisabled } from "./is-disabled";
export const RemarkField = () => {
const { t } = useTranslation()
@@ -33,6 +34,7 @@ export const RemarkField = () => {
<PopoverGuide />
</PopoverContent>
</Popover>
+ <IsDisabled />
</FormLabel>
<FormControl>
<Input {...field} />
diff --git a/dashboard/src/features/hosts/schema/get-default.ts b/dashboard/src/features/hosts/schema/get-default.ts
@@ -14,5 +14,6 @@ export const getDefaultValues = (): HostSchemaType => {
alpn: "",
allowinsecure: false,
fingerprint: "",
+ is_disabled: false,
}
};
diff --git a/dashboard/src/features/hosts/schema/hosts-schema.ts b/dashboard/src/features/hosts/schema/hosts-schema.ts
@@ -81,4 +81,5 @@ export const HostSchema = z.object({
])
.optional()
.default("none"),
+ is_disabled: z.boolean(),
});
diff --git a/dashboard/src/features/subscription-settings/form/fields/index.ts b/dashboard/src/features/subscription-settings/form/fields/index.ts
@@ -2,7 +2,4 @@ export * from "./url-prefix"
export * from "./profile-title"
export * from "./support-link"
export * from "./update-interval"
-export * from "./template-on-acceptance"
export * from "./placeholder-remark"
-export * from "./placeholder-if-disabled"
-export * from "./shuffle-configs"
diff --git a/dashboard/src/features/subscription-settings/form/fields/placeholder-if-disabled.tsx b/dashboard/src/features/subscription-settings/form/fields/placeholder-if-disabled.tsx
@@ -1,35 +0,0 @@
-import {
- FormField,
- FormItem,
- FormLabel,
- Checkbox,
- FormControl,
-} from "@marzneshin/components";
-import { useFormContext } from "react-hook-form";
-import { useTranslation } from "react-i18next";
-
-export const PlaceholderIfDisabledField = () => {
- const { t } = useTranslation()
- const form = useFormContext();
- return (
- <FormField
- control={form.control}
- name="placeholder_if_disabled"
- render={({ field }) => (
- <FormItem className="flex flex-row items-start space-x-3 space-y-0 rounded-md py-2">
- <FormControl>
- <Checkbox
- checked={field.value}
- onCheckedChange={field.onChange}
- />
- </FormControl>
- <div className="space-y-1 leading-none">
- <FormLabel>
- {t("page.settings.subscription-settings.placeholder-if-disabled")}
- </FormLabel>
- </div>
- </FormItem>
- )}
- />
- )
-}
diff --git a/dashboard/src/features/subscription-settings/form/fields/template-on-acceptance.tsx b/dashboard/src/features/subscription-settings/form/fields/template-on-acceptance.tsx
@@ -1,35 +0,0 @@
-import {
- FormField,
- FormItem,
- FormLabel,
- Checkbox,
- FormControl,
-} from "@marzneshin/components";
-import { useFormContext } from "react-hook-form";
-import { useTranslation } from "react-i18next";
-
-export const TemplateOnAcceptanceField = () => {
- const { t } = useTranslation()
- const form = useFormContext();
- return (
- <FormField
- control={form.control}
- name="template_on_acceptance"
- render={({ field }) => (
- <FormItem className="flex flex-row items-start space-x-3 space-y-0 rounded-md py-2">
- <FormControl>
- <Checkbox
- checked={field.value}
- onCheckedChange={field.onChange}
- />
- </FormControl>
- <div className="space-y-1 leading-none">
- <FormLabel>
- {t("page.settings.subscription-settings.template-on-acceptance")}
- </FormLabel>
- </div>
- </FormItem>
- )}
- />
- )
-}
diff --git a/dashboard/src/features/subscription-settings/form/form.tsx b/dashboard/src/features/subscription-settings/form/form.tsx
@@ -12,17 +12,15 @@ import {
FormLabel,
Separator,
Awaiting,
+ CheckboxField,
} from "@marzneshin/components";
import { Schema } from "./schema"
import { Overlay } from "./overlay"
import {
- TemplateOnAcceptanceField,
ProfileTitleField,
SupportLinkField,
UpdateIntervalField,
PlaceholderRemarkField,
- PlaceholderIfDisabledField,
- ShuffleConfigsField
} from "./fields";
import { NoRulesAlert } from "./no-rules-alert";
import {
@@ -82,10 +80,19 @@ export function SubscriptionRulesForm() {
<UpdateIntervalField />
<SupportLinkField />
</div>
- <TemplateOnAcceptanceField />
+ <CheckboxField
+ name="template_on_acceptance"
+ label={t("page.settings.subscription-settings.template-on-acceptance")}
+ />
<PlaceholderRemarkField />
- <PlaceholderIfDisabledField />
- <ShuffleConfigsField />
+ <CheckboxField
+ name="placeholder_if_disabled"
+ label={t("page.settings.subscription-settings.placeholder-if-disabled")}
+ />
+ <CheckboxField
+ name="shuffle_configs"
+ label={t("page.settings.subscription-settings.shuffle-configs")}
+ />
<Separator className="my-3" />
<h4 className="text-lg mt-2">
{t("page.settings.subscription-settings.subscription-title")}
diff --git a/dashboard/src/features/users/components/dialogs/mutation/fields/activation-deadline.tsx b/dashboard/src/features/users/components/dialogs/mutation/fields/activation-deadline.tsx
@@ -1,5 +1,5 @@
-import { DateField } from "@marzneshin/features/users";
+import { DateField } from "@marzneshin/components";
import { FC } from "react";
export const ActivationDeadlineField: FC = () => {
diff --git a/dashboard/src/features/users/components/dialogs/mutation/fields/expire-date.tsx b/dashboard/src/features/users/components/dialogs/mutation/fields/expire-date.tsx
@@ -1,4 +1,4 @@
-import { DateField } from "@marzneshin/features/users";
+import { DateField } from "@marzneshin/components";
import { FC } from "react";
export const ExpireDateField: FC = () => {
diff --git a/dashboard/src/features/users/components/form-fields/index.ts b/dashboard/src/features/users/components/form-fields/index.ts
@@ -1,2 +1 @@
export * from "./username";
-export * from "./date";