Skip to content

Commit 50c276c

Browse files
committed
Add --replace option to podman artifact add command
This commit implements the --replace functionality for the artifact add command, allowing users to replace existing artifacts without having to manually remove them first. Changes made: - Add Replace field to ArtifactAddOptions entity types - Add --replace CLI flag with validation to prevent conflicts with --append - Implement replace logic in ABI backend to remove existing artifacts before adding - Update API handlers and tunnel implementation for podman-remote support - Add comprehensive documentation and examples to man page - Add e2e and system BATS tests for --replace functionality - Fix code formatting in pkg/bindings/artifacts/types_pull_options.go: * Reorder imports with proper spacing * Fix function declaration spacing * Convert spaces to proper tab indentation * Remove extraneous blank lines The --replace option follows the same pattern as other podman replace options like 'podman container create --replace' and 'podman pod create --replace'. It gracefully handles cases where no existing artifact exists (no error thrown). Usage examples: podman artifact add --replace quay.io/myimage/artifact:latest /path/to/file podman artifact add --replace localhost/test/artifact /tmp/newfile.txt Fixes: Implements requested --replace functionality for artifact add command Signed-off-by: Daniel J Walsh <[email protected]>
1 parent d7f33a7 commit 50c276c

File tree

20 files changed

+3035
-0
lines changed

20 files changed

+3035
-0
lines changed

.codespelldict

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
usasge->usage
2+
ramamlama->ramalama
3+
olama->ollama
4+
alterting->altering
5+
annotationg->annotating
6+
assemlbe->assemble
7+
capabiltiies->capabilities
8+
custommizing->customizing
9+
eaxecutes->executes
10+
maximumn->maximum
11+
mountns->mounts
12+
name_missmatch->name_mismatch
13+
notaibly->notably
14+
pessimitically->pessimistically
15+
recoreded->recorded
16+
specicifed->specified
17+
unsuppored->unsupported

0002-Replace-instances-of-PodmanExitCleanly-in-play_kube_.patch~

Lines changed: 1984 additions & 0 deletions
Large diffs are not rendered by default.

