summaryrefslogtreecommitdiff
path: root/lib/gitlab/language_detection.rb
diff options
context:
space:
mode:
Diffstat (limited to 'lib/gitlab/language_detection.rb')
-rw-r--r--lib/gitlab/language_detection.rb68
1 files changed, 68 insertions, 0 deletions
diff --git a/lib/gitlab/language_detection.rb b/lib/gitlab/language_detection.rb
new file mode 100644
index 00000000000..a41435fdb79
--- /dev/null
+++ b/lib/gitlab/language_detection.rb
@@ -0,0 +1,68 @@
+module Gitlab
+ class LanguageDetection
+ MAX_LANGUAGES = 5
+
+ def initialize(repository, repository_languages)
+ @repository = repository
+ @repository_languages = repository_languages
+ end
+
+ def languages
+ detection.keys
+ end
+
+ def language_color(name)
+ detection.dig(name, :color)
+ end
+
+ # Newly detected languages, returned in a structure accepted by
+ # Gitlab::Database.bulk_insert
+ def insertions(programming_languages)
+ lang_to_id = programming_languages.map { |p| [p.name, p.id] }.to_h
+
+ (languages - previous_language_names).map do |new_lang|
+ {
+ project_id: @repository.project.id,
+ share: detection[new_lang][:value],
+ programming_language_id: lang_to_id[new_lang]
+ }
+ end
+ end
+
+ # updates analyses which records only require updating of their share
+ def updates
+ to_update = @repository_languages.select do |lang|
+ detection.key?(lang.name) && detection[lang.name][:value] != lang.share
+ end
+
+ to_update.map do |lang|
+ { programming_language_id: lang.programming_language_id, share: detection[lang.name][:value] }
+ end
+ end
+
+ # Returns the ids of the programming languages that do not occur in the detection
+ # as current repository languages
+ def deletions
+ @repository_languages.map do |repo_lang|
+ next if detection.key?(repo_lang.name)
+
+ repo_lang.programming_language_id
+ end.compact
+ end
+
+ private
+
+ def previous_language_names
+ @previous_language_names ||= @repository_languages.map(&:name)
+ end
+
+ def detection
+ @detection ||=
+ @repository
+ .languages
+ .first(MAX_LANGUAGES)
+ .map { |l| [l[:label], l] }
+ .to_h
+ end
+ end
+end