Skip to content

Commit 9d07679

Browse files
committed
Add pulp_rust CLI impl + tests
Assisted-By: claude-opus-4.6
1 parent 5d03ee7 commit 9d07679

13 files changed

Lines changed: 547 additions & 0 deletions

File tree

CHANGES/+rust-cli.feature

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Added CLI support for the unreleased / tech-preview "pulp_rust" plugin, for creating local private registries and mirrors of public registries (i.e. crates.io) for Rust package content.

pulp-glue/src/pulp_glue/rust/__init__.py

Whitespace-only changes.
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
from pulp_glue.common.context import (
2+
PluginRequirement,
3+
PulpContentContext,
4+
PulpDistributionContext,
5+
PulpRemoteContext,
6+
PulpRepositoryContext,
7+
PulpRepositoryVersionContext,
8+
)
9+
from pulp_glue.common.i18n import get_translation
10+
11+
translation = get_translation(__package__)
12+
_ = translation.gettext
13+
14+
15+
class PulpRustContentContext(PulpContentContext):
16+
PLUGIN = "rust"
17+
RESOURCE_TYPE = "packages"
18+
ENTITY = _("rust package")
19+
ENTITIES = _("rust packages")
20+
HREF = "rust_rust_package_content_href"
21+
ID_PREFIX = "content_rust_packages"
22+
NEEDS_PLUGINS = [PluginRequirement("rust")]
23+
24+
25+
class PulpRustDistributionContext(PulpDistributionContext):
26+
PLUGIN = "rust"
27+
RESOURCE_TYPE = "rust"
28+
ENTITY = _("rust distribution")
29+
ENTITIES = _("rust distributions")
30+
HREF = "rust_rust_distribution_href"
31+
ID_PREFIX = "distributions_rust_rust"
32+
NEEDS_PLUGINS = [PluginRequirement("rust")]
33+
34+
35+
class PulpRustRemoteContext(PulpRemoteContext):
36+
PLUGIN = "rust"
37+
RESOURCE_TYPE = "rust"
38+
ENTITY = _("rust remote")
39+
ENTITIES = _("rust remotes")
40+
HREF = "rust_rust_remote_href"
41+
ID_PREFIX = "remotes_rust_rust"
42+
NEEDS_PLUGINS = [PluginRequirement("rust")]
43+
44+
45+
class PulpRustRepositoryVersionContext(PulpRepositoryVersionContext):
46+
HREF = "rust_rust_repository_version_href"
47+
ID_PREFIX = "repositories_rust_rust_versions"
48+
NEEDS_PLUGINS = [PluginRequirement("rust")]
49+
50+
51+
class PulpRustRepositoryContext(PulpRepositoryContext):
52+
PLUGIN = "rust"
53+
RESOURCE_TYPE = "rust"
54+
HREF = "rust_rust_repository_href"
55+
ENTITY = _("rust repository")
56+
ENTITIES = _("rust repositories")
57+
ID_PREFIX = "repositories_rust_rust"
58+
VERSION_CONTEXT = PulpRustRepositoryVersionContext
59+
CAPABILITIES = {
60+
"sync": [PluginRequirement("rust")],
61+
}
62+
NULLABLES = PulpRepositoryContext.NULLABLES | {"remote"}
63+
NEEDS_PLUGINS = [PluginRequirement("rust")]

pyproject.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ core = "pulpcore.cli.core"
5151
file = "pulpcore.cli.file"
5252
python = "pulpcore.cli.python"
5353
rpm = "pulpcore.cli.rpm"
54+
rust = "pulpcore.cli.rust"
5455

5556
[tool.setuptools.packages.find]
5657
# This section is managed by the cookiecutter templates.

src/pulpcore/cli/rust/__init__.py

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import typing as t
2+
3+
import click
4+
5+
from pulp_glue.common.i18n import get_translation
6+
7+
from pulp_cli.generic import pulp_group
8+
from pulpcore.cli.rust.content import content
9+
from pulpcore.cli.rust.distribution import distribution
10+
from pulpcore.cli.rust.remote import remote
11+
from pulpcore.cli.rust.repository import repository
12+
13+
translation = get_translation(__package__)
14+
_ = translation.gettext
15+
16+
17+
@pulp_group(name="rust")
18+
def rust_group() -> None:
19+
pass
20+
21+
22+
def mount(main: click.Group, **kwargs: t.Any) -> None:
23+
rust_group.add_command(repository)
24+
rust_group.add_command(remote)
25+
rust_group.add_command(distribution)
26+
rust_group.add_command(content)
27+
main.add_command(rust_group)

