diff options
author | Clement Ho <ClemMakesApps@gmail.com> | 2018-01-08 13:01:53 -0600 |
---|---|---|
committer | Clement Ho <ClemMakesApps@gmail.com> | 2018-01-08 13:01:53 -0600 |
commit | a2b80c89d8b6b38eb1f5c59109006ea48a2e9e5a (patch) | |
tree | 2d22d33ab68a57d4c934f0c44b43621f482cb192 /doc/development/utilities.md | |
parent | 65791c9c2a234685e297e334dd3d56e56858f27c (diff) | |
parent | 1d7b46062feb1d93dd3efaf6ba4d5d934068342c (diff) | |
download | gitlab-ce-move-markdown-preview.tar.gz |
Merge branch 'master' into move-markdown-previewmove-markdown-preview
Diffstat (limited to 'doc/development/utilities.md')
-rw-r--r-- | doc/development/utilities.md | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/doc/development/utilities.md b/doc/development/utilities.md new file mode 100644 index 00000000000..951c3ef85ce --- /dev/null +++ b/doc/development/utilities.md @@ -0,0 +1,92 @@ +# GitLab utilities + +We developed a number of utilities to ease development. + +## [`MergeHash`](https://gitlab.com/gitlab-org/gitlab-ce/blob/master/lib/gitlab/utils/merge_hash.rb) + +* Deep merges an array of hashes: + + ``` ruby + Gitlab::Utils::MergeHash.merge( + [{ hello: ["world"] }, + { hello: "Everyone" }, + { hello: { greetings: ['Bonjour', 'Hello', 'Hallo', 'Dzien dobry'] } }, + "Goodbye", "Hallo"] + ) + ``` + + Gives: + + ``` ruby + [ + { + hello: + [ + "world", + "Everyone", + { greetings: ['Bonjour', 'Hello', 'Hallo', 'Dzien dobry'] } + ] + }, + "Goodbye" + ] + ``` + +* Extracts all keys and values from a hash into an array: + + ``` ruby + Gitlab::Utils::MergeHash.crush( + { hello: "world", this: { crushes: ["an entire", "hash"] } } + ) + ``` + + Gives: + + ``` ruby + [:hello, "world", :this, :crushes, "an entire", "hash"] + ``` + +## [`StrongMemoize`](https://gitlab.com/gitlab-org/gitlab-ce/blob/master/lib/gitlab/utils/strong_memoize.rb) + +* Memoize the value even if it is `nil` or `false`. + + We often do `@value ||= compute`, however this doesn't work well if + `compute` might eventually give `nil` and we don't want to compute again. + Instead we could use `defined?` to check if the value is set or not. + However it's tedious to write such pattern, and `StrongMemoize` would + help us use such pattern. + + Instead of writing patterns like this: + + ``` ruby + class Find + def result + return @result if defined?(@result) + + @result = search + end + end + ``` + + We could write it like: + + ``` ruby + class Find + include Gitlab::Utils::StrongMemoize + + def result + strong_memoize(:result) do + search + end + end + end + ``` + +* Clear memoization + + ``` ruby + class Find + include Gitlab::Utils::StrongMemoize + end + + Find.new.clear_memoization(:result) + ``` |