github.com/elves/elvish@v0.15.0/website/cmd/elvdoc/main_test.go (about)

     1  package main
     2  
     3  import (
     4  	"io/ioutil"
     5  	"os"
     6  	"path"
     7  	"strings"
     8  	"testing"
     9  
    10  	"github.com/elves/elvish/pkg/testutil"
    11  )
    12  
    13  var extractTests = []struct {
    14  	name    string
    15  	src     string
    16  	ns      string
    17  	wantDoc string
    18  }{
    19  	{name: "Empty source", src: "", wantDoc: ""},
    20  	{name: "Source without elvdoc", src: "package x\n// not elvdoc", wantDoc: ""},
    21  
    22  	{
    23  		name: "Source with doc-fn",
    24  		src: `package x
    25  
    26  //elvdoc:fn cd
    27  //
    28  // Changes directory.
    29  `,
    30  		wantDoc: `# Functions
    31  
    32  ## cd
    33  
    34  Changes directory.
    35  `,
    36  	},
    37  
    38  	{
    39  		name: "Source with unstable symbols",
    40  		src: `package x
    41  
    42  //elvdoc:fn -b
    43  // -B.
    44  
    45  //elvdoc:fn a
    46  // A.
    47  
    48  //elvdoc:fn b
    49  // B.
    50  `,
    51  		ns: "ns:",
    52  		wantDoc: `# Functions
    53  
    54  ## ns:a
    55  A.
    56  
    57  ## ns:b
    58  B.
    59  
    60  ## ns:-b
    61  -B.
    62  `,
    63  	},
    64  	{
    65  		name: "Source with multiple doc-fn",
    66  		src: `package x
    67  
    68  //elvdoc:fn b
    69  // B.
    70  
    71  //elvdoc:fn a
    72  // A.
    73  
    74  //elvdoc:fn c
    75  // C.
    76  `,
    77  		wantDoc: `# Functions
    78  
    79  ## a
    80  A.
    81  
    82  ## b
    83  B.
    84  
    85  ## c
    86  C.
    87  `,
    88  	},
    89  
    90  	{
    91  		name: "Source with both doc-fn and var-fn",
    92  		src: `package x
    93  
    94  //elvdoc:fn a
    95  // A.
    96  
    97  //elvdoc:var b
    98  // B.
    99  `,
   100  		wantDoc: `# Variables
   101  
   102  ## $b
   103  B.
   104  
   105  
   106  # Functions
   107  
   108  ## a
   109  A.
   110  `,
   111  	},
   112  
   113  	{
   114  		name: "Source without trailing newline",
   115  		src: `package x
   116  
   117  //elvdoc:fn a
   118  // A.`,
   119  		wantDoc: `# Functions
   120  
   121  ## a
   122  A.
   123  `,
   124  	},
   125  	{
   126  		name: "Source with both doc-fn and var-fn",
   127  		src: `package x
   128  
   129  //elvdoc:fn a
   130  // A.
   131  
   132  //elvdoc:var b
   133  // B.
   134  `,
   135  		ns: "ns:",
   136  		wantDoc: `# Variables
   137  
   138  ## $ns:b
   139  B.
   140  
   141  
   142  # Functions
   143  
   144  ## ns:a
   145  A.
   146  `,
   147  	}}
   148  
   149  func TestExtract(t *testing.T) {
   150  	for _, test := range extractTests {
   151  		t.Run(test.name, func(t *testing.T) {
   152  			r := strings.NewReader(test.src)
   153  			w := new(strings.Builder)
   154  			extract(r, test.ns, w)
   155  			compare(t, w.String(), test.wantDoc)
   156  		})
   157  	}
   158  }
   159  
   160  func TestRun_MultipleFiles(t *testing.T) {
   161  	teardown := setup()
   162  	defer teardown()
   163  
   164  	w := new(strings.Builder)
   165  	run([]string{"a.go", "b.go"}, emptyReader, w)
   166  	compare(t, w.String(), `# Variables
   167  
   168  ## $v2
   169  
   170  Variable 2 from b.
   171  
   172  
   173  # Functions
   174  
   175  ## f1
   176  
   177  Function 1 from b.
   178  
   179  ## f2
   180  
   181  Function 2 from a.
   182  
   183      Some indented code.
   184  `)
   185  }
   186  
   187  func TestRun_Directory(t *testing.T) {
   188  	teardown := setup()
   189  	defer teardown()
   190  
   191  	w := new(strings.Builder)
   192  	run([]string{"-dir", "."}, emptyReader, w)
   193  	compare(t, w.String(), `# Variables
   194  
   195  ## $v1
   196  
   197  Variable 1 from c.
   198  
   199  ## $v2
   200  
   201  Variable 2 from b.
   202  
   203  
   204  # Functions
   205  
   206  ## f1
   207  
   208  Function 1 from b.
   209  
   210  ## f2
   211  
   212  Function 2 from a.
   213  
   214      Some indented code.
   215  `)
   216  }
   217  
   218  func TestRun_Filter(t *testing.T) {
   219  	teardown := setup()
   220  	defer teardown()
   221  
   222  	in := strings.NewReader(`Some text.
   223  
   224  @elvdoc a.go
   225  
   226  Some more text.`)
   227  	out := new(strings.Builder)
   228  	run([]string{"-filter"}, in, out)
   229  	compare(t, out.String(), `Some text.
   230  
   231  # Functions
   232  
   233  ## f2
   234  
   235  Function 2 from a.
   236  
   237      Some indented code.
   238  
   239  Some more text.
   240  `)
   241  }
   242  
   243  func compare(t *testing.T, got, want string) {
   244  	t.Helper()
   245  	if got != want {
   246  		t.Errorf("\n<<<<< Got\n%s\n=====\n%s\n>>>>> Want", got, want)
   247  	}
   248  }
   249  
   250  // Set up a temporary directory with several .go files and directories
   251  // containing .go files. Returns a teardown function. Useful for testing the run
   252  // function.
   253  func setup() func() {
   254  	_, teardown := testutil.InTestDir()
   255  	writeFile("a.go", `package x
   256  //elvdoc:fn f2
   257  //
   258  // Function 2 from a.
   259  //
   260  //     Some indented code.
   261  `)
   262  	writeFile("b.go", `package x
   263  //elvdoc:fn f1
   264  //
   265  // Function 1 from b.
   266  
   267  //elvdoc:var v2
   268  //
   269  // Variable 2 from b.
   270  `)
   271  	writeFile("c.go", `package x
   272  //elvdoc:var v1
   273  //
   274  // Variable 1 from c.
   275  `)
   276  	writeFile("notgo.gox", `package x
   277  //elvdoc:var wontappear
   278  //
   279  // This won't appear because it is not in a .go file.
   280  `)
   281  	// Subdirectories are ignored with -dir.
   282  	writeFile("subpkg/a.go", `package subpkg
   283  //elvdoc:fn subpkg:f
   284  //
   285  // Function f from subpkg/a.
   286  
   287  //elvdoc:var subpkg:v
   288  //
   289  // Variable v from subpkg/a.
   290  `)
   291  	return teardown
   292  }
   293  
   294  func writeFile(name, data string) {
   295  	dir := path.Dir(name)
   296  	err := os.MkdirAll(dir, 0700)
   297  	if err != nil {
   298  		panic(err)
   299  	}
   300  	ioutil.WriteFile(name, []byte(data), 0600)
   301  }