
kata Persia yang berarti "kecil" atau "li'l". Sering digunakan untuk merujuk pada seorang gadis saat menggoda, (dengan makna, gadis li'l)
Kamus Perkotaan
Selamat datang di KooChooloo : Proyek praktis yang elegan dibuat untuk merampingkan pengembangan aplikasi Golang. Menawarkan arsitektur yang terorganisir dengan baik, KooChooloo mengintegrasikan fitur-fitur vital seperti penanganan database dan manajemen konfigurasi, mencontohkan praktik terbaik dalam membangun aplikasi istirahat yang kuat dengan Go.
init : menghindari global dan kompleksitas fungsi init untuk menjaga hal -hal sederhana. Memanfaatkan fx sebagai kerangka injeksi ketergantungan kami, Koochooloo memberikan:
fx dalam pengujian dengan kemudahan yang sama seperti dalam produksi.Memulai perjalanan dengan koochooloo dan mendefinisikan kembali pendekatan Anda untuk membuat aplikasi yang tenang di Go. Apakah Anda memperluas keahlian Anda atau membangun fondasi yang kuat untuk aplikasi yang kompleks, KooChooloo adalah mitra Anda dalam desain perangkat lunak yang efisien, bersih, dan dapat diskalakan.
Pertama -tama, paket cmd berisi binari proyek ini dengan menggunakan Cobra. Adalah baik untuk memiliki binari sederhana untuk tugas -tugas seperti migrasi basis data yang dapat dijalankan pada fase inisiasi proyek. Setiap biner memiliki main.go dalam paketnya dan mendaftarkan dirinya dengan fungsi Register . Dalam root.go cmd fungsi Register ini dari sub-komandan disebut. Berikut adalah contoh untuk fungsi register:
// Register server command.
func Register ( root * cobra. Command ) {
root . AddCommand (
& cobra. Command {
Use : "server" ,
Short : "Run server to serve the requests" ,
Run : func ( _ * cobra. Command , _ [] string ) {
fx . New (
fx . Provide ( config . Provide ),
fx . Invoke ( main ),
). Run ()
},
},
)
} Sekali lagi setiap perintah mendaftarkan benderanya dengan sendirinya, jadi kami memiliki pemisahan dari perintah lain. Kadang -kadang kita perlu memiliki bendera berbagi antar perintah, maka lebih baik memilikinya di konfigurasi. Untuk kasus selanjutnya, koanf dapat membantu kami dengan struktur seperti di bawah ini:
func Register ( fs * pflag. FlagSet ) {
fs . StringP (
"url" , "u" ,
nats . DefaultURL ,
fmt . Sprintf ( "nats server url(s) e.g. %s" , nats . DefaultURL ),
)
}Register fungsi ini dibagikan bendera, dan kemudian kami memuat konfigurasi berdasarkan mereka dengan fungsi berikut:
k := koanf . New ( "." )
if err := k . Load ( posflag . Provider ( fs , "." , k ), nil ); err != nil {
log . Errorf ( "error loading config.yml: %s" , err )
}
if err := k . Unmarshal ( "" , & instance ); err != nil {
log . Fatalf ( "error unmarshalling config: %s" , err )
}Bagian utama dari setiap aplikasi adalah konfigurasinya. Ada banyak cara untuk memiliki konfigurasi dalam proyek dari file konfigurasi ke variabel lingkungan. Koanf memiliki semuanya dalam satu paket yang indah. Poin utamanya di sini adalah:
config dan akan meneruskannya dalam inisiasinya.PS Koanf jauh lebih baik daripada Viper karena memiliki konfigurasi yang diketik. Dengan konfigurasi yang diketik saya maksud Anda memiliki struktur yang ditentukan untuk konfigurasi dan kemudian memuat konfigurasi dari banyak sumber ke dalamnya.
Untuk menginstal koanf Anda dapat menggunakan perintah berikut:
go get -u github.com/knadh/koanf/v2
go get -u github.com/knadh/koanf/providers/file
go get -u github.com/knadh/koanf/providers/env
go get -u github.com/knadh/koanf/providers/structs
go get -u github.com/knadh/koanf/parsers/toml Paket dan layanan yang didefinisikan dalam paket domain hanya menggunakan paket lain dari domain tanpa menggunakan paket pihak ke -3. Paket dan layanan ini menentukan konsep domain inti.
Ada paket db yang bertanggung jawab untuk menghubungkan ke database. Paket ini menggunakan konfigurasi database yang didefinisikan dalam modul config dan membuat instance database. Adalah ide yang bagus untuk melakukan ping database Anda di sini untuk sepenuhnya percaya diri dengan instance database Anda sebelum maju. Juga untuk memiliki wawasan di database kesehatan Anda dapat menyebut fungsi ping ini secara berkala dan melaporkan hasilnya dengan metrik (yang tidak saya lakukan di sini).
Model proyek didefinisikan dalam paket model . Model -model ini digunakan secara internal tetapi dapat digunakan dalam paket response atau request . Tidak ada struktur untuk berkomunikasi dengan database dalam paket ini.
Repositori bertanggung jawab untuk berkomunikasi dengan database untuk menyimpan atau mengambil model. Repositori adalah interface dan ada implementasi konkret dan diejek untuk mereka. Implementasi konkret digunakan dalam kode utama dan diejek satu digunakan untuk tes. Harap dicatat bahwa tes untuk repositori sensitif dan selesai dengan database yang sebenarnya.
HTTP Handler didefinisikan dalam paket handler . Echo adalah kerangka kerja HTTP yang luar biasa yang telah Anda butuhkan. Setiap penangan memiliki strukturnya dengan metode Register yang mendaftarkan rutenya ke dalam kelompok rute tertentu. Route Group adalah konsep dari Echo Framework untuk rute pengelompokan di bawah jalur induk tertentu. Setiap penangan memiliki apa yang dibutuhkannya ke dalam strukturnya. Struktur pawang dibuat di main.go kemudian mendaftar pada grup mereka.
type Healthz struct {}
// Handle shows server is up and running.
func ( h Healthz ) Handle ( c echo. Context ) error {
return c . NoContent ( http . StatusNoContent )
}
// Register registers the routes of healthz handler on given echo group.
func ( h Healthz ) Register ( g * echo. Group ) {
g . GET ( "/healthz" , h . Handle )
} Semua metrik dikumpulkan menggunakan Prometheus berdasarkan pada-telemetri. Setiap paket memiliki metric.go yang mendefinisikan struktur berisi metrik dan memiliki metode untuk mengubahnya. Untuk bermigrasi dari Prometheus ke layanan lain, Anda hanya perlu mengubah telemetry . Metrik tidak global dan mereka dibuat untuk setiap contoh secara terpisah berkat desain telemetri terbuka. Untuk memiliki pengontrol yang lebih baik pada titik akhir metrik ada server HTTP lain yang didefinisikan dalam paket telemetry untuk pemantauan.
Adalah baik untuk memiliki paket yang terpisah untuk permintaan dan tanggapan. Paket -paket ini juga berisi logika validasi. Salah satu pakcage validasi yang baik di Go adalah ozzo-validator. Setelah memberikan metode validasi, setelah mendapatkan permintaan, Anda dapat memvalidasi dengan metodenya dengan mudah.
Mencatat salah satu bagian terpenting dari aplikasi. Pada awalnya tidak perlu memiliki sesuatu yang lebih dari log stdout sederhana. Tetapi di masa depan Anda perlu melakukan log dan mengirimkannya ke dalam sistem agregasi karena ketika sistem Anda tumbuh mendeteksi masalah dari log teks tidak akan mudah.
Zap adalah salah satu logger terbaik untuk pencatatan struktur. zap memaksa Anda untuk meneruskannya ke modul anak Anda dan Anda juga memberi nama penebang dengan metode Named . Dengan menggunakan Logger bernama, Anda dapat dengan mudah menemukan log modul Anda di agregator log Anda.
Proyek ini hanya membutuhkan MongoDB, dan Anda dapat menjalankannya dengan docker-compose yang disediakan.
cd deployments && docker-compose up -d
cd cmd/koochooloo/ && go build && ./koochooloocurl -X POST -d ' {"url": "https://elahe-dastan.github.io"} ' -H ' Content-Type: application/json ' 127.0.0.1:1378/api/urls
curl -L 127.0.0.1:1378/api/CKaniA checks.....................: 99.83% ✓ 2995 ✗ 5
data_received..............: 2.0 MB 64 kB/s
data_sent..................: 521 kB 17 kB/s
group_duration.............: avg=649.18ms min=153.18µs med=265.45ms max=30.95s p(90)=1.61s p(95)=2.06s
http_req_blocked...........: avg=14.12ms min=0s med=3µs max=1.65s p(90)=13µs p(95)=147.04µs
http_req_connecting........: avg=6.23ms min=0s med=0s max=1.36s p(90)=0s p(95)=0s
http_req_duration..........: avg=272.98ms min=0s med=127.99ms max=4.81s p(90)=830.93ms p(95)=1.29s
http_req_receiving.........: avg=125.23µs min=0s med=60µs max=11.21ms p(90)=228µs p(95)=363µs
http_req_sending...........: avg=50.78µs min=0s med=22µs max=7.28ms p(90)=86µs p(95)=138µs
http_req_tls_handshaking...: avg=7.86ms min=0s med=0s max=653.63ms p(90)=0s p(95)=0s
http_req_waiting...........: avg=272.8ms min=0s med=127.71ms max=4.81s p(90)=830.87ms p(95)=1.29s
http_reqs..................: 4000 129.093962/s
iteration_duration.........: avg=1.29s min=142.34ms med=1.04s max=30.97s p(90)=2.18s p(95)=2.64s
iterations.................: 1000 32.273491/s
vus........................: 100 min=100 max=100
vus_max....................: 100 min=100 max=100