davideisinger.com

My personal website
Log | Files | Refs | README

medium-com-efpmux.txt (14373B)


      1 [1]Open in app
      2 
      3 Sign up
      4 
      5 [3]Sign in
      6 
      7 [4]
      8 [5][                    ]
      9 [6]
     10 Write
     11 [7]
     12 
     13 Sign up
     14 
     15 [9]Sign in
     16 
     17 [1]
     18 
     19 Go Project Layout
     20 
     21 [11]
     22 Kyle C. Quest (Q)
     23 [12]
     24 golang-learn
     25 
     26 [13]Kyle C. Quest (Q)
     27 
     28 ·
     29 
     30 [14]Follow
     31 
     32 Published in
     33 [15]
     34 
     35 golang-learn
     36 
     37 ·
     38 5 min read
     39 ·
     40 Sep 11, 2017
     41 
     42 --
     43 
     44 11
     45 
     46 Listen
     47 
     48 Share
     49 
     50 You went through the ‘[19]Tour of Go’, played with [20]https://play.golang.org/
     51 and you feel you are ready to write some code. Great! However, you are not sure
     52 how to structure your projects. Can you put your code anywhere you want? Is
     53 there a standard way to organize your code? What if you need to have multiple
     54 application binaries? What does it mean to be ‘go gettable’? These are some of
     55 the questions you’ll be asking yourself.
     56 
     57 First, you have to understand Go workspaces. ‘[21]How to Write Go Code’ is a
     58 good place to start. By default, Go keeps and expects all code in a single
     59 workspace. This place is identified by the GOPATH environment variable. What
     60 does it mean for you? It means you have to put your code in the default
     61 workspace or you have to change the GOPATH variable to point to your own
     62 location. Either way the actual source code for your project needs to be placed
     63 in the src subdirectory (e.g., $GOPATH/src/your_project or $GOPATH/src/
     64 github.com/your_github_username/your_project). Technically your project doesn’t
     65 have to be in a workspace if you don’t import external packages and you use
     66 relative imports for your own code, but it’s not recommended. It’s fine for a
     67 toy project or a PoC though. Go v1.11 does introduce the concept of [22]modules
     68 that allows you to have your project code outside of your GOPATHwithout the
     69 import restrictions mentioned above, but it’s still an experimental feature at
     70 this point in time.
     71 
     72 You have your project directory in the right place. What’s next?
     73 
     74 For a PoC or a very small project where you are the only one writing the code
     75 using a single main.go file in the root directory for your project is enough.
     76 If you know your project will be large enough or it’ll go into production and
     77 others will be contributing to it you should consider adopting, at least, some
     78 of the project layout patterns outlined here.
     79 
     80 There are a number of project layout patterns emerging in the Go ecosystem. The
     81 two most common patterns are the cmd and pkg directories. You should adopt
     82 these patterns unless you have a tiny project.
     83 
     84 The cmd layout pattern is very useful when you need to have more than one
     85 application binary. Each binary gets a subdirectory (e.g., your_project/cmd/
     86 your_app). This patterns also helps you keep your project/package ‘go
     87 gettable’. What does it mean? It means you can use the go get command to fetch
     88 (and install) your project, its applications and its libraries (e.g., go get
     89 github.com/your_github_username/your_project/cmd/appxg). You don’t have to
     90 separate the application files. You’ll be able to build each application with
     91 the right set of go build flags, but go get will no longer work because it will
     92 not know which application code to build. The official [23]Go tools is one
     93 example of the cmd layout patter. A number of other well known projects use the
     94 same pattern: [24]Kubernetes, [25]Docker, [26]Prometheus, [27]Influxdb.
     95 
     96 The pkg layout pattern is also pretty popular. For new Go developers it’s one
     97 of the most confusing package structure concepts because Go workspaces have a
     98 directory with the same name and that directory has a different purpose (it’s
     99 used to store object files for the packages the Go compiler builds). The pkg
    100 directory is where you put your public libraries. They can be used internally
    101 by your application. They can also be used by external projects. This is an
    102 informal contract between you and other external users of your code. Other
    103 projects will import these libraries expecting them to work, so think twice
    104 before you put something here. Many well known projects use this pattern: [28]
    105 Kubernetes, [29]Docker, [30]Grafana, [31]Influxdb, [32]Etcd.
    106 
    107 Some of the libraries in the pkg directory are not always for public use. Why
    108 is that? It happens because many existing Go projects predate the ability to
    109 hide internal packages. Some projects put those internal libraries in the pkg
    110 directory to be consistent with the rest of their code structure. Other
    111 projects put their internal libraries into separate directories outside of the
    112 pkg directory. [33]Go 1.4 introduce an ability to hide code using internal
    113 directories. What does it mean? If you put your code in an ‘internal’ directory
    114 no external project will be able to import that code. Even other code in your
    115 project won’t be able to access this internal code if it lives outside of its
    116 parent directory. This feature is not widely used yet because it’s relatively
    117 new; however, it’s extremely valuable as an additional layer of control (in
    118 addition to the lowercase and uppercase function visibility rules in Go). A
    119 number of new and well known projects use this pattern: [34]Dep, [35]Docker, 
    120 [36]Nsq, [37]Go Ethereal, [38]Contour.
    121 
    122 The internal directory is the place to put your private packages. You can
    123 optionally add additional structure by separating your internally shared
    124 libraries (e.g., your_project/internal/pkg/your_private_lib) and the
    125 application code you don’t want others to import (e.g., your_project/internal/
    126 app/your_app). When you put all of you private code in the ‘internal’ directory
    127 the application code in the cmd directory will be limited to small files that
    128 define the ‘main’ function for the corresponding application binaries.
    129 Everything else will be imported from the internal or pkg directories ([39]ark,
    130 from Heptio, and [40]loki, from Grafana, are good examples of this tiny main
    131 package pattern).
    132 
    133 What if you forked and modified a piece of an external project? Some projects
    134 put that code in the pkg directory, but it’s better to put it in the
    135 third_party top level directory to keep your code separate from the code you
    136 borrowed from others.
    137 
    138 What about the external packages you import in your projects? Where do they go?
    139 You have several options. You can keep them outside of your project. The
    140 packages you install with go get will be saved in your Go workspace. It works
    141 most of the times, but depending on the package it might be brittle and
    142 unpredictable because when somebody else tries to build your project they might
    143 get a backward incompatible version of that package. The solution is
    144 ‘vendoring’. With ‘vendoring’ you freeze your dependencies by committing them
    145 with your project. [41]Go 1.6 introduced a standard way to ‘vendor’ external
    146 packages (it was an experimental feature in Go 1.5). Put your external package
    147 in the vendor directory. How is this different from the third_party directory?
    148 If you import and use external code as-is then it should go into the vendor
    149 directory. If you are using a modified version of an external project then put
    150 it in the third_party directory.
    151 
    152 If you want to learn more about the project structure used by other Go projects
    153 read the ‘[42]Analysis of the Top 1000 Go Repositories’. It’s a little dated,
    154 but it’s still useful.
    155 
    156 A real project will have additional directories too. You can use this layout
    157 template as a starting point for your Go projects: [43]https://github.com/
    158 golang-standards/project-layout. It covers the Go project layout patterns
    159 described in this blog post and it includes a number of supporting directories
    160 you’ll need to have.
    161 
    162 Now it’s time to write some code! If you don’t have Go installed take a look at
    163 this [44]quick setup guide for Mac OS X (setup on other platforms is similar).
    164 Go through the ‘[45]Tour of Go’ if you haven’t done it yet and then read ’[46]
    165 50 Shades of Go’ to learn about the most common gotchas in Go, which will save
    166 you quite a bit of time when you start writing and debugging code.
    167 
    168 [47]
    169 Golang
    170 [48]
    171 Go
    172 [49]
    173 Standards
    174 [50]
    175 Project Structure
    176 
    177 --
    178 
    179 --
    180 
    181 11
    182 
    183 [53]
    184 Kyle C. Quest (Q)
    185 [54]
    186 golang-learn
    187 Follow
    188 [56]
    189 [58]
    190 
    191 Written by Kyle C. Quest (Q)
    192 
    193 [59]358 Followers
    194 ·Editor for
    195 [60]
    196 
    197 golang-learn
    198 
    199 CTO / Redefining DevOps * Hacker @DockerSlim * @Golang50Shades * Cloud Native *
    200 Data * Security
    201 
    202 Follow
    203 [62]
    204 [64]
    205 
    206 Help
    207 
    208 [65]
    209 
    210 Status
    211 
    212 [66]
    213 
    214 About
    215 
    216 [67]
    217 
    218 Careers
    219 
    220 [68]
    221 
    222 Blog
    223 
    224 [69]
    225 
    226 Privacy
    227 
    228 [70]
    229 
    230 Terms
    231 
    232 [71]
    233 
    234 Text to speech
    235 
    236 [72]
    237 
    238 Teams
    239 
    240 
    241 References:
    242 
    243 [1] https://rsci.app.link/?%24canonical_url=https%3A%2F%2Fmedium.com%2Fp%2Fe5213cdcfaa2&%7Efeature=LoOpenInAppButton&%7Echannel=ShowPostUnderCollection&source=---two_column_layout_nav----------------------------------
    244 [3] https://medium.com/m/signin?operation=login&redirect=https%3A%2F%2Fmedium.com%2Fgolang-learn%2Fgo-project-layout-e5213cdcfaa2&source=post_page---two_column_layout_nav-----------------------global_nav-----------
    245 [4] https://medium.com/?source=---two_column_layout_nav----------------------------------
    246 [6] https://medium.com/m/signin?operation=register&redirect=https%3A%2F%2Fmedium.com%2Fnew-story&source=---two_column_layout_nav-----------------------new_post_topnav-----------
    247 [7] https://medium.com/search?source=---two_column_layout_nav----------------------------------
    248 [9] https://medium.com/m/signin?operation=login&redirect=https%3A%2F%2Fmedium.com%2Fgolang-learn%2Fgo-project-layout-e5213cdcfaa2&source=post_page---two_column_layout_nav-----------------------global_nav-----------
    249 [11] https://medium.com/@kcq?source=post_page-----e5213cdcfaa2--------------------------------
    250 [12] https://medium.com/golang-learn?source=post_page-----e5213cdcfaa2--------------------------------
    251 [13] https://medium.com/@kcq?source=post_page-----e5213cdcfaa2--------------------------------
    252 [14] https://medium.com/m/signin?actionUrl=https%3A%2F%2Fmedium.com%2F_%2Fsubscribe%2Fuser%2F6aac7a58837&operation=register&redirect=https%3A%2F%2Fmedium.com%2Fgolang-learn%2Fgo-project-layout-e5213cdcfaa2&user=Kyle+C.+Quest+%28Q%29&userId=6aac7a58837&source=post_page-6aac7a58837----e5213cdcfaa2---------------------post_header-----------
    253 [15] https://medium.com/golang-learn?source=post_page-----e5213cdcfaa2--------------------------------
    254 [19] https://tour.golang.org/
    255 [20] https://play.golang.org/
    256 [21] https://golang.org/doc/code.html
    257 [22] https://github.com/golang/go/wiki/Modules
    258 [23] https://github.com/golang/tools/tree/master/cmd
    259 [24] https://github.com/kubernetes/kubernetes/tree/master/cmd
    260 [25] https://github.com/moby/moby/tree/master/cmd
    261 [26] https://github.com/prometheus/prometheus/tree/master/cmd
    262 [27] https://github.com/influxdata/influxdb/tree/master/cmd
    263 [28] https://github.com/kubernetes/kubernetes/tree/master/pkg
    264 [29] https://github.com/moby/moby/tree/master/pkg
    265 [30] https://github.com/grafana/grafana/tree/master/pkg
    266 [31] https://github.com/influxdata/influxdb/tree/master/pkg
    267 [32] https://github.com/coreos/etcd/tree/master/pkg
    268 [33] https://golang.org/doc/go1.4#internalpackages
    269 [34] https://github.com/golang/dep/tree/master/internal
    270 [35] https://github.com/moby/moby/tree/master/internal
    271 [36] https://github.com/nsqio/nsq/tree/master/internal
    272 [37] https://github.com/ethereum/go-ethereum/tree/master/internal
    273 [38] https://github.com/heptio/contour/tree/master/internal
    274 [39] https://github.com/heptio/ark/blob/master/cmd/ark/main.go
    275 [40] https://github.com/grafana/loki/blob/master/cmd/loki/main.go
    276 [41] https://golang.org/doc/go1.6#go_command
    277 [42] http://blog.sgmansfield.com/2016/01/an-analysis-of-the-top-1000-go-repositories/
    278 [43] https://github.com/golang-standards/project-layout
    279 [44] https://medium.com/golang-learn/quick-go-setup-guide-on-mac-os-x-956b327222b8
    280 [45] https://tour.golang.org/
    281 [46] http://devs.cloudimmunity.com/gotchas-and-common-mistakes-in-go-golang/
    282 [47] https://medium.com/tag/golang?source=post_page-----e5213cdcfaa2---------------golang-----------------
    283 [48] https://medium.com/tag/go?source=post_page-----e5213cdcfaa2---------------go-----------------
    284 [49] https://medium.com/tag/standards?source=post_page-----e5213cdcfaa2---------------standards-----------------
    285 [50] https://medium.com/tag/project-structure?source=post_page-----e5213cdcfaa2---------------project_structure-----------------
    286 [53] https://medium.com/@kcq?source=post_page-----e5213cdcfaa2--------------------------------
    287 [54] https://medium.com/golang-learn?source=post_page-----e5213cdcfaa2--------------------------------
    288 [56] https://medium.com/m/signin?actionUrl=%2F_%2Fapi%2Fsubscriptions%2Fnewsletters%2F997b4efe98f9&operation=register&redirect=https%3A%2F%2Fmedium.com%2Fgolang-learn%2Fgo-project-layout-e5213cdcfaa2&newsletterV3=6aac7a58837&newsletterV3Id=997b4efe98f9&user=Kyle+C.+Quest+%28Q%29&userId=6aac7a58837&source=-----e5213cdcfaa2---------------------subscribe_user-----------
    289 [58] https://medium.com/@kcq?source=post_page-----e5213cdcfaa2--------------------------------
    290 [59] https://medium.com/@kcq/followers?source=post_page-----e5213cdcfaa2--------------------------------
    291 [60] https://medium.com/golang-learn?source=post_page-----e5213cdcfaa2--------------------------------
    292 [62] https://medium.com/m/signin?actionUrl=%2F_%2Fapi%2Fsubscriptions%2Fnewsletters%2F997b4efe98f9&operation=register&redirect=https%3A%2F%2Fmedium.com%2Fgolang-learn%2Fgo-project-layout-e5213cdcfaa2&newsletterV3=6aac7a58837&newsletterV3Id=997b4efe98f9&user=Kyle+C.+Quest+%28Q%29&userId=6aac7a58837&source=-----e5213cdcfaa2---------------------subscribe_user-----------
    293 [64] https://help.medium.com/hc/en-us?source=post_page-----e5213cdcfaa2--------------------------------
    294 [65] https://medium.statuspage.io/?source=post_page-----e5213cdcfaa2--------------------------------
    295 [66] https://medium.com/about?autoplay=1&source=post_page-----e5213cdcfaa2--------------------------------
    296 [67] https://medium.com/jobs-at-medium/work-at-medium-959d1a85284e?source=post_page-----e5213cdcfaa2--------------------------------
    297 [68] https://blog.medium.com/?source=post_page-----e5213cdcfaa2--------------------------------
    298 [69] https://policy.medium.com/medium-privacy-policy-f03bf92035c9?source=post_page-----e5213cdcfaa2--------------------------------
    299 [70] https://policy.medium.com/medium-terms-of-service-9db0094a1e0f?source=post_page-----e5213cdcfaa2--------------------------------
    300 [71] https://speechify.com/medium?source=post_page-----e5213cdcfaa2--------------------------------
    301 [72] https://medium.com/business?source=post_page-----e5213cdcfaa2--------------------------------