Visual Studio에서 개발 1 년을 병합하기위한 전략


32

우리는 2016 년 전체에 걸쳐 새로운 개발을 주요 지점과 분리하여 유지해야한다고 주장하는 고객이 있습니다. 그들은 3-4 명의 다른 팀이 다양한 용량으로 응용 프로그램을 작업하고있었습니다. 의존성 주입 방식 변경, ReSharper로 코드 정리 등 수많은 변경이 이루어졌습니다. 이제 변경 사항을 체인으로 푸시 할 준비를하기 위해 main을 새로운 dev 브랜치에 병합해야했습니다.

초기 병합 풀에서 TFS는 충돌 해결을 통해 ~ 6500 개의 파일을보고했습니다. 이 중 일부는 쉽지만 일부는 훨씬 더 어려울 것입니다 (특히 일부 컨트롤러, API 컨트롤러 및 이러한 컨트롤러를 지원하는 서비스).

내가 더 쉽게 할 수있는 접근법이 있습니까?

명확히하기 위해, 나는이 접근법에 여러 번 많은 관심을 표명했습니다. 고객은 이것의 어려움을 알고있었습니다. 그들은 QA 직원 (4 명의 개발자를위한 1 명의 테스터, 자동화 된 테스트가없고 회귀 테스트가 거의 없음)을 결심하기로 결정했기 때문에, 우리는 이것이 우리의 필요성을 줄이겠다 고 주장하면서 본점의 변화로부터 브랜치를 유지해야한다고 주장했습니다. 테스터는 다른 곳에서 변경 사항을 알고 있습니다.

여기서 가장 큰 문제 중 하나는 각도 버전과 다른 타사 소프트웨어로의 업그레이드입니다. 불행히도 모든 조각이 제자리에 다시 놓일 때 까지이 솔루션을 구축하는 좋은 방법을 찾지 못했습니다.


63
아니. 1 년 동안 활발하게 개발 된 두 개의 별도 지점이 있습니다. 합병이 빨라질 것입니다.
17 개

2
팀이 변경 한 정도는 얼마입니까? 이러한 변경 사항을 식별 한 다음 현재 마스터 코드베이스에 수동으로 다시 적용하는 것이 더 효율적일 수 있습니다.
kdgregory

2
2015 년 또는 2016 년 전체입니까? 2015 년이 2 년이면 두 배가 빨라집니다.
David는 Reinstate Monica

1
고객이 수행하는 작업이 버전 관리 시스템의 별도 분기에있는 경우 고객이 관심을 갖는 이유는 무엇입니까?
Ixrec

17
무엇을 하든지 매시간 청구합니다.
Sean McSomething

답변:


37

이 불행한 상황에 빠지지 않고 새로운 개발을 메인 지점과 분리 한 간단한 방법이 있었을 것입니다. 트렁크의 모든 변경 사항은 매일 dev 지점으로 병합되어야 합니다 . (고객이 너무 근시안적이어서 언젠가 지점이 언젠가 다시 메인 라인으로 다시 돌아올 필요가 있다고 예상 할 수 없었습니까?)

어쨌든 최선의 접근 방법은 IMHO가 직접 수행해야 할 일을 다시 시도하는 것입니다.

  • 브랜치가 생성 된 후 1 일 동안 메인 라인의 변경 사항 의 의미 를 식별합니다 . 가능한 한 현재 코드베이스에 적용하십시오. "로컬 변경"인 경우, 널리 사용되는 클래스의 이름을 바꾸는 것과 같은 "교차 절단 리팩토링"인 경우 단순해야합니다. 현재 코드베이스에 의미 적으로 동일한 방식으로 적용하십시오. 그 해에 코드베이스에서 "귀하의"브랜치에서 모순되는 교차 절단 변경이 없었 으면 좋겠습니다. 그렇지 않으면 이것이 실제 두뇌 티저가 될 수 있습니다.
  • 결과를 테스트하십시오 (이 작업에 적합한 테스트 스위트가 필요하다고 언급 했습니까?) 테스트에서 밝혀진 모든 버그 수정
  • 이제 2 일, 3 일 등의 주요 행 변경 사항에 대해이 프로세스를 반복하십시오.

팀이 고전적인 버전 제어 규칙 ( "컴파일 가능하고 테스트 된 상태 만 커밋"및 "초기 및 자주 체크인")을 엄격하게 준수한 경우이 기능이 작동 할 수 있습니다.

365 번 반복 (또는 250 개, 운이 좋으며 주말 변경을 위해 작업을 묶을 수있는 경우) 한 경우 거의 완료됩니다 (통합 기간 동안 기본 라인에 발생할 변경 수를 추가해야하기 때문에) ). 마지막 단계는 업데이트 된 dev 브랜치를 트렁크에 다시 병합하는 것입니다 (따라서 트렁크 기록을 잃지 않아야합니다). 기술적으로는 영향을받는 파일을 대체하기 만하면되므로 쉬워야합니다.

