灵活与静态分支(Git 与 Clearcase/Accurev)
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/763099/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Flexible vs static branching (Git vs Clearcase/Accurev)
提问by jbhope
My question is about the way in which Git handles branches: whenever you branch from a commit, this branch won't ever receive changes from the parent branch unless you forceit with a merge.
我的问题是关于 Git 处理分支的方式:每当您从提交分支时,除非您通过合并强制它,否则该分支将永远不会收到来自父分支的更改。
But in other systems such us Clearcase or Accurev, you can specify how branches get filled with some sort of inheritance mechanism: I mean, with Clearcase, using a config_spec, you can say “get all the files modified on branch /main/issue001 and then continue with the ones on /main or with this specific baseline”.
但是在我们 Clearcase 或 Accurev 等其他系统中,您可以指定如何用某种继承机制填充分支:我的意思是,使用 Clearcase,使用 config_spec,您可以说“获取分支 /main/issue001 上修改的所有文件和然后继续使用 /main 或此特定基线上的那些”。
In Accurev you also have a similar mechanism which let's streams receive changes from upper branches (streams how they call them) without merging or creating a new commit on the branch.
在 Accurev 中,您也有一个类似的机制,让我们的流从上层分支接收更改(流如何调用它们),而无需在分支上合并或创建新的提交。
Don't you miss this while using Git? Can you enumerate scenarios where this inheritanceis a must?
你在使用 Git 时不会错过这个吗?你能列举出必须继承的场景吗?
Thanks
谢谢
UpdatePlease read VonC answer below to actually focus my question. Once we agree "linear storage" and DAG based SCMs have different capabilities, my question is: which are the real life scenarios (especially for companies more than OSS) where linear can do things not possible for DAG? Are they worth?
更新请阅读下面的 VonC 答案以真正关注我的问题。一旦我们同意“线性存储”和基于 DAG 的 SCM 具有不同的功能,我的问题是:在哪些现实生活场景中(尤其是对于超过 OSS 的公司),线性可以做 DAG 无法做到的事情?他们值得吗?
采纳答案by VonC
To understand why Git does not offer some kind of what you are referring to as an "inheritance mechanism" (not involving a commit), you must first understand one of the core conceptsof those SCMs (Git vs. ClearCase for instance)
要理解为什么 Git 不提供某种您所说的“继承机制”(不涉及提交),您必须首先了解这些 SCM的核心概念之一(例如 Git 与 ClearCase)
ClearCase uses a linear version storage: each version of an element (file or directory) is linked in a direct linearrelationship with the the previous version of the same element.
Git uses a DAG - Directed Acyclic Graph: each "version" of a file is actually part of a global set of changes in a tree that is itself part of a commit. The previous version of that must be found in a previous commit, accessible through a single directed acyclic graph path.
ClearCase 使用线性版本存储:元素(文件或目录)的每个版本都与同一元素的前一个版本以直接线性关系链接。
Git 使用DAG - 有向无环图:文件的每个“版本”实际上是树中全局更改集的一部分,树本身是提交的一部分。之前的版本必须在之前的提交中找到,可通过单个有向无环图路径访问。
In a linear system, a config spec can specify several rules for achieving the "inheritance" you see (for a given file, first select a certain version, and if not present, then select another version, and if not present, then select a third, and so on).
在线性系统中,配置规范可以指定几个规则来实现您看到的“继承”(对于给定的文件,首先选择某个版本,如果不存在,则选择另一个版本,如果不存在,则选择一个第三,依此类推)。
The branch is a forkin a linearhistory a given version for a given select rule (all the other select rules before that one still apply, hence the "inheritance" effect)
该分支是一个叉的线性历史给定的选择规则的特定版本(所有其他选择规则一个仍然适用之前,因而有“继承”效果)
In a DAG, a commit represents all the "inheritance" you will ever get; there is no "cumulative" selection of versions. There is only one path in this graph to select all the files you will see at this exact point (commit).
A branch is just a new path in this graph.
在 DAG 中,提交代表您将获得的所有“继承”;没有“累积”的版本选择。此图中只有一个路径可以选择您将在此确切点(提交)看到的所有文件。
分支只是此图中的一条新路径。
To apply, in Git, some other versions, you must either:
要在 Git 中应用其他一些版本,您必须:
- merge into your branch some other commit (like in the git pull" mentioned by stsquad's answer) or
- rebase your branch (as Greg mentions)
- 将其他一些提交合并到您的分支中(例如在stsquad 的回答中提到的 git pull 中)或
- 重新设置你的分支(正如Greg 提到的)
But since Git is a DAG-based SCM, it will always result in a new commit.
但是由于 Git 是基于 DAG 的 SCM,因此它总是会导致新的提交。
What you are "losing" with Git is some kind of "composition" (when you are selecting different versions with different successive select rules), but that would not be practical in a DVCS (as in "Distributed"): when you are making a branch with Git, you need to do so with a starting point and a contentclearly defined and easily replicated to other repositories.
您在 Git 中“丢失”的是某种“组合”(当您选择具有不同连续选择规则的不同版本时),但这在DVCS 中并不实用(如“分布式”):当您用 Git 创建一个分支,你需要有一个起点和一个明确定义的内容,并且很容易复制到其他存储库。
In a purely central VCS, you can define your workspace (in ClearCase, your "view", either snapshot or dynamic) with whatever rules you want.
在纯粹的中央 VCS 中,您可以使用您想要的任何规则定义您的工作区(在 ClearCase 中,您的“视图”,快照或动态)。
unknown-googleadds in the comment (and in his question above):
未知谷歌在评论中添加(以及在他上面的问题中):
So, once we see the two models can achieve different things (linear vs DAG), my question is: which are the real life scenarios (especially for companies more than OSS) where linear can do things not possible for DAG? Are they worth it?
所以,一旦我们看到这两种模型可以实现不同的东西(线性 vs DAG),我的问题是:哪些是现实生活场景(尤其是对于超过 OSS 的公司),其中线性可以做 DAG 无法实现的事情?他们值得吗?
When it comes to "real-life scenario" in term of selection rules, what you can do in a linear model is to have severalselection rules for the same set of files.
当谈到选择规则方面的“现实场景”时,您可以在线性模型中做的是为同一组文件设置多个选择规则。
Consider this "config spec" (i.e. "configuration specification" for selection rules with ClearCase):
考虑这个“配置规范”(即 ClearCase 选择规则的“配置规范”):
element /aPath/... aLabel3 -mkbranch myNewBranch
element /aPath/... aLabel2 -mkbranch myNewBranch
It selects all the files labelled 'aLabel2
' (and branch from there), except for those labelled 'aLabel3
' - and branch from there - (because that rule precedes the one mentioning 'aLabel2
').
它选择所有标记为 ' aLabel2
'(并从那里分支)的文件,除了标记为 ' aLabel3
' 的文件 - 并从那里分支 - (因为该规则在提到 ' aLabel2
' 的那个之前)。
Is it worth it?
这值得么?
No.
不。
Actually, the UCM flavor of ClearCase (the "Unified Configuration Management" methodology included with the ClearCase product, and representing all the "best practices" deduced from base ClearCase usage) does not allow it, for reasons of simplificity. A set of files is called a "component", and if you want to branch for a given label (known as a "baseline"), that would be translated like this following config spec:
实际上,出于简单的原因,ClearCase 的 UCM 风格(ClearCase 产品中包含的“统一配置管理”方法,代表从基本 ClearCase 使用中推导出的所有“最佳实践”)不允许这样做。一组文件称为“组件”,如果您想针对给定标签(称为“基线”)进行分支,则将按照以下配置规范进行转换:
element /aPath/... .../myNewBranch
element /aPath/... aLabel3 -mkbranch myNewBranch
element /aPath/... /main/0 -mkbranch myNewBranch
You have to pick onestarting point (here, 'aLabel3
') and go from there.
If you want also the files from 'aLabel2
', you will make a merge from all the 'aLabel2
' files to the ones in 'myNewBranch'.
您必须选择一个起点(此处为“ aLabel3
”)并从那里开始。如果您还想要来自“ aLabel2
”的文件,您将从所有“ aLabel2
”文件合并到“myNewBranch”中的文件。
That is a "simplification" you do not have to make with a DAG, where each node of the graph represents a uniquely defined "starting point" for a branch, whatever is the set of files involved.
这是您不必使用 DAG 进行的“简化”,其中图形的每个节点都代表一个唯一定义的分支“起点”,无论涉及的文件集是什么。
Merge and rebase are enough to combine that starting point with other versions of a given set of files, in order to achieve the desired "composition", while keeping that particular history in isolationin a branch.
合并和变基足以将该起点与给定文件集的其他版本相结合,以实现所需的“组合”,同时将特定历史记录隔离在一个分支中。
The general goal is to reason in "coherentVersion Control operations applied to a coherentcomponent". A "coherent" set of files is one in a well-defined coherent state:
一般目标是在“应用于一致组件的一致版本控制操作”中进行推理。一组“连贯”的文件是一个定义明确的连贯状态:
- if labelled, allits files are labelled
- if branched, allits files will branch from the same uniquestarting point
- 如果标记,则其所有文件都被标记
- 如果分支,它的所有文件都将从相同的唯一起点分支
That is easily done in a DAG system; it can be more difficult in a linear system (especially with "Base ClearCase" where the "config spec" can be tricky), but it is enforced with the UCM methodology of that same linear-based tool.
这在 DAG 系统中很容易做到;在线性系统中可能会更困难(尤其是“Base ClearCase”,其中“配置规范”可能很棘手),但它是通过同一个基于线性的工具的 UCM 方法强制执行的。
Instead of achieving that "composition" through a "private selection rule trick" (with ClearCase, some select rule order), you achieve it only with VCS operations (rebase or merge), which leave a clear trace for everyone to follow (as opposed to a config spec private to a developer, or shared amongst some but not all developers). Again, it enforces a senses of coherency, as opposed to a "dynamic flexibility", that you may have a hard time to reproduce later on.
而不是通过“私人选择规则技巧”(使用 ClearCase,一些选择规则顺序)来实现“组合”,您只能通过 VCS 操作(rebase 或合并)来实现它,这会为每个人留下清晰的跟踪(相反)到开发人员私有的配置规范,或在一些但不是所有开发人员之间共享)。再一次,它加强了连贯性,而不是“动态灵活性”,您以后可能很难重现这种感觉。
That allows you to leave the realm of VCS (Version Control System)and enter the realm of SCM (Software Configuration Management), which is mainly concerned with "reproducibility". And that (SCM features) can be achieved with a linear-based or a DAG-based VCS.
这让你离开了VCS(版本控制系统)的领域,进入了SCM(软件配置管理)的领域,这个领域主要关注“再现性”。而这(SCM 功能)可以通过基于线性或基于 DAG 的 VCS 来实现。
回答by Greg Hewgill
It sounds like what you're looking for might be git rebase
. Rebasing a branch conceptually detaches it from its original branch point and reattaches it at some other point. (In reality, the rebase is implemented by applying each patch of the branch in sequence to the new branch point, creating a new set of patches.) In your example, you can rebase a branch to the current tip of an upper branch, which will essentially "inherit" all the changes made to the other branch.
听起来您正在寻找的可能是git rebase
。重新定义分支在概念上将其与原始分支点分离,并在其他点重新连接。(实际上,rebase 是通过将分支的每个补丁依次应用到新分支点,创建一组新补丁来实现的。)在您的示例中,您可以将一个分支 rebase 到上分支的当前尖端,即将基本上“继承”对另一个分支所做的所有更改。
回答by stsquad
I'm not totally clear on what your asking for but it sounds like git's tracking semantics are what you want. When you branch from am origin you can do something like:
我不完全清楚您的要求,但听起来 git 的跟踪语义就是您想要的。当您从 am origin 分支时,您可以执行以下操作:
git -t -b my_branch origin/master
git -t -b my_branch origin/master
And then future "git pull"s will auto merge origin/master into your working branch. You can then use "git cherry -v origin/master" to see what the difference is. You can use "git rebase" before you publish your changes to clean up the history, but you shouldn't use rebase once your history is public (i.e. other people are following that branch).
然后未来的“git pull”将自动将 origin/master 合并到您的工作分支中。然后你可以使用“git cherry -v origin/master”来看看有什么区别。您可以在发布更改之前使用“git rebase”来清理历史记录,但是一旦您的历史记录公开(即其他人正在关注该分支),您就不应该使用 rebase。
回答by Martin Ba
As to the inheritance scheme used by accurev: GIT users will probably "get" the whole thing when the look at git-flow(see also: http://github.com/nvie/gitflowand http://jeffkreeftmeijer.com/2010/why-arent-you-using-git-flow/)
至于 accurev 使用的继承方案:GIT 用户在查看git-flow时可能会“得到”整个事情(另见:http: //github.com/nvie/gitflow和http://jeffkreeftmeijer.com/ 2010/为什么你不使用-git-flow/)
This GIT branching model more or less does (manually / with the help of the git-flow tool) what accurev does out-of-the-box automatically and with greatGUI support.
这个 GIT 分支模型或多或少地(手动/在 git-flow 工具的帮助下)完成了 accurev 自动开箱即用的功能,并具有强大的GUI 支持。
So it appearsGIT can do what accurev does. Since I never actually used git/git-flow day-to-day I can't really say how it works out but it does look promising. (Minus proper GUI support :-)
所以看起来GIT 可以做 accurev 所做的。因为我从来没有真正每天使用 git/git-flow 我不能说它是如何工作的,但它看起来很有希望。(减去适当的 GUI 支持 :-)
回答by FedeN
I'll try to answer you question. (I have to say here that I have not used GIT only read about it, so if something that I mention below is wrong, please correct me)
我会尽力回答你的问题。(我不得不在这里说,我没有使用过 GIT 只是阅读了它,所以如果我在下面提到的东西是错误的,请纠正我)
"Can you enumerate scenarios where this inheritance is a must?"
“你能列举出必须继承的场景吗?”
I won't say it is a must, because you can solve a problem with the tool you have, and might be a valid solution for your environment. I guess it is more a matter of the processes than the tool itself. Making sure your process is coherent and also allows you to go back in time to reproduce any intermediate step/state is the goal, and the plus is that the tool let you run you your process and SCMP as painless as possible
我不会说这是必须的,因为您可以使用您拥有的工具解决问题,并且可能是您环境的有效解决方案。我想这更多是过程的问题,而不是工具本身。确保您的流程连贯一致,并允许您及时返回以重现任何中间步骤/状态是目标,而且该工具可让您尽可能轻松地运行您的流程和 SCMP
The one scenario I can see it is handy to have this 'inheritance'behavior and use the power of the config spec, is when you want your set of changes "isolated" mapped to a task (devtask, CR, SR, or whatever defines the purpose/scope of your change set)
我可以看到的一个场景是,拥有这种“继承”行为并使用配置规范的强大功能是很方便的,即当您希望将更改集“隔离”映射到任务(devtask、CR、SR 或任何定义的更改集的目的/范围)
Using this composition allows you to have your development branch clean and still use different combination (using composition) of the rest of the code, and still have only what is relevant for the taskisolated in a branch during the wholelife cycle of the task, just until the integration phase.
使用这种组合可以让您的开发分支保持干净,并且仍然使用其余代码的不同组合(使用组合),并且在任务的整个生命周期中仍然只有与分支中隔离的任务相关的内容,直到集成阶段。
Being purist having to commit/merge/rebase just to have a "defined starting point" , I guess it would 'pollute' your branch and you will end up with your changes + others changes in your branch/change set.
作为纯粹主义者必须提交/合并/重新定位只是为了有一个“定义的起点”,我想它会“污染”你的分支,你最终会在你的分支/更改集中进行你的更改+其他更改。
When/Where this isolation is useful? The points bellow might only make sense on the context of companies pursuing CMM and some ISO certifications, and might be of no interest for other kind of companies or OSS
这种隔离何时/何地有用?以下几点可能仅对追求 CMM 和某些 ISO 认证的公司有意义,而其他类型的公司或 OSS 可能不感兴趣
Being really picky, you might want to accurately count the lines of code (added/modified/deleted) of the change set corresponding to a single developer, later used as one input for code and effort estimations.
It can be easier to review the code at different stages, having just your code in a single branch (not glued with other changes)
非常挑剔,您可能希望准确计算与单个开发人员对应的变更集的代码行数(添加/修改/删除),稍后用作代码和工作量估算的一个输入。
在不同阶段查看代码会更容易,只需将您的代码放在一个分支中(不与其他更改粘在一起)
On big projects with several teams and +500 developers actively working concurrently on the same base code, (where graphical individual element version trees looks like a messy tangled web with several loadlines, one for each big customer, or one for each technology ) large config specs using composition of several degrees in depth made this amount of people work seamlessly to adapt the same product/system (base code) to different purposes. Using this config spec, dynamically gave each team or sub team, a different view to what they need and from where they need to branch of, (cascading on several cases) without the need of creating intermediate integration branches, or constantly merging and rebasing all the bits that you need to start with. Code from the same task/purpose was branching of different labels but made sense. (You can argue here the 'known baseline' as a principle of the SCM but simple labels contemplated in a written SCM Plan did the work) It must be possible to solve this with GIT (I guess in a non dynamic way) but I find really hard to picture without this 'inheritance' behavior. I guess the point mentioned by VonC "if branched, all its files will branch from the same unique starting point" was broken here, but beside it was well documented on the SCMP, I remember there were strong business reason to do it that way.
在有多个团队和 500 多名开发人员积极同时处理相同基本代码的大型项目中,(其中图形化的单个元素版本树看起来像一个杂乱无章的网络,有多个负载线,每个大客户一个,或每个技术一个)大型配置使用多个深度组合的规范使如此多的人无缝地工作,以使相同的产品/系统(基本代码)适应不同的目的。使用此配置规范,动态地为每个团队或子团队提供不同的视图,了解他们需要什么以及从哪里分支,(在几个案例中级联),而无需创建中间集成分支,或不断合并和重新建立所有分支你需要开始的位。来自同一任务/目的的代码是不同标签的分支,但有意义。(您可以在这里争论“已知基线”作为 SCM 的原则,但书面 SCM 计划中考虑的简单标签完成了工作)必须可以用 GIT 解决这个问题(我猜是非动态方式),但我发现如果没有这种“继承”行为,真的很难想象。我想 VonC 提到的“如果分支,它的所有文件将从同一个独特的起点分支”在这里被打破了,但除了它在 SCMP 上有很好的记录之外,我记得有很强的商业理由这样做。
Yes building these config specs that I mentioned above was not free, in the beginning there where 4-5 well paid people behind the SCM but were later reduced by automated scripts that asked you what you want on terms of labels/branches/features and will write the CS for you.
是的,构建我上面提到的这些配置规范并不是免费的,一开始有 4-5 名高薪人员在 SCM 后面,但后来被自动脚本减少了,这些脚本会询问您在标签/分支/功能方面想要什么,并且会为你写CS。
The reproducibility here was achieved by just saving the Config Spec along with the task in the devTask system, so each task upstream mapped to requirements, and downstream mapped to a config spec, an a set of changes (code files, design documents, test documents etc)
这里的再现性是通过将 Config Spec 与任务一起保存在 devTask 系统中来实现的,因此每个任务上游映射到需求,下游映射到配置规范,一组更改(代码文件、设计文档、测试文档)等等)
So up to here one conclusion here might be, only if your project is big/complicated enough (and you can afford SC Managers along the life of the project:) ) then you only will start thinking if you need the 'inheritance' behavior or really versatile tool, otherwise you will go directly to a a tool that is free and already take care of the coherence of you SCM ... but there could be other factors on the SCM tool that might make you stick to one or to another ...read on..
所以到目前为止,这里的一个结论可能是,只有当您的项目足够大/足够复杂(并且您可以在项目的整个生命周期内负担得起 SC 经理:))然后您才会开始考虑是否需要“继承”行为或真正多功能的工具,否则您将直接使用免费的工具,并且已经处理了 SCM 的连贯性……但是 SCM 工具上可能还有其他因素可能会让您坚持使用一个或另一个 .. .继续阅读...
Some side notes, that might be out of topic, but I guess in some cases like mine need to be considered.
一些旁注,这可能与主题无关,但我想在某些情况下,像我这样的情况需要考虑。
I have to add here that we use the "good-ol CC" not UCM. Totally agree with VonC on the a good methodology allows to "guide" the flexibility towards a more coherent configuration. The good thing is that CC is pretty flexible and you can find (not without some effort) a good way to have thing coherent while in other SCM you might have it for free. But for example here (and other places that I've worked with CC) for C/C++ projects we cannot afford the price of not having the winkinfeature (reusing the Derive objects), that reduce several X times compiling time. It can be argued that having a better design , a more decoupled code, and optimizing Makefiles can reduce the need to compile the whole thing, but there are cases that you need to compile the whole beast many times a day, and sharing the DO saves heaps of time/money. Where I'm now we try to use as much free tool as we can, and I think we will get rid of CC if we can find a cheaper or free tool that implements the winkinfeature.
我必须在这里补充一点,我们使用“good-ol CC”而不是 UCM。完全同意 VonC 的一个好的方法论可以“引导”灵活性以实现更连贯的配置。好消息是 CC 非常灵活,您可以找到(并非不费吹灰之力)一种使事情连贯一致的好方法,而在其他 SCM 中,您可能会免费获得它。但是例如在这里(以及我与 CC 合作过的其他地方)对于 C/C++ 项目,我们无法承受没有眨眼的代价功能(重用 Derive 对象),减少了 X 倍的编译时间。可以说有更好的设计,更解耦的代码,优化 Makefiles 可以减少编译整个东西的需要,但有些情况你需要一天编译很多次,共享 DO 节省大量的时间/金钱。在我现在的情况下,我们尝试使用尽可能多的免费工具,如果我们能找到实现winkin功能的更便宜或免费的工具,我认为我们将摆脱 CC 。
I'll finish with something that Paul mention , different tools are better that other for different purposesbut I will add that you can get away from some limitation of the tool by having a coherent process and without scarifying reproducibility, key points off the SCM In the end I guess the answer to it is worth?depends on your "problem", the SDLC you are running, your SCM processes, and if there is any extra feature (like winkin) that might be useful in your environment.
我将用 Paul 提到的东西结束,不同的工具对于不同的目的更好,但我会补充说,你可以通过有一个连贯的过程和不破坏可重复性,SCM 的关键点来摆脱工具的一些限制我猜这个答案到底值不值?取决于您的“问题”、您正在运行的 SDLC、您的 SCM 进程,以及是否有任何可能在您的环境中有用的额外功能(如 winkin)。
my 2 cents
我的 2 美分
回答by Martin
Have you noticed that you can checkout specfific file versions with GIT too?
你有没有注意到你也可以用 GIT 检出特定的文件版本?
Just use this:
只需使用这个:
git checkout [< tree-ish >] [--] < paths >
Like per config spec any existing version of a file (paths) can be loaded into the worktree. Quote from git-checkout docs:
像每个配置规范一样,文件(路径)的任何现有版本都可以加载到工作树中。引用 git-checkout 文档:
The following sequence checks out the master branch, reverts the Makefile to two revisions back, deletes hello.c
by mistake, and gets it back from the index:
以下序列检查主分支,将 Makefile 恢复为两个修订版本,hello.c
错误删除,然后从索引中取回:
$ git checkout master
$ git checkout master~2 Makefile
$ rm -f hello.c
$ git checkout hello.c
回答by enigment
Theory aside, here's a kind of obvious practical take on this, from my perspective using AccuRev in a commercial production environment for a number of years: The inheritance model works very well as long as child streams haven't diverged too much from ancestors that are still in development. It breaks down when the inheriting streams are too different.
撇开理论不谈,从我多年来在商业生产环境中使用 AccuRev 的角度来看,这里有一种明显的实践意义:只要子流与祖先流没有太大分歧,继承模型就可以很好地工作。仍在开发中。当继承的流太不同时,它就会崩溃。
Inheritance (later versions as children of earlier ones) allows changes in ancestor streams to be active in child streams without anyone doing anything (unless a merge is required, in which case it shows up as deep overlap, which is good to be able to see).
继承(后来的版本作为早期版本的子代)允许祖先流中的更改在子流中处于活动状态,而无需任何人做任何事情(除非需要合并,在这种情况下它显示为深度重叠,这是很好的能够看到)。
That sounds great, and in practice it is, when all streams involved are relatively similar. We use that model for hotfix and service pack level streams below a given production release. (It's a actually a bit more complicated than that for us, but that's the general idea.)
这听起来很棒,实际上,当所有涉及的流都相对相似时。我们将该模型用于给定生产版本以下的修补程序和服务包级别流。(这对我们来说实际上比这复杂一点,但这是总体思路。)
Production releases are in parallel, no inheritance, with those hotfix and service pack children below each of them. Starting a new release means creating a new release-level stream, and manually pushing everything from the most recent maintenance stream for the prior release into it. After that, changes to earlier releases that apply to later ones have to be manually pushed into each of them, requiring more work, but allowing much greater control.
生产版本是并行的,没有继承,在每个版本下面都有那些修补程序和服务包子项。开始一个新版本意味着创建一个新的版本级别流,并手动将所有内容从先前版本的最新维护流推送到其中。之后,对适用于较晚版本的早期版本的更改必须手动推送到每个版本中,这需要更多的工作,但允许更大的控制。
We originally used the inheritance model across all releases, where later ones were children of earlier ones. That worked well for a while, but got unmanageable over time. Major architectural differences across releases made unavoidably inheriting changes a Bad Idea. Yes, you can put a snapshot in between to block inheritance, but then all changes have to be pushed manually, and the only real difference between parent-snapshot-child and parallel non-inheriting streams is that the entire graphical stream view continually pushes down and to the right, which is a PITA.
我们最初在所有版本中使用继承模型,其中较晚的版本是较早版本的子代。这在一段时间内运作良好,但随着时间的推移变得难以管理。版本之间的主要架构差异使得不可避免地继承更改成为一个坏主意。是的,您可以在两者之间放置一个快照来阻止继承,但是所有更改都必须手动推送,父快照子流和并行非继承流之间唯一真正的区别是整个图形流视图不断向下推右边是 PITA。
One really nice thing about AccuRev is that you have this choice, all the time. It's not a inherent constraint of your SCM program's architecture.
AccuRev 的一个真正好处是您可以随时选择。这不是 SCM 程序架构的固有约束。
回答by Darren Yeats
ClearCase, without MultiSite, is a single repository but Git is distributed. ClearCase commits at the file level but Git commits at the repository level. (This last difference means the original question is based on a misunderstanding, as pointed out in the other posts here.)
ClearCase,没有 MultiSite,是一个单一的存储库,但 Git 是分布式的。ClearCase 在文件级别提交,而 Git 在存储库级别提交。(最后一个差异意味着原始问题是基于误解,正如此处的其他帖子所指出的那样。)
If these are the differences we're talking about then I think 'linear' versus 'DAG' is a confusing way to distinguish these SCM systems. In ClearCase all the versions for a file are referred to as the file's version "tree" but really it is a directed acyclic graph! The real difference to Git is that ClearCase's DAGs exist per file. So I think it is misleading to refer to ClearCase as non-DAG and Git as DAG.
如果这些是我们正在谈论的差异,那么我认为“线性”与“DAG”是区分这些 SCM 系统的一种令人困惑的方式。在 ClearCase 中,文件的所有版本都被称为文件的版本“树”,但实际上它是一个有向无环图!与 Git 的真正区别在于每个文件都存在 ClearCase 的 DAG。所以我认为将 ClearCase 称为非 DAG,将 Git 称为 DAG 是一种误导。
(BTW ClearCase versions its directories in a similar way to its files - but that's another story.)
(顺便说一句,ClearCase 以与其文件类似的方式对其目录进行版本化 - 但那是另一回事。)
回答by Paul
I'm not sure if you are asking anything, but you are demonstrating that Accurev streams are different tools than Git (or SVN) branches. (I don't know Clearcase.)
我不确定您是否在问什么,但是您正在证明 Accurev 流是与 Git(或 SVN)分支不同的工具。(我不知道 Clearcase。)
For example, with Accurev you are forced, as you say, to use certain workflows, which gives you an auditable history of changes that is not supported in Git. Accurev's inheritance makes certain workflows more efficient and others impossible.
例如,使用 Accurev,您将被迫使用某些工作流,这为您提供了 Git 不支持的可审计更改历史记录。Accurev 的继承使某些工作流程更高效,而其他工作流程则不可能。
With Git you can have exploratory coding segregated in local repos or in feature branches, which would not be supported very well by Accurev.
使用 Git,您可以将探索性编码隔离在本地存储库或功能分支中,而 Accurev 不会很好地支持这些。
Different tools are good for different purposes; it's useful to ask what each one is good for.
不同的工具有不同的用途;询问每个人的好处是有用的。