Merge pull request #53 from sdomino/feature/private-flags

private flags
diff --git a/README.md b/README.md
index 247ceca..e74dd50 100644
--- a/README.md
+++ b/README.md
@@ -216,24 +216,33 @@
 myFlagSet.SetNormalizeFunc(aliasNormalizeFunc)
 ```
 
-## Deprecating a flag or its shorthand 
-It is possible to deprecate a flag, or just its shorthand. Deprecating a flag/shorthand hides it from help text and prints a usage message when the deprecated flag/shorthand is used. 
+## Deprecating a flag or its shorthand
+It is possible to deprecate a flag, or just its shorthand. Deprecating a flag/shorthand hides it from help text and prints a usage message when the deprecated flag/shorthand is used.
 
-**Example #1**: You want to deprecate a flag named "badflag" as well as inform the users what flag they should use instead. 
+**Example #1**: You want to deprecate a flag named "badflag" as well as inform the users what flag they should use instead.
 ```go
-// deprecate a flag by specifying its name and a usage message 
+// deprecate a flag by specifying its name and a usage message
 flags.MarkDeprecated("badflag", "please use --good-flag instead")
 ```
-This hides "badflag" from help text, and prints `Flag --badflag has been deprecated, please use --good-flag instead` when "badflag" is used. 
+This hides "badflag" from help text, and prints `Flag --badflag has been deprecated, please use --good-flag instead` when "badflag" is used.
 
-**Example #2**: You want to keep a flag name "noshorthandflag" but deprecate its shortname "n". 
+**Example #2**: You want to keep a flag name "noshorthandflag" but deprecate its shortname "n".
 ```go
-// deprecate a flag shorthand by specifying its flag name and a usage message 
+// deprecate a flag shorthand by specifying its flag name and a usage message
 flags.MarkShorthandDeprecated("noshorthandflag", "please use --noshorthandflag only")
 ```
-This hides the shortname "n" from help text, and prints `Flag shorthand -n has been deprecated, please use --noshorthandflag only` when the shorthand "n" is used. 
+This hides the shortname "n" from help text, and prints `Flag shorthand -n has been deprecated, please use --noshorthandflag only` when the shorthand "n" is used.
 
-Note that usage message is essential here, and it should not be empty. 
+Note that usage message is essential here, and it should not be empty.
+
+## Hidden flags
+It is possible to mark a flag as hidden, meaning it will still function as normal, however will not show up in usage/help text.
+
+**Example**: You have a flag named "secretFlag" that you need for internal use only and don't want it showing up in help text, or for its usage text to be available.
+```go
+// hide a flag by specifying its name
+flags.MarkHidden("secretFlag")
+```
 
 ## More info
 
diff --git a/flag.go b/flag.go
index 73f202f..66ef096 100644
--- a/flag.go
+++ b/flag.go
@@ -157,8 +157,9 @@
 	Changed             bool                // If the user set the value (or if left to default)
 	NoOptDefVal         string              //default value (as text); if the flag is on the command line without any options
 	Deprecated          string              // If this flag is deprecated, this string is the new or now thing to use
+	Hidden              bool                // used by cobra.Command to allow flags to be hidden from help/usage text
 	ShorthandDeprecated string              // If the shorthand of this flag is deprecated, this string is the new or now thing to use
-	Annotations         map[string][]string // used by cobra.Command  bash autocomple code
+	Annotations         map[string][]string // used by cobra.Command bash autocomple code
 }
 
 // Value is the interface to the dynamic value stored in a flag.
@@ -321,6 +322,17 @@
 	return nil
 }
 
+// MarkHidden sets a flag to 'hidden' in your program. It will continue to
+// function but will not show up in help or usage messages.
+func (f *FlagSet) MarkHidden(name string) error {
+	flag := f.Lookup(name)
+	if flag == nil {
+		return fmt.Errorf("flag %q does not exist", name)
+	}
+	flag.Hidden = true
+	return nil
+}
+
 // Lookup returns the Flag structure of the named command-line flag,
 // returning nil if none exists.
 func Lookup(name string) *Flag {
@@ -394,7 +406,7 @@
 	x := new(bytes.Buffer)
 
 	f.VisitAll(func(flag *Flag) {
-		if len(flag.Deprecated) > 0 {
+		if len(flag.Deprecated) > 0 || flag.Hidden {
 			return
 		}
 		format := ""
diff --git a/flag_test.go b/flag_test.go
index 165f689..1b4005c 100644
--- a/flag_test.go
+++ b/flag_test.go
@@ -831,3 +831,35 @@
 		t.Fatal("Expected normalizeFlagNameInvocations to be 1; got ", normalizeFlagNameInvocations)
 	}
 }
+
+//
+func TestHiddenFlagInUsage(t *testing.T) {
+	f := NewFlagSet("bob", ContinueOnError)
+	f.Bool("secretFlag", true, "shhh")
+	f.MarkHidden("secretFlag")
+
+	out := new(bytes.Buffer)
+	f.SetOutput(out)
+	f.PrintDefaults()
+
+	if strings.Contains(out.String(), "secretFlag") {
+		t.Errorf("found hidden flag in usage!")
+	}
+}
+
+//
+func TestHiddenFlagUsage(t *testing.T) {
+	f := NewFlagSet("bob", ContinueOnError)
+	f.Bool("secretFlag", true, "shhh")
+	f.MarkHidden("secretFlag")
+
+	args := []string{"--secretFlag"}
+	out, err := parseReturnStderr(t, f, args)
+	if err != nil {
+		t.Fatal("expected no error; got ", err)
+	}
+
+	if strings.Contains(out, "shhh") {
+		t.Errorf("usage message printed when using a hidden flag!")
+	}
+}