feat: dependency syncing in mapped doctypes
This commit is contained in:
parent
1706f46b17
commit
85d6da6e2e
4 changed files with 74 additions and 38 deletions
|
|
@ -7,15 +7,13 @@
|
|||
"field_order": [
|
||||
"local_fieldname",
|
||||
"remote_fieldname",
|
||||
"has_default_value",
|
||||
"default_value",
|
||||
"column_break_5",
|
||||
"is_child_table",
|
||||
"child_table_mapping"
|
||||
"mapping_type",
|
||||
"mapping"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"depends_on": "eval:!doc.has_default_value;",
|
||||
"fieldname": "remote_fieldname",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
|
|
@ -28,40 +26,32 @@
|
|||
"label": "Local Fieldname",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"fieldname": "is_child_table",
|
||||
"fieldtype": "Check",
|
||||
"label": "Is Child Table"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval: doc.is_child_table == 1",
|
||||
"fieldname": "child_table_mapping",
|
||||
"fieldtype": "Link",
|
||||
"label": "Child Table Mapping",
|
||||
"options": "Document Type Mapping"
|
||||
},
|
||||
{
|
||||
"fieldname": "column_break_5",
|
||||
"fieldtype": "Column Break"
|
||||
},
|
||||
{
|
||||
"default": "0",
|
||||
"description": "Check this If the value of the field is a default value and not to be fetched from the remote DocType's field",
|
||||
"fieldname": "has_default_value",
|
||||
"fieldtype": "Check",
|
||||
"label": "Has Default Value"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval:doc.has_default_value;",
|
||||
"fieldname": "default_value",
|
||||
"fieldtype": "Data",
|
||||
"label": "Default Value"
|
||||
},
|
||||
{
|
||||
"fieldname": "mapping_type",
|
||||
"fieldtype": "Select",
|
||||
"label": "Mapping Type",
|
||||
"options": "\nChild Table\nDocument"
|
||||
},
|
||||
{
|
||||
"depends_on": "eval:doc.mapping_type;",
|
||||
"fieldname": "mapping",
|
||||
"fieldtype": "Link",
|
||||
"label": "Mapping",
|
||||
"options": "Document Type Mapping"
|
||||
}
|
||||
],
|
||||
"istable": 1,
|
||||
"links": [],
|
||||
"modified": "2020-03-16 13:42:41.104161",
|
||||
"modified": "2020-03-16 14:54:33.546135",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Event Streaming",
|
||||
"name": "Document Type Field Mapping",
|
||||
|
|
|
|||
|
|
@ -9,27 +9,52 @@ from frappe.model.document import Document
|
|||
|
||||
|
||||
class DocumentTypeMapping(Document):
|
||||
def get_mapped_doc(self, update):
|
||||
doc = frappe._dict(json.loads(update))
|
||||
def get_mapped_update(self, doc, producer_site):
|
||||
remote_fields = []
|
||||
# list of tuples (local_fieldname, dependent_doc)
|
||||
dependencies = []
|
||||
|
||||
for mapping in self.field_mapping:
|
||||
if doc.get(mapping.remote_fieldname):
|
||||
if mapping.is_child_table:
|
||||
doc[mapping.local_fieldname] = self.get_mapped_child_table_docs(mapping.child_table_mapping, doc[mapping.remote_fieldname])
|
||||
if mapping.mapping_type == 'Document':
|
||||
dependency = self.get_mapped_dependency(mapping, producer_site, doc.get(mapping.remote_fieldname), mapping.remote_fieldname)
|
||||
dependencies.append((mapping.local_fieldname, dependency))
|
||||
|
||||
if mapping.mapping_type == 'Child Table':
|
||||
doc[mapping.local_fieldname] = self.get_mapped_child_table_docs(mapping.child_table_mapping, doc[mapping.remote_fieldname])
|
||||
else:
|
||||
# copy value into local fieldname key and remove remote fieldname key
|
||||
doc[mapping.local_fieldname] = doc[mapping.remote_fieldname]
|
||||
remote_fields.append(mapping.remote_fieldname)
|
||||
|
||||
elif mapping.has_default_value:
|
||||
if not doc.get(mapping.local_fieldname) and mapping.default_value:
|
||||
doc[mapping.local_fieldname] = mapping.default_value
|
||||
|
||||
#remove the remote fieldnames
|
||||
for field in remote_fields:
|
||||
doc.pop(field, None)
|
||||
|
||||
doc['doctype'] = self.local_doctype
|
||||
return frappe.as_json(doc)
|
||||
|
||||
mapped_update = {'doc': frappe.as_json(doc)}
|
||||
if len(dependencies):
|
||||
mapped_update['dependencies'] = dependencies
|
||||
return mapped_update
|
||||
|
||||
|
||||
def get_mapped_dependency(self, mapping, producer_site, dependent_field_val, dependent_field):
|
||||
inner_mapping = frappe.get_doc('Document Type Mapping', mapping.mapping)
|
||||
filters = {}
|
||||
for pair in inner_mapping.field_mapping:
|
||||
if pair.remote_fieldname == dependent_field:
|
||||
filters[pair.remote_fieldname] = dependent_field_val
|
||||
break
|
||||
|
||||
matching_docs = producer_site.get_doc(inner_mapping.remote_doctype, filters=filters)
|
||||
if len(matching_docs):
|
||||
remote_docname = matching_docs[0].get('name')
|
||||
remote_doc = producer_site.get_doc(inner_mapping.remote_doctype, remote_docname)
|
||||
doc = inner_mapping.get_mapped_update(remote_doc, producer_site).get('doc')
|
||||
return doc
|
||||
|
||||
|
||||
def get_mapped_child_table_docs(child_map, table_entries):
|
||||
|
|
|
|||
|
|
@ -93,6 +93,7 @@ class EventProducer(Document):
|
|||
if self.is_producer_online():
|
||||
producer_site = get_producer_site(self.producer_url)
|
||||
event_consumer = producer_site.get_doc('Event Consumer', get_url())
|
||||
event_consumer = frappe._dict(event_consumer)
|
||||
if event_consumer:
|
||||
config = event_consumer.consumer_doctypes
|
||||
event_consumer.consumer_doctypes = []
|
||||
|
|
@ -172,7 +173,7 @@ def pull_from_node(event_producer):
|
|||
mapping = mapping_config.get(update.ref_doctype)
|
||||
if mapping:
|
||||
update.mapping = mapping
|
||||
update = get_mapped_update(update)
|
||||
update = get_mapped_update(update, producer_site)
|
||||
if not update.update_type == 'Delete':
|
||||
update.data = json.loads(update.data)
|
||||
|
||||
|
|
@ -225,8 +226,13 @@ def set_insert(update, producer_site, event_producer):
|
|||
return
|
||||
doc = frappe.get_doc(update.data)
|
||||
|
||||
if not update.mapping:
|
||||
if update.mapping:
|
||||
dependencies_created = sync_mapped_dependencies(update.dependencies, producer_site)
|
||||
for fieldname, value in iteritems(dependencies_created):
|
||||
doc.update({ fieldname : value })
|
||||
else:
|
||||
sync_dependencies(doc, producer_site)
|
||||
|
||||
if update.use_same_name:
|
||||
doc.insert(set_name=update.docname, set_child_names=False)
|
||||
else:
|
||||
|
|
@ -346,6 +352,7 @@ def sync_dependencies(document, producer_site):
|
|||
child_table = doc.get(df.fieldname)
|
||||
for entry in child_table:
|
||||
child_doc = producer_site.get_doc(entry.doctype, entry.name)
|
||||
child_doc = frappe._dict(child_doc)
|
||||
set_dependencies(child_doc, frappe.get_meta(entry.doctype).get_link_fields(), producer_site)
|
||||
|
||||
def sync_link_dependencies(doc, link_fields, producer_site):
|
||||
|
|
@ -397,6 +404,15 @@ def sync_dependencies(document, producer_site):
|
|||
dependencies[document] = False
|
||||
|
||||
|
||||
def sync_mapped_dependencies(dependencies, producer_site):
|
||||
dependencies_created = {}
|
||||
for entry in dependencies:
|
||||
doc = frappe._dict(json.loads(entry[1]))
|
||||
doc = frappe.get_doc(doc).insert(set_child_names=False)
|
||||
dependencies_created[entry[0]] = doc.name
|
||||
|
||||
return dependencies_created
|
||||
|
||||
def log_event_sync(update, event_producer, sync_status, error=None):
|
||||
"""Log event update received with the sync_status as Synced or Failed"""
|
||||
doc = frappe.new_doc('Event Sync Log')
|
||||
|
|
@ -417,11 +433,15 @@ def log_event_sync(update, event_producer, sync_status, error=None):
|
|||
doc.insert()
|
||||
|
||||
|
||||
def get_mapped_update(update):
|
||||
def get_mapped_update(update, producer_site):
|
||||
"""get the new update document with mapped fields"""
|
||||
mapping = frappe.get_doc('Document Type Mapping', update.mapping)
|
||||
if update.update_type != 'Delete':
|
||||
update.data = mapping.get_mapped_doc(update.data)
|
||||
doc = frappe._dict(json.loads(update.data))
|
||||
mapped_update = mapping.get_mapped_update(doc, producer_site)
|
||||
update.data = mapped_update.get('doc')
|
||||
update.dependencies = mapped_update.get('dependencies', None)
|
||||
|
||||
update.ref_doctype = mapping.local_doctype
|
||||
return update
|
||||
|
||||
|
|
|
|||
|
|
@ -199,8 +199,9 @@ class FrappeClient(object):
|
|||
|
||||
res = self.session.get(self.url + "/api/resource/" + doctype + "/" + name,
|
||||
params=params, verify=self.verify, headers=self.headers)
|
||||
print('==================res', res.text, filters)
|
||||
|
||||
return frappe._dict(self.post_process(res))
|
||||
return self.post_process(res)
|
||||
|
||||
def rename_doc(self, doctype, old_name, new_name):
|
||||
'''Rename remote document
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue