From 6054610dd492b8866160bf21ba37758c64ac8c28 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:16:00 +0000 Subject: [PATCH 1/8] fix(guides): ensure all example configuration is valid and clear/copyable --- guides/get-going-with-gitops.mdx | 143 ++++++++++++++++++++++++++----- 1 file changed, 120 insertions(+), 23 deletions(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index 3183cd7..94d397c 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -84,7 +84,8 @@ Instead of calling `bubblesort` directly, we're going to use the [Flipt Go SDK]( This flag is going to be a **boolean** type flag, and so we use the `sdk.Evaluation().Boolean()` call to evaluate the `enabled` property of our flag. We provide this evaluation call with a request containing the flags key, an entity ID and a context map. -```diff + +```diff diff.go func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { words, err := getWords(r.Context()) if err != nil { @@ -114,6 +115,37 @@ We provide this evaluation call with a request containing the flags key, an enti } ``` +```go pkg/server/words.go +func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { + words, err := getWords(r.Context()) + if err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + + bubbleSort(words) + flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ + FlagKey: "use-quicksort-algorithm", + EntityId: getUser(r.Context()), + Context: map[string]string{ + "organization": getOrganization(r.Context()), + }, + }) + + if flag.Enabled { + quicksort(words) + } else { + bubblesort(words) + } + + if err := json.NewEncoder(w).Encode(words); err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } +} +``` + + The entity ID used here is going to be an identifier for the requests authenticated user. This is returned by the call to `getUser(r.Context())`. Our context map is going to contain a single key `organization`, which is populated by a call to `getOrganization(r.Context())`. @@ -164,9 +196,10 @@ This flag will be a _boolean_ type flag and be in a disabled (`enabled = false`) version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false ``` ### Running Flipt Locally @@ -263,11 +296,14 @@ git checkout -b enable-flag-for-internal-organization We open the `features.yml` file and update the definition with a new segment and add a rollout rule on our flag which returns `enable = true` when the request matches our new segment. -```diff features.yml + + +```diff features.diff version: "1.2" namespace: default flags: - key: use-quicksort-algorithm + name: Use Quicksort Algorithm type: BOOLEAN_FLAG_TYPE enabled: false + rollouts: @@ -276,13 +312,40 @@ We open the `features.yml` file and update the definition with a new segment and + value: true +segments: +- key: internal-users ++ name: Internal Users ++ match_type: ANY_MATCH_TYPE + constraints: + - property: organization -+ operatior: eq ++ operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` +```yaml features.yml +version: "1.2" +namespace: default +flags: +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true +segments: +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE +``` + + + Breaking this change down we've got: #### The `internal-users` Segment @@ -290,12 +353,14 @@ Breaking this change down we've got: ```yaml features.yml # ... segments: - - key: internal-users - constraints: - - property: organization - operatior: eq - value: internal - type: STRING_COMPARISON_TYPE +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` This [segment](/concepts#segments) definition matches any evaluation request where there exists a key `organization` on the context, with a value `internal`. @@ -308,12 +373,12 @@ Now, when the user happens to be associated with the `internal` organization, it ```yaml features.yml flags: - - key: user-quicksort-algorithm - # ... - rollouts: - - segment: - key: internal-users - value: true +- key: use-quicksort-algorithm + # ... + rollouts: + - segment: + key: internal-users + value: true ``` Finally, we add a [rollout rule](/concepts#rollouts) to our boolean flag. @@ -379,11 +444,13 @@ git checkout -b enable-flag-for-20-percent Then we're going to edit `features.yml` and add a threshold percentage rule. -```diff features.yml + +```diff features.diff version: "1.2" namespace: default flags: - key: use-quicksort-algorithm + name: Use Quicksort Algorithm type: BOOLEAN_FLAG_TYPE enabled: false rollouts: @@ -395,13 +462,42 @@ Then we're going to edit `features.yml` and add a threshold percentage rule. + value: true segments: - key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE constraints: - property: organization - operatior: eq + operator: eq value: internal type: STRING_COMPARISON_TYPE ``` +```yaml features.yaml +version: "1.2" +namespace: default +flags: +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true + - threshold: + percentage: 20 + value: true +segments: +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE +``` + + Again, breaking this change down: #### A New Threshold Rollout Rule @@ -457,9 +553,10 @@ Once we get to the stage of enabling the flag for 100% of users, we can either s version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - type: BOOLEAN_FLAG_TYPE - enabled: true +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: true ``` Beyond this, we can further close the loop by removing the feature flag call from our application code and simply use the new `quicksort` function. From 9084dfa622b3b54b4ebe8b3f3ffc8adabf213749 Mon Sep 17 00:00:00 2001 From: GeorgeMac Date: Wed, 13 Dec 2023 11:18:34 +0000 Subject: [PATCH 2/8] chore: format code --- guides/get-going-with-gitops.mdx | 162 ++++++++++++++++--------------- 1 file changed, 83 insertions(+), 79 deletions(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index 94d397c..dbedc3e 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -93,27 +93,29 @@ We provide this evaluation call with a request containing the flags key, an enti return } -- bubbleSort(words) -+ flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ -+ FlagKey: "use-quicksort-algorithm", -+ EntityId: getUser(r.Context()), -+ Context: map[string]string{ -+ "organization": getOrganization(r.Context()), -+ }, -+ }) -+ -+ if flag.Enabled { -+ quicksort(words) -+ } else { -+ bubblesort(words) -+ } - - if err := json.NewEncoder(w).Encode(words); err != nil { - http.Error(w, err.Error(), http.StatusInternalServerError) - return - } - } -``` +- bubbleSort(words) + +* flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ +* FlagKey: "use-quicksort-algorithm", +* EntityId: getUser(r.Context()), +* Context: map[string]string{ +* "organization": getOrganization(r.Context()), +* }, +* }) +* +* if flag.Enabled { +* quicksort(words) +* } else { +* bubblesort(words) +* } + + if err := json.NewEncoder(w).Encode(words); err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + } + +```` ```go pkg/server/words.go func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { @@ -143,7 +145,8 @@ func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { return } } -``` +```` + The entity ID used here is going to be an identifier for the requests authenticated user. This is returned by the call to `getUser(r.Context())`. @@ -196,10 +199,10 @@ This flag will be a _boolean_ type flag and be in a disabled (`enabled = false`) version: "1.2" namespace: default flags: -- key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false + - key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false ``` ### Running Flipt Locally @@ -325,23 +328,23 @@ We open the `features.yml` file and update the definition with a new segment and version: "1.2" namespace: default flags: -- key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false - rollouts: - - segment: - key: internal-users - value: true + - key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true segments: -- key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE + - key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` @@ -353,14 +356,14 @@ Breaking this change down we've got: ```yaml features.yml # ... segments: -- key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE + - key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` This [segment](/concepts#segments) definition matches any evaluation request where there exists a key `organization` on the context, with a value `internal`. @@ -373,12 +376,12 @@ Now, when the user happens to be associated with the `internal` organization, it ```yaml features.yml flags: -- key: use-quicksort-algorithm - # ... - rollouts: - - segment: - key: internal-users - value: true + - key: use-quicksort-algorithm + # ... + rollouts: + - segment: + key: internal-users + value: true ``` Finally, we add a [rollout rule](/concepts#rollouts) to our boolean flag. @@ -475,27 +478,28 @@ Then we're going to edit `features.yml` and add a threshold percentage rule. version: "1.2" namespace: default flags: -- key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false - rollouts: - - segment: - key: internal-users - value: true - - threshold: - percentage: 20 - value: true + - key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true + - threshold: + percentage: 20 + value: true segments: -- key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE + - key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` + Again, breaking this change down: @@ -553,10 +557,10 @@ Once we get to the stage of enabling the flag for 100% of users, we can either s version: "1.2" namespace: default flags: -- key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: true + - key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: true ``` Beyond this, we can further close the loop by removing the feature flag call from our application code and simply use the new `quicksort` function. From fd2f45afaa488b907b6de909489b4eb85c121398 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:20:54 +0000 Subject: [PATCH 3/8] chore(guides): remove bubblesort line from example --- guides/get-going-with-gitops.mdx | 1 - 1 file changed, 1 deletion(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index 94d397c..ebe0971 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -123,7 +123,6 @@ func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { return } - bubbleSort(words) flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ FlagKey: "use-quicksort-algorithm", EntityId: getUser(r.Context()), From 15f30c9934a112689809cf5a1d924256cc49f07b Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:28:03 +0000 Subject: [PATCH 4/8] fix(guide): correct diff after gh workflow borked it --- guides/get-going-with-gitops.mdx | 42 +++++++++++++++----------------- 1 file changed, 20 insertions(+), 22 deletions(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index 997925d..fc8fed7 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -94,28 +94,26 @@ We provide this evaluation call with a request containing the flags key, an enti } - bubbleSort(words) - -* flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ -* FlagKey: "use-quicksort-algorithm", -* EntityId: getUser(r.Context()), -* Context: map[string]string{ -* "organization": getOrganization(r.Context()), -* }, -* }) -* -* if flag.Enabled { -* quicksort(words) -* } else { -* bubblesort(words) -* } - - if err := json.NewEncoder(w).Encode(words); err != nil { - http.Error(w, err.Error(), http.StatusInternalServerError) - return - } - } - -```` ++ flag, err := s.flipt.Evaluation().Boolean(r.Context(), &evaluation.EvaluationRequest{ ++ FlagKey: "use-quicksort-algorithm", ++ EntityId: getUser(r.Context()), ++ Context: map[string]string{ ++ "organization": getOrganization(r.Context()), ++ }, ++ }) ++ ++ if flag.Enabled { ++ quicksort(words) ++ } else { ++ bubblesort(words) ++ } + + if err := json.NewEncoder(w).Encode(words); err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + } +``` ```go pkg/server/words.go func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { From b5f4d13354599490abaa35922b0a94bda4c3c494 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:28:31 +0000 Subject: [PATCH 5/8] fix(guide): remove trailing backtick --- guides/get-going-with-gitops.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index fc8fed7..d65a170 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -142,7 +142,7 @@ func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { return } } -```` +``` From f3687690566ec0450cb2f992dc33904d3f35be50 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:30:16 +0000 Subject: [PATCH 6/8] fix(guide): remove trailing newline in codegroup --- guides/get-going-with-gitops.mdx | 1 - 1 file changed, 1 deletion(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index d65a170..53d0788 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -143,7 +143,6 @@ func (s *Server) ListWords(w http.ResponseWriter, r *http.Request) { } } ``` - The entity ID used here is going to be an identifier for the requests authenticated user. This is returned by the call to `getUser(r.Context())`. From 2d5c328fa7ef99563104f13bbe6b03554fd63375 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:34:28 +0000 Subject: [PATCH 7/8] fix(prettier): ignore gitops guide --- .prettierignore | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.prettierignore b/.prettierignore index a17d5f9..e8516e5 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1,2 +1,3 @@ openapi.yaml -mint.json \ No newline at end of file +mint.json +guides/get-going-with-gitops.mdx From 34e2bd9fd70bfadd08a5bd04a2b1720707cad008 Mon Sep 17 00:00:00 2001 From: George MacRorie Date: Wed, 13 Dec 2023 11:39:58 +0000 Subject: [PATCH 8/8] fix(guides): reduce indentation in copyable examples --- guides/get-going-with-gitops.mdx | 126 +++++++++++++++---------------- 1 file changed, 63 insertions(+), 63 deletions(-) diff --git a/guides/get-going-with-gitops.mdx b/guides/get-going-with-gitops.mdx index 53d0788..a7f66f2 100644 --- a/guides/get-going-with-gitops.mdx +++ b/guides/get-going-with-gitops.mdx @@ -195,10 +195,10 @@ This flag will be a _boolean_ type flag and be in a disabled (`enabled = false`) version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false ``` ### Running Flipt Locally @@ -324,23 +324,23 @@ We open the `features.yml` file and update the definition with a new segment and version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false - rollouts: - - segment: - key: internal-users - value: true +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true segments: - - key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` @@ -352,14 +352,14 @@ Breaking this change down we've got: ```yaml features.yml # ... segments: - - key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` This [segment](/concepts#segments) definition matches any evaluation request where there exists a key `organization` on the context, with a value `internal`. @@ -372,12 +372,12 @@ Now, when the user happens to be associated with the `internal` organization, it ```yaml features.yml flags: - - key: use-quicksort-algorithm - # ... - rollouts: - - segment: - key: internal-users - value: true +- key: use-quicksort-algorithm + # ... + rollouts: + - segment: + key: internal-users + value: true ``` Finally, we add a [rollout rule](/concepts#rollouts) to our boolean flag. @@ -474,26 +474,26 @@ Then we're going to edit `features.yml` and add a threshold percentage rule. version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: false - rollouts: - - segment: - key: internal-users - value: true - - threshold: - percentage: 20 - value: true +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: false + rollouts: + - segment: + key: internal-users + value: true + - threshold: + percentage: 20 + value: true segments: - - key: internal-users - name: Internal Users - match_type: ANY_MATCH_TYPE - constraints: - - property: organization - operator: eq - value: internal - type: STRING_COMPARISON_TYPE +- key: internal-users + name: Internal Users + match_type: ANY_MATCH_TYPE + constraints: + - property: organization + operator: eq + value: internal + type: STRING_COMPARISON_TYPE ``` @@ -514,12 +514,12 @@ If no rules match, then the flags top-level `enabled` property is used as the fi flags: - key: use-quicksort-algorithm # ... - - segment: - key: internal-users - value: true - - threshold: - percentage: 20 - value: true +- segment: + key: internal-users + value: true +- threshold: + percentage: 20 + value: true ``` This threshold percentage is set to `20`, meaning roughly `20%` of entity IDs will match and cause the flag to return `enabled = true`. @@ -553,10 +553,10 @@ Once we get to the stage of enabling the flag for 100% of users, we can either s version: "1.2" namespace: default flags: - - key: use-quicksort-algorithm - name: Use Quicksort Algorithm - type: BOOLEAN_FLAG_TYPE - enabled: true +- key: use-quicksort-algorithm + name: Use Quicksort Algorithm + type: BOOLEAN_FLAG_TYPE + enabled: true ``` Beyond this, we can further close the loop by removing the feature flag call from our application code and simply use the new `quicksort` function.