mercurial/repoview.py
changeset 35493 3c9c05a38d78
parent 35492 3ad582b2895c
child 35495 07fdac1d5c66
equal deleted inserted replaced
35492:3ad582b2895c 35493:3c9c05a38d78
    63         for p in pfunc(stack.pop()):
    63         for p in pfunc(stack.pop()):
    64             if p != nullrev and p in hidden:
    64             if p != nullrev and p in hidden:
    65                 hidden.remove(p)
    65                 hidden.remove(p)
    66                 stack.append(p)
    66                 stack.append(p)
    67 
    67 
    68 def computehidden(repo):
    68 def computehidden(repo, visibilityexceptions=None):
    69     """compute the set of hidden revision to filter
    69     """compute the set of hidden revision to filter
    70 
    70 
    71     During most operation hidden should be filtered."""
    71     During most operation hidden should be filtered."""
    72     assert not repo.changelog.filteredrevs
    72     assert not repo.changelog.filteredrevs
    73 
    73 
    74     hidden = hideablerevs(repo)
    74     hidden = hideablerevs(repo)
    75     if hidden:
    75     if hidden:
    76         hidden = set(hidden - pinnedrevs(repo))
    76         hidden = set(hidden - pinnedrevs(repo))
       
    77         if visibilityexceptions:
       
    78             hidden -= visibilityexceptions
    77         pfunc = repo.changelog.parentrevs
    79         pfunc = repo.changelog.parentrevs
    78         mutablephases = (phases.draft, phases.secret)
    80         mutablephases = (phases.draft, phases.secret)
    79         mutable = repo._phasecache.getrevset(repo, mutablephases)
    81         mutable = repo._phasecache.getrevset(repo, mutablephases)
    80 
    82 
    81         visible = mutable - hidden
    83         visible = mutable - hidden
    82         _revealancestors(pfunc, hidden, visible)
    84         _revealancestors(pfunc, hidden, visible)
    83     return frozenset(hidden)
    85     return frozenset(hidden)
    84 
    86 
    85 def computeunserved(repo):
    87 def computeunserved(repo, visibilityexceptions=None):
    86     """compute the set of revision that should be filtered when used a server
    88     """compute the set of revision that should be filtered when used a server
    87 
    89 
    88     Secret and hidden changeset should not pretend to be here."""
    90     Secret and hidden changeset should not pretend to be here."""
    89     assert not repo.changelog.filteredrevs
    91     assert not repo.changelog.filteredrevs
    90     # fast path in simple case to avoid impact of non optimised code
    92     # fast path in simple case to avoid impact of non optimised code
    98         secrets = set(r for r in revs if getphase(repo, r) >= secret)
   100         secrets = set(r for r in revs if getphase(repo, r) >= secret)
    99         return frozenset(hiddens | secrets)
   101         return frozenset(hiddens | secrets)
   100     else:
   102     else:
   101         return hiddens
   103         return hiddens
   102 
   104 
   103 def computemutable(repo):
   105 def computemutable(repo, visibilityexceptions=None):
   104     assert not repo.changelog.filteredrevs
   106     assert not repo.changelog.filteredrevs
   105     # fast check to avoid revset call on huge repo
   107     # fast check to avoid revset call on huge repo
   106     if any(repo._phasecache.phaseroots[1:]):
   108     if any(repo._phasecache.phaseroots[1:]):
   107         getphase = repo._phasecache.phase
   109         getphase = repo._phasecache.phase
   108         maymutable = filterrevs(repo, 'base')
   110         maymutable = filterrevs(repo, 'base')
   109         return frozenset(r for r in maymutable if getphase(repo, r))
   111         return frozenset(r for r in maymutable if getphase(repo, r))
   110     return frozenset()
   112     return frozenset()
   111 
   113 
   112 def computeimpactable(repo):
   114 def computeimpactable(repo, visibilityexceptions=None):
   113     """Everything impactable by mutable revision
   115     """Everything impactable by mutable revision
   114 
   116 
   115     The immutable filter still have some chance to get invalidated. This will
   117     The immutable filter still have some chance to get invalidated. This will
   116     happen when:
   118     happen when:
   117 
   119 
   143 filtertable = {'visible': computehidden,
   145 filtertable = {'visible': computehidden,
   144                'served': computeunserved,
   146                'served': computeunserved,
   145                'immutable':  computemutable,
   147                'immutable':  computemutable,
   146                'base':  computeimpactable}
   148                'base':  computeimpactable}
   147 
   149 
   148 def filterrevs(repo, filtername):
   150 def filterrevs(repo, filtername, visibilityexceptions=None):
   149     """returns set of filtered revision for this filter name"""
   151     """returns set of filtered revision for this filter name
       
   152 
       
   153     visibilityexceptions is a set of revs which must are exceptions for
       
   154     hidden-state and must be visible. They are dynamic and hence we should not
       
   155     cache it's result"""
   150     if filtername not in repo.filteredrevcache:
   156     if filtername not in repo.filteredrevcache:
   151         func = filtertable[filtername]
   157         func = filtertable[filtername]
       
   158         if visibilityexceptions:
       
   159             return func(repo.unfiltered, visibilityexceptions)
   152         repo.filteredrevcache[filtername] = func(repo.unfiltered())
   160         repo.filteredrevcache[filtername] = func(repo.unfiltered())
   153     return repo.filteredrevcache[filtername]
   161     return repo.filteredrevcache[filtername]
   154 
   162 
   155 class repoview(object):
   163 class repoview(object):
   156     """Provide a read/write view of a repo through a filtered changelog
   164     """Provide a read/write view of a repo through a filtered changelog
   208         # bypass call to changelog.method
   216         # bypass call to changelog.method
   209         unfiindex = unfichangelog.index
   217         unfiindex = unfichangelog.index
   210         unfilen = len(unfiindex) - 1
   218         unfilen = len(unfiindex) - 1
   211         unfinode = unfiindex[unfilen - 1][7]
   219         unfinode = unfiindex[unfilen - 1][7]
   212 
   220 
   213         revs = filterrevs(unfi, self.filtername)
   221         revs = filterrevs(unfi, self.filtername, self._visibilityexceptions)
   214         cl = self._clcache
   222         cl = self._clcache
   215         newkey = (unfilen, unfinode, hash(revs), unfichangelog._delayed)
   223         newkey = (unfilen, unfinode, hash(revs), unfichangelog._delayed)
   216         # if cl.index is not unfiindex, unfi.changelog would be
   224         # if cl.index is not unfiindex, unfi.changelog would be
   217         # recreated, and our clcache refers to garbage object
   225         # recreated, and our clcache refers to garbage object
   218         if (cl is not None and
   226         if (cl is not None and