Slide 1

Slide 1 text

gostyle IS NOT Go Style খࢁ݈Ұ࿠ / GMO PEPABO inc. 2023.12.18 Fukuoka.go#19 Reboot 1

Slide 2

Slide 2 text

ࣗݾ঺հ ٕज़෦ɹٕज़ج൫νʔϜ 2018೥ த్ೖࣾ খࢁ ݈Ұ࿠ Ken’ichiro Oyama গ࣮͠༻తͰখ͞ͳOSSΛॻ͘ͷ͕झຯɻ ● GitHub : k1LoW ● Twitter : @k1LoW 2

Slide 3

Slide 3 text

GMOϖύϘʹ͍ͭͯ 3 https://pepabo.com

Slide 4

Slide 4 text

ΞδΣϯμ • Goʹ͓͚ΔίʔσΟϯάελΠϧ • Goʹ͓͚ΔLinter • gostyle • gostyleͷ࣮૷ • ͓ΘΓʹ 4

Slide 5

Slide 5 text

5 Goʹ͓͚ΔίʔσΟϯάελΠϧ

Slide 6

Slide 6 text

6 Goʹ͓͚ΔίʔσΟϯάελΠϧ go fmt

Slide 7

Slide 7 text

7 Goʹ͓͚ΔίʔσΟϯάελΠϧ go fmt • GoެࣜͷϑΥʔϚολ • ४ެࣜͱͯ͠golang.org/x/tools/cmd/goimports΋͋Δ • ιʔείʔυͷ੔ܗͯ͘͠ΕΔ • ʮΠϯσϯτ͸Կʹ͢Δ͔ʯͱ͍ͬͨʮύʔΩϯιϯͷຌଏ๏ଇ a.k.a ࣗసंஔ͖৔ͷٞ࿦ʯΛ ͳ͘͢͜ͱʹߩݙ͍ͯ͠Δ • ެ͕ࣜఏڙ͍ͯ͠Δͷ͜Ε͚ͩͰOK • ʹͳΔ͸ͣͩͬͨ

Slide 8

Slide 8 text

8 Goʹ͓͚ΔίʔσΟϯάελΠϧ go fmtͰΧόʔͰ͖Δൣғ͸ݶఆతʢͰ΋͋Δʣ • go fmtͰΧόʔͰ͖Δൣғ͸ίʔυͷϑΥʔϚοτ·Ͱ • ʮࣗసंஔ͖৔ͷٞ࿦ʯʹͳΔ༨஍͸࢒೦ͳ͕Β·ͩ͋Δ • ·ͨɺ1ͭͷϓϩμΫτ಺ʹҟͳΔελΠϧ͕ࠞࡏ͢Δͱೝ஌ෛՙ͕େ͖͘ͳΔͷ΋ࣄ࣮ • ΍͸ΓνʔϜʹίʔσΟϯάελΠϧ͸ඞཁͳͷͰ͸ͳ͍͔ • ίʔυϕʔεΛ؅ཧ͠΍͘͢͢ΔͨΊ • ೝ஌ෛՙΛܰݮ͢ΔͨΊ • ʢ݁Ռͱͯ͠ͷʣόάͷൃੜΛܰݮ͢ΔͨΊ • ϨϏϡʔෛՙΛܰݮ͢ΔͨΊʢػցʹͰ͖Δ͜ͱ͸ػցʹ೚ͤͨํ͕͍͍ʣ

Slide 9

Slide 9 text

9 Goʹ͓͚Δ ͍Ζ͍Ζͳ ίʔσΟϯάελΠϧ

Slide 10

Slide 10 text

10 Goʹ͓͚Δ͍Ζ͍ΖͳίʔσΟϯάελΠϧ Effective Go • Goެࣜͷ໌֬Ͱ׳༻తͳGoίʔυΛॻͨ͘Ίͷώϯτ • GoΒ͍͠ίʔυΛॻͨ͘ΊʹࠓͰ΋༗༻ͳυΩϡϝϯτ • Go͕ϦϦʔε͞Εͨ2009೥ʹॻ͔Εͨ΋ͷͰͦΕҎདྷେ෯ͳߋ৽͸͞Ε͍ͯͳ͍ ʢEffective Go 2022೥1݄௥هΑΓʣ

