Skip to content

Prevent Merging an MR When Namespace Storage Limits Are Exceeded

What does this MR do and why?

Prevent merging a merge request when namespace storage limits have been exceeded.

Note that we already prevent creating a new merge request when namespace storage limits are exceeded. This MR is to handle merge requests that already exist prior to exceeding the limit.

Issue: https://gitlab.com/gitlab-org/gitlab/-/issues/362945

Screen recordings

PreventMergeMR-small

How to set up and validate locally

Initial Setup

  1. Create a merge request. You need to do this first, because we prevent creating merge requests when namespace storage limits have been exceeded.

Enable namespace storage limits and set the threshold low enough that it is exceeded

  1. Make sure the automatic_purchased_storage_allocation and enforce_namespace_storage_limit application settings are both enabled (true).
gitlabhq_development=# SELECT automatic_purchased_storage_allocation, enforce_namespace_storage_limit FROM application_settings;
 automatic_purchased_storage_allocation | enforce_namespace_storage_limit 
----------------------------------------+---------------------------------
 t                                      | t
(1 row)

gitlabhq_development=# 
  1. Enable the :namespace_storage_limit, :enforce_storage_limit_for_paid, :enforce_storage_limit_for_free, and :namespace_storage_limit_bypass_date_check feature flags in a rails console.
[1] pry(main)> Feature.enable(:namespace_storage_limit)
[...]
[2] pry(main)> Feature.enable(:enforce_storage_limit_for_paid)
[...]
[3] pry(main)> Feature.enable(:enforce_storage_limit_for_free)
[...]
[4] pry(main)> Feature.enable(:namespace_storage_limit_bypass_date_check)
[...]
[5] pry(main)> 
  1. Apply the following patch to your local gitlab instance. This patch disables some caching around storage size and storage limits.
diff --git a/ee/app/models/ee/namespace/root_storage_size.rb b/ee/app/models/ee/namespace/root_storage_size.rb
index fd612db00ec..b37918bdfbc 100644
--- a/ee/app/models/ee/namespace/root_storage_size.rb
+++ b/ee/app/models/ee/namespace/root_storage_size.rb
@@ -26,16 +26,16 @@ def usage_ratio
     end
 
     def current_size
-      @current_size ||= Rails.cache.fetch(['namespaces', root_namespace.id, CURRENT_SIZE_CACHE_KEY], expires_in: EXPIRATION_TIME) do
+      # @current_size ||= Rails.cache.fetch(['namespaces', root_namespace.id, CURRENT_SIZE_CACHE_KEY], expires_in: EXPIRATION_TIME) do
         root_namespace.root_storage_statistics&.storage_size
-      end
+      # end
     end
 
     def limit
-      @limit ||= Rails.cache.fetch(['namespaces', root_namespace.id, LIMIT_CACHE_KEY], expires_in: EXPIRATION_TIME) do
+      # @limit ||= Rails.cache.fetch(['namespaces', root_namespace.id, LIMIT_CACHE_KEY], expires_in: EXPIRATION_TIME) do
         root_namespace.actual_limits.storage_size_limit.megabytes +
             root_namespace.additional_purchased_storage_size.megabytes
-      end
+      # end
     end
 
     def remaining_storage_percentage
  1. Restart your GDK simulating saas mode with $ GITLAB_SIMULATE_SAAS=1 gdk start.

  2. Navigate to your project's group page. In the example here, my project is "Storage Test Project" under the "Storage Test Group" group so I navigate to the "Storage Test Group" page, pictured below.

Screen_Shot_2022-05-23_at_1.45.05_PM

Navigate to Settings > Usage Quotas. Click the Storage tab. You can see how much total namespace storage you currently have here.

Screen_Shot_2022-05-23_at_1_47_08_PM

This can give you a good idea of what number to use in the SQL UPDATE statements in the following steps.

  1. Find the plan_limit.id of your local plan_limit for the free plan. (The project in these examples is in a group on the free plan. You may need to use a different plan if your project is on an Ultimate or Premium plan.)
gitlabhq_development=# SELECT p.id, p.name, p.title, l.id, l.storage_size_limit FROM plans AS p JOIN plan_limits AS l ON p.id = l.plan_id;
 id |      name      |           title           | id | storage_size_limit 
----+----------------+---------------------------+----+--------------------
  1 | default        | Default                   |  1 |                  0
  2 | bronze         | Bronze                    |  6 |                  0
  3 | silver         | Silver                    |  7 |                  0
  4 | gold           | Gold                      |  8 |                  0
  5 | free           |                           |  5 |                 30
  6 | premium        | Premium (Formerly Silver) | 23 |                  0
  7 | ultimate       | Ultimate (Formerly Gold)  | 26 |                  0
  8 | ultimate_trial | Ultimate Trial            |  3 |                  0
  9 | premium_trial  | Premium Trial             |  4 |                  0
 10 | opensource     | Open Source Program       | 28 |                  0
(10 rows)

gitlabhq_development=# 
  1. Update the storage limit. Pick a number below the total namespace storage.
gitlabhq_development=# UPDATE plan_limits SET storage_size_limit = 3 WHERE id = 5;
UPDATE 1
gitlabhq_development=# 

Verify merge request cannot be merged

  1. Try to merge the merge request. Note the error message as seen in the video above under Screen recordings.

MR acceptance checklist

This checklist encourages us to confirm any changes have been analyzed to reduce risks in quality, performance, reliability, security, and maintainability.

Edited by Jason Goodman

Merge request reports

Loading