Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

config: Add support for remapping Postgres configs into Gel enums #8275

Merged
merged 3 commits into from
Jan 30, 2025

Conversation

elprans
Copy link
Member

@elprans elprans commented Jan 29, 2025

We have a long-standing rule that configuration parameters should avoid
using a boolean type and use enums instead (though we've not generally
been super diligent about this always). Postgres, on the other hand,
has lots of boolean settings. To solve this, teach the config framework
how to remap backend config values onto arbitrary frontend enums. In
general the below is all that is required:

class EnabledDisabledEnum(enum.StrEnum):
    Enabled = "Enabled"
    Disabled = "Disabled"

class EnabledDisabledType(
    EnumScalarType[EnabledDisabledEnum],
    edgeql_type="cfg::TestEnabledDisabledEnum",
):
    @classmethod
    def get_translation_map(cls) -> Mapping[EnabledDisabledEnum, str]:
        return {
            EnabledDisabledEnum.Enabled: "true",
            EnabledDisabledEnum.Disabled: "false",
        }

We have a long-standing rule that configuration parameters should avoid
using a boolean type and use enums instead (though we've not generally
been super diligent about this always).  Postgres, on the other hand,
has lots of boolean settings.  To solve this, teach the config framework
how to remap backend config values onto arbitrary frontend enums.  In
general the below is all that is required:

    class EnabledDisabledEnum(enum.StrEnum):
        Enabled = "Enabled"
        Disabled = "Disabled"

    class EnabledDisabledType(
        EnumScalarType[EnabledDisabledEnum],
        edgeql_type="cfg::TestEnabledDisabledEnum",
    ):
        @classmethod
        def get_translation_map(cls) -> Mapping[EnabledDisabledEnum, str]:
            return {
                EnabledDisabledEnum.Enabled: "true",
                EnabledDisabledEnum.Disabled: "false",
            }
@elprans elprans requested review from msullivan and fantix January 29, 2025 23:48
Copy link
Member

@msullivan msullivan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

An epic yak shave.

Probably will be a bit of a pain in my ass to backport this but I think I have it coming after sending you down this rabbit hole.

Comment on lines +647 to +676
def __reduce__(self) -> tuple[
Callable[..., EnumScalarType[Any]],
tuple[
Optional[tuple[type, ...] | type],
E,
],
]:
assert type(self).is_fully_resolved(), \
f'{type(self)} parameters are not resolved'

cls: type[EnumScalarType[E]] = self.__class__
types: Optional[tuple[type, ...]] = self.orig_args
if types is None or not cls.is_anon_parametrized():
typeargs = None
else:
typeargs = types[0] if len(types) == 1 else types
return (cls.__restore__, (typeargs, self._val))

@classmethod
def __restore__(
cls,
typeargs: Optional[tuple[type, ...] | type],
val: E,
) -> Self:
if typeargs is None or cls.is_anon_parametrized():
obj = cls(val)
else:
obj = cls[typeargs](val) # type: ignore[index]

return obj
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do we need all this special handling/parametric type stuff for? How are we using the type param?

(Probably add a comment explaining)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Parametric basically gives us runtime access to the generic type arg and lets us avoid copy-pasting the constructors. Given a bunch of enums are added #8276 (and possibly more settings later) I figured it's worth complicating the base type to make implementations essentially glorified mappings.

class PostgresJsonConfigValueToGelConfigValueFunction(
trampoline.VersionedFunction,
):
"""Convert a Postgres config value to Gel config value.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think my inclination is to keep calling it "edgedb" as a "codename" in internal code like this, but I don't feel strongly.

Just makes it a little easier to be consistent in function names and stuff, though obviously it is kind of fucked no matter what.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We also have the backend (postgres) and frontend (edgedb-server) used around (which I think I prefer)

@elprans elprans merged commit 2d6035b into master Jan 30, 2025
23 checks passed
@elprans elprans deleted the enum-config branch January 30, 2025 18:44
elprans added a commit that referenced this pull request Jan 31, 2025
…estmode

When adding remapping machinery in #8275 I forgot that `_testmode`
config gets grafted onto bootstrap cache shipped in production builds.
Rectify that.
elprans added a commit that referenced this pull request Jan 31, 2025
…estmode (#8283)

When adding remapping machinery in #8275 I forgot that `_testmode`
config gets grafted onto bootstrap cache shipped in production builds.
Rectify that.
@msullivan msullivan added the to-backport-6.x PRs that *should* be backported to 6.x label Feb 4, 2025
msullivan pushed a commit that referenced this pull request Feb 4, 2025
)

We have a long-standing rule that configuration parameters should avoid
using a boolean type and use enums instead (though we've not generally
been super diligent about this always).  Postgres, on the other hand,
has lots of boolean settings.  To solve this, teach the config framework
how to remap backend config values onto arbitrary frontend enums.  In
general the below is all that is required:

    class EnabledDisabledEnum(enum.StrEnum):
        Enabled = "Enabled"
        Disabled = "Disabled"

    class EnabledDisabledType(
        EnumScalarType[EnabledDisabledEnum],
        edgeql_type="cfg::TestEnabledDisabledEnum",
    ):
        @classmethod
def get_translation_map(cls) -> Mapping[EnabledDisabledEnum, str]:
            return {
                EnabledDisabledEnum.Enabled: "true",
                EnabledDisabledEnum.Disabled: "false",
            }

BACKPORT NOTES: The patches won't work until the next two commits are
applied. Fixing patches wound up being downstream of this PR in
annoying way.
msullivan pushed a commit that referenced this pull request Feb 4, 2025
…estmode (#8283)

When adding remapping machinery in #8275 I forgot that `_testmode`
config gets grafted onto bootstrap cache shipped in production builds.
Rectify that.
@msullivan msullivan added backported-6.x PRs that *have* been backported to 6.x and removed to-backport-6.x PRs that *should* be backported to 6.x labels Feb 4, 2025
msullivan pushed a commit that referenced this pull request Feb 4, 2025
)

We have a long-standing rule that configuration parameters should avoid
using a boolean type and use enums instead (though we've not generally
been super diligent about this always).  Postgres, on the other hand,
has lots of boolean settings.  To solve this, teach the config framework
how to remap backend config values onto arbitrary frontend enums.  In
general the below is all that is required:

    class EnabledDisabledEnum(enum.StrEnum):
        Enabled = "Enabled"
        Disabled = "Disabled"

    class EnabledDisabledType(
        EnumScalarType[EnabledDisabledEnum],
        edgeql_type="cfg::TestEnabledDisabledEnum",
    ):
        @classmethod
def get_translation_map(cls) -> Mapping[EnabledDisabledEnum, str]:
            return {
                EnabledDisabledEnum.Enabled: "true",
                EnabledDisabledEnum.Disabled: "false",
            }

BACKPORT NOTES: The patches won't work until the next two commits are
applied. Fixing patches wound up being downstream of this PR in
annoying way.
msullivan pushed a commit that referenced this pull request Feb 4, 2025
…estmode (#8283)

When adding remapping machinery in #8275 I forgot that `_testmode`
config gets grafted onto bootstrap cache shipped in production builds.
Rectify that.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
backported-6.x PRs that *have* been backported to 6.x
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants