/// <summary> /// Replace this reference with a symbolic reference to another reference. /// <para/> /// This exact reference (not its traversed leaf) is replaced with a symbolic /// reference to the requested name. /// </summary> /// <param name="target"> /// name of the new target for this reference. The new target name /// must be absolute, so it must begin with {@code refs/}. /// </param> /// <returns><see cref="RefUpdateResult.NEW"/> or <see cref="RefUpdateResult.FORCED"/> on success.</returns> public RefUpdateResult link(string target) { if (!target.StartsWith(Constants.R_REFS)) { throw new ArgumentException("Not " + Constants.R_REFS); } if (getRefDatabase().isNameConflicting(Name)) { return(RefUpdateResult.LOCK_FAILURE); } try { if (!tryLock(false)) { return(RefUpdateResult.LOCK_FAILURE); } Ref old = getRefDatabase().getRef(Name); if (old != null && old.isSymbolic()) { Ref dst = old.getTarget(); if (target.Equals(dst.getName())) { return(result = RefUpdateResult.NO_CHANGE); } } if (old != null && old.getObjectId() != null) { OldObjectId = (old.getObjectId()); } Ref dst2 = getRefDatabase().getRef(target); if (dst2 != null && dst2.getObjectId() != null) { NewObjectId = (dst2.getObjectId()); } return(result = doLink(target)); } catch (IOException) { result = RefUpdateResult.IO_FAILURE; throw; } finally { unlock(); } }
public override Ref peel(Ref @ref) { Ref leaf = @ref.getLeaf(); if (leaf.isPeeled() || leaf.getObjectId() == null) { return(@ref); } RevWalk.RevWalk rw = new RevWalk.RevWalk(getRepository()); RevObject obj = rw.parseAny(leaf.getObjectId()); ObjectIdRef newLeaf; if (obj is RevTag) { do { obj = rw.parseAny(((RevTag)obj).getObject()); } while (obj is RevTag); newLeaf = new PeeledTag(leaf.getStorage(), leaf .getName(), leaf.getObjectId(), obj.Copy()); } else { newLeaf = new PeeledNonTag(leaf.getStorage(), leaf .getName(), leaf.getObjectId()); } // Try to remember this peeling in the cache, so we don't have to do // it again in the future, but only if the reference is unchanged. if (leaf.getStorage().IsLoose) { RefList <LooseRef> curList = looseRefs.get(); int idx = curList.find(leaf.getName()); if (0 <= idx && curList.get(idx) == leaf) { LooseRef asPeeled = ((LooseRef)leaf).peel(newLeaf); RefList <LooseRef> newList = curList.set(idx, asPeeled); looseRefs.compareAndSet(curList, newList); } } return(recreate(@ref, newLeaf)); }
public override IDictionary <string, Ref> getRefs(string prefix) { RefList <Ref> packed = getPackedRefs(); RefList <LooseRef> oldLoose = looseRefs.get(); var scan = new LooseScanner(oldLoose, this); scan.scan(prefix); RefList <LooseRef> loose; if (scan.newLoose != null) { loose = scan.newLoose.toRefList(); if (looseRefs.compareAndSet(oldLoose, loose)) { modCnt.incrementAndGet(); } } else { loose = oldLoose; } fireRefsChanged(); RefList <Ref> .Builder <Ref> symbolic = scan.symbolic; for (int idx = 0; idx < symbolic.size();) { Ref @ref = symbolic.get(idx); @ref = resolve(@ref, 0, prefix, loose, packed); if (@ref != null && @ref.getObjectId() != null) { symbolic.set(idx, @ref); idx++; } else { // A broken symbolic reference, we have to drop it from the // collections the client is about to receive. Should be a // rare occurrence so pay a copy penalty. loose = loose.remove(idx); symbolic.remove(idx); } } return(new RefMap(prefix, packed, upcast(loose), symbolic.toRefList())); }
public override string ToString() { var r = new StringBuilder(); r.Append("SymbolicRef["); Ref cur = this; while (cur.isSymbolic()) { r.Append(cur.getName()); r.Append(" -> "); cur = cur.getTarget(); } r.Append(cur.getName()); r.Append('='); r.Append(ObjectId.ToString(cur.getObjectId())); r.Append("]"); return(r.ToString()); }
protected override bool tryLock(bool deref) { Ref dst = Ref; if (deref) { dst = dst.getLeaf(); } string name = dst.getName(); _lock = new LockFile(_database.fileFor(name)); if (_lock.Lock()) { dst = _database.getRef(name); OldObjectId = (dst != null ? dst.getObjectId() : null); return(true); } else { return(false); } }
protected RefUpdate(Ref @ref) { _ref = @ref; oldValue = @ref.getObjectId(); refLogMessage = ""; }
private static RefList <Ref> parsePackedRefs(TextReader br) { var all = new RefList <Ref> .Builder <Ref>(); Ref last = null; bool peeled = false; bool needSort = false; string p; while ((p = br.ReadLine()) != null) { if (p[0] == '#') { if (p.StartsWith(PACKED_REFS_HEADER)) { p = p.Substring(PACKED_REFS_HEADER.Length); peeled = p.Contains(PACKED_REFS_PEELED); } continue; } if (p[0] == '^') { if (last == null) { throw new IOException("Peeled line before ref."); } ObjectId id = ObjectId.FromString(p.Substring(1)); last = new PeeledTag(Storage.Packed, last.getName(), last .getObjectId(), id); all.set(all.size() - 1, last); continue; } int sp = p.IndexOf(' '); ObjectId id2 = ObjectId.FromString(p.Slice(0, sp)); string name = copy(p, sp + 1, p.Length); ObjectIdRef cur; if (peeled) { cur = new PeeledNonTag(Storage.Packed, name, id2); } else { cur = new Unpeeled(Storage.Packed, name, id2); } if (last != null && RefComparator.compareTo(last, cur) > 0) { needSort = true; } all.add(cur); last = cur; } if (needSort) { all.sort(); } return(all.toRefList()); }