diff --git a/app/db/crud.py b/app/db/crud.py
@@ -162,7 +162,7 @@ def add_host(db: Session, inbound: Inbound, host: InboundHostModify):
host=host.host,
inbound=inbound,
security=host.security,
- alpn=host.alpn,
+ alpn=host.alpn.value,
fingerprint=host.fingerprint,
fragment=host.fragment.model_dump() if host.fragment else None,
mux=host.mux,
@@ -181,7 +181,7 @@ def update_host(db: Session, db_host: InboundHost, host: InboundHostModify):
db_host.sni = host.sni
db_host.host = host.host
db_host.security = host.security
- db_host.alpn = host.alpn
+ db_host.alpn = host.alpn.value
db_host.fingerprint = host.fingerprint
db_host.fragment = host.fragment.model_dump() if host.fragment else None
db_host.mux = host.mux
diff --git a/app/db/migrations/versions/5410d8ec78ff_alpn_to_string.py b/app/db/migrations/versions/5410d8ec78ff_alpn_to_string.py
@@ -0,0 +1,70 @@
+"""make host alpn string
+
+Revision ID: 5410d8ec78ff
+Revises: b0357faf51c8
+Create Date: 2024-07-24 22:47:51.528849
+
+"""
+
+import sqlalchemy as sa
+from alembic import op
+from sqlalchemy.dialects import postgresql, mysql
+
+# revision identifiers, used by Alembic.
+revision = "5410d8ec78ff"
+down_revision = "b0357faf51c8"
+branch_labels = None
+depends_on = None
+
+
+def upgrade() -> None:
+ # ### commands auto generated by Alembic - please adjust! ###
+ if (dialect := op.get_bind().dialect.name) == "postgresql":
+ op.alter_column(
+ "hosts",
+ "alpn",
+ existing_type=postgresql.ENUM(
+ "none", "h2", "http/1.1", "h2,http/1.1", name="proxyhostalpn"
+ ),
+ type_=sa.String(length=32),
+ existing_nullable=False,
+ nullable=True,
+ server_default=None,
+ )
+ elif dialect == "mysql" or dialect == "mariadb":
+ op.alter_column(
+ "hosts",
+ "alpn",
+ existing_type=mysql.ENUM("none", "h2", "http/1.1", "h2,http/1.1"),
+ type_=sa.String(length=32),
+ nullable=True,
+ )
+ # ### end Alembic commands ###
+
+
+def downgrade() -> None:
+ # ### commands auto generated by Alembic - please adjust! ###
+ if (dialect := op.get_bind().dialect.name) == "postgresql":
+ op.alter_column(
+ "hosts",
+ "alpn",
+ existing_type=sa.String(length=32),
+ type_=postgresql.ENUM(
+ "none", "h2", "http/1.1", "h2,http/1.1", name="proxyhostalpn"
+ ),
+ existing_nullable=True,
+ nullable=False,
+ existing_server_default=None,
+ server_default=sa.text("'none'::proxyhostalpn"),
+ )
+ elif dialect == "mysql" or dialect == "mariadb":
+ op.alter_column(
+ "hosts",
+ "alpn",
+ existing_type=sa.String(length=32),
+ type_=mysql.ENUM("none", "h2", "http/1.1", "h2,http/1.1"),
+ nullable=False,
+ existing_server_default=None,
+ server_default=sa.text("'none'"),
+ )
+ # ### end Alembic commands ###
diff --git a/app/db/models.py b/app/db/models.py
@@ -28,7 +28,6 @@ from app.config.env import SUBSCRIPTION_URL_PREFIX
from app.db.base import Base
from app.models.node import NodeStatus
from app.models.proxy import (
- InboundHostALPN,
InboundHostFingerprint,
InboundHostSecurity,
ProxyTypes,
@@ -315,10 +314,8 @@ class InboundHost(Base):
default=InboundHostSecurity.inbound_default,
)
alpn = Column(
- Enum(InboundHostALPN),
- nullable=False,
- default=InboundHostSecurity.none,
- server_default=InboundHostSecurity.none.name,
+ String(32),
+ server_default=sqlalchemy.sql.null(),
)
fingerprint = Column(
Enum(InboundHostFingerprint),
diff --git a/app/models/proxy.py b/app/models/proxy.py
@@ -22,7 +22,7 @@ class InboundHostSecurity(str, Enum):
InboundHostALPN = Enum(
"ProxyHostALPN",
{
- "none": "",
+ "none": "none",
"h2": "h2",
"http/1.1": "http/1.1",
"h2,http/1.1": "h2,http/1.1",
@@ -88,6 +88,13 @@ class InboundHost(BaseModel):
return v
+ @field_validator("alpn", mode="before")
+ @classmethod
+ def validate_alpn(cls, v):
+ if not v:
+ return InboundHostALPN.none
+ return v
+
class InboundHostResponse(InboundHost):
id: int
diff --git a/app/utils/share.py b/app/utils/share.py
@@ -63,7 +63,6 @@ handlers_templates = {
def generate_subscription_template(
db_user, subscription_settings: SubscriptionSettings
):
- print(subscription_settings.shuffle_configs)
links = generate_subscription(
user=db_user,
config_format="links",
@@ -266,7 +265,7 @@ def generate_user_configs(
host=req_host,
tls=host_tls or inbound["tls"],
header_type=inbound.get("header_type"),
- alpn=host.alpn.value or None,
+ alpn=host.alpn if host.alpn != "none" else None,
path=(
host.path.format_map(format_variables)
if host.path