Skip to content

Commit 0dfe6b7

Browse files
authored
Merge branch 'main' into patch-3
2 parents d87172f + 0e3c5ec commit 0dfe6b7

5 files changed

Lines changed: 58 additions & 29 deletions

File tree

.github/workflows/codeql.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ jobs:
3535

3636
# Initializes the CodeQL tools for scanning.
3737
- name: Initialize CodeQL
38-
uses: github/codeql-action/init@89a39a4e59826350b863aa6b6252a07ad50cf83e # v4.32.4
38+
uses: github/codeql-action/init@0d579ffd059c29b07949a3cce3983f0780820c98 # v4.32.6
3939
with:
4040
languages: go
4141
# xref: https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#using-queries-in-ql-packs
@@ -52,6 +52,6 @@ jobs:
5252
make install
5353
5454
- name: Perform CodeQL Analysis
55-
uses: github/codeql-action/analyze@89a39a4e59826350b863aa6b6252a07ad50cf83e # v4.32.4
55+
uses: github/codeql-action/analyze@0d579ffd059c29b07949a3cce3983f0780820c98 # v4.32.6
5656
with:
5757
category: "/language:go"

.github/workflows/release.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -46,20 +46,20 @@ jobs:
4646
cosign-release: 'v2.6.2'
4747

4848
- name: Setup QEMU
49-
uses: docker/setup-qemu-action@c7c53464625b32c7a7e944ae62b3e17d2b600130 # v3.7.0
49+
uses: docker/setup-qemu-action@ce360397dd3f832beb865e1373c09c0e9f86d70a # v4.0.0
5050

5151
- name: Setup Docker Buildx
52-
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0
52+
uses: docker/setup-buildx-action@4d04d5d9486b7bd6fa91e7baf45bbb4f8b9deedd # v4.0.0
5353

5454
- name: Login to GitHub Container Registry
55-
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0
55+
uses: docker/login-action@b45d80f862d83dbcd57f89517bcf500b2ab88fb2 # v4.0.0
5656
with:
5757
registry: ghcr.io
5858
username: ${{ github.actor }}
5959
password: ${{ secrets.GITHUB_TOKEN }}
6060

6161
- name: Login to Quay.io
62-
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0
62+
uses: docker/login-action@b45d80f862d83dbcd57f89517bcf500b2ab88fb2 # v4.0.0
6363
with:
6464
registry: quay.io
6565
username: ${{ secrets.QUAY_BOT_USERNAME }}

cmd/sops/edit.go

Lines changed: 28 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ type runEditorUntilOkOpts struct {
3939
TmpFileName string
4040
OriginalHash []byte
4141
InputStore sops.Store
42+
OutputStore common.Store
4243
ShowMasterKeys bool
4344
Tree *sops.Tree
4445
}
@@ -147,8 +148,12 @@ func editTree(opts editOpts, tree *sops.Tree, dataKey []byte) ([]byte, error) {
147148

148149
// Let the user edit the file
149150
err = runEditorUntilOk(runEditorUntilOkOpts{
150-
InputStore: opts.InputStore, OriginalHash: origHash, TmpFileName: tmpfileName,
151-
ShowMasterKeys: opts.ShowMasterKeys, Tree: tree})
151+
InputStore: opts.InputStore,
152+
OutputStore: opts.OutputStore,
153+
OriginalHash: origHash,
154+
TmpFileName: tmpfileName,
155+
ShowMasterKeys: opts.ShowMasterKeys,
156+
Tree: tree})
152157
if err != nil {
153158
return nil, err
154159
}
@@ -169,6 +174,12 @@ func editTree(opts editOpts, tree *sops.Tree, dataKey []byte) ([]byte, error) {
169174
return encryptedFile, nil
170175
}
171176