src/pulpcore/cli/rust/content.py

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
import click
2+
3+
from pulp_glue.common.i18n import get_translation
4+
from pulp_glue.rust.context import PulpRustContentContext
5+
6+
from pulp_cli.generic import (
7+
PulpCLIContext,
8+
content_filter_options,
9+
href_option,
10+
list_command,
11+
pass_pulp_context,
12+
pulp_group,
13+
show_command,
14+
)
15+
16+
translation = get_translation(__package__)
17+
_ = translation.gettext
18+
19+
20+
@pulp_group()
21+
@click.option(
22+
"-t",
23+
"--type",
24+
"content_type",
25+
type=click.Choice(["rust"], case_sensitive=False),
26+
default="rust",
27+
)
28+
@pass_pulp_context
29+
@click.pass_context
30+
def content(ctx: click.Context, pulp_ctx: PulpCLIContext, /, content_type: str) -> None:
31+
if content_type == "rust":
32+
ctx.obj = PulpRustContentContext(pulp_ctx)
33+
else:
34+
raise NotImplementedError()
35+
36+
37+
lookup_options = [
38+
href_option,
39+
]
40+
41+
content.add_command(
42+
list_command(
43+
decorators=[
44+
click.option("--name"),
45+
click.option("--vers"),
46+
*content_filter_options,
47+
]
48+
)
49+
)
50+
content.add_command(show_command(decorators=lookup_options))
Lines changed: 100 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,100 @@
1+
import click
2+
3+
from pulp_glue.common.i18n import get_translation
4+
from pulp_glue.rust.context import (
5+
PulpRustDistributionContext,
6+
PulpRustRemoteContext,
7+
PulpRustRepositoryContext,
8+
)
9+
10+
from pulp_cli.generic import (
11+
PulpCLIContext,
12+
common_distribution_create_options,
13+
content_guard_option,
14+
create_command,
15+
destroy_command,
16+
distribution_filter_options,
17+
distribution_lookup_option,
18+
href_option,
19+
label_command,
20+
list_command,
21+
name_option,
22+
pass_pulp_context,
23+
pulp_group,
24+
pulp_labels_option,
25+
pulp_option,
26+
resource_option,
27+
show_command,
28+
update_command,
29+
)
30+
31+
translation = get_translation(__package__)
32+
_ = translation.gettext
33+
34+
35+
repository_option = resource_option(
36+
"--repository",
37+
default_plugin="rust",
38+
default_type="rust",
39+
context_table={"rust:rust": PulpRustRepositoryContext},
40+
href_pattern=PulpRustRepositoryContext.HREF_PATTERN,
41+
help=_(
42+
"Repository to be used for auto-distributing."
43+
" Specified as '[[<plugin>:]<type>:]<name>' or as href."
44+
),
45+
)
46+
47+
48+
@pulp_group()
49+
@click.option(
50+
"-t",
51+
"--type",
52+
"distribution_type",
53+
type=click.Choice(["rust"], case_sensitive=False),
54+
default="rust",
55+
)
56+
@pass_pulp_context
57+
@click.pass_context
58+
def distribution(ctx: click.Context, pulp_ctx: PulpCLIContext, /, distribution_type: str) -> None:
59+
if distribution_type == "rust":
60+
ctx.obj = PulpRustDistributionContext(pulp_ctx)
61+
else:
62+
raise NotImplementedError()
63+
64+
65+
lookup_options = [href_option, name_option, distribution_lookup_option]
66+
nested_lookup_options = [distribution_lookup_option]
67+
update_options = [
68+
repository_option,
69+
pulp_option(
70+
"--version",
71+
type=int,
72+
help=_(
73+
"The repository version number to distribute."
74+
" When unset, the latest version of the repository will be auto-distributed."
75+
),
76+
),
77+
resource_option(
78+
"--remote",
79+
default_plugin="rust",
80+
default_type="rust",
81+
context_table={"rust:rust": PulpRustRemoteContext},
82+
href_pattern=PulpRustRemoteContext.HREF_PATTERN,
83+
help=_(
84+
"Remote to use for pull-through caching."
85+
" Specified as '[[<plugin>:]<type>:]<name>' or as href."
86+
),
87+
),
88+
content_guard_option,
89+
pulp_labels_option,
90+
]
91+
create_options = common_distribution_create_options + update_options
92+
93+
distribution.add_command(list_command(decorators=distribution_filter_options))
94+
distribution.add_command(show_command(decorators=lookup_options))
95+
distribution.add_command(create_command(decorators=create_options))
96+
distribution.add_command(
97+
update_command(decorators=lookup_options + update_options + [click.option("--base-path")])
98+
)
99+
distribution.add_command(destroy_command(decorators=lookup_options))
100+
distribution.add_command(label_command(decorators=nested_lookup_options))

src/pulpcore/cli/rust/remote.py

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
import click
2+
3+
from pulp_glue.common.i18n import get_translation
4+
from pulp_glue.rust.context import PulpRustRemoteContext
5+
6+
from pulp_cli.generic import (
7+
PulpCLIContext,
8+
common_remote_create_options,
9+
common_remote_update_options,
10+
create_command,
11+
destroy_command,
12+
href_option,
13+
label_command,
14+
list_command,
15+
name_option,
16+
pass_pulp_context,
17+
pulp_group,
18+
remote_filter_options,
19+
remote_lookup_option,
20+
show_command,
21+
update_command,
22+
)
23+
24+
translation = get_translation(__package__)
25+
_ = translation.gettext
26+
27+
28+
@pulp_group()
29+
@click.option(
30+
"-t",
31+
"--type",
32+
"remote_type",
33+
type=click.Choice(["rust"], case_sensitive=False),
34+
default="rust",
35+
)
36+
@pass_pulp_context
37+
@click.pass_context
38+
def remote(ctx: click.Context, pulp_ctx: PulpCLIContext, /, remote_type: str) -> None:
39+
if remote_type == "rust":
40+
ctx.obj = PulpRustRemoteContext(pulp_ctx)
41+
else:
42+
raise NotImplementedError()
43+
44+
45+
lookup_options = [href_option, name_option, remote_lookup_option]
46+
nested_lookup_options = [remote_lookup_option]
47+
rust_remote_options = [
48+
click.option(
49+
"--policy", type=click.Choice(["immediate", "on_demand", "streamed"], case_sensitive=False)
50+
),
51+
]
52+
53+
remote.add_command(list_command(decorators=remote_filter_options))
54+
remote.add_command(show_command(decorators=lookup_options))
55+
remote.add_command(create_command(decorators=common_remote_create_options + rust_remote_options))
56+
remote.add_command(
57+
update_command(decorators=lookup_options + common_remote_update_options + rust_remote_options)
58+
)
59+
remote.add_command(destroy_command(decorators=lookup_options))
60+
remote.add_command(label_command(decorators=nested_lookup_options))

0 commit comments

Comments
 (0)