Skip to content

Unify "merging" MR Widgets

Thomas Randolph requested to merge tor/feature/unify-merging-states into master

What does this MR do?

For #324175 (closed)

This MR attempts to simplify a few different "merging" states into one unified component to display that state.

It does this by consolidating the following states to all display using the mr_widget_merging.vue component:

  1. Merging: Auto-merge immediately — ready_to_merge.vue
  2. Merging: Regular merge (not immediately) — ready_to_merge.vue
  3. Merging — mr_widget_merging.vue

Both of the former two are internal to the "Ready To Merge" component, triggered by user interaction on the ready component (e.g. click "Merge immediately").

The latter is when the MR loads already in that state, and shouldn't need to be modified except that it's now the same component as the other states.

Implementation Notes

The implementation found here can essentially be summed up as "Short Circuit Component Display In Certain States."

That is: for some of the existing cases, show a different component instead of the normal rendered content. Unfortunately dozens of state variables that mix together make it difficult to "carve out" the few small cases we want to exclude.

You'll note that the implementation in this MR adds a state machine.
In the code comments, I note that this new state machine is intended to replace all of it... eventually. After all, the widget can't be in multiple states at once, it must be reducible to a single state at a time.

However, I have to acknowledge that in the mean time, this does further increase the complexity: now there are all those dozens of state variables plus a state machine. The only saving grace - I hope - is that this is pretty removed: given a certain state machine value, the rest of the render logic need not apply.

Screenshots or Screencasts (strongly suggested)

image

How to setup and validate locally (strongly suggested)

Click the "Merge" button on normal MRs to see the output if the merge will occur slowly enough for the normal polling update to occur, but this is unlikely.

The same output can also be seen when using the "Merge Immediately" merge button when Merge Trains are enabled.

To see this output, enable Merge Trains on your instance (requires a Premium-tier license).
Add your test MR to a merge train, and then click "Merge Immediately".


In most cases, the default behavior (e.g. actually merging, polling overwriting local state) and the speed with which it happens is a roadblock to testing.

I use this patch to first make the polling and the merging inert. Then, I use these developer console commands to step the component through it's various stages:

1. Inert state

The MR is ready to merge.

var widget = document.querySelector( ".mr-widget-body" ).__vue__.$parent;

widget.mr.state = "readyToMerge";

2. "Merging" state

This is what happens when you click either the "Merge" or "Merge Immediately" buttons.

widget.mr.transitionStateMachine( { transition: "start-merge" } );

3. Failure

This is what happens when the merge fails after clicking merge.

Note: this view is missing most data because an actual failure would set various error data to the component, which this skips.

widget.mr.state = "mergeChecksFailed";
widget.mr.transitionStateMachine( { transition: "merge-failed" } );

4. Success

This is what happens after polling has resulted in a merged MR (or on a new pageload that starts with a merged state).

Note: this view is missing user information about who merged, because it skips the steps that would receive that info.
Note: If you've already moved to the failure state, get back to the "Merging" state by first setting the "1. Inert state" and then moving to the "Merging" (2.) state.

widget.mr.state = "merged";
widget.mr.transitionStateMachine( { transition: "merge-done" } );

Does this MR meet the acceptance criteria?

Conformity

Availability and Testing

Edited by Thomas Randolph

Merge request reports