177+
const pressKeyMsg = "Press enter to return to the editor, or Ctrl+C to exit."
178+
179+
func waitForKeyPress() {
180+
bufio.NewReader(os.Stdin).ReadByte()
181+
}
182+
172183
func runEditorUntilOk(opts runEditorUntilOkOpts) error {
173184
for {
174185
err := runEditor(opts.TmpFileName)
@@ -191,10 +202,8 @@ func runEditorUntilOk(opts runEditorUntilOkOpts) error {
191202
log.WithField(
192203
"error",
193204
err,
194-
).Errorf("Could not load tree, probably due to invalid " +
195-
"syntax. Press a key to return to the editor, or Ctrl+C to " +
196-
"exit.")
197-
bufio.NewReader(os.Stdin).ReadByte()
205+
).Errorf("Could not load tree, probably due to invalid syntax. " + pressKeyMsg)
206+
waitForKeyPress()
198207
continue
199208
}
200209
if opts.ShowMasterKeys {
@@ -205,14 +214,22 @@ func runEditorUntilOk(opts runEditorUntilOkOpts) error {
205214
log.WithField(
206215
"error",
207216
err,
208-
).Errorf("SOPS metadata is invalid. Press a key to " +
209-
"return to the editor, or Ctrl+C to exit.")
210-
bufio.NewReader(os.Stdin).ReadByte()
217+
).Errorf("SOPS metadata is invalid. " + pressKeyMsg)
218+
waitForKeyPress()
211219
continue
212220
}
213221
// Replace the whole tree, because otherwise newBranches would
214222
// contain the SOPS metadata
215223
opts.Tree = &t
224+
} else {
225+
if userErr, _ := validateFileForEncryption(opts.OutputStore, newBranches); userErr != nil {
226+
log.WithField(
227+
"error",
228+
userErr.UserError(),
229+
).Errorf("Tree not valid for encryption. " + pressKeyMsg)
230+
waitForKeyPress()
231+
continue
232+
}
216233
}
217234
opts.Tree.Branches = newBranches
218235
needVersionUpdated, err := version.AIsNewerThanB(version.Version, opts.Tree.Metadata.Version)
@@ -223,10 +240,8 @@ func runEditorUntilOk(opts runEditorUntilOkOpts) error {
223240
opts.Tree.Metadata.Version = version.Version
224241
}
225242
if opts.Tree.Metadata.MasterKeyCount() == 0 {
226-
log.Error("No master keys were provided, so sops can't " +
227-
"encrypt the file. Press a key to return to the editor, or " +
228-
"Ctrl+C to exit.")
229-
bufio.NewReader(os.Stdin).ReadByte()
243+
log.Error("No master keys were provided, so sops can't encrypt the file. " + pressKeyMsg)
244+
waitForKeyPress()
230245
continue
231246
}
232247
break

cmd/sops/encrypt.go

Lines changed: 20 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -52,15 +52,28 @@ func (err *fileAlreadyEncryptedError) UserError() string {
5252
"encrypt files that already contain such an entry.\n\n" +
5353
"If this is an unencrypted file, rename the '" + stores.SopsMetadataKey + "' entry.\n\n" +
5454
"If this is an encrypted file and you want to edit it, use the " +
55-
"editor mode, for example: `sops my_file.yaml`"
55+
"editor mode, for example: `sops edit my_file.yaml`"
5656
return wordwrap.WrapString(message, 75)
5757
}
5858

59-
func ensureNoMetadata(opts encryptOpts, branch sops.TreeBranch) error {
60-
if opts.OutputStore.HasSopsTopLevelKey(branch) {
61-
return &fileAlreadyEncryptedError{}
59+
type needAtLeastOneDocument struct{}
60+
61+
func (err *needAtLeastOneDocument) Error() string {
62+
return "Empty file"
63+
}
64+
65+
func (err *needAtLeastOneDocument) UserError() string {
66+
return "File cannot be completely empty, it must contain at least one document"
67+
}
68+
69+
func validateFileForEncryption(outputStore sops.Store, branches []sops.TreeBranch) (sops.UserError, int) {
70+
if len(branches) < 1 {
71+
return &needAtLeastOneDocument{}, codes.NeedAtLeastOneDocument
72+
}
73+
if outputStore.HasSopsTopLevelKey(branches[0]) {
74+
return &fileAlreadyEncryptedError{}, codes.FileAlreadyEncrypted
6275
}
63-
return nil
76+
return nil, 0
6477
}
6578

6679
func metadataFromEncryptionConfig(config encryptConfig) sops.Metadata {
@@ -96,11 +109,8 @@ func encrypt(opts encryptOpts) (encryptedFile []byte, err error) {
96109
if err != nil {
97110
return nil, common.NewExitError(fmt.Sprintf("Error unmarshalling file: %s", err), codes.CouldNotReadInputFile)
98111
}
99-
if len(branches) < 1 {
100-
return nil, common.NewExitError("File cannot be completely empty, it must contain at least one document", codes.NeedAtLeastOneDocument)
101-
}
102-
if err := ensureNoMetadata(opts, branches[0]); err != nil {
103-
return nil, common.NewExitError(err, codes.FileAlreadyEncrypted)
112+
if err, code := validateFileForEncryption(opts.OutputStore, branches); err != nil {
113+
return nil, common.NewExitError(err, code)
104114
}
105115
path, err := filepath.Abs(opts.InputPath)
106116
if err != nil {

cmd/sops/set.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,10 @@ func set(opts setOpts) ([]byte, bool, error) {
5151
var changed bool
5252
tree.Branches[0], changed = tree.Branches[0].Set(opts.TreePath, opts.Value)
5353

54+
if err, code := validateFileForEncryption(opts.OutputStore, tree.Branches); err != nil {
55+
return nil, false, common.NewExitError(err, code)
56+
}
57+
5458
err = common.EncryptTree(common.EncryptTreeOpts{
5559
DataKey: dataKey, Tree: tree, Cipher: opts.Cipher,
5660
})

0 commit comments

Comments
 (0)