그리고 네, 진지합니다. 아마도 이것에 대한 지름길이 없을 것입니다. "일일 부분"이 때때로 너무 작을 수도 있지만, 이것을 기대하지는 않을 것입니다. 일일 부분이 너무 큰 것으로 밝혀 질 가능성이 높습니다. 나는 당신의 고객이 이것에 대해 정말로 당신에게 돈을 지불하기를 바랍니다. 그리고 이것은 그에게 너무 비싸서 그의 실패로부터 배울 것입니다.

스위치 측면에서도 시도해 볼 수 있습니다. 브랜치의 변경 사항을 작은 부분에서 메인 라인으로 다시 통합하십시오. 개발자 브랜치에서 트렁크보다 변경 사항이 훨씬 적거나 대부분의 변경 사항이 현재 트렁크의 일부가 아닌 새 소스 파일에서 발생한 경우이 방법이 더 간단 할 수 있습니다. 이를 제품 A (개발 지점)에서 다소 다른 제품 B (트렁크의 현재 상태)로 기능을 "포팅"하는 것으로 볼 수 있습니다. 그러나 크로스 컷팅 리팩토링의 대부분이 메인 라인에서 수행되어 새 코드에 영향을 미치는 경우 (6500 병합 충돌이 이에 대한 증거 인 것처럼 보입니다), 내가 처음 설명 한 방법이 더 쉬울 수 있습니다.


9
재 통합하는 동안 트렁크에서 개발을 계속하는 경우 먼저 트렁크 팁을 분기하여 개발하는 것이 좋습니다. 그렇지 않으면 당신은 효과적으로 과거와 미래를 동시에 병합하고 있습니다. 그러나 나는 자연스럽게 시공간 불연속에 대해 Doc Brown을 연기합니다.
radarbob

1
@ radarbob : OP가 dev에서 트렁크로 통합하는 경우에만 의미가 있지만, 먼저 설명했듯이 트렁크에서 dev로 병합하기로 결정한 경우에는 그렇지 않습니다. OP가 트렁크에서 매일 자신의 개발 지점으로 변경 사항을 전송하면 (과거 365 일 변경으로 시작) 트렁크에서 개발이 진행되는지는 중요하지 않습니다. 그는 현재에 도달 할 때까지이 전술을 계속해야 할 것입니다 (하루에 하루에 3-4 팀의 변경 사항을 통합 및 테스트 할 수 있다고 가정).
Doc Brown

인용구 : "매일 번들의 브랜치에서 메인 라인으로 변경 사항을 다시 통합하여 전환 된 측면 에서도이 작업을 시도 할 수 있다고 덧붙여 야합니다. " 충돌 변화 통합과 함께 "고조파 공명 왜곡"의 캐스케이드를 감지합니다.
radarbob

이것은 좋은 조언입니다. 여기에서 몇 가지 사항을 해결하려면 편집을 참조하십시오.
user258451

