Skip to content

Commit f5390f3

Browse files
authored
Import page: fix wizard form (#7702)
The initial data is set at the class level, this means it doesn't survive for the next form. I'm using the same method the wizard uses to store information per session. This doesn't mean the data is always set as default after saving, it means the default values are going to be set when the user is in the advanced form. So, due to that I have moved the default_branch field to the basic form, this way the form will always have the default branch.
1 parent cb17c66 commit f5390f3

File tree

3 files changed

+65
-4
lines changed

3 files changed

+65
-4
lines changed

readthedocs/projects/forms.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ class ProjectBasicsForm(ProjectForm):
8585

8686
class Meta:
8787
model = Project
88-
fields = ('name', 'repo', 'repo_type')
88+
fields = ('name', 'repo', 'repo_type', 'default_branch')
8989

9090
remote_repository = forms.CharField(
9191
widget=forms.HiddenInput(),
@@ -166,7 +166,6 @@ class Meta:
166166
fields = (
167167
'description',
168168
'documentation_type',
169-
'default_branch',
170169
'language',
171170
'programming_language',
172171
'tags',

readthedocs/projects/views/private.py

Lines changed: 28 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -245,14 +245,40 @@ class ImportWizardView(
245245
SessionWizardView,
246246
):
247247

248-
"""Project import wizard."""
248+
"""
249+
Project import wizard.
250+
251+
The get and post methods are overridden in order to save the initial_dict data
252+
per session (since it's per class).
253+
"""
249254

250255
form_list = [
251256
('basics', ProjectBasicsForm),
252257
('extra', ProjectExtraForm),
253258
]
254259
condition_dict = {'extra': lambda self: self.is_advanced()}
255260

261+
initial_dict_key = 'initial-data'
262+
263+
def get(self, *args, **kwargs):
264+
# The method from the parent should run first,
265+
# as the storage is initialized there.
266+
response = super().get(*args, **kwargs)
267+
self._set_initial_dict()
268+
return response
269+
270+
def _set_initial_dict(self):
271+
"""Set or restore the initial_dict from the session."""
272+
if self.initial_dict:
273+
self.storage.data[self.initial_dict_key] = self.initial_dict
274+
else:
275+
self.initial_dict = self.storage.data.get(self.initial_dict_key, {})
276+
277+
def post(self, *args, **kwargs):
278+
self._set_initial_dict()
279+
# The storage is reset after everything is done.
280+
return super().post(*args, **kwargs)
281+
256282
def get_form_kwargs(self, step=None):
257283
"""Get args to pass into form instantiation."""
258284
kwargs = {}
@@ -417,7 +443,7 @@ def get(self, request, *args, **kwargs):
417443
def post(self, request, *args, **kwargs):
418444
initial_data = {}
419445
initial_data['basics'] = {}
420-
for key in ['name', 'repo', 'repo_type', 'remote_repository']:
446+
for key in ['name', 'repo', 'repo_type', 'remote_repository', 'default_branch']:
421447
initial_data['basics'][key] = request.POST.get(key)
422448
initial_data['extra'] = {}
423449
for key in ['description', 'project_url']:

readthedocs/rtd_tests/tests/test_project_views.py

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,7 @@ def test_form_import_from_remote_repo(self):
111111
'repo': 'https://github.com/fail/sauce',
112112
'repo_type': 'git',
113113
'remote_repository': '1234',
114+
'default_branch': 'main',
114115
}
115116
resp = self.client.post(
116117
'/dashboard/import/',
@@ -177,6 +178,41 @@ def setUp(self):
177178
'tags': 'foo, bar, baz',
178179
}
179180

181+
def test_initial_params(self):
182+
extra_initial = {
183+
'description': 'An amazing project',
184+
'project_url': "https://foo.bar",
185+
}
186+
basic_initial = {
187+
'name': 'foobar',
188+
'repo': 'https://github.com/foo/bar',
189+
'repo_type': 'git',
190+
'default_branch': 'main',
191+
'remote_repository': '',
192+
}
193+
initial = dict(**extra_initial, **basic_initial)
194+
self.client.force_login(self.user)
195+
196+
# User selects a remote repo to import.
197+
resp = self.client.post(reverse('projects_import'), initial)
198+
199+
# The correct initial data for the basic form is set.
200+
form = resp.context_data['form']
201+
self.assertEqual(form.initial, basic_initial)
202+
203+
# User selects advanced.
204+
basic_initial['advanced'] = True
205+
step_data = {
206+
f'basics-{k}': v
207+
for k, v in basic_initial.items()
208+
}
209+
step_data[f'{self.wizard_class_slug}-current_step'] = 'basics'
210+
resp = self.client.post(self.url, step_data)
211+
212+
# The correct initial data for the advanced form is set.
213+
form = resp.context_data['form']
214+
self.assertEqual(form.initial, extra_initial)
215+
180216
def test_form_pass(self):
181217
"""Test all forms pass validation."""
182218
resp = self.post_step('basics')

0 commit comments

Comments
 (0)