Slide 11

Slide 11 text

11 Goʹ͓͚Δ͍Ζ͍ΖͳίʔσΟϯάελΠϧ Go Code Review Comments • https://go.dev/wiki/CodeReviewComments • ݩʑ͸ https://github.com/golang/go/wiki/CodeReviewComments ʹ͕͋ͬͨɺ͍ͭ2023೥ 12݄14೔ʹҠಈ͞Εͨ • https://github.com/golang/go/issues/61940 • GoίʔυͷϨϏϡʔதʹΑ͋͘ΔίϝϯτΛ͋ͭΊͨҰൠతͳελΠϧͷཏྻʢελΠϧΨΠ υͰ͸ͳ͍ʣ

Slide 12

Slide 12 text

12 Goʹ͓͚Δ͍Ζ͍ΖͳίʔσΟϯάελΠϧ Go Style in Google Style Guide • https://google.github.io/styleguide/go/ • Google͕؅ཧ͢ΔελΠϧΨΠυͱͦΕʹ෇ਵ͢ΔυΩϡϝϯτ • GoogleͰGoͷίʔυΛϨϏϡʔ͢Δਓ͕༩͑ΔελΠϧΨΠμϯεΛ౷Ұ͢Δ໾ׂ΋࣋ͭ • Style GuideɺStyle DecisionsɺBest Practicesͷ3ͭͷυΩϡϝϯτ͔ΒͳΔ

Slide 13

Slide 13 text

13 Goʹ͓͚Δ͍Ζ͍ΖͳίʔσΟϯάελΠϧ Uber Go Style Guide • https://github.com/uber-go/guide/blob/master/style.md • Uber͕؅ཧ͢ΔελΠϧΨΠυ • UberͰGoͷίʔυΛॻ͘ͱ͖ͷʮ΍Δ΂͖͜ͱʯͱʮ΍ͬͯ͸͍͚ͳ͍͜ͱʯΛৄ͘͠આ໌͢ Δ͜ͱ͕ΰʔϧ • ΤϯδχΞ͕GoݴޠͷػೳΛੜ࢈తʹ࢖༻Ͱ͖ΔΑ͏ʹ͠ͳ͕ΒɺίʔυϕʔεΛ؅ཧ͠ ΍͘͢อͭͨΊʹଘࡏ

Slide 14

Slide 14 text

14 Goʹ͓͚ΔLinter

Slide 15

Slide 15 text

15 Goʹ͓͚ΔLinter GolintʢDeprecatedʣ • https://github.com/golang/lint • ͔ͭͯͷGoެࣜLinter • ίʔσΟϯάελΠϧͷͨΊͷLinter • Effective GoͱCodeReviewCommentʹॻ͔Ε͍ͯΔελΠϧͷ׳शʹ͍ͭͯͷνΣοΫͷ ΈΛείʔϓͱ͍ͯ͠Δ

Slide 16

Slide 16 text

16 Goʹ͓͚ΔLinter go vet • GoެࣜͷɺGoͷιʔείʔυΛݕࠪʢ੩తղੳʣͯ͠ɺٙΘ͍͠ίʔυΛใࠂ͢ΔͨΊͷπʔ ϧɻ • ϏϧτΠϯ͞Ε͍ͯΔAnalyzerҎ֎ʹɺҾ਺Ͱ೚ҙͷvettoolΛ౉͢͜ͱ͕Ͱ͖Δɻ

Slide 17

Slide 17 text

