From 1be59687b21f825354eb0829925bb772485969ec Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Fr=C3=A9d=C3=A9ric=20P=C3=A9ters?= <fpeters@entrouvert.com>
Date: Tue, 5 Oct 2021 10:23:18 +0200
Subject: [PATCH] formdef: don't try preserving intenral_identifier in SQL mode
 (#57540)

---
 tests/test_formdef.py | 13 +++++++------
 tests/test_sql.py     | 32 ++++++++++++++++++++++++++++++++
 wcs/formdef.py        | 10 ++++++----
 3 files changed, 45 insertions(+), 10 deletions(-)

diff --git a/tests/test_formdef.py b/tests/test_formdef.py
index 3e20292bc..7c26727d4 100644
--- a/tests/test_formdef.py
+++ b/tests/test_formdef.py
@@ -126,12 +126,13 @@ def test_title_change(pub):
     assert FormDef.get(formdef.id).url_name == 'foo'
     assert FormDef.get(formdef.id).internal_identifier == 'bar'
 
-    # makes sure the internal_name doesn't change if there are submitted forms
-    formdef.data_class()().store()
-    formdef.name = 'baz'
-    formdef.store()
-    assert FormDef.get(formdef.id).name == 'baz'
-    assert FormDef.get(formdef.id).internal_identifier == 'bar'  # didn't change
+    if not pub.is_using_postgresql():
+        # makes sure the internal_name doesn't change if there are submitted forms
+        formdef.data_class()().store()
+        formdef.name = 'baz'
+        formdef.store()
+        assert FormDef.get(formdef.id).name == 'baz'
+        assert FormDef.get(formdef.id).internal_identifier == 'bar'  # didn't change
 
 
 def test_substitution_variables(pub):
diff --git a/tests/test_sql.py b/tests/test_sql.py
index abd1eb9d4..38bcda35e 100644
--- a/tests/test_sql.py
+++ b/tests/test_sql.py
@@ -1,7 +1,9 @@
 import datetime
+import io
 import random
 import string
 import time
+import zipfile
 
 import psycopg2
 import pytest
@@ -2075,3 +2077,33 @@ def test_logged_error_store_without_integrity_error(sql_queries):
     assert len(sql_queries) == 2
     assert 'SELECT' in sql_queries[0]
     assert 'UPDATE' in sql_queries[1]
+
+
+def test_sql_import_zip_create_tables():
+    pub = create_temporary_pub(sql_mode=True)
+
+    c = io.BytesIO()
+    with zipfile.ZipFile(c, 'w') as z:
+        z.writestr(
+            'formdefs_xml/123',
+            '''<?xml version="1.0"?>
+<formdef id="123">
+  <name>crash</name>
+  <url_name>crash</url_name>
+  <internal_identifier>different-identifier</internal_identifier>
+  <max_field_id>1</max_field_id>
+  <fields>
+  </fields>
+</formdef>
+''',
+        )
+    c.seek(0)
+
+    pub.import_zip(c)
+
+    formdef = FormDef.get(123)
+
+    conn, cur = sql.get_connection_and_cursor()
+    assert table_exists(cur, formdef.table_name)
+    conn.commit()
+    cur.close()
diff --git a/wcs/formdef.py b/wcs/formdef.py
index 26170b1c9..8f2b66799 100644
--- a/wcs/formdef.py
+++ b/wcs/formdef.py
@@ -93,7 +93,7 @@ class FormDef(StorableObject):
     description = None
     keywords = None
     url_name = None
-    internal_identifier = None  # mostly for pickle
+    internal_identifier = None  # used to have a stable pickle object class name
     table_name = None  # for SQL only
     fields = None
     category_id = None
@@ -402,13 +402,15 @@ class FormDef(StorableObject):
         new_internal_identifier = self.get_new_internal_identifier()
         if not self.internal_identifier:
             self.internal_identifier = new_internal_identifier
-        object_only = kwargs.pop('object_only', False)
         if new_internal_identifier != self.internal_identifier:
             # title changed, internal identifier will be changed only if
             # the formdef is currently being imported (self.id is None)
-            # or if there are not yet any submitted forms
-            if self.id is None or self.data_class().count() == 0:
+            # or if there are not yet any submitted forms (or if site
+            # is using the SQL storage as internal identifier is not used
+            # in that mode.
+            if self.id is None or get_publisher().is_using_postgresql() or self.data_class().count() == 0:
                 self.internal_identifier = new_internal_identifier
+        object_only = kwargs.pop('object_only', False)
         StorableObject.store(self, *args, **kwargs)
         if object_only:
             return
-- 
2.33.0

