먼저 새 개발자 가이드 를 읽어보세요.
기본 지침 및 코딩 스타일
다음 내용의 대부분은 오픈 소스 작업이나 상업적 프로그래밍 환경에서 일한 경험이 있는 사람이라면 누구나 알 수 있는 상식입니다. 다음 내용은 주로 메인 개발 브랜치인 i2p.i2p에 적용됩니다. 다른 브랜치, 플러그인 및 외부 앱에 대한 가이드라인은 상당히 다를 수 있으므로 적절한 개발자에게 문의하여 안내를 받으시기 바랍니다.
커뮤니티
- 코드만 작성하지 마세요. 가능하다면 다음을 포함한 다른 개발 활동에도 참여하세요: IRC와 i2pforum.i2p에서의 개발 논의 및 지원; 테스팅; 버그 보고 및 응답; 문서화; 코드 리뷰 등.
- 활동 중인 개발자는 주기적으로 IRC
#i2p-dev에서 접속 가능해야 합니다. 현재 릴리스 주기를 숙지하세요. 기능 동결(feature freeze), 태그 동결(tag freeze), 릴리스를 위한 체크인 마감일과 같은 릴리스 마일스톤을 준수하세요.
릴리스 주기
일반적인 릴리스 주기는 10~16주이며, 연간 4회 릴리스가 이루어집니다. 다음은 일반적인 13주 주기 내의 대략적인 마감일입니다. 각 릴리스의 실제 마감일은 릴리스 관리자가 전체 팀과 협의한 후 설정됩니다.
- 이전 릴리스 후 1-2일: trunk에 체크인이 허용됩니다.
- 이전 릴리스 후 2-3주: 다른 브랜치에서 trunk로 주요 변경 사항을 전파하는 마감일.
- 릴리스 4-5주 전: 새로운 홈페이지 링크 요청 마감일.
- 릴리스 3-4주 전: 기능 동결. 주요 신규 기능 마감일.
- 릴리스 2-3주 전: 새로운 홈페이지 링크 요청이 있는 경우 검토를 위한 프로젝트 회의 개최.
- 릴리스 10-14일 전: 문자열 동결. 번역된(태그된) 문자열의 추가 변경 불가. Transifex에 문자열 푸시, Transifex에서 번역 마감일 공지.
- 릴리스 10-14일 전: 기능 마감일. 이 시점 이후로는 버그 수정만 가능. 더 이상의 기능 추가, 리팩토링 또는 정리 작업 불가.
- 릴리스 3-4일 전: 번역 마감일. Transifex에서 번역을 가져와 체크인.
- 릴리스 3-4일 전: 체크인 마감일. 이 시점 이후 릴리스 빌더의 허가 없이 체크인 불가.
- 릴리스 수 시간 전: 코드 리뷰 마감일.
Git
- 이전에 git을 사용해본 적이 없더라도 분산 소스 관리 시스템에 대한 기본적인 이해가 있어야 합니다. 필요하면 도움을 요청하세요. 일단 push하면 체크인은 영구적입니다. 되돌릴 수 없습니다. 신중하게 진행하세요. git을 사용해본 적이 없다면 작은 단계부터 시작하세요. 작은 변경사항을 체크인하고 어떻게 진행되는지 확인하세요.
- 체크인하기 전에 변경사항을 테스트하세요. 체크인 후 테스트 개발 모델을 선호한다면, 자신의 계정에 있는 개발 브랜치를 사용하고 작업이 완료되면 MR을 생성하세요. 빌드를 망가뜨리지 마세요. 회귀(이전 버전보다 기능이 저하되는 현상)를 일으키지 마세요. 만약 그렇게 되면 (이런 일은 발생합니다), 변경사항을 push한 후 오랫동안 사라지지 마세요.
- 변경사항이 사소하지 않거나 사람들이 테스트하도록 하고 변경사항이 테스트되었는지 알기 위해 좋은 테스트 보고서가 필요한 경우,
history.txt에 체크인 코멘트를 추가하고RouterVersion.java의 빌드 리비전을 증가시키세요. - 릴리스 주기 후반에 main i2p.i2p 브랜치에 주요 변경사항을 체크인하지 마세요. 프로젝트가 며칠 이상 걸릴 것 같으면, 자신의 계정에 git 브랜치를 만들어 거기서 개발하여 릴리스를 막지 않도록 하세요.
- 큰 변경사항(일반적으로 100줄 이상이거나 세 개 이상의 파일을 수정하는 경우)은 자신의 GitLab 계정에 새 브랜치로 체크인하고 MR을 생성하여 검토자를 지정하세요. MR을 자신에게 할당하세요. 검토자가 승인하면 직접 MR을 병합하세요.
- 메인 I2P_Developers 계정에 WIP 브랜치를 생성하지 마세요 (i2p.www 제외). WIP는 자신의 계정에 있어야 합니다. 작업이 완료되면 MR을 생성하세요. 메인 계정의 브랜치는 포인트 릴리스와 같은 진정한 포크(분기)만 있어야 합니다.
- 투명한 방식으로 커뮤니티를 염두에 두고 개발하세요. 자주 체크인하세요. 위의 가이드라인을 고려하여 가능한 한 자주 main 브랜치에 체크인하거나 병합하세요. 자신의 브랜치/계정에서 큰 프로젝트를 진행하고 있다면, 사람들이 따라가며 검토/테스트/코멘트할 수 있도록 알리세요.
코딩 스타일
- 대부분의 코드에서 들여쓰기는 공백 4칸을 사용합니다. 탭을 사용하지 마세요. 코드를 재포맷하지 마세요. IDE나 에디터가 모든 것을 재포맷하려고 한다면, 이를 제어하세요. 일부 위치에서는 코딩 스타일이 다를 수 있습니다. 상식을 사용하세요. 수정하는 파일의 스타일을 모방하세요.
- 모든 새로운 public 및 package-private 클래스와 메서드에는 Javadocs가 필요합니다.
@since릴리스 번호를 추가하세요. 새로운 private 메서드에 대한 Javadocs도 권장됩니다. - 추가된 모든 Javadocs에는 doclint 오류나 경고가 없어야 합니다. Oracle Java 14 이상에서
ant javadoc을 실행하여 확인하세요. 모든 매개변수에는@param라인이 있어야 하고, 모든 non-void 메서드에는@return라인이 있어야 하며, 선언된 모든 예외에는@throws라인이 있어야 하고, HTML 오류가 없어야 합니다. core/(i2p.jar)의 클래스와 i2ptunnel의 일부는 공식 API의 일부입니다. 이 API에 의존하는 여러 out-of-tree 플러그인과 다른 애플리케이션이 있습니다. 호환성을 깨뜨리는 변경을 하지 않도록 주의하세요. 일반적으로 유용한 경우가 아니면 API에 메서드를 추가하지 마세요. API 메서드에 대한 Javadocs는 명확하고 완전해야 합니다. API를 추가하거나 변경하는 경우, 웹사이트의 문서도 업데이트하세요(i2p.www 브랜치).- 적절한 경우 번역용 문자열에 태그를 지정하세요. 이는 모든 UI 문자열에 해당됩니다. 기존 번역이 깨지므로 정말 필요한 경우가 아니면 기존 태그된 문자열을 변경하지 마세요. 릴리스 주기의 태그 동결 이후에는 태그된 문자열을 추가하거나 변경하지 마세요. 그래야 번역자들이 릴리스 전에 업데이트할 기회를 가질 수 있습니다.
- 가능한 경우 제네릭과 동시성 클래스를 사용하세요. I2P는 매우 멀티스레드된 애플리케이션입니다.
- FindBugs/SpotBugs에서 감지하는 일반적인 Java 함정에 익숙해지세요. 자세한 내용은
ant findbugs를 실행하세요. - 릴리스 0.9.47부터 I2P를 빌드하고 실행하려면 Java 8이 필요합니다. 임베디드 하위 시스템에서는 Java 7 또는 8 클래스나 메서드를 사용하지 마세요: addressbook, core, i2ptunnel.jar(non-UI), mstreaming, router, routerconsole(뉴스만), streaming. 이러한 하위 시스템은 Java 6만 필요한 Android 및 임베디드 애플리케이션에서 사용됩니다. 모든 클래스는 Android API 14에서 사용 가능해야 합니다. Java 7 언어 기능은 현재 버전의 Android SDK에서 지원하고 Java 6 호환 코드로 컴파일되는 경우 이러한 하위 시스템에서 허용됩니다.
- Try-with-resources는 런타임에서
java.lang.AutoCloseable을 필요로 하며, 이는 Android API 19(KitKat 4.4)부터 사용 가능하므로 임베디드 하위 시스템에서 사용할 수 없습니다. java.nio.file패키지는 Android API 26(Oreo 8)부터 사용 가능하므로 임베디드 하위 시스템에서 사용할 수 없습니다.- 위의 제한 사항을 제외하고, Java 8 클래스, 메서드 및 구조는 다음 하위 시스템에서만 사용할 수 있습니다: BOB, desktopgui, i2psnark, i2ptunnel.war(UI), jetty-i2p.jar, jsonrpc, routerconsole(뉴스 제외), SAM, susidns, susimail, systray.
- 플러그인 작성자는
plugin.config파일을 통해 최소 Java 버전을 요구할 수 있습니다. - 기본 타입과 클래스 간 변환은 명시적으로 수행하세요. 오토박싱/언박싱에 의존하지 마세요.
URL을 사용하지 마세요.URI를 사용하세요.Exception을 catch하지 마세요.RuntimeException과 체크된 예외를 개별적으로 catch하세요.- UTF-8 charset 인수 없이
String.getBytes()를 사용하지 마세요.DataHelper.getUTF8()또는DataHelper.getASCII()를 사용할 수도 있습니다. - 파일을 읽거나 쓸 때는 항상 UTF-8 charset을 지정하세요.
DataHelper유틸리티가 도움이 될 수 있습니다. String.toLowerCase()또는String.toUpperCase()를 사용할 때는 항상 locale(예:Locale.US)을 지정하세요. locale을 지정할 수 없으므로String.equalsIgnoreCase()를 사용하지 마세요.String.split()을 사용하지 마세요.DataHelper.split()을 사용하세요.- 날짜와 시간을 포맷하는 코드를 추가하지 마세요.
DataHelper.formatDate()와DataHelper.formatTime()을 사용하세요. InputStream과OutputStream이 finally 블록에서 닫히도록 하세요.- 모든
for와while블록에{}를 사용하세요. 한 줄이어도 마찬가지입니다.if,else또는if-else블록 중 하나에{}를 사용하면 모든 블록에 사용하세요.} else {를 한 줄에 배치하세요. - 가능한 모든 곳에서 필드를
final로 지정하세요. I2PAppContext,RouterContext,Log또는 router나 context 항목에 대한 다른 참조를 static 필드에 저장하지 마세요.- 생성자에서 스레드를 시작하지 마세요.
Thread대신I2PAppThread를 사용하세요.
로깅
다음 지침은 라우터, 웹앱 및 모든 플러그인에 적용됩니다.
- 기본 로그 레벨(WARN, INFO, DEBUG)에서 표시되지 않는 메시지의 경우, 메시지가 정적 문자열(연결 없음)이 아닌 한, 불필요한 객체 생성을 피하기 위해 항상 로그 호출 전에
log.shouldWarn(),log.shouldInfo(), 또는log.shouldDebug()를 사용하세요. - 기본 로그 레벨(ERROR, CRIT,
logAlways())에서 표시될 수 있는 로그 메시지는 비기술적 사용자가 이해할 수 있도록 간결하고 명확해야 합니다. 여기에는 함께 표시될 수 있는 예외 원인 텍스트도 포함됩니다. 오류가 발생할 가능성이 높은 경우(예: 폼 제출 오류) 번역을 고려하세요. 그렇지 않으면 번역이 필수는 아니지만, 다른 곳에서 이미 번역 태그가 지정된 문자열을 검색하여 재사용하는 것이 도움이 될 수 있습니다. - 기본 로그 레벨(WARN, INFO, DEBUG)에서 표시되지 않는 로그 메시지는 개발자 사용을 위한 것이며, 위의 요구사항을 따를 필요가 없습니다. 그러나 WARN 메시지는 Android 로그 탭에서 사용 가능하며, 사용자가 문제를 디버깅하는 데 도움이 될 수 있으므로 WARN 메시지 작성 시에도 주의를 기울이세요.
- INFO 및 DEBUG 로그 메시지는 특히 빈번하게 실행되는 코드 경로에서 신중하게 사용해야 합니다. 개발 중에는 유용하지만, 테스트가 완료된 후에는 제거하거나 주석 처리하는 것을 고려하세요.
- stdout 또는 stderr(wrapper 로그)에 로그를 기록하지 마세요.
라이선스
- 본인이 직접 작성한 코드만 체크인하세요. 다른 출처의 코드나 라이브러리 JAR을 체크인하기 전에, 왜 필요한지 정당화하고, 라이선스 호환성을 확인하며, 릴리스 관리자의 승인을 받아야 합니다.
- 외부 코드나 JAR 추가 승인을 받은 경우, Debian 또는 Ubuntu 패키지에서 바이너리를 사용할 수 있다면 외부 패키지를 대신 사용하도록 빌드 및 패키징 옵션을 구현해야 합니다. 수정할 파일 체크리스트:
build.properties,build.xml,debian/control,debian/i2p-router.install,debian/i2p-router.links,debian/rules,sub-build.xml. - 외부 출처의 이미지를 체크인하는 경우, 라이선스 호환성을 먼저 확인하는 것은 귀하의 책임입니다. 체크인 코멘트에 라이선스 및 출처 정보를 포함하세요.
버그
- 이슈 관리는 모두의 일입니다. 도움을 주세요. GitLab 에서 당신이 도울 수 있는 이슈를 모니터링하세요. 가능하다면 이슈에 댓글을 달고, 수정하고, 종료하세요.
- 새로운 개발자는 이슈 수정으로 시작해야 합니다. 수정사항이 있으면 이슈에 패치를 첨부하고
review-needed키워드를 추가하세요. 성공적으로 리뷰되고 변경사항을 체크인하기 전까지는 이슈를 종료하지 마세요. 몇 개의 티켓에 대해 이 과정을 원활하게 완료하면, 위의 일반적인 절차를 따를 수 있습니다. - 문제를 수정했다고 생각되면 이슈를 종료하세요. 티켓을 검증하고 종료할 테스트 부서가 없습니다. 수정했는지 확실하지 않다면, 이슈를 종료하고 “수정했다고 생각합니다. 테스트해보시고 여전히 문제가 있으면 다시 열어주세요"라는 메모를 추가하세요. 개발 빌드 번호나 리비전과 함께 댓글을 추가하고 마일스톤을 다음 릴리스로 설정하세요.