Skip to content

Commit

Permalink
fix #66
Browse files Browse the repository at this point in the history
  • Loading branch information
laowantong committed Dec 12, 2022
1 parent 71c51d3 commit e2ce435
Show file tree
Hide file tree
Showing 19 changed files with 3,774 additions and 4,758 deletions.
3,829 changes: 1,791 additions & 2,038 deletions doc/fr_refman.html

Large diffs are not rendered by default.

4,028 changes: 1,720 additions & 2,308 deletions doc/fr_refman.ipynb

Large diffs are not rendered by default.

4 changes: 4 additions & 0 deletions mocodo/entity.py
Expand Up @@ -4,6 +4,10 @@
class Entity:
def __init__(self, clause):
(name, attribute_labels) = clause.split(":", 1)
self.is_deletable = True
if name.startswith("+"):
self.is_deletable = False
name = name[1:]
self.name = name.strip().replace("\\", "")
self.attribute_labels = outer_split(attribute_labels)
self.name_view = self.name[:-1] if self.name[-1].isdigit() else self.name # get rid of single digit suffix, if any
Expand Down
47 changes: 35 additions & 12 deletions mocodo/relations.py
@@ -1,5 +1,6 @@
import collections
import os
import pprint
import re

from .file_helpers import write_contents
Expand Down Expand Up @@ -63,6 +64,7 @@ def may_update_params_with_guessed_title():
self.process_associations()
self.process_inheritances()
self.delete_inheritance_parent_or_children_to_delete()
self.delete_deletable_relations()
self.make_primary_keys_first()
self.may_disambiguate_with_leg_notes = set_disambiguation_strategy(params["disambiguation"])
may_update_params_with_guessed_title()
Expand Down Expand Up @@ -101,7 +103,9 @@ def set_defaults(template):
},
"column_separator": ", ",
"compose_relation": "{this_relation_name} ({columns})",
"transform_single_column_relation": [],
"deleted_relation_separator": "",
"compose_deleted_relation": "",
"compose_deleted_relations": "",
"transform_forced_relation": [],
"transform_relation": [],
"relation_separator": "\n",
Expand Down Expand Up @@ -135,6 +139,14 @@ def set_defaults(template):
result.setdefault("compose_strengthening_primary_key", result["compose_primary_foreign_key"])
result.setdefault("compose_unsourced_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_unsourced_primary_foreign_key", result["compose_primary_key"])
result.setdefault("compose_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_primary_naturalized_foreign_key", result["compose_primary_key"])
result.setdefault("compose_deleted_child_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_deleted_parent_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_demoted_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_stopped_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_unsourced_naturalized_foreign_key", result["compose_normal_attribute"])
result.setdefault("compose_unsourced_primary_naturalized_foreign_key", result["compose_primary_key"])
return result
template = set_defaults(template)

Expand Down Expand Up @@ -193,8 +205,6 @@ def make_labels_from_raw_labels():
data["sorted_columns"] = template["column_separator"].join(sorted(fields, key=lambda field: extract_sorting_key(field, "column_sorting_key")))
data["columns"] = template["column_separator"].join(fields)
line = template["compose_relation"].format(**data)
if len(relation["columns"]) == 1:
line = transform(line, "transform_single_column_relation")
if relation["is_forced"]:
line = transform(line, "transform_forced_relation")
line = transform(line, "transform_relation")
Expand Down Expand Up @@ -225,6 +235,16 @@ def make_labels_from_raw_labels():
lines.pop()
data["relations"] = template["relation_separator"].join(lines)
data["sorted_relations"] = template["relation_separator"].join(sorted(lines, key=lambda line: extract_sorting_key(line, "relation_sorting_key")))

if self.deleted_relations:
lines = []
for deleted_relation in self.deleted_relations:
lines.append(template["compose_deleted_relation"].format(this_relation_name=deleted_relation))
deleted_relation_lines = template["deleted_relation_separator"].join(lines)
data["deleted_relations"] = template["compose_deleted_relations"].format(deleted_relation_lines=deleted_relation_lines)
else:
data["deleted_relations"] = ""

