Apa praktik terbaik saat ini untuk penomoran bangun sistematis dan manajemen nomor versi dalam proyek Java? Secara khusus:
Bagaimana mengelola angka membangun secara sistematis dalam lingkungan pengembangan terdistribusi
Cara mempertahankan nomor versi dalam sumber / tersedia untuk aplikasi runtime
Cara mengintegrasikan dengan benar dengan repositori sumber
Cara mengelola nomor versi secara lebih otomatis vs. tag repositori
Bagaimana mengintegrasikan dengan infrastruktur pembangunan berkelanjutan
Ada cukup banyak alat yang tersedia, dan semut (sistem build yang kami gunakan) memiliki tugas yang akan mempertahankan nomor build, tetapi tidak jelas bagaimana mengelola ini dengan beberapa, pengembang bersamaan menggunakan CVS, svn, atau serupa .
[EDIT]
Beberapa jawaban parsial atau spesifik yang baik dan bermanfaat telah muncul di bawah, jadi saya akan meringkas beberapa di antaranya. Bagi saya, sepertinya tidak ada "praktik terbaik" yang kuat dalam hal ini, melainkan kumpulan ide yang tumpang tindih. Di bawah, temukan rangkuman saya dan beberapa pertanyaan yang mungkin orang coba jawab sebagai tindak lanjut. [Baru di stackoverflow ... berikan komentar jika saya melakukan ini salah.]
Jika Anda menggunakan SVN, versi checkout tertentu datang untuk perjalanan. Penomoran build dapat mengeksploitasi ini untuk membuat nomor build unik yang mengidentifikasi checkout / revisi tertentu. [CVS, yang kami gunakan untuk alasan warisan, tidak cukup memberikan tingkat wawasan ini ... intervensi manual dengan tag membuat Anda berpisah di sana.]
Jika Anda menggunakan maven sebagai sistem build Anda, ada dukungan untuk menghasilkan nomor versi dari SCM, serta modul rilis untuk secara otomatis menghasilkan rilis. [Kita tidak bisa menggunakan pakar, karena berbagai alasan, tetapi ini membantu mereka yang bisa. [Terima kasih kepada marcelo-morales ]]
Jika Anda menggunakan semut sebagai sistem build Anda, deskripsi tugas berikut ini dapat membantu menghasilkan file Java .properties yang mengambil informasi build, yang kemudian dapat dilipat ke build Anda dalam sejumlah cara. [Kami memperluas gagasan ini untuk memasukkan informasi yang diturunkan dari hudson, terima kasih marty-lamb ].
Semut dan pakar (dan hudson serta kontrol jelajah) menyediakan cara mudah untuk mendapatkan nomor build ke file .properties, atau ke file .txt / .html. Apakah ini "aman" cukup agar tidak dirusak dengan sengaja atau tidak sengaja? Apakah lebih baik mengkompilasinya menjadi kelas "versi" pada waktu pembuatan?
Pernyataan: Nomor penomoran harus didefinisikan / diberlakukan dalam sistem integrasi berkelanjutan seperti hudson . [Terima kasih kepada marcelo-morales ] Kami telah mengambil saran ini, tetapi itu membuka pertanyaan rekayasa rilis: Bagaimana rilis bisa terjadi? Apakah ada beberapa buildnumber dalam rilis? Apakah ada hubungan yang bermakna antara buildnumber dengan rilis yang berbeda?
Pertanyaan: Apa tujuan di balik angka membangun? Apakah ini digunakan untuk QA? Bagaimana? Apakah ini digunakan terutama oleh pengembang untuk disambiguasi antara beberapa build selama pengembangan, atau lebih untuk QA untuk menentukan build apa yang didapatkan pengguna akhir? Jika tujuannya adalah reproduktifitas, secara teori inilah yang harus disediakan oleh nomor versi rilis - mengapa tidak? (tolong jawab ini sebagai bagian dari jawaban Anda di bawah, ini akan membantu menerangi pilihan yang telah Anda buat / sarankan ...)
Pertanyaan: Apakah ada tempat untuk membuat angka dalam pembuatan manual? Apakah ini sangat bermasalah sehingga SEMUA ORANG harus menggunakan solusi CI?
Pertanyaan: Haruskah nomor gedung diperiksa di SCM? Jika tujuannya secara andal dan tidak ambigu mengidentifikasi bangunan tertentu, bagaimana cara mengatasi berbagai sistem pembangunan berkelanjutan atau manual yang mungkin macet / restart / dll ...
Pertanyaan: Haruskah nomor build pendek dan manis (mis., Bilangan bulat meningkat secara monoton) sehingga mudah untuk memasukkan nama file untuk arsip, mudah untuk merujuk dalam komunikasi, dll ... atau harus panjang dan penuh dengan nama pengguna, stempel data, nama mesin, dll?
Pertanyaan: Harap berikan perincian tentang bagaimana penugasan nomor build sesuai dengan proses rilis otomatis Anda yang lebih besar. Ya, pecinta maven, kita tahu ini dilakukan dan dilakukan, tetapi tidak semua dari kita sudah minum kool-bantuan ...
Saya benar-benar ingin menyempurnakan ini menjadi jawaban yang lengkap, setidaknya untuk contoh nyata dari pengaturan cvs / semut / hudson kami, sehingga seseorang dapat membangun strategi lengkap berdasarkan pertanyaan ini. Saya akan menandai sebagai "The Answer" siapa pun yang dapat memberikan deskripsi sup-ke-kacang untuk kasus khusus ini (termasuk skema penandaan cvs, item konfigurasi CI yang relevan, dan prosedur pelepasan yang melipat nomor build ke dalam rilis sedemikian rupa sehingga secara terprogram dapat diakses.) Jika Anda ingin bertanya / menjawab untuk konfigurasi tertentu lainnya (misalnya, svn / maven / cruise control) saya akan menautkan ke pertanyaan dari sini. --JA
[EDIT 23 Okt 09] Saya menerima jawaban terpilih karena saya pikir itu solusi yang masuk akal, sementara beberapa jawaban lain juga termasuk ide bagus. Jika seseorang ingin mengambil celah dalam mensintesis beberapa dari ini dengan marty-lamb 's, saya akan mempertimbangkan untuk menerima yang berbeda. Satu-satunya masalah yang saya miliki dengan marty-lamb's adalah tidak menghasilkan nomor build bersambung yang andal - tergantung pada jam lokal di sistem builder untuk memberikan angka build yang jelas, yang tidak bagus.
[Edit 10 Jul]
Kami sekarang menyertakan kelas seperti di bawah ini. Ini memungkinkan nomor versi untuk dikompilasi ke dalam executable akhir. Berbagai bentuk info versi dipancarkan dalam data logging, produk-produk keluaran jangka panjang yang diarsipkan, dan digunakan untuk melacak analisis produk-produk keluaran kami (terkadang bertahun-tahun kemudian) ke bangunan tertentu.
public final class AppVersion
{
// SVN should fill this out with the latest tag when it's checked out.
private static final String APP_SVNURL_RAW =
"$HeadURL: svn+ssh://user@host/svnroot/app/trunk/src/AppVersion.java $";
private static final String APP_SVN_REVISION_RAW = "$Revision: 325 $";
private static final Pattern SVNBRANCH_PAT =
Pattern.compile("(branches|trunk|releases)\\/([\\w\\.\\-]+)\\/.*");
private static final String APP_SVNTAIL =
APP_SVNURL_RAW.replaceFirst(".*\\/svnroot\\/app\\/", "");
private static final String APP_BRANCHTAG;
private static final String APP_BRANCHTAG_NAME;
private static final String APP_SVNREVISION =
APP_SVN_REVISION_RAW.replaceAll("\\$Revision:\\s*","").replaceAll("\\s*\\$", "");
static {
Matcher m = SVNBRANCH_PAT.matcher(APP_SVNTAIL);
if (!m.matches()) {
APP_BRANCHTAG = "[Broken SVN Info]";
APP_BRANCHTAG_NAME = "[Broken SVN Info]";
} else {
APP_BRANCHTAG = m.group(1);
if (APP_BRANCHTAG.equals("trunk")) {
// this isn't necessary in this SO example, but it
// is since we don't call it trunk in the real case
APP_BRANCHTAG_NAME = "trunk";
} else {
APP_BRANCHTAG_NAME = m.group(2);
}
}
}
public static String tagOrBranchName()
{ return APP_BRANCHTAG_NAME; }
/** Answers a formatter String descriptor for the app version.
* @return version string */
public static String longStringVersion()
{ return "app "+tagOrBranchName()+" ("+
tagOrBranchName()+", svn revision="+svnRevision()+")"; }
public static String shortStringVersion()
{ return tagOrBranchName(); }
public static String svnVersion()
{ return APP_SVNURL_RAW; }
public static String svnRevision()
{ return APP_SVNREVISION; }
public static String svnBranchId()
{ return APP_BRANCHTAG + "/" + APP_BRANCHTAG_NAME; }
public static final String banner()
{
StringBuilder sb = new StringBuilder();
sb.append("\n----------------------------------------------------------------");
sb.append("\nApplication -- ");
sb.append(longStringVersion());
sb.append("\n----------------------------------------------------------------\n");
return sb.toString();
}
}
Tinggalkan komentar jika ini layak menjadi diskusi wiki.
sumber
gradle
dan / ataugit
?Jawaban:
Untuk beberapa proyek saya, saya menangkap nomor revisi subversi, waktu, pengguna yang menjalankan build, dan beberapa informasi sistem, memasukkannya ke file .properties yang dimasukkan ke dalam toples aplikasi, dan membaca toples itu pada saat runtime.
Kode semutnya terlihat seperti ini:
Sangat mudah untuk memperluas ini untuk memasukkan informasi apa pun yang mungkin ingin Anda tambahkan.
sumber
Build.xml Anda
Kode java Anda
sumber
META-INF/maven/<project group>/<project id>/pom.properties
. File .properties akan berisi properti versi.sumber
Perangkat lunak:
Hudson memiliki tiga bangunan / pekerjaan: Continuous, Nightly and Release.
Untuk build Continuous / Nightly: Build number adalah revisi SVN, ditemukan menggunakan svntask.
Untuk pekerjaan / rilis Release: Build number adalah nomor Release, dibaca oleh Ant, dari file Properties. File properti juga dapat didistribusikan dengan rilis untuk menampilkan nomor build saat runtime.
Skrip build Ant menempatkan nomor build dalam file manifes file jar / perang yang dibuat selama build. Berlaku untuk semua build.
Tindakan pasca-pembangunan untuk rilis Build, dilakukan dengan mudah menggunakan Hudson plug-in: tag SVN dengan nomor build.
Manfaat:
Semoga ini membantu.
sumber
Saya juga menggunakan Hudson, meskipun skenario yang jauh lebih sederhana:
Skrip Ant saya memiliki target di dalamnya yang terlihat seperti:
Hudson menetapkan variabel lingkungan ini untuk saya setiap kali pekerjaan saya berjalan.
Dalam kasus saya, proyek ini adalah aplikasi web dan saya memasukkan
build-number.txt
file ini ke folder root aplikasi web - saya tidak terlalu peduli siapa yang melihatnya.Kami tidak memberi tag kontrol sumber saat ini dilakukan karena kami sudah menyiapkan pekerjaan Hudson kami untuk menandainya dengan nomor build / cap waktu ketika build berhasil.
Solusi saya hanya mencakup angka build inkremental untuk pengembangan, kami belum cukup jauh dalam proyek di mana kami sedang meliput angka rilis.
sumber
Anda mungkin juga ingin melihat plugin BuildNumber Maven dan tugas Ant dalam satu toples yang ditemukan di http://code.google.com/p/codebistro/wiki/BuildNumber . Saya mencoba membuatnya sederhana dan mudah. Ini adalah file jar yang sangat kecil yang hanya bergantung pada baris perintah Subversion yang diinstal.
sumber
Beginilah cara saya menyelesaikan ini:
Berikut adalah file java yang menyimpan info versi:
Dan inilah anttask "versioninfo":
sumber
Ini 2 sen saya:
Skrip build saya membuat nomor build (dengan stempel waktu!) Setiap kali saya membuat aplikasi. Ini menciptakan terlalu banyak angka tetapi tidak pernah terlalu sedikit. Jika saya memiliki perubahan dalam kode, nomor build akan berubah setidaknya sekali.
Saya versi nomor build dengan setiap rilis (meskipun tidak peralihan). Ketika saya memperbarui proyek dan saya mendapatkan nomor build baru (karena orang lain melakukan rilis), saya menimpa versi lokal saya dan memulai dari awal. Ini dapat mengarah ke nomor build yang lebih rendah itulah sebabnya saya menyertakan cap waktu.
Ketika rilis terjadi, nomor build dikomit sebagai item terakhir dalam komit tunggal dengan pesan "build 1547". Setelah itu, ketika ini merupakan rilis resmi, seluruh pohon ditandai. Dengan cara ini, file build selalu memiliki semua tag dan ada pemetaan 1: 1 sederhana antara tag dan nomor build.
[EDIT] Saya menggunakan version.html dengan proyek saya dan kemudian, saya bisa menggunakan scraper untuk hanya mengumpulkan peta yang akurat apa yang diinstal di mana. Jika Anda menggunakan Tomcat atau yang serupa, masukkan nomor build dan cap waktu di
description
elemen web.xml . Ingat: Jangan pernah menghafal apa pun saat komputer dapat melakukannya untuk Anda.sumber
Kami menjalankan build kami melalui CruiseControl (masukkan build manager favorit Anda di sini), dan melakukan build utama dan tes.
Kami kemudian menambah nomor versi menggunakan Semut dan BuildNumber dan membuat file properti dengan info ini ditambah tanggal pembuatan dan metadata lainnya.
Kami memiliki kelas yang didedikasikan untuk membaca ini dan menyediakannya untuk GUI / log dll.
Kami kemudian mengemas semua ini dan membangun ikatan yang dapat dipasang bersama-sama nomor build dan build yang sesuai. Semua server kami membuang informasi meta ini saat memulai. Kita dapat kembali melalui log CruiseControl dan mengikat nomor build ke tanggal dan checkin.
sumber