1
@ user258451 : 트렁크와 새로운 dev 브랜치에 대해 서로 다른 QA 팀이 서로 대화하고 싶지 않은가? 위대한 스캇 :-((
Doc Brown

14

그 병합 단계에서 자동화 된 병합은 프로세스를 지나치게 복잡하게 만들 수 있다고 말합니다. 나는 1 년 이상 분기 된 지점과 비슷한 문제를 겪었으며 가장 효과적인 방법은 다음을 수행하는 것입니다.

  • 병합되지 않은 원래 상태의 사본을 만듭니다.
  • 병합되지 않은 것과 최신의 차이점
  • 공통 요소를 분류
    • 예를 들어, 모든 기능 이름 변경을 수행 한 다음 매개 변수 변경 등을 수행하십시오.
    • 표준이 변경되면 diff에서 공백을 무시하십시오. 그렇지 않으면 공백을 계산하는 데 많은 시간이 낭비됩니다
  • 핵심 기능에 먼저 집중

결국 컴파일러 경고와 diff는 가장 친한 친구가 될 것입니다. 병합되지 않은 diff를 계속 사용하여 무엇이 달라 졌는지 정확히보고 계속 진행하십시오. 도움을주기 위해 사용할 수있는 다양한 도구가있을 수 있지만, 가장 적합한 도구를 찾는 것은 귀하에게 달려 있습니다.

열쇠는 계속 진행하는 것입니다.

편집하다:

경고의 말로,이 접근 방식은 분기 간 병합 및 병합되지 않은 지점의 기록을 잃어 버림에 따라 버전 제어 기록이 '손상'될 수 있음을 의미합니다.

'Jack Aidley'와 '17 of 26 '의 의견 덕분


1
이 접근 방식의 주요 문제점은 버전 관리 시스템에 남아있는 변경 기록을 파괴한다는 것입니다.
Jack Aidley

본질적으로 병합하는 동안 두 번째로 동일한 변경 사항을 모두 수행하면 변경 사항에 대한 로그가 여전히 남아 있으며 개발 중에 수행 된 순서 대신 병합에서 순서대로 수행됩니다. 이상적이지는 않지만 아무것도 아닌 것보다 낫습니다. 또한 버전 제어 상태로 유지 된 경우 원래 병합되지 않은 상태가됩니다.
Erdrik Ironrose

변경 사항에 대한 로그는 있지만 변경 사항이 지점에서 지점으로 병합되었다는 기록적인 증거는 없습니다. 이것은 TFS에서 엄청나게 큰 일이며, 지점에서 지점으로 병합 할 때 병합되지 않은 변경 세트 만 제공합니다.
17의

@ 17of26 변경 기록을 복원 할 수 있다는 데 동의하지만,이 기록이 완전하지 않거나 정확하지 않을 수 있습니다. 현재 상황이 좋지 않은 상황에서 이러한 기록 손실을 허용 가능한 타협으로 만들려면이 방법이 훨씬 더 쉬울 수 있습니다. 그러나 저는 그들이 결정한 내용에 관계없이 인식하는 것이 중요한 단점이라고 생각합니다.
Jack Aidley

1
@ Jack Aidley 확실히 문제라는 데 동의하므로 내 대답에 약간의 내용을 추가했습니다. 괜찮아요?
Erdrik Ironrose

8

몇 년 전 우리는 지점을 별도로 유지해야하는 동일한 요구 사항을 가진 고객이있었습니다. 그래서 우리는했다.

우리는 그들의 지점을 다시 합병하지 않았습니다. 그들은 고유 한 버전을 가지고있었습니다. 본질적으로 1 개의 주요 트렁크와 지점 대신 2 개의 주요 트렁크가 있었으므로 변경 사항에 대해 추가 비용을 청구했습니다.

우리는 트렁크로 합병을 시도했지만 2 주 후에는 실질적인 혜택없이 몇 시간 동안 불타고 있었기 때문에 그 노력을 포기하기로 결정했습니다.

따라서 다시 병합하지 마십시오. 필요에 따라 해당 클라이언트 브랜치에 병합 중요 수정 사항을 계속 진행하면 해당 클라이언트에 특별히 청구되는 기능이 향상됩니다.


이 전략은 다른 개발 라인이 다른 클라이언트를 대상으로하는 경우에만 실현 가능합니다. 또는 제품과 관련된 사용 사례가 통합되지 않은 방식으로 두 개의 서로 다른 제품 라인을 병렬로 사용할 수있는 경우. 내 이해에 따르면 OP는 새로운 개발 라인이 트렁크를 사용하는 것과 동일한 클라이언트를 대상으로하는 상황을 설명하며 두 제품 라인의 병렬 사용이 그의 경우에 의미가 있는지 확실하지 않습니다.
Doc Brown

1

재미있을 것 같지는 않지만, 얼마나 고통 스러울지는 변화의 본질과 그들이 얼마나 고립되어 있는지에 달려 있습니다.

실제 병합을 수행 하기 전에 리팩토링을 통해 분기를 수렴하려고 시도하는 것이 좋습니다 .

병합 도구는 텍스트 차이 만보고 어떤 식 으로든 코드를 이해하지 못하기 때문에 일종의 바보입니다. 기본 분기가 응용 프로그램 전체에서 사용되는 클래스 이름을 변경하고 기능 분기가 일부 새 코드에서 이전 이름을 사용하는 경우 병합 도구는 클래스 이름도 새 코드에서 변경되어야한다는 것을 이해하지 못합니다. 그러나 분기 B에서 리팩토링을 수행하여 분기 A에서와 같이 클래스 이름을 바꾸면 이전 코드와 새 코드 모두에서 작동하며 병합이 원활하게 진행됩니다.

둘째, 개발 지점의 변경 사항이 현지화되어 있는지 검사해야합니다. 기능 분기의 변경 사항이 일부 영역으로 지역화 된 경우 영향을받지 않는 코드를 수렴 할 필요가없는 경우 기본 분기에서 복사 및 덮어 쓰기 만하면됩니다.

두 가지 모두에서 사소한 변경이 발생한 코드 영역에서는 코드를주의 깊게 검사하고 다시 작성하는 방법을 결정해야합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.