17 Goʹ͓͚ΔLinter golangci-lint • https://github.com/golangci/golangci-lint • ෳ਺ͷLinterΛ·ͱΊ࣮ͯߦͰ͖ΔLinter runner • .golangci.yml ͰઃఆมߋՄೳ • GitHub ActionsͷAction΋༻ҙ͞Ε͍ͯΔͳͲCIͱͷ࿈ܞ΋͠΍͘͢ɺ࣮ߦ଎౓΋͸΍͘ɺෳ਺ ͷLinterΛ੍ޚͰ͖ΔͷͰΑ͘࢖ΘΕ͍ͯΔͷΛΈΔ

Slide 18

Slide 18 text

18 Goʹ͓͚ΔLinter revive • https://github.com/mgechev/revive • Golintͷ୅ସ+α • ͢Ͱʹଟ͘ͷಠࣗϧʔϧ͕࣮૷͞Ε͍ͯΔ • TOMLͰઃఆมߋՄೳ • Golintͱಉ͡ઃఆ͕Ͱ͖Δ • golangci-lint͔Βݺͼग़͢͜ͱ΋Մೳ

Slide 19

Slide 19 text

19 Goʹ͓͚ΔLinter طଘLinterॴײ • ʮόάΛੜΈͦ͏ͳٙΘ͍͠ίʔυΛൃݟ͢ΔͨΊͷLinterʯͱʮίʔσΟϯάελΠϧΛ νΣοΫ͢ΔͨΊͷLinterʯ͕ଘࡏ͢Δ • golangci-lintʹ͓͍ͯ͸ࠞࡏ͍ͯ͠Δ • ίʔσΟϯάελΠϧΛνΣοΫ͢ΔͨΊͷLinterʹ͓͍ͯɺଟ͘ͷϧʔϧ͕͋Δ͕ϦϑΝϨϯ εͱͯ͠Կ͔͠ΒͷίʔσΟϯάελΠϧυΩϡϝϯτͱඥ͍͍ͮͯΔ΋ͷ͹͔ΓͰ͸ͳ͍ • Linterಠࣗͷ΋ͷ͕ͭ͘ΒΕ͍ͯΔ͜ͱ͕ଟ͍ • νʔϜʹίʔσΟϯάελΠϧΛνΣοΫ͢ΔLinterΛಋೖ͢Δࡍ͸ɺυΩϡϝϯτͱඥ͍ͮͯ ͍Δ΄͏͕ಋೖ͕͠΍͍͔͢΋͠Εͳ͍ʢίϯηϯαεͷͱΓ΍͢͞ʣ

Slide 20

Slide 20 text

20 gostyle

Slide 21

Slide 21 text

21 gostyle gostyle • https://github.com/k1LoW/gostyle • ίʔσΟϯάελΠϧΛνΣοΫ͢ΔͨΊͷLinter • go vetͷ࢓૊Έͷ্ʹߏங͍ͯ͠Δ • go vet -vettool=`which gostyle` -gostyle.config=$PWD/.gostyle.yml ./... • ࣍ͷίʔσΟϯάελΠϧυΩϡϝϯτΛϕʔεʹAnalyzerΛ࡞੒ • Effective Go • Go Code Review Comments • Go Style in Google Style Guide • YAMLͰઃఆมߋՄೳ • //nostyle:dontpanic ͳͲͷίϝϯτͰϞμϯͳLinterͱಉ͡Α͏ʹࡉ͔͘Ignore͕Մೳ

Slide 22

Slide 22 text