data["relations"] = template["compose_relational_schema"].format(**data)
result = transform(data["relations"], "transform_relational_schema")
return result
Expand Down Expand Up @@ -260,6 +280,7 @@ def relations_from_entities(self):
self.relations[name] = {
"this_relation_name": entity.name,
"is_forced": False,
"is_deletable": entity.is_deletable,
"columns": []
}
for attribute in entity.attributes:
Expand Down Expand Up @@ -568,17 +589,19 @@ def delete_inheritance_parent_or_children_to_delete(self):
for entity_to_delete in self.inheritance_parent_or_children_to_delete:
del self.relations[entity_to_delete]



def delete_deletable_relations(self):
deleted_outer_sources = set()
for (name, relation) in list(self.relations.items()):
if relation.get("is_deletable") and all(column["nature"] == "primary_key" for column in relation["columns"]):
del self.relations[name]
deleted_outer_sources.add(name)
for relation in self.relations.values():
for column in relation["columns"]:
if column["outer_source"] in deleted_outer_sources:
column["nature"] = column["nature"].replace("foreign", "naturalized_foreign")
self.deleted_relations = sorted(deleted_outer_sources)

def make_primary_keys_first(self):
for relation in self.relations.values():
relation["columns"].sort(key=lambda column: not column["primary"])



