termenv.go 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. package termenv
  2. import (
  3. "errors"
  4. "github.com/mattn/go-isatty"
  5. )
  6. var (
  7. // ErrStatusReport gets returned when the terminal can't be queried.
  8. ErrStatusReport = errors.New("unable to retrieve status report")
  9. )
  10. const (
  11. // Escape character
  12. ESC = '\x1b'
  13. // Bell
  14. BEL = '\a'
  15. // Control Sequence Introducer
  16. CSI = string(ESC) + "["
  17. // Operating System Command
  18. OSC = string(ESC) + "]"
  19. // String Terminator
  20. ST = string(ESC) + `\`
  21. )
  22. func (o *Output) isTTY() bool {
  23. if o.assumeTTY || o.unsafe {
  24. return true
  25. }
  26. if len(o.environ.Getenv("CI")) > 0 {
  27. return false
  28. }
  29. if o.TTY() == nil {
  30. return false
  31. }
  32. return isatty.IsTerminal(o.TTY().Fd())
  33. }
  34. // ColorProfile returns the supported color profile:
  35. // Ascii, ANSI, ANSI256, or TrueColor.
  36. func ColorProfile() Profile {
  37. return output.ColorProfile()
  38. }
  39. // ForegroundColor returns the terminal's default foreground color.
  40. func ForegroundColor() Color {
  41. return output.ForegroundColor()
  42. }
  43. // BackgroundColor returns the terminal's default background color.
  44. func BackgroundColor() Color {
  45. return output.BackgroundColor()
  46. }
  47. // HasDarkBackground returns whether terminal uses a dark-ish background.
  48. func HasDarkBackground() bool {
  49. return output.HasDarkBackground()
  50. }
  51. // EnvNoColor returns true if the environment variables explicitly disable color output
  52. // by setting NO_COLOR (https://no-color.org/)
  53. // or CLICOLOR/CLICOLOR_FORCE (https://bixense.com/clicolors/)
  54. // If NO_COLOR is set, this will return true, ignoring CLICOLOR/CLICOLOR_FORCE
  55. // If CLICOLOR=="0", it will be true only if CLICOLOR_FORCE is also "0" or is unset.
  56. func (o *Output) EnvNoColor() bool {
  57. return o.environ.Getenv("NO_COLOR") != "" || (o.environ.Getenv("CLICOLOR") == "0" && !o.cliColorForced())
  58. }
  59. // EnvNoColor returns true if the environment variables explicitly disable color output
  60. // by setting NO_COLOR (https://no-color.org/)
  61. // or CLICOLOR/CLICOLOR_FORCE (https://bixense.com/clicolors/)
  62. // If NO_COLOR is set, this will return true, ignoring CLICOLOR/CLICOLOR_FORCE
  63. // If CLICOLOR=="0", it will be true only if CLICOLOR_FORCE is also "0" or is unset.
  64. func EnvNoColor() bool {
  65. return output.EnvNoColor()
  66. }
  67. // EnvColorProfile returns the color profile based on environment variables set
  68. // Supports NO_COLOR (https://no-color.org/)
  69. // and CLICOLOR/CLICOLOR_FORCE (https://bixense.com/clicolors/)
  70. // If none of these environment variables are set, this behaves the same as ColorProfile()
  71. // It will return the Ascii color profile if EnvNoColor() returns true
  72. // If the terminal does not support any colors, but CLICOLOR_FORCE is set and not "0"
  73. // then the ANSI color profile will be returned.
  74. func EnvColorProfile() Profile {
  75. return output.EnvColorProfile()
  76. }
  77. // EnvColorProfile returns the color profile based on environment variables set
  78. // Supports NO_COLOR (https://no-color.org/)
  79. // and CLICOLOR/CLICOLOR_FORCE (https://bixense.com/clicolors/)
  80. // If none of these environment variables are set, this behaves the same as ColorProfile()
  81. // It will return the Ascii color profile if EnvNoColor() returns true
  82. // If the terminal does not support any colors, but CLICOLOR_FORCE is set and not "0"
  83. // then the ANSI color profile will be returned.
  84. func (o *Output) EnvColorProfile() Profile {
  85. if o.EnvNoColor() {
  86. return Ascii
  87. }
  88. p := o.ColorProfile()
  89. if o.cliColorForced() && p == Ascii {
  90. return ANSI
  91. }
  92. return p
  93. }
  94. func (o *Output) cliColorForced() bool {
  95. if forced := o.environ.Getenv("CLICOLOR_FORCE"); forced != "" {
  96. return forced != "0"
  97. }
  98. return false
  99. }