server/msplanner.py
changeset 1230 232e16835fff
parent 1229 dd9bdcfc03b6
child 1231 1457a545af03
equal deleted inserted replaced
1229:dd9bdcfc03b6 1230:232e16835fff
   342                             self.needsplit = True               
   342                             self.needsplit = True               
   343         # add source for rewritten constants to sourcesterms
   343         # add source for rewritten constants to sourcesterms
   344         for vconsts in self.rqlst.stinfo['rewritten'].itervalues():
   344         for vconsts in self.rqlst.stinfo['rewritten'].itervalues():
   345             const = vconsts[0]
   345             const = vconsts[0]
   346             source = self._session.source_from_eid(const.eval(self.plan.args))
   346             source = self._session.source_from_eid(const.eval(self.plan.args))
   347             if source is self._repo.system_source:
   347             if source is repo.system_source:
   348                 for const in vconsts:
   348                 for const in vconsts:
   349                     self._set_source_for_term(source, const)
   349                     self._set_source_for_term(source, const)
   350             elif source in self._sourcesterms:
   350             elif source in self._sourcesterms:
   351                 source_scopes = frozenset(t.scope for t in self._sourcesterms[source])
   351                 source_scopes = frozenset(t.scope for t in self._sourcesterms[source])
   352                 for const in vconsts:
   352                 for const in vconsts:
   353                     if const.scope in source_scopes:
   353                     if const.scope in source_scopes:
   354                         self._set_source_for_term(source, const)
   354                         self._set_source_for_term(source, const)
       
   355                         # if system source is used, add every rewritten constant
       
   356                         # to its supported terms even when associated entity
       
   357                         # doesn't actually comes from it so we get a changes
       
   358                         # that allequals will return True as expected when
       
   359                         # computing needsplit
       
   360                         if repo.system_source in sourcesterms:
       
   361                             self._set_source_for_term(repo.system_source, const)
   355         # add source for relations
   362         # add source for relations
   356         rschema = self._schema.rschema
   363         rschema = self._schema.rschema
   357         termssources = {}
   364         termssources = {}
   358         for rel in self.rqlst.iget_nodes(Relation):
   365         for rel in self.rqlst.iget_nodes(Relation):
   359             # process non final relations only
   366             # process non final relations only
   397                 crossvars = set(x.variable for x in rel.get_nodes(VariableRef))
   404                 crossvars = set(x.variable for x in rel.get_nodes(VariableRef))
   398                 for const in rel.get_nodes(Constant):
   405                 for const in rel.get_nodes(Constant):
   399                     if source.uri != 'system' and not const in self._sourcesterms.get(source, ()):
   406                     if source.uri != 'system' and not const in self._sourcesterms.get(source, ()):
   400                         continue
   407                         continue
   401                     crossvars.add(const)
   408                     crossvars.add(const)
   402                     # XXX this is counter intuitive, though this is currently a
       
   403                     # trick to add const to system source terms so we get a
       
   404                     # chance that solutions will compare to equals when
       
   405                     # computing need split
       
   406                     allsols = set(self._solindices)
       
   407                     try:
       
   408                         self._sourcesterms[ssource][const] = allsols
       
   409                     except KeyError:
       
   410                         self._sourcesterms[ssource] = {const: allsols}
       
   411                 self._crossrelations.setdefault(source, {})[rel] = crossvars
   409                 self._crossrelations.setdefault(source, {})[rel] = crossvars
   412                 if len(crossvars) < 2:
   410                 if len(crossvars) < 2:
   413                     # this means there is a constant in the relation which is
   411                     # this means there is a constant in the relation which is
   414                     # not supported by the source, so we can stop here
   412                     # not supported by the source, so we can stop here
   415                     continue
   413                     continue
   515         norelsup = self._norel_support_set(rel)
   513         norelsup = self._norel_support_set(rel)
   516         termsources = termssources[term]
   514         termsources = termssources[term]
   517         invalid_sources = termsources - (termssources[oterm] | norelsup)
   515         invalid_sources = termsources - (termssources[oterm] | norelsup)
   518         if invalid_sources and self._repo.can_cross_relation(rel.r_type):
   516         if invalid_sources and self._repo.can_cross_relation(rel.r_type):
   519             invalid_sources -= self._sys_source_set
   517             invalid_sources -= self._sys_source_set
   520             if invalid_sources and isinstance(term, Variable) and self._need_ext_source_access(term, rel):
   518             if invalid_sources and isinstance(term, Variable) \
       
   519                    and self._need_ext_source_access(term, rel):
   521                 # if the term is a not invariant variable, we should filter out
   520                 # if the term is a not invariant variable, we should filter out
   522                 # source where the relation is a cross relation from invalid
   521                 # source where the relation is a cross relation from invalid
   523                 # sources
   522                 # sources
   524                 invalid_sources = frozenset([(s, solidx) for s, solidx in invalid_sources
   523                 invalid_sources = frozenset([(s, solidx) for s, solidx in invalid_sources
   525                                              if not (s in self._crossrelations and
   524                                              if not (s in self._crossrelations and
   561                         # multi-sources relation
   560                         # multi-sources relation
   562                         if self._crossrelations:
   561                         if self._crossrelations:
   563                             for reldict in self._crossrelations.itervalues():
   562                             for reldict in self._crossrelations.itervalues():
   564                                 for rel, terms in reldict.iteritems():
   563                                 for rel, terms in reldict.iteritems():
   565                                     for term in terms:
   564                                     for term in terms:
   566                                         if isinstance(term, Variable) and self._need_ext_source_access(term, rel):
   565                                         if isinstance(term, Variable) \
       
   566                                                and self._need_ext_source_access(term, rel):
   567                                             self.needsplit = True
   567                                             self.needsplit = True
   568                                             return
   568                                             return
   569 
   569 
   570     @cached
   570     @cached
   571     def _need_ext_source_access(self, var, rel):
   571     def _need_ext_source_access(self, var, rel):