if __name__=="__main__":
import sys
sys.path.append("/Users/aristide/Dropbox/Sites/mocodo_online/mocodo")
from .mocodo import main
main()
28 changes: 2 additions & 26 deletions mocodo/resources/relation_templates/diagram.json
Expand Up @@ -2,16 +2,10 @@
"extension": ".mld",
"highlight": "plain",
"compose_primary_key": "_{label}",
"compose_foreign_key": "#{label}-><MAY_BE_SUPPRESSED>{outer_source}</MAY_BE_SUPPRESSED>->{raw_label}",
"compose_foreign_key": "#{label}->{outer_source}->{raw_label}",
"compose_outer_attribute": "{label}",
"compose_primary_foreign_key": "_#{label}-><MAY_BE_SUPPRESSED>{outer_source}</MAY_BE_SUPPRESSED>->{raw_label}",
"compose_primary_foreign_key": "_#{label}->{outer_source}->{raw_label}",
"compose_relation": "{this_relation_name}: {columns}",
"transform_single_column_relation": [
{
"search": "(?s)(.+:) .+",
"replace": "\\1</TO_SUPPRESS>"
}
],
"transform_relation": [
{
"comment": "By default, the first attribute is an identifier",
Expand All @@ -21,24 +15,6 @@
],
"compose_relational_schema": "%%mocodo\n{relations}",
"transform_relational_schema": [
{
"search": "(?sm)#([^,\n]+)-><MAY_BE_SUPPRESSED>(.+?)</MAY_BE_SUPPRESSED>->.+?(?=[,\n])(.+?^\\2:</TO_SUPPRESS>)",
"replace": "\\1\\3",
"iterated": true
},
{
"search": "(?sm)(^(.+?):</TO_SUPPRESS>.+?)#([^,\n]+)-><MAY_BE_SUPPRESSED>\\2</MAY_BE_SUPPRESSED>->(.+?)(?=[,\n])",
"replace": "\\1\\3",
"iterated": true
},
{
"search": "(?m)^.+?</TO_SUPPRESS>\n?",
"replace": ""
},
{
"search": "</?MAY_BE_SUPPRESSED>",
"replace": ""
},
{
"search": "(?m)^:\n(?=:)",
"replace": ":"
Expand Down
6 changes: 0 additions & 6 deletions mocodo/resources/relation_templates/html.json
Expand Up @@ -35,11 +35,5 @@
"compose_primary_foreign_key": "<span class='foreign primary'>#{label}</span>",
"column_separator": ",\n ",
"compose_relation": "<div>\n <span class='relation'>{this_relation_name}</span> (\n {columns}\n )\n</div>",
"transform_single_column_relation": [
{
"search": "(?s)(.+)",
"replace": "<!--\n\\1\n-->"
}
],
"compose_relational_schema": "<html>\n<head>\n<meta charset='utf-8'>\n<style>\n #mld .relation {{ font-variant: small-caps; font-weight: bold }}\n #mld .primary {{ text-decoration: underline }}\n #mld .foreign {{ font-style: oblique }}\n #mld .normal {{ }}\n</style>\n</head>\n<body>\n<div id='mld'>\n{relations}\n</div>\n</body>\n</html>"
}
36 changes: 29 additions & 7 deletions mocodo/resources/relation_templates/html_verbose.json
Expand Up @@ -55,14 +55,18 @@
"compose_strengthening_primary_key": "<span title='strengthening_primary_key ({outer_source})' class='foreign primary'>#{label}</span><item>Le champ <i>{label}</i> fait partie de la clé primaire de la table<primary></primary>. Il a migré à partir de l'entité <i>{outer_source}</i> pour renforcer l'identifiant.</item>",
"compose_unsourced_foreign_key": "<span title='unsourced_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré par l'association de dépendance fonctionnelle <i>{association_name}</i> à partir de l'entité <i>{adjacent_source}</i> (supprimée). <b>Attention</b> : aucune contrainte d'intégrité référentielle n'est plus assurée.</item>",
"compose_unsourced_primary_foreign_key": "<span title='unsourced_primary_foreign_key ({outer_source})' class='primary'>{label}</span><item>Le champ <i>{label}</i> fait partie de la clé primaire de la table<primary></primary>. Il a migré par l'association de dépendance fonctionnelle <i>{association_name}</i> à partir de l'entité <i>{adjacent_source}</i> (supprimée). <b>Attention</b> : aucune contrainte d'intégrité référentielle n'est plus assurée.</item>",
"compose_deleted_child_naturalized_foreign_key": "<span title='deleted_child_naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré à travers l'entité-fille <i>{adjacent_source}</i> (supprimée) dans laquelle il avait déjà migré à partir de l'entité <i>{outer_source}</i> (également supprimée).</item>",
"compose_deleted_parent_naturalized_foreign_key": "<span title='deleted_parent_naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré à travers l'entité-mère <i>{adjacent_source}</i> (supprimée), et réfère maintenant directement à l'entité <i>{outer_source}</i>.</item>",
"compose_demoted_naturalized_foreign_key": "<span title='demoted_naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> est un simple attribut. Sa table d'origine, <i>{outer_source}</i>, ayant été supprimée, il n'est pas considéré comme clé étrangère. Il devrait normalement faire partie de l'identifiant de <i>{this_relation_name}</i>, mais a été rétrogradé explicitement au rang de simple attribut.</item>",
"compose_naturalized_foreign_key": "<span title='naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré par l'association de dépendance fonctionnelle <i>{association_name}</i> à partir de l'entité <i>{outer_source}</i> en perdant son caractère identifiant. De plus, comme la table créée à partir de cette entité a été supprimée, il n'est pas considéré comme clé étrangère.</item>",
"compose_primary_naturalized_foreign_key": "<span title='primary_naturalized_foreign_key ({outer_source})' class='primary'>{label}</span><item>Le champ <i>{label}</i> fait partie de la clé primaire de la table<primary></primary>. Sa table d'origine (<i>{outer_source}</i>) ayant été supprimée, il n'est pas considéré comme clé étrangère.</item>",
"compose_stopped_naturalized_foreign_key": "<span title='stopped_naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré directement de l'entité <i>{outer_source}</i> en perdant son caractère identifiant. La table correspondante ayant été supprimée, il n'est pas considéré comme clé étrangère.</item>",
"compose_unsourced_naturalized_foreign_key": "<span title='unsourced_naturalized_foreign_key ({outer_source})' class='normal'>{label}</span><item>Le champ <i>{label}</i> a migré par l'association de dépendance fonctionnelle <i>{association_name}</i> à partir de l'entité <i>{adjacent_source}</i> (supprimée). <b>Attention</b> : aucune contrainte d'intégrité référentielle n'est plus assurée.</item>",
"compose_unsourced_primary_naturalized_foreign_key": "<span title='unsourced_primary_naturalized_foreign_key ({outer_source})' class='primary'>{label}</span><item>Le champ <i>{label}</i> fait partie de la clé primaire de la table<primary></primary>. Il a migré par l'association de dépendance fonctionnelle <i>{association_name}</i> à partir de l'entité <i>{adjacent_source}</i> (supprimée). <b>Attention</b> : aucune contrainte d'intégrité référentielle n'est plus assurée.</item>",
"column_separator": ",\n ",
"compose_relation": "<div>\n <details><summary><span class='relation'>{this_relation_name}</span> (\n {columns}\n )</summary>\n</div>",
"transform_single_column_relation": [
{
"search": "(?s)(.+)$",
"replace": "\\1\n <li><strong>Avertissement.</strong> Cette table ne comportant qu'un seul champ, on peut envisager de la supprimer.</li>"
}
],
"compose_deleted_relation": "La table <i>{this_relation_name}</i> a été supprimée car elle était réduite à la clé primaire de son entité d'origine. Pour empêcher cette supression, préfixez d'un « + » le nom de l'entité.",
"compose_deleted_relations": "<br><hr><br><div><span><strong>NB.</strong> {deleted_relation_lines}</span></div>",
"transform_forced_relation": [
{
"search": "(?s)(.+)$",
Expand Down Expand Up @@ -93,6 +97,15 @@
"search": " <li>Le champ (.+), (.+?) est une clé étrangère\\. Il a (migré à partir de l'entité .+? par l'association de dépendance fonctionnelle .+? en perdant) son (caractère identifiant.)",
"replace": " <li>Les champs \\1 et \\2 sont des clés étrangères. Ils ont \\3 leur \\4"
},
{
"search": "( <li>Le champ )(.+?)( fait partie de la clé primaire de la table<primary></primary>. Sa table d'origine .+?)\n\\1(.+?)\\3",
"replace": "\\1\\2, \\4\\3",
"iterated": true
},
{
"search": " <li>Le champ (.+), (.+?) fait partie de la clé primaire de la table<primary></primary>. Sa table d'origine (.+?) ayant été supprimée, il n'est pas considéré comme clé étrangère.",
"replace": " <li>Les champs \\1 et \\2 font partie de la clé primaire de la table<primary></primary>. Leur table d'origine \\3 ayant été supprimée, ils ne sont pas considérés comme clés étrangères."
},
{
"search": "( <li>Le champ )(.+?)( fait partie de la clé primaire de la table<primary></primary>.+?)\n\\1(.+?)\\3",
"replace": "\\1\\2, \\4\\3",
Expand Down Expand Up @@ -140,8 +153,17 @@
"replace": "\n"
}
],
"compose_relational_schema": "<html>\n<head>\n<meta charset='utf-8'>\n<style>\n #mld .relation {{ font-variant: small-caps; font-weight: bold }}\n #mld .primary {{ text-decoration: underline }}\n #mld .foreign {{ font-style: oblique }}\n #mld .normal {{ }}\n #mld strong {{ font-weight: bold }}\n #mld i {{ font-style: italic }}\n #mld ul {{ list-style-type:square; margin: 0 0 1em 2em }}\n</style>\n</head>\n<body>\n<div id='mld'>\n{relations}\n</div>\n</body>\n</html>",
"compose_relational_schema": "<html>\n<head>\n<meta charset='utf-8'>\n<style>\n #mld .relation {{ font-variant: small-caps; font-weight: bold }}\n #mld .primary {{ text-decoration: underline }}\n #mld .foreign {{ font-style: oblique }}\n #mld .normal {{ }}\n #mld strong {{ font-weight: bold }}\n #mld i {{ font-style: italic }}\n #mld ul {{ list-style-type:square; margin: 0 0 1em 2em }}\n</style>\n</head>\n<body>\n<div id='mld'>\n{relations}{deleted_relations}\n</div>\n</body>\n</html>",
"transform_relational_schema": [
{
"search": "(La table )(.+?)( a été supprimée .+)\\1(.+?)\\3",
"replace": "\\1\\2, \\4\\3",
"iterated": true
},
{
"search": "La table (.+), (.+?) a été supprimée .+",
"replace": "Les tables \\1 et \\2 ont été supprimées car elles étaient réduites à la clé primaire de leur entité d'origine. Pour empêcher cette supression, préfixez d'un « + » le nom de l'entité."
},
{
"search": "\\s+$",
"replace": ""
Expand Down
5 changes: 4 additions & 1 deletion mocodo/resources/relation_templates/json.json
Expand Up @@ -8,7 +8,10 @@
"column_separator": ",\n ",
"compose_relation": "{{\n \"this_relation_name\": \"{this_relation_name}\",\n \"this_relation_name_lowercase\": \"{this_relation_name_lowercase}\",\n \"this_relation_name_uppercase\": \"{this_relation_name_uppercase}\",\n \"this_relation_name_titlecase\": \"{this_relation_name_titlecase}\",\n \"is_forced\": \"{is_forced}\",\n \"columns\": [\n {columns}\n ]\n }}",
"relation_separator": ",\n ",
"compose_relational_schema": "{{\n \"title\": \"{title}\",\n \"title_lowercase\": \"{title_lowercase}\",\n \"title_uppercase\": \"{title_uppercase}\",\n \"title_titlecase\": \"{title_titlecase}\",\n \"relations\": [\n {relations}\n ]\n}}",
"compose_deleted_relation": "\"{this_relation_name}\"",
"deleted_relation_separator": ", ",
"compose_deleted_relations": ",\n \"deleted_relations\": [{deleted_relation_lines}]",
"compose_relational_schema": "{{\n \"title\": \"{title}\",\n \"title_lowercase\": \"{title_lowercase}\",\n \"title_uppercase\": \"{title_uppercase}\",\n \"title_titlecase\": \"{title_titlecase}\"{deleted_relations},\n \"relations\": [\n {relations}\n ]\n}}",
"transform_relational_schema": [
{
"search": "MOCODO_REPLACE_True",
Expand Down
6 changes: 0 additions & 6 deletions mocodo/resources/relation_templates/latex.json
Expand Up @@ -26,11 +26,5 @@
"compose_foreign_key": "\\foreign{{{label}}}",
"compose_primary_foreign_key": "\\foreign{{\\prim{{{label}}}}}",
"compose_relation": " {this_relation_name_titlecase} & ({columns})\\\\",
"transform_single_column_relation": [
{
"search": " (.+)",
"replace": "% \\1"
}
],
"compose_relational_schema": "% Copy this before \\begin{{document}}\n\n\\usepackage[normalem]{{ulem}}\n\\newenvironment{{mld}}\n {{\\par\\begin{{minipage}}{{\\linewidth}}\\begin{{tabular}}{{rp{{0.7\\linewidth}}}}}}\n {{\\end{{tabular}}\\end{{minipage}}\\par}}\n\\newcommand{{\\relat}}[1]{{\\textsc{{#1}}}}\n\\newcommand{{\\attr}}[1]{{\\emph{{#1}}}}\n\\newcommand{{\\prim}}[1]{{\\uline{{#1}}}}\n\\newcommand{{\\foreign}}[1]{{\\#\\textsl{{#1}}}}\n\n% Copy that after \\begin{{document}}\n\n\\begin{{mld}}\n{relations}\n\\end{{mld}}"
}
6 changes: 0 additions & 6 deletions mocodo/resources/relation_templates/markdown.json
Expand Up @@ -5,12 +5,6 @@
"compose_foreign_key": "_#{label}_",
"compose_primary_foreign_key": "<ins>_#{label}_</ins>",
"compose_relation": "**{this_relation_name}** ({columns})",
"transform_single_column_relation": [
{
"search": "(?s)(.+)",
"replace": "<!--\n\\1<br>\n-->"
}
],
"relation_separator": "<br>\n",
"transform_relational_schema": [
{
Expand Down

0 comments on commit e2ce435

Please sign in to comment.