1 module hunt.entity.EntityFieldManyToManyOwner;
2 
3 import hunt.Exceptions;
4 import hunt.entity;
5 import hunt.logging;
6 
7 import std.format;
8 import std.variant;
9 
10 
11 class EntityFieldManyToManyOwner(T : Object, F : Object = T,string MAPPEDBY = "") : EntityFieldInfo {
12     
13     private ManyToMany _mode;
14     private string _primaryKey;
15     private string _findString;
16     private T[][string] _decodeCache;
17     private EntityManager _em;
18 
19     this(EntityManager manager, string fieldName, string primaryKey, string tableName, ManyToMany mode, F owner, bool isMainMapped ) {
20         // logDebug("ManyToManyOwner(%s,%s) not main mapped ( %s , %s , %s , %s ,%s )".format(T.stringof,F.stringof,fieldName,primaryKey,tableName,mode,isMainMapped));
21         _em = manager;
22         super(fieldName, "", tableName);
23         _isMainMapped = isMainMapped;
24         init(primaryKey, mode, owner);
25     }
26 
27     this(EntityManager manager, string fieldName, string primaryKey, string tableName, ManyToMany mode, F owner, 
28             bool isMainMapped ,JoinTable joinTable , JoinColumn jc  ,InverseJoinColumn ijc ) {
29         // logDebug("ManyToManyOwner(%s,%s) main mapped( %s , %s , %s , %s ,%s , %s , %s , %s )".format(T.stringof,F.stringof,fieldName,primaryKey,tableName,mode,isMainMapped,joinTable,jc,ijc));
30         _em = manager;
31         super(fieldName, "", tableName);
32         _isMainMapped = isMainMapped;
33         _joinColumn = jc.name;
34         _inverseJoinColumn = ijc.name;
35         _joinTable = joinTable.name;
36         init(primaryKey, mode, owner);
37     }
38 
39     private void init(string primaryKey,  ManyToMany mode, F owner) {
40         _mode = mode;       
41         _enableJoin = _mode.fetch == FetchType.EAGER;    
42         _primaryKey = primaryKey;
43         static if(MAPPEDBY != "")
44         {
45             if(!_isMainMapped )
46             {
47                 _inverseJoinColumn =  hunt.entity.utils.Common.getInverseJoinColumn!(T,MAPPEDBY).name;
48                 _joinColumn =   hunt.entity.utils.Common.getJoinColumn!(T,MAPPEDBY).name;
49                 _joinTable =   _em.getPrefix() ~ hunt.entity.utils.Common.getJoinTableName!(T,MAPPEDBY);
50             }
51         }
52         
53         // logDebug("----(%s , %s ,%s )".format(_joinColumn,_inverseJoinColumn,_joinTable));
54         
55         initJoinData();
56     }
57 
58     private void initJoinData() {
59         _joinSqlData = new JoinSqlBuild(); 
60         _joinSqlData.tableName = _joinTable;
61         if(_isMainMapped)
62             _joinSqlData.joinWhere = getTableName() ~ "." ~ _primaryKey ~ " = " ~ _joinTable ~ "." ~ _joinColumn;
63         else
64             _joinSqlData.joinWhere = getTableName() ~ "." ~ _primaryKey ~ " = " ~ _joinTable ~ "." ~ _inverseJoinColumn;
65         _joinSqlData.joinType = JoinType.LEFT;
66         // foreach(value; _entityInfo.getFields()) {
67         //     _joinSqlData.columnNames ~= value.getSelectColumn();
68         // }
69         // logDebug("many to many owner join sql : %s ".format(_joinSqlData));
70     }
71 
72     override public string getSelectColumn() {
73         return "";
74     }
75 
76 
77 
78     public string getPrimaryKey() {return _primaryKey;}
79     public ManyToMany getMode() {return _mode;}
80     
81     FetchType fetchType() {
82         return _mode.fetch;
83     }
84 
85 
86     public T[] deSerialize(Row[] rows, int startIndex, bool isFromManyToOne) {
87         T[] ret;
88         if (_mode.fetch == FetchType.LAZY)
89             return ret;
90         return ret;
91     }
92 
93 
94     public void setMode(ManyToMany mode) {
95         _mode = mode;
96         _enableJoin = _mode.fetch == FetchType.EAGER;    
97     }
98 
99     override bool isAggregateType() {
100         return false;
101     }
102     
103     LazyData getLazyData(Row row) {
104         version(HUNT_DEBUG) logDebug("--- MappedBy: %s , row: %s ".format(_mode.mappedBy, row));
105 
106         string name = EntityExpression.getColumnAsName(_primaryKey, getTableName());
107         Variant v = row.getValue(name);
108         if(!v.hasValue()) {
109             version(HUNT_DEBUG) warningf("Can't find value for %s", name);
110             return null;
111         }
112         
113         string value = v.toString();
114         version(HUNT_ENTITY_DEBUG) tracef("A column: %s=%s", name, value);
115         LazyData ret = new LazyData(_mode.mappedBy, value);   
116         return ret;     
117     }
118 
119 }
120 
121