gostyle Analyzers of gostyle (18 analyzers in v0.18.4) • Effective Go • ifacenames ... based on https://go.dev/doc/effective_go#interface-names • Go Style in Google Style Guides • Guide • mixedcaps ... based on https://google.github.io/styleguide/go/guide#mixed-caps • Decisions • funcfmt ... based on https://google.github.io/styleguide/go/decisions#function-formatting • getters ... based on https://google.github.io/styleguide/go/decisions#getters • nilslices ... based on https://google.github.io/styleguide/go/decisions#nil-slices • pkgnames ... based on https://google.github.io/styleguide/go/decisions#package-names • recvnames ... based on https://google.github.io/styleguide/go/decisions#receiver-names • recvtype ... based on https://google.github.io/styleguide/go/decisions#receiver-type • repetition ... based on https://google.github.io/styleguide/go/decisions#repetition • typealiases ... based on https://google.github.io/styleguide/go/decisions#type-aliases • underscores ... based on https://google.github.io/styleguide/go/decisions#underscores • useany ... based on https://google.github.io/styleguide/go/decisions#use-any • useq ... based on https://google.github.io/styleguide/go/decisions#use-q • varnames ... based on https://google.github.io/styleguide/go/decisions#variable-names • Go Code Review Comments in Go wiki • contexts ... based on https://go.dev/wiki/CodeReviewComments#contexts • dontpanic ... based on https://go.dev/wiki/CodeReviewComments#dont-panic • errorstrings ... based on https://go.dev/wiki/CodeReviewComments#error-strings • handlerrors ... based on https://go.dev/wiki/CodeReviewComments#handle-errors

Slide 23

Slide 23 text

23 gostyleͷ࣮૷

Slide 24

Slide 24 text

24 gostyleͷ࣮૷ go vetʹ౉͢vetίϚϯυͷ࡞Γํ • go vetͷ-vettoolͷϑϥάʹ౉͞ΕΔϓϩάϥϜ • ʢ1ͭͷํ๏ͱͯ͠ʣmain()Ͱ golang.org/x/tools/go/analysis/unitchecker.Main() Λ࣮ߦ͢Δ͜ͱͰ࣮૷Ͱ͖Δ • vetπʔϧ͸1ͭҎ্ͷgolang.org/x/tools/go/analysis.Analyzer͔Βߏ੒͞ΕΔ • ͜ͷAnalyzer1ͭ1͕ͭ੩తղੳΛͯ͠Կ͔͠ΒͷνΣοΫ͢ΔػೳΛ࣋ͭ • go vetͷσϑΥϧτͷڍಈ΋vetίϚϯυͱͯ͠࡞ΒΕ͍ͯΔʢmain()Ͱෳ਺ͷgolang.org/x/tools/go/ analysis.AnalyzerΛҾ਺ʹgolang.org/x/tools/go/analysis/unitchecker.Main()Λ࣮ߦ͍ͯ͠Δʣ • https://cs.opensource.google/go/go/+/refs/tags/go1.21.5:src/cmd/vet/main.go • https://cs.opensource.google/go/go/+/master:src/cmd/go/internal/vet/ vetflag.go;l=71-73;drc=e44b8b15b19058b7a22a859ab4159f924856f688

Slide 25

Slide 25 text

25 gostyleͷ࣮૷ Example: src/cmd/vet/main.go • unitcheker.Main() ؔ਺ΛϏϧτΠϯͷ *analysis.AnalyzerΛҾ਺ʹ࣮ߦ͍ͯ͠Δ͚ͩ • unitcheker.Main()͕ϑϥά΋ؚΊͯ͢΂ͯྑ͖ʹܭ Βͬͯ͘ΕΔ • ͭ·ΓɺvetίϚϯυͷ࣮ଶ͸ *analysis.Analyzer • gostyle΋ಉ༷ʹෳ਺ͷ *analysis.Analyzer ͷू߹ମ

Slide 26

Slide 26 text

26 gostyleͷ࣮૷ analysis.AnalyzerͷϑΟʔϧυʢanalysis.AnalyzerͰͰ͖Δ͜ͱʣ • Name: ໊લΛઃఆͰ͖Δ • ϑϥάͷ໊લͳͲʹ࢖ΘΕΔ • Doc, URL: આ໌΍URLΛઃఆͰ͖Δ • Flags: ઐ༻ͷϑϥάΛઃఆͰ͖Δ • Run: analysis.Pass Λड͚औͬͯղੳΛ࣮ߦ͢Δؔ਺ΛઃఆͰ͖ΔʢϝΠϯͷॲཧʣ • Requires: ґଘ͢ΔAnalyzerΛઃఆͰ͖Δ • ґଘ͢ΔAnalyzer͔Βͷ݁ՌΛ analysis.Pass.ResultOf[analysis.Analyzer] Ͱड͚औΔ͜ͱ͕ Ͱ͖Δ • ʢݸਓͷײ૝ʣgithub.com/spf13/cobra.Commandʹࣅ͍ͯΔ

