Skip to content

Commit

Permalink
Merge pull request #387 from hellozee/output-flag-patch
Browse files Browse the repository at this point in the history
Added an output flag for saving the output to a specified file
  • Loading branch information
autrilla committed Nov 7, 2018
2 parents d2d08a1 + 6ce0290 commit 1836d7e
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 12 deletions.
6 changes: 6 additions & 0 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -720,6 +720,12 @@ provide more than one backend, and SOPS will log to all of them:
- connection_string: "postgres://sops:sops@localhost/sops?sslmode=verify-full"
- connection_string: "postgres://sops:sops@remotehost/sops?sslmode=verify-full"
Saving Output to a File
~~~~~~~~~~~~~~~~~~~~~~~
By default ``sops`` just dumps all the output to the standard output. We can use the
``--output`` flag followed by a filename to save the output to the file specified.
Beware using both ``--in-place`` and ``--output`` flags will result in an error.
Important information on types
------------------------------
Expand Down
36 changes: 24 additions & 12 deletions cmd/sops/main.go
Original file line number Diff line number Diff line change
@@ -1,24 +1,18 @@
package main //import "go.mozilla.org/sops/cmd/sops"

import (
encodingjson "encoding/json"
"fmt"
"net"
"net/url"

"google.golang.org/grpc"

"go.mozilla.org/sops"

"fmt"
"os"
"strings"
"time"

encodingjson "encoding/json"
"reflect"

"strconv"
"strings"
"time"

"github.com/sirupsen/logrus"
"go.mozilla.org/sops"
"go.mozilla.org/sops/aes"
_ "go.mozilla.org/sops/audit"
"go.mozilla.org/sops/azkv"
Expand All @@ -37,6 +31,7 @@ import (
"go.mozilla.org/sops/stores/dotenv"
"go.mozilla.org/sops/stores/json"
yamlstores "go.mozilla.org/sops/stores/yaml"
"google.golang.org/grpc"
"gopkg.in/urfave/cli.v1"
)

Expand Down Expand Up @@ -408,6 +403,10 @@ func main() {
Name: "verbose",
Usage: "Enable verbose logging output",
},
cli.StringFlag{
Name: "output",
Usage: "Save the output after encryption or decryption to the file specified",
},
}, keyserviceFlags...)

app.Action = func(c *cli.Context) error {
Expand All @@ -417,6 +416,9 @@ func main() {
if c.NArg() < 1 {
return common.NewExitError("Error: no file specified", codes.NoFileSpecified)
}
if c.Bool("in-place") && c.String("output") != "" {
return common.NewExitError("Error: cannot operate on both --output and --in-place", codes.ErrorConflictingParameters)
}
fileName := c.Args()[0]
if _, err := os.Stat(fileName); os.IsNotExist(err) {
if c.String("add-kms") != "" || c.String("add-pgp") != "" || c.String("add-gcp-kms") != "" || c.String("add-azure-kv") != "" ||
Expand Down Expand Up @@ -620,7 +622,17 @@ func main() {
log.Info("File written successfully")
return nil
}
_, err = os.Stdout.Write(output)

outputFile := os.Stdout
if c.String("output") != "" {
file, err := os.Create(c.String("output"))
if err != nil {
return common.NewExitError(fmt.Sprintf("Could not open output file for writing: %s", err), codes.CouldNotWriteOutputFile)
}
defer file.Close()
outputFile = file
}
_, err = outputFile.Write(output)
return toExitError(err)
}
app.Run(os.Args)
Expand Down
23 changes: 23 additions & 0 deletions functional-tests/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ mod tests {
use tempdir::TempDir;
use std::process::Command;
use serde_yaml::Value;
use std::path::Path;
const SOPS_BINARY_PATH: &'static str = "./sops";

macro_rules! assert_encrypted {
Expand Down Expand Up @@ -409,4 +410,26 @@ b: ba"#
assert_eq!(output.stdout, data);
}

#[test]
fn output_flag() {
let input_path = prepare_temp_file("test_output_flag.binary", b"foo");
let output_path = Path::join(TMP_DIR.path(), "output_flag.txt");
let output = Command::new(SOPS_BINARY_PATH)
.arg("--output")
.arg(&output_path)
.arg("-e")
.arg(input_path.clone())
.output()
.expect("Error running sops");
assert!(output.status
.success(),
"SOPS failed to decrypt a binary file");
assert_eq!(output.stdout, &[]);
let mut f = File::open(&output_path).expect("output file not found");

let mut contents = String::new();
f.read_to_string(&mut contents)
.expect("couldn't read output file contents");
assert_ne!(contents, "", "Output file is empty");
}
}

0 comments on commit 1836d7e

Please sign in to comment.