From 4031e05a1d0b654db9601263592098ab4b9b7e94 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Fr=C3=A9d=C3=A9ric=20P=C3=A9ters?= <fpeters@entrouvert.com>
Date: Thu, 24 Nov 2022 20:35:29 +0100
Subject: [PATCH] misc: clean old migrate methods (#71693)

---
 tests/test_formdef.py      | 77 +-------------------------------------
 tests/test_role.py         | 15 --------
 tests/workflow/test_all.py | 29 --------------
 wcs/categories.py          |  7 ----
 wcs/data_sources.py        |  9 -----
 wcs/fields.py              | 60 ++---------------------------
 wcs/formdata.py            | 12 +-----
 wcs/formdef.py             | 61 +-----------------------------
 wcs/roles.py               |  7 +---
 wcs/users.py               | 21 -----------
 wcs/wf/create_formdata.py  |  2 +-
 wcs/wf/jump.py             | 10 -----
 wcs/workflows.py           |  7 +---
 13 files changed, 11 insertions(+), 306 deletions(-)

diff --git a/tests/test_formdef.py b/tests/test_formdef.py
index cb24464e5..cc9b1db40 100644
--- a/tests/test_formdef.py
+++ b/tests/test_formdef.py
@@ -13,7 +13,7 @@ from wcs import fields
 from wcs.admin.settings import UserFieldsFormDef
 from wcs.blocks import BlockDef
 from wcs.carddef import CardDef
-from wcs.fields import DateField, FileField, ItemField, PageField, StringField
+from wcs.fields import DateField, ItemField, StringField
 from wcs.formdef import FormDef, get_formdefs_of_all_kinds
 from wcs.qommon.http_request import HTTPRequest
 from wcs.qommon.upload_storage import PicklableUpload
@@ -212,57 +212,6 @@ def test_substitution_variables_object(pub):
     assert substs.formdef is formdef
 
 
-def test_file_field_migration(pub):
-    pub.cfg['filetypes'] = {
-        1: {
-            'mimetypes': [
-                'application/pdf',
-                'application/vnd.oasis.opendocument.text',
-                'application/msword',
-                'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
-                'application/vnd.oasis.opendocument.spreadsheet',
-                'application/vnd.ms-excel',
-                'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
-            ],
-            'label': 'Documents',
-        }
-    }
-
-    FormDef.wipe()
-    formdef = FormDef()
-    formdef.name = 'foo'
-    formdef.fields = [
-        FileField(type='file', id='1', label='images & docs'),
-        FileField(type='file', id='2', label='images'),
-    ]
-    formdef.fields[0].__dict__['file_type'] = [
-        'image/*',
-        (
-            'application/pdf,application/vnd.oasis.opendocument.text,application/msword,'
-            'application/vnd.openxmlformats-officedocument.wordprocessingml.document,'
-            'application/vnd.oasis.opendocument.spreadsheet,application/vnd.ms-excel,'
-            'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'
-        ),
-    ]
-    formdef.fields[1].__dict__['file_type'] = ['image/*']
-    formdef.store()
-    formdef = FormDef.get(1)
-    assert 'file_type' not in formdef.fields[0].__dict__
-    assert formdef.fields[0].document_type
-    assert formdef.fields[0].document_type['id'] == '_legacy'
-    assert formdef.fields[0].document_type['mimetypes'] == [
-        'image/*',
-        (
-            'application/pdf,application/vnd.oasis.opendocument.text,application/msword,'
-            'application/vnd.openxmlformats-officedocument.wordprocessingml.document,'
-            'application/vnd.oasis.opendocument.spreadsheet,application/vnd.ms-excel,'
-            'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'
-        ),
-    ]
-    assert formdef.fields[1].document_type['label'] == 'Image files'
-    assert formdef.fields[0].document_type['label'] == 'Image files, Documents'
-
-
 def test_internal_identifier_migration(pub):
     FormDef.wipe()
     formdef = FormDef()
@@ -283,30 +232,6 @@ def test_internal_identifier_migration(pub):
     assert formdef.internal_identifier == 'foo'
 
 
-def test_page_field_migration(pub):
-    # disable snapshots as XML serialization of old post_conditions structure
-    # is not possible.
-    pub.snapshot_class = None
-    FormDef.wipe()
-    formdef = FormDef()
-    formdef.name = 'foo'
-    formdef.fields = [
-        PageField(
-            id='1',
-            type='page',
-            condition='foo',
-            # old post_conditions structure
-            post_conditions=[{'condition': 'blah', 'error_message': 'blah'}],
-        ),
-    ]
-    formdef.store()
-    formdef = FormDef.get(formdef.id)
-    assert formdef.fields[0].condition == {'type': 'python', 'value': 'foo'}
-    assert formdef.fields[0].post_conditions == [
-        {'condition': {'type': 'python', 'value': 'blah'}, 'error_message': 'blah'}
-    ]
-
-
 def test_unused_file_removal_job(pub):
     from wcs.formdef import clean_unused_files
 
diff --git a/tests/test_role.py b/tests/test_role.py
index 5cb76f28e..88f09cb2e 100644
--- a/tests/test_role.py
+++ b/tests/test_role.py
@@ -1,6 +1,5 @@
 from quixote import get_publisher
 
-from wcs import sql
 from wcs.roles import get_user_roles
 
 from .utilities import clean_temporary_pub, create_temporary_pub
@@ -33,20 +32,6 @@ def test_duplicated_name():
     assert role.slug == 'hello-world-1'
 
 
-def test_migrate():
-    get_publisher().role_class.wipe()
-    role = get_publisher().role_class(name='Hello world')
-    role.store()
-
-    conn, cur = sql.get_connection_and_cursor()
-    sql_statement = 'UPDATE roles SET slug = NULL'
-    cur.execute(sql_statement)
-    conn.commit()
-    cur.close()
-
-    assert get_publisher().role_class.get(role.id).slug == 'hello-world'
-
-
 def test_get_user_roles():
     get_publisher().role_class.wipe()
     get_publisher().role_class(name='f1').store()
diff --git a/tests/workflow/test_all.py b/tests/workflow/test_all.py
index 2d96b0d9f..7c9c753f1 100644
--- a/tests/workflow/test_all.py
+++ b/tests/workflow/test_all.py
@@ -3112,19 +3112,6 @@ def test_choice_button_template_label(pub):
     assert '>[if-any test]a[else]b[end]</button>' in str(form.render())
 
 
-def test_workflow_role_type_migration(pub):
-    workflow = Workflow(name='role migration')
-    st1 = workflow.add_status('Status1', 'st1')
-
-    jump = st1.add_action('jump', id='_jump')
-    jump.by = [1, 2]
-
-    workflow.store()
-
-    reloaded_workflow = Workflow.get(workflow.id)
-    assert reloaded_workflow.possible_status[0].items[0].by == ['1', '2']
-
-
 def test_workflow_display_message(pub):
     pub.substitutions.feed(MockSubstitutionVariables())
 
@@ -4553,22 +4540,6 @@ def test_redirect_to_url(pub):
     assert item.perform(formdata) is None
 
 
-def test_workflow_jump_condition_migration(pub):
-    workflow = Workflow(name='jump condition migration')
-    st1 = workflow.add_status('Status1', 'st1')
-
-    jump = st1.add_action('jump', id='_jump')
-    workflow.store()
-
-    reloaded_workflow = Workflow.get(workflow.id)
-    assert reloaded_workflow.possible_status[0].items[0].condition is None
-
-    jump.condition = 'foobar'
-    workflow.store()
-    reloaded_workflow = Workflow.get(workflow.id)
-    assert reloaded_workflow.possible_status[0].items[0].condition == {'type': 'python', 'value': 'foobar'}
-
-
 def test_workflow_action_condition(pub):
     pub._set_request(None)  # to avoid after jobs
     workflow = Workflow(name='jump condition migration')
diff --git a/wcs/categories.py b/wcs/categories.py
index 2681bbc5b..1c92a9a4a 100644
--- a/wcs/categories.py
+++ b/wcs/categories.py
@@ -58,13 +58,6 @@ class Category(XmlStorableObject):
         StorableObject.__init__(self)
         self.name = name
 
-    def migrate(self):
-        changed = False
-        if not self.url_name:
-            changed = True  # trigger new slug in .store()
-        if changed:
-            self.store(comment=_('Automatic update'), snapshot_store_user=False)
-
     @classmethod
     def get_object_class(cls):
         from .formdef import FormDef
diff --git a/wcs/data_sources.py b/wcs/data_sources.py
index 327c96dc7..8a00b85aa 100644
--- a/wcs/data_sources.py
+++ b/wcs/data_sources.py
@@ -680,15 +680,6 @@ class NamedDataSource(XmlStorableObject):
             if datasource.data_source.get('value') == self.data_source.get('value'):
                 return datasource
 
-    def migrate(self):
-        changed = False
-
-        if not self.slug:
-            # .store() will take care of setting the slug
-            changed = True
-        if changed:
-            self.store(comment=_('Automatic update'), snapshot_store_user=False)
-
     def store(self, comment=None, snapshot_store_user=True, *args, **kwargs):
         assert not self.is_readonly()
         if self.slug is None:
diff --git a/wcs/fields.py b/wcs/fields.py
index 5c994c6e9..e37a76f76 100644
--- a/wcs/fields.py
+++ b/wcs/fields.py
@@ -82,7 +82,6 @@ from .qommon.misc import (
     ellipsize,
     get_as_datetime,
     get_document_type_value_options,
-    get_document_types,
     strftime,
     strip_some_tags,
     xml_node_text,
@@ -602,7 +601,7 @@ class Field:
 
     def migrate(self):
         changed = False
-        if getattr(self, 'in_listing', None):
+        if getattr(self, 'in_listing', None):  # 2019-09-28
             self.display_locations = self.display_locations[:]
             self.display_locations.append('listings')
             changed = True
@@ -1343,7 +1342,7 @@ class StringField(WidgetField):
 
     def migrate(self):
         changed = super().migrate()
-        if isinstance(self.validation, str):
+        if isinstance(self.validation, str):  # 2019-08-10
             self.validation = {'type': 'regex', 'value': self.validation}
             changed = True
         return changed
@@ -1379,7 +1378,7 @@ class TextField(WidgetField):
 
     def migrate(self):
         changed = super().migrate()
-        if isinstance(getattr(self, 'pre', None), bool):
+        if isinstance(getattr(self, 'pre', None), bool):  # 2022-09-16
             if self.pre:
                 self.display_mode = 'pre'
             else:
@@ -1804,39 +1803,6 @@ class FileField(WidgetField):
             if value and hasattr(value, 'token'):
                 get_request().form[self.field_key + '$token'] = value.token
 
-    def migrate(self):
-        changed = super().migrate()
-        if 'file_type' in self.__dict__:
-            self.document_type = {}
-            if self.__dict__['file_type']:
-                file_type = self.__dict__['file_type']
-                document_types = get_document_types(self.document_type)
-                parts = []
-                for key, value in document_types.items():
-                    if file_type == value.get('mimetypes'):
-                        self.document_type = value.copy()
-                        self.document_type['id'] = key
-                        break
-                    if not value.get('mimetypes'):
-                        continue
-                    if ','.join(value['mimetypes']) in file_type:
-                        parts.append(value['label'])
-                else:
-                    # self.file_type is a combination of file type, we create a
-                    # virtual one from them
-                    if parts and len(parts) > 1:
-                        label = ', '.join([str(x) for x in parts])
-                    else:
-                        label = ','.join(file_type)
-                    self.document_type = {
-                        'id': '_legacy',
-                        'label': label,
-                        'mimetypes': file_type,
-                    }
-            del self.__dict__['file_type']
-            changed = True
-        return changed
-
     def export_to_xml(self, charset, include_id=False):
         # convert some sub-fields to strings as export_to_xml() only supports
         # dictionnaries with strings values
@@ -2229,7 +2195,7 @@ class ItemField(WidgetField, MapOptionsMixin, ItemFieldMixin):
 
     def migrate(self):
         changed = super().migrate()
-        if isinstance(getattr(self, 'show_as_radio', None), bool):
+        if isinstance(getattr(self, 'show_as_radio', None), bool):  # 2019-03-19
             if self.show_as_radio:
                 self.display_mode = 'radio'
             else:
@@ -3049,24 +3015,6 @@ class PageField(Field):
     def get_admin_attributes(self):
         return Field.get_admin_attributes(self) + ['post_conditions']
 
-    def migrate(self):
-        changed = super().migrate()
-        if isinstance(self.condition, str):
-            if self.condition:
-                self.condition = {'type': 'python', 'value': self.condition}
-            else:
-                self.condition = {}
-            changed = True
-        for post_condition in self.post_conditions or []:
-            condition = post_condition.get('condition')
-            if isinstance(condition, str):
-                if condition:
-                    post_condition['condition'] = {'type': 'python', 'value': condition}
-                else:
-                    post_condition['condition'] = {}
-                changed = True
-        return changed
-
     def add_to_view_form(self, *args, **kwargs):
         pass
 
diff --git a/wcs/formdata.py b/wcs/formdata.py
index 97fac0961..09348fdc9 100644
--- a/wcs/formdata.py
+++ b/wcs/formdata.py
@@ -318,24 +318,16 @@ class FormData(StorableObject):
 
     def migrate(self):
         changed = False
-        if self.status and not self.status.startswith('wf-') and self.status != 'draft':
-            self.status = 'wf-%s' % self.status
-            changed = True
-        if self.evolution:
-            for evo in self.evolution:
-                evo._formdata = self  # link from evolution to formdata
-                if evo.status and not evo.status.startswith('wf-'):
-                    evo.status = 'wf-%s' % evo.status
-                    changed = True
         if (
             not self.submission_agent_id
             and self.submission_context
             and self.submission_context.get('agent_id')
         ):
+            # 2020-07-13
             self.submission_agent_id = str(self.submission_context.get('agent_id'))
             changed = True
 
-        if 'digest' in self.__dict__:
+        if 'digest' in self.__dict__:  # 2021-06-24
             # migration from a simple digest to digests
             if not self.digests:
                 self.digests = {}
diff --git a/wcs/formdef.py b/wcs/formdef.py
index 4aa330ef7..697a62338 100644
--- a/wcs/formdef.py
+++ b/wcs/formdef.py
@@ -224,73 +224,14 @@ class FormDef(StorableObject):
             # don't run migration on lightweight objects
             return
 
-        if 'receiver' in self.__dict__:
-            self.receiver_id = self.__dict__['receiver']
-            del self.__dict__['receiver']
-            changed = True
-
-        if 'category' in self.__dict__:
-            self.category_id = self.__dict__['category']
-            del self.__dict__['category']
-            changed = True
-
-        if not self.url_name:
-            try:
-                int(self.id)
-            except ValueError:
-                self.url_name = self.id
-            else:
-                self.url_name = self.get_new_url_name()
-            changed = True
-
-        if self.fields and isinstance(self.fields[0], dict):
-            for f in self.fields:
-                if 'name' in f:
-                    f['label'] = f['name']
-                    del f['name']
-            self.fields = [FormField(**x) for x in self.fields]
-            for i, f in enumerate(self.fields):
-                f.id = str(i)
-            for formdata in self.data_class().select():
-                for f in self.fields:
-                    if f.label not in formdata.data:
-                        continue
-                    formdata.data[f.id] = formdata.data[f.label]
-                    del formdata.data[f.label]
-                formdata.store()
-            changed = True
-
-        if self.fields and isinstance(self.fields[0], FormField):
-            # migration from generic FormField to specific Field classes
-            # (200603)
-            self.fields = [x.real_field for x in self.fields]
-
-        if 'public' in self.__dict__:
-            del self.__dict__['public']
-            changed = True
-
-        if 'receiver_id' in self.__dict__:
-            # migration from a simple receiver role to workflow roles
-            if not self.workflow_roles:
-                self.workflow_roles = {}
-            self.workflow_roles['_receiver'] = self.__dict__['receiver_id']
-            del self.__dict__['receiver_id']
-            changed = True
-
         if 'digest_template' in self.__dict__:
-            # migration from a simple template to templates
+            # 2021-06-22 - migration from a simple template to templates
             if not self.digest_templates:
                 self.digest_templates = {}
             self.digest_templates['default'] = self.__dict__['digest_template']
             del self.__dict__['digest_template']
             changed = True
 
-        if not self.table_name and get_publisher().has_site_option('postgresql'):
-            from . import sql
-
-            self.table_name = sql.get_formdef_table_name(self)
-            changed = True
-
         if self.max_field_id is None and self.fields:
             self.max_field_id = max(lax_int(x.id) for x in self.fields)
             changed = True
diff --git a/wcs/roles.py b/wcs/roles.py
index 5ea555041..94c585f53 100644
--- a/wcs/roles.py
+++ b/wcs/roles.py
@@ -51,12 +51,7 @@ class Role(StorableObject):
         return bool(self.__class__ is other.__class__ and self.id == other.id)
 
     def migrate(self):
-        changed = False
-        if not self.slug:
-            # .store() will take care of setting the slug
-            changed = True
-        if changed:
-            self.store()
+        pass
 
     def store(self):
         if self.slug is None:
diff --git a/wcs/users.py b/wcs/users.py
index 3df9a5e95..72208fba6 100644
--- a/wcs/users.py
+++ b/wcs/users.py
@@ -64,27 +64,6 @@ class User(StorableObject):
         self.verified_fields = []
         self.roles = []
 
-    def migrate(self):
-        changed = False
-
-        if self.roles and 'site-admin' in self.roles:
-            self.is_admin = True
-            self.roles = [x for x in self.roles if x != 'site-admin']
-            changed = True
-
-        if self.roles:
-            for role in self.roles:
-                if isinstance(role, int):
-                    self.roles = [str(x) for x in self.roles]
-                    changed = True
-                    break
-
-        if not self.verified_fields:
-            self.verified_fields = []
-
-        if changed:
-            self.store()
-
     @invalidate_substitution_cache
     def store(self, *args, **kwargs):
         return super().store(*args, **kwargs)
diff --git a/wcs/wf/create_formdata.py b/wcs/wf/create_formdata.py
index 5dee7946d..f8b47cac7 100644
--- a/wcs/wf/create_formdata.py
+++ b/wcs/wf/create_formdata.py
@@ -355,7 +355,7 @@ class CreateFormdataWorkflowStatusItem(WorkflowStatusItem):
 
     def migrate(self):
         changed = super().migrate()
-        if getattr(self, 'keep_user', False) is True:
+        if getattr(self, 'keep_user', False) is True:  # 2021-03-15
             self.user_association_mode = 'keep-user'
             delattr(self, 'keep_user')
             changed = True
diff --git a/wcs/wf/jump.py b/wcs/wf/jump.py
index 74ea2f187..6292f46a7 100644
--- a/wcs/wf/jump.py
+++ b/wcs/wf/jump.py
@@ -141,16 +141,6 @@ class JumpWorkflowStatusItem(WorkflowStatusJumpItem):
             else:
                 self.timeout = int(timeout)
 
-    def migrate(self):
-        changed = super().migrate()
-        if isinstance(self.condition, str):
-            if self.condition:
-                self.condition = {'type': 'python', 'value': self.condition}
-            else:
-                self.condition = {}
-            changed = True
-        return changed
-
     @property
     def waitpoint(self):
         if self.timeout or self.trigger:
diff --git a/wcs/workflows.py b/wcs/workflows.py
index 868434cbc..6d8d696bd 100644
--- a/wcs/workflows.py
+++ b/wcs/workflows.py
@@ -2491,12 +2491,7 @@ class WorkflowStatusItem(XmlSerialisable):
 
     def migrate(self):
         changed = False
-        for roles_attribute in ('to', 'by'):
-            attribute_value = getattr(self, roles_attribute, []) or []
-            if any(x for x in attribute_value if isinstance(x, int)):
-                setattr(self, roles_attribute, [str(x) for x in attribute_value])
-                changed = True
-        if getattr(self, 'attachments', None):
+        if getattr(self, 'attachments', None):  # 2022-06-19
             if any(x for x in self.attachments if not x.startswith('{{')):
                 # convert old attachment python expression to templates
                 for field in self.parent.parent.get_backoffice_fields():
-- 
2.38.1

