Organización de un proyecto Go de varios archivos
Nota: esta pregunta está relacionada con esta, pero dos años es un tiempo muy largo en la historia de Go.
¿Cuál es la forma estándar de organizar un proyecto Go durante el desarrollo ?
Mi proyecto es un solo paquete mypack
, así que supongo que pongo todos los .ir archivos en un directorio mypack
.
Pero entonces, me gustaría probarlo durante el desarrollo, por lo que necesito al menos un archivo que declare el paquete main
, para que pueda hacer go run trypack.go
¿Cómo debo organizar esto ? Tengo que hacer go install mypack
cada vez que quiero probarlo ?
7 answers
Recomendaría revisar esta página en Cómo Escribir Código Go
Documenta tanto cómo estructurar su proyecto de una manera go build
amigable, como también cómo escribir pruebas. Las pruebas no necesitan ser un cmd usando el paquete main
. Simplemente pueden ser funciones TestX nombradas como parte de cada paquete, y luego go test
las descubrirá.
La estructura sugerida en ese enlace en su pregunta está un poco desactualizada, ahora con el lanzamiento de Go 1. Ya no necesitarías coloque un directorio pkg
bajo src
. Los únicos 3 directorios relacionados con especificaciones son los 3 en la raíz de tu GOPATH: bin, pkg, src . Debajo de src, simplemente puede colocar su proyecto mypack
, y debajo de eso está todo su .ir archivos incluyendo el mypack_test.go
go build
luego se construirá en el nivel raíz pkg y bin.
Así que tu GOPATH podría verse así: {[13]]}
~/projects/
bin/
pkg/
src/
mypack/
foo.go
bar.go
mypack_test.go
export GOPATH=$HOME/projects
$ go build mypack
$ go test mypack
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-02-02 20:07:13
Jdi tiene la información correcta sobre el uso de GOPATH
. Yo añadiría que si usted tiene la intención de tener un binario, así que es posible que desee añadir un nivel adicional a los directorios.
~/projects/src/
myproj/
mypack/
lib.go
lib_test.go
...
myapp/
main.go
Ejecutando go build myproj/mypack
construirá el paquete mypack
junto con sus dependencias
ejecutar go build myproj/myapp
construirá el binario myapp
junto con sus dependencias que probablemente incluyen la biblioteca mypack
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-03-24 19:29:27
He estudiado una serie de proyectos Go y hay un poco de variación. Puede decir quién viene de C y quién viene de Java, ya que el primero volcó casi todo en el directorio raíz de proyectos en un paquete main
, y el segundo tiende a poner todo en un directorio src
. Sin embargo, ninguno es óptimo. Cada uno tiene consecuencias porque afectan las rutas de importación y cómo otros pueden reutilizarlas.
Para obtener los mejores resultados he elaborado lo siguiente enfoque.
myproj/
main/
mypack.go
mypack.go
Donde mypack.go
es package mypack
y main/mypack.go
es (obviamente) package main
.
Si necesita archivos de soporte adicionales, tiene dos opciones. Manténgalos todos en el directorio raíz, o ponga archivos de soporte privados en un subdirectorio lib
. Por ejemplo,
myproj/
main/
mypack.go
myextras/
someextra.go
mypack.go
mysupport.go
O
myproj.org/
lib/
mysupport.go
myextras/
someextra.go
main/
mypack.go
mypage.go
Solo coloque los archivos en un directorio lib
si no están destinados a ser importados por otro proyecto. En otras palabras, si son archivos de soporte privados. Esa es la idea detrás teniendo lib
separate para separar las interfaces públicas de las privadas.
Hacer las cosas de esta manera le dará una ruta de importación agradable, myproj.org/mypack
para reutilizar el código en otros proyectos. Si usa lib
entonces los archivos de soporte internos tendrán una ruta de importación que es indicativa de eso, myproj.org/lib/mysupport
.
Al construir el proyecto, use main/mypack
, por ejemplo go build main/mypack
. Si tiene más de un ejecutable, también puede separarlos bajo main
sin tener que crear proyectos separados. por ejemplo, main/myfoo/myfoo.go
y main/mybar/mybar.go
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-03-26 11:02:54
Me parece muy útil para entender cómo organizar el código en Golang este capítulo http://www.golang-book.com/11 del libro escrito por Caleb Doxsey
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-08-02 06:42:33
No parece haber una forma estándar de organizar proyectos Go pero https://golang.org/doc/code.html especifica una buena práctica para la mayoría de los proyectos. la respuesta de jdi es buena, pero si usas github o bitbucket y también tienes bibliotecas adicionales, deberías crear la siguiente estructura:
~/projects/
bin/
pkg/
src/
github.com/
username/
mypack/
foo.go
bar.go
mypack_test.go
mylib/
utillib.go
utillib_test.go
Al hacerlo de esta manera, puede tener un repositorio separado para mylib que puede ser utilizado para otros proyectos y puede ser recuperado por "go get". Tu proyecto mypack puede importar su biblioteca usando "github.com/username/mylib". Para más información:
Http://www.alexvictorchan.com/2014/11/06/go-project-structure /
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-11-09 04:33:06
Mantenga los archivos en el mismo directorio y use package main
en todos los archivos.
myproj/
your-program/
main.go
lib.go
Luego ejecute:
~/myproj/your-program$ go build && ./your-program
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-10-24 16:13:08
Vamos a explorar cómo el comando go get repository_remote_url
administra la estructura del proyecto bajo $GOPATH
. Si hacemos un go get github.com/gohugoio/hugo
clonará el repositorio bajo
GOP GOPATH/src/repository_remote / user_name / project_name
$GOPATH/src/github.com/gohugoio/hugo
Esta es una buena manera de crear su ruta inicial del proyecto. Ahora vamos a explorar cuáles son los tipos de proyectos por ahí y cómo sus estructuras internas son organizado. Todos los proyectos de golang en la comunidad se pueden clasificar en
-
Libraries
(sin binarios ejecutables) -
Single Project
(contiene solo 1 binario ejecutable) -
Tooling Projects
(contiene varios binarios ejecutables)
Generalmente los archivos del proyecto golang se pueden empaquetar bajo cualquier principio de diseño como DDD, POD
La mayoría de los proyectos go disponibles siguen este Orientado a paquetes Diseño
Diseño orientado a paquetes anime al desarrollador a mantener la implementación solo dentro de sus propios paquetes, aparte del paquete /internal
esos paquetes no pueden comunicarse entre sí
Bibliotecas
- Proyectos como controladores de base de datos, qt puede poner en esta categoría.
- Algunas bibliotecas como color, ahora sigue una estructura plana sin ningún otro paquete.
- La mayoría de estos proyectos de bibliotecas gestionan un paquete llamado internal.
-
/internal
package se usa para mantener archivos go que usan otros paquetes múltiples dentro del proyecto. - no tiene ningún binarios ejecutables, así que no hay archivos que contiene el principal func.
~/$GOPATH/
bin/
pkg/
src/
repository_remote/
user_name/
project_name/
internal/
other_pkg/
Proyecto único
- Proyectos como hugo, etcd tiene un func principal único en el nivel raíz y.
- El objetivo es generar un único binario
Proyectos de herramientas
- Proyectos como kubernetes, go-ethereum tiene múltiples func principal organizado bajo un paquete llamado cmd
-
cmd/
el paquete gestiona el número de binarios (herramientas) que queremos compilar
~/$GOPATH/
bin/
pkg/
src/
repository_remote/
user_name/
project_name/
cmd/
binary_one/
main.go
binary_two/
main.go
binary_three/
main.go
other_pkg/
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-08-21 06:54:29