cmd/podman/artifact/add.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,9 @@ func init() {
5353
appendFlagName := "append"
5454
flags.BoolVarP(&addOpts.Append, appendFlagName, "a", false, "Append files to an existing artifact")
5555

56+
replaceFlagName := "replace"
57+
flags.BoolVar(&addOpts.Replace, replaceFlagName, false, "Replace an existing artifact")
58+
5659
fileMIMETypeFlagName := "file-type"
5760
flags.StringVarP(&addOpts.FileMIMEType, fileMIMETypeFlagName, "", "", "Set file type to use for the artifact (layer)")
5861
_ = addCmd.RegisterFlagCompletionFunc(fileMIMETypeFlagName, completion.AutocompleteNone)
@@ -62,6 +65,10 @@ func add(cmd *cobra.Command, args []string) error {
6265
artifactName := args[0]
6366
blobs := args[1:]
6467

68+
if addOpts.Append && addOpts.Replace {
69+
return fmt.Errorf("--append and --replace options cannot be used together")
70+
}
71+
6572
annots, err := utils.ParseAnnotations(addOpts.AnnotationsCLI)
6673
if err != nil {
6774
return err
@@ -72,6 +79,7 @@ func add(cmd *cobra.Command, args []string) error {
7279
ArtifactMIMEType: addOpts.ArtifactMIMEType,
7380
Append: addOpts.Append,
7481
FileMIMEType: addOpts.FileMIMEType,
82+
Replace: addOpts.Replace,
7583
}
7684

7785
artifactBlobs := make([]entities.ArtifactBlob, 0, len(blobs))
Lines changed: 140 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,140 @@
1+
#!/usr/bin/perl
2+
3+
use v5.14;
4+
5+
my $opt = shift(@ARGV) or die;
6+
$opt =~ s/^-+//;
7+
8+
# Handle "cpu.pod" or "cpu.container", meaning, separate file & option name
9+
my $opt_filename = $opt;
10+
$opt =~ s/\.\S+$//;
11+
12+
my @matches = find_files($opt, @ARGV)
13+
or die "No files with --$opt";
14+
15+
@matches > 1
16+
or die "Only 1 file with --$opt\n";
17+
18+
#use Data::Dump; dd \@matches;
19+
(my $baseline = $matches[0][1]) =~ s/\s+/ /sm;
20+
my $all_match = 1;
21+
for my $tuple (@matches) {
22+
(my $this = $tuple->[1]) =~ s/\s+/ /sm;
23+
if ($this eq $baseline) {
24+
print "[ $matches[0][0] == $tuple->[0] ]\n";
25+
}
26+
else {
27+
show_diff($matches[0], $tuple);
28+
$all_match = 0;
29+
}
30+
}
31+
32+
if (!$all_match) {
33+
printf "[ %s ]\n", join(" ", map { (my $tmp = $_->[0]) =~ s/^podman-//; $tmp; } @matches);
34+
die "They don't all match\n";
35+
}
36+
37+
print "YAY! All match!\n";
38+
39+
my @not_in = grep { $_ !~ /\.in$/ } map { $_->[0] } @matches;
40+
if (@not_in) {
41+
die "BOO! File(s) need to be renamed to .in: @not_in\n";
42+
}
43+
44+
# FIXME: pass 2: rewrite files
45+
open my $fh, '>', "options/$opt_filename.md" or die;
46+
print { $fh } $matches[0][1];
47+
close $fh;
48+
system('git', 'add', "options/$opt_filename.md") == 0
49+
or die "git add $opt_filename.md failed\n";
50+
51+
for my $tuple (@matches) {
52+
my $f = $tuple->[0];
53+
my @cmd = ('sed', '-i', '-e', "$tuple->[2],$tuple->[3]c\@\@option $opt_filename\\
54+
", $f);
55+
system(@cmd) == 0
56+
or die "Command failed on $f\n";
57+
system('git', 'add', $f) == 0
58+
or die "git add $f failed\n";
59+
}
60+
61+
62+
sub find_files {
63+
my $want = shift;
64+
65+
my @matches;
66+
for my $f (glob("*.md"), glob("*.md.in")) {
67+
# Skip foo.md if there's an existing foo.md.in
68+
next if -e "$f.in";
69+
70+
# Skip the main podman man page; there's nothing in it
71+
# that we can refactor
72+
next if $f eq 'podman.1.md';
73+
74+
# Further args mean limit to just these files, eg 'create run'
75+
if (@_) {
76+
grep { $f =~ /$_/ } @_
77+
or next;
78+
}
79+
80+
my $in_opts = 0;
81+
my $in_wanted_opt = 0;
82+
83+
open my $fh, '<', $f or die;
84+
while (my $line = <$fh>) {
85+
if ($line =~ /^##\s+(GLOBAL\s+)?OPTIONS/) {
86+
$in_opts = 1;
87+
}
88+
elsif ($line =~ /^##\s/) {
89+
$in_opts = 0;
90+
}
91+
next unless $in_opts;
92+
93+
if ($line =~ /^####\s+\*+-+([a-z0-9-]+)\*/) {
94+
if ($1 eq $want) {
95+
$in_wanted_opt = 1;
96+
push @matches, [ $f, $line, $., $. ];
97+
}
98+
else {
99+
$in_wanted_opt = 0;
100+
}
101+
}
102+
elsif ($line =~ /^(###|\@\@)/) {
103+
$in_wanted_opt = 0;
104+
}
105+
elsif ($line =~ /^\[\/\/\]:\s+\#\s/) { # markdown comments
106+
$in_wanted_opt = 0;
107+
}
108+
elsif ($in_wanted_opt) {
109+
$matches[-1][1] .= $line;
110+
$matches[-1][3] = $.;
111+
}
112+
}
113+
close $fh;
114+
}
115+
116+
# Strip off trailing empty lines
117+
for my $m (@matches) {
118+
$m->[1] =~ s/^\n$//gm;
119+
}
120+
121+
@matches;
122+
}
123+
124+
sub show_diff {
125+
use File::Temp qw(tempdir);
126+
127+
my $tmpdir = tempdir( "option-refactor.tmp.XXXXXXX", TMPDIR => 1, CLEANUP => 1 );
128+
for my $tuple (@_) {
129+
my $f = "$tmpdir/$tuple->[0]";
130+
open my $fh, '>', $f or die;
131+
print { $fh } $tuple->[1];
132+
close $fh or die;
133+
}
134+
135+
my @f = map { $_->[0] } @_;
136+
137+
# system('cdif', '-u', '-w', map { "$tmpdir/$_->[0]" } @_);
138+
system("diff -u --label $f[0] --label $f[1] $tmpdir/$f[0] $tmpdir/$f[1] | cdif");
139+
print "\n";
140+
}

docs/source/markdown/podman-artifact-add.1.md.in

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,11 @@ Note: Set annotations for each file being added.
2323

2424
Append files to an existing artifact. This option cannot be used with the **--type** option.
2525

26+
#### **--replace**
27+
28+
If an artifact with the same name already exists, replace and remove it. The default is **false**.
29+
This option cannot be used with the **--append** option.
30+
2631
#### **--file-type**
2732

2833
Set the media type of the artifact file instead of allowing detection to determine the type
@@ -65,6 +70,11 @@ Override the media type of the artifact being added
6570
$ podman artifact add --file-type text/yaml quay.io/myartifact/descriptors:latest /tmp/info.yaml
6671
```
6772

73+
Replace an existing artifact with the same name
74+
```
75+
$ podman artifact add --replace quay.io/myartifact/myml:latest /tmp/newfoobar.ml
76+
```
77+
6878

6979
## SEE ALSO
7080
**[podman(1)](podman.1.md)**, **[podman-artifact(1)](podman-artifact.1.md)**

erofs

7.5 MB
Binary file not shown.

hosts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
2+
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
3+
192.168.7.9 f2ba6a8ea32f bug1

pkg/api/handlers/libpod/artifacts.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -217,6 +217,7 @@ func AddArtifact(w http.ResponseWriter, r *http.Request) {
217217
Annotations []string `schema:"annotations"`
218218
ArtifactMIMEType string `schema:"artifactMIMEType"`
219219
Append bool `schema:"append"`
220+
Replace bool `schema:"replace"`
220221
}{}
221222

222223
if err := decoder.Decode(&query, r.URL.Query()); err != nil {
@@ -240,6 +241,7 @@ func AddArtifact(w http.ResponseWriter, r *http.Request) {
240241
Annotations: annotations,
241242
ArtifactMIMEType: query.ArtifactMIMEType,
242243
FileMIMEType: query.FileMIMEType,
244+
Replace: query.Replace,
243245
}
244246

245247
artifactBlobs := []entities.ArtifactBlob{{

pkg/bindings/artifacts/types.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@ type AddOptions struct {
6262
ArtifactMIMEType *string
6363
Append *bool
6464
FileMIMEType *string
65+
Replace *bool
6566
}
6667

6768
// ExtractOptions

pkg/bindings/artifacts/types_add_options.go

Lines changed: 15 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)