Slide 27

Slide 27 text

27 gostyleͷ࣮૷ AnalyzerΛ·͍ͨͩઃఆϑΝΠϧΛ࣮ݱ͢Δ • Analyzer.RequiresΛ׆༻͢Δ 1. ઃఆϑΝΠϧΛಡΈࠐΉ͚ͩͷAnalyzerΛ࡞Δʢconfig.Loaderʣ 2. gostyleΛߏ੒͢ΔAnalyzerશͯͰ config.Loader ΛRequiresʹઃఆ͢Δ 3. analysis.Pass.ResultOf[config.Loader] ͔ΒઃఆΛड͚औͬͯ࢖༻͢Δ

Slide 28

Slide 28 text

28 gostyleͷ࣮૷ AnalyzerΛ·͍ͨͩઃఆϑΝΠϧΛ࣮ݱ͢Δ • Analyzer.RequiresΛ׆༻͢Δ 1. ઃఆϑΝΠϧΛಡΈࠐΉ͚ͩͷAnalyzerΛ࡞Δʢconfig.Loaderʣ 2. gostyleΛߏ੒͢ΔAnalyzerશͯͰ config.Loader ΛRequiresʹઃఆ͢Δ 3. analysis.Pass.ResultOf[config.Loader] ͔ΒઃఆΛड͚औͬͯ࢖༻͢Δ

Slide 29

Slide 29 text

29 gostyleͷ࣮૷ ίʔυίϝϯτʹΑΔAnalyzerͷߦ୯Ґͷ੍ޚΛ࣮ݱ͢Δ • analysis.Analyzerʹ͓͚ΔνΣοΫΤϥʔ͸analysis.Pass.Report΍analysis.Pass.ReportfͰϨ ϙʔτ͢Δ • analysis.Pass.ReportΛ࣮ߦ͢Δલʹίʔυίϝϯτͷ൑ఆΛ͢ΔϥούʔΛ࡞੒͢Δ͜ͱͰɺ ʮίʔυίϝϯτʹΑͬͯIgnore͞Ε͍ͯΕ͹ɺanalysis.Pass.ReportΛ࣮ߦ͠ͳ͍ʯ͜ͱͰ੍ ޚΛ࣮ݱ͢Δ • https://github.com/k1LoW/gostyle/tree/main/reporter • ίϝϯτ৘ใΛऔಘ͢ΔͨΊʹ github.com/gostaticanalysis/comment/passes/ commentmap.AnalyzerΛRequiresʹೖΕ͓ͯ͘

Slide 30

Slide 30 text

͓ΘΓʹ 30

Slide 31

Slide 31 text

• gostyle IS NOT Go Style • ϦϑΝϨϯεͱͳΔυΩϡϝϯτ͕͋ΔίʔσΟϯάελΠϧͷLinterΛ࡞͍ͬͯΔ • ϓϩδΣΫτ͝ͱͷLinter͕͋ͬͯ΋ྑ͍ʢ͠ɺ࣮ࡍʹ࡞͍ͬͯͨΓ͢Δʣ • AnalyzerΛ·ͱΊͯ unitcheker.Main() Λ࣮ߦ͢Δ͚ͩͰ΋OK • ͱ͜ΖͰΈͳ͞ΜνʔϜͷίʔσΟϯάελΠϧͲ͏͍ͯ͠·͢ʁ 31 ͓ΘΓʹ ͓ΘΓʹ

Slide 32

Slide 32 text

Thank You! Thank You! 32