mirror of
https://codeberg.org/scip/rpnc.git
synced 2025-12-16 20:11:02 +01:00
Internal/add gh actions and tests (#3)
* add gh actions and templates * add show-versions in Makefile * force go 1.20 * added test facilities
This commit is contained in:
31
.github/ISSUE_TEMPLATE/bug_report.md
vendored
Normal file
31
.github/ISSUE_TEMPLATE/bug_report.md
vendored
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
---
|
||||||
|
name: Bug report
|
||||||
|
about: Create a report to help us improve
|
||||||
|
title: "[bug-report]"
|
||||||
|
labels: bug
|
||||||
|
assignees: TLINDEN
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
**Describtion**
|
||||||
|
<!-- Please provide a clear and concise description of the issue: -->
|
||||||
|
|
||||||
|
|
||||||
|
**Steps To Reproduce**
|
||||||
|
<!-- Please detail the steps to reproduce the behavior: -->
|
||||||
|
|
||||||
|
|
||||||
|
**Expected behavior**
|
||||||
|
<!-- What do you expected to happen instead? -->
|
||||||
|
|
||||||
|
|
||||||
|
**Version information**
|
||||||
|
<!--
|
||||||
|
Please provide as much version information as possible:
|
||||||
|
- if you have just installed a binary, provide the output of: rpn -v
|
||||||
|
- if you installed from source, provide the output of: make show-version
|
||||||
|
- provide additional details: operating system and version and shell environment
|
||||||
|
-->
|
||||||
|
|
||||||
|
|
||||||
|
**Additional informations**
|
||||||
23
.github/ISSUE_TEMPLATE/feature_request.md
vendored
Normal file
23
.github/ISSUE_TEMPLATE/feature_request.md
vendored
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
---
|
||||||
|
name: Feature request
|
||||||
|
about: Suggest a feature
|
||||||
|
title: "[feature-request]"
|
||||||
|
labels: feature-request
|
||||||
|
assignees: TLINDEN
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
**Describtion**
|
||||||
|
<!-- Please provide a clear and concise description of the feature you desire: -->
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
**Version information**
|
||||||
|
<!--
|
||||||
|
Just in case the feature is already present, please provide as
|
||||||
|
much version information as possible:
|
||||||
|
- if you have just installed a binary, provide the output of: rpn -v
|
||||||
|
- if you installed from source, provide the output of: make show-version
|
||||||
|
- provide additional details: operating system and version and shell environment
|
||||||
|
-->
|
||||||
|
|
||||||
36
.github/workflows/ci.yaml
vendored
Normal file
36
.github/workflows/ci.yaml
vendored
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
name: build-and-test-rpn
|
||||||
|
on: [push, pull_request]
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
strategy:
|
||||||
|
matrix:
|
||||||
|
version: [1.21]
|
||||||
|
os: [ubuntu-latest, windows-latest, macos-latest]
|
||||||
|
name: Build
|
||||||
|
runs-on: ${{ matrix.os }}
|
||||||
|
steps:
|
||||||
|
- name: Set up Go
|
||||||
|
uses: actions/setup-go@v3
|
||||||
|
with:
|
||||||
|
go-version: ${{ matrix.version }}
|
||||||
|
id: go
|
||||||
|
|
||||||
|
- name: checkout
|
||||||
|
uses: actions/checkout@v3
|
||||||
|
|
||||||
|
- name: build
|
||||||
|
run: go build
|
||||||
|
|
||||||
|
- name: test
|
||||||
|
run: make test
|
||||||
|
|
||||||
|
golangci:
|
||||||
|
name: lint
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/setup-go@v3
|
||||||
|
with:
|
||||||
|
go-version: 1.21
|
||||||
|
- uses: actions/checkout@v3
|
||||||
|
- name: golangci-lint
|
||||||
|
uses: golangci/golangci-lint-action@v3
|
||||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -1,3 +1,4 @@
|
|||||||
releases
|
releases
|
||||||
rpn
|
rpn
|
||||||
rpn.1
|
rpn.1
|
||||||
|
coverage.out
|
||||||
|
|||||||
17
Makefile
17
Makefile
@@ -39,10 +39,6 @@ ifdef HAVE_POD
|
|||||||
echo "var manpage = \`" >> $*.go
|
echo "var manpage = \`" >> $*.go
|
||||||
pod2text $*.pod >> $*.go
|
pod2text $*.pod >> $*.go
|
||||||
echo "\`" >> $*.go
|
echo "\`" >> $*.go
|
||||||
|
|
||||||
echo "var usage = \`" >> $*.go
|
|
||||||
awk '/SYNOPS/{f=1;next} /DESCR/{f=0} f' $*.pod | sed 's/^ //' >> $*.go
|
|
||||||
echo "\`" >> $*.go
|
|
||||||
endif
|
endif
|
||||||
|
|
||||||
buildlocal:
|
buildlocal:
|
||||||
@@ -59,7 +55,6 @@ clean:
|
|||||||
|
|
||||||
test:
|
test:
|
||||||
go test -v ./...
|
go test -v ./...
|
||||||
bash t/test.sh
|
|
||||||
|
|
||||||
singletest:
|
singletest:
|
||||||
@echo "Call like this: ''make singletest TEST=TestPrepareColumns MOD=lib"
|
@echo "Call like this: ''make singletest TEST=TestPrepareColumns MOD=lib"
|
||||||
@@ -77,3 +72,15 @@ buildall:
|
|||||||
|
|
||||||
release: buildall
|
release: buildall
|
||||||
gh release create v$(VERSION) --generate-notes releases/*
|
gh release create v$(VERSION) --generate-notes releases/*
|
||||||
|
|
||||||
|
show-versions: buildlocal
|
||||||
|
@echo "### rpn version:"
|
||||||
|
@./rpn -v
|
||||||
|
|
||||||
|
@echo
|
||||||
|
@echo "### go module versions:"
|
||||||
|
@go list -m all
|
||||||
|
|
||||||
|
@echo
|
||||||
|
@echo "### go version used for building:"
|
||||||
|
@grep -m 1 go go.mod
|
||||||
|
|||||||
@@ -1,3 +1,7 @@
|
|||||||
|
[](https://github.com/tlinden/rpnc/actions)
|
||||||
|
[](https://github.com/tlinden/rpnc/blob/master/LICENSE)
|
||||||
|
[](https://goreportcard.com/report/github.com/tlinden/rpnc)
|
||||||
|
|
||||||
## Reverse Polish Notation Calculator for the commandline
|
## Reverse Polish Notation Calculator for the commandline
|
||||||
|
|
||||||
This is a small commandline calculator which takes its input in
|
This is a small commandline calculator which takes its input in
|
||||||
|
|||||||
45
calc.go
45
calc.go
@@ -20,7 +20,6 @@ package main
|
|||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"math"
|
|
||||||
"os"
|
"os"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strconv"
|
"strconv"
|
||||||
@@ -376,50 +375,6 @@ func (c *Calc) Debug(msg string) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// do simple calculations
|
|
||||||
func (c *Calc) simple(op byte) {
|
|
||||||
c.stack.Backup()
|
|
||||||
|
|
||||||
for c.stack.Len() > 1 {
|
|
||||||
b := c.stack.Pop()
|
|
||||||
a := c.stack.Pop()
|
|
||||||
var x float64
|
|
||||||
|
|
||||||
c.Debug(fmt.Sprintf("evaluating: %.2f %c %.2f", a, op, b))
|
|
||||||
|
|
||||||
switch op {
|
|
||||||
case '+':
|
|
||||||
x = a + b
|
|
||||||
case '-':
|
|
||||||
x = a - b
|
|
||||||
case 'x':
|
|
||||||
fallthrough // alias for *
|
|
||||||
case '*':
|
|
||||||
x = a * b
|
|
||||||
case '/':
|
|
||||||
if b == 0 {
|
|
||||||
fmt.Println("error: division by null!")
|
|
||||||
return
|
|
||||||
}
|
|
||||||
x = a / b
|
|
||||||
case '^':
|
|
||||||
x = math.Pow(a, b)
|
|
||||||
default:
|
|
||||||
panic("invalid operator!")
|
|
||||||
}
|
|
||||||
|
|
||||||
c.stack.Push(x)
|
|
||||||
|
|
||||||
c.History("%f %c %f = %f", a, op, b, x)
|
|
||||||
|
|
||||||
if !c.batch {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
c.Result()
|
|
||||||
}
|
|
||||||
|
|
||||||
func (c *Calc) luafunc(funcname string) {
|
func (c *Calc) luafunc(funcname string) {
|
||||||
// called from calc loop
|
// called from calc loop
|
||||||
var x float64
|
var x float64
|
||||||
|
|||||||
141
calc_test.go
Normal file
141
calc_test.go
Normal file
@@ -0,0 +1,141 @@
|
|||||||
|
/*
|
||||||
|
Copyright © 2023 Thomas von Dein
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestCalc(t *testing.T) {
|
||||||
|
calc := NewCalc()
|
||||||
|
|
||||||
|
var tests = []struct {
|
||||||
|
name string
|
||||||
|
cmd string
|
||||||
|
exp float64
|
||||||
|
batch bool
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
name: "plus",
|
||||||
|
cmd: `15 15 +`,
|
||||||
|
exp: 30,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "power",
|
||||||
|
cmd: `4 2 ^`,
|
||||||
|
exp: 16,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "minus",
|
||||||
|
cmd: `100 50 -`,
|
||||||
|
exp: 50,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "multi",
|
||||||
|
cmd: `4 4 x`,
|
||||||
|
exp: 16,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "divide",
|
||||||
|
cmd: `10 2 /`,
|
||||||
|
exp: 5,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "percent",
|
||||||
|
cmd: `400 20 %`,
|
||||||
|
exp: 80,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "percent-minus",
|
||||||
|
cmd: `400 20 %-`,
|
||||||
|
exp: 320,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "percent-plus",
|
||||||
|
cmd: `400 20 %+`,
|
||||||
|
exp: 480,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "mod",
|
||||||
|
cmd: `9 2 mod`,
|
||||||
|
exp: 1,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "sqrt",
|
||||||
|
cmd: `16 sqrt`,
|
||||||
|
exp: 4,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "ceil",
|
||||||
|
cmd: `15.5 ceil`,
|
||||||
|
exp: 16,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "dim",
|
||||||
|
cmd: `6 4 dim`,
|
||||||
|
exp: 2,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "batch-sum",
|
||||||
|
cmd: `2 2 2 2 sum`,
|
||||||
|
exp: 8,
|
||||||
|
batch: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "batch-median",
|
||||||
|
cmd: `1 2 3 4 5 median`,
|
||||||
|
exp: 3,
|
||||||
|
batch: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "batch-mean",
|
||||||
|
cmd: `2 2 8 2 2 mean`,
|
||||||
|
exp: 3.2,
|
||||||
|
batch: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "batch-min",
|
||||||
|
cmd: `1 2 3 4 5 min`,
|
||||||
|
exp: 1,
|
||||||
|
batch: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "batch-max",
|
||||||
|
cmd: `1 2 3 4 5 max`,
|
||||||
|
exp: 5,
|
||||||
|
batch: true,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, tt := range tests {
|
||||||
|
testname := fmt.Sprintf("cmd-%s-expect-%.2f",
|
||||||
|
tt.name, tt.exp)
|
||||||
|
|
||||||
|
t.Run(testname, func(t *testing.T) {
|
||||||
|
calc.batch = tt.batch
|
||||||
|
calc.Eval(tt.cmd)
|
||||||
|
got := calc.Result()
|
||||||
|
calc.stack.Clear()
|
||||||
|
if got != tt.exp {
|
||||||
|
t.Errorf("calc failed:\n+++ got: %f\n--- want: %f",
|
||||||
|
got, tt.exp)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
14
rpn.go
14
rpn.go
@@ -222,17 +222,3 @@ AUTHORS
|
|||||||
Thomas von Dein tom AT vondein DOT org
|
Thomas von Dein tom AT vondein DOT org
|
||||||
|
|
||||||
`
|
`
|
||||||
var usage = `
|
|
||||||
|
|
||||||
Usage: rpn [-bdvh] [<operator>]
|
|
||||||
|
|
||||||
Options:
|
|
||||||
-b, --batchmode enable batch mode
|
|
||||||
-d, --debug enable debug mode
|
|
||||||
-v, --version show version
|
|
||||||
-h, --help show help
|
|
||||||
|
|
||||||
When <operator> is given, batch mode ist automatically enabled. Use
|
|
||||||
this only when working with stdin. E.g.: echo "2 3 4 5" | rpn +
|
|
||||||
|
|
||||||
`
|
|
||||||
|
|||||||
190
stack_test.go
Normal file
190
stack_test.go
Normal file
@@ -0,0 +1,190 @@
|
|||||||
|
/*
|
||||||
|
Copyright © 2023 Thomas von Dein
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestPush(t *testing.T) {
|
||||||
|
t.Run("push", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
|
||||||
|
if s.linklist.Back().Value != 5.0 {
|
||||||
|
t.Errorf("push failed:\n+++ got: %f\n--- want: %f",
|
||||||
|
s.linklist.Back().Value, 5.0)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPop(t *testing.T) {
|
||||||
|
t.Run("pop", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
got := s.Pop()
|
||||||
|
|
||||||
|
if got != 5.0 {
|
||||||
|
t.Errorf("pop failed:\n+++ got: %f\n--- want: %f",
|
||||||
|
got, 5.0)
|
||||||
|
}
|
||||||
|
|
||||||
|
if s.Len() != 0 {
|
||||||
|
t.Errorf("stack not empty after pop()")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPops(t *testing.T) {
|
||||||
|
t.Run("pops", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
s.Push(5)
|
||||||
|
s.Push(5)
|
||||||
|
s.Pop()
|
||||||
|
|
||||||
|
if s.Len() != 2 {
|
||||||
|
t.Errorf("stack len not correct after pop:\n+++ got: %d\n--- want: %d",
|
||||||
|
s.Len(), 2)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestShift(t *testing.T) {
|
||||||
|
t.Run("shift", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Shift()
|
||||||
|
|
||||||
|
if s.Len() != 0 {
|
||||||
|
t.Errorf("stack not empty after shift()")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestClear(t *testing.T) {
|
||||||
|
t.Run("clear", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
s.Push(5)
|
||||||
|
s.Push(5)
|
||||||
|
s.Clear()
|
||||||
|
|
||||||
|
if s.Len() != 0 {
|
||||||
|
t.Errorf("stack not empty after clear()")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestLast(t *testing.T) {
|
||||||
|
t.Run("last", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
got := s.Last()
|
||||||
|
|
||||||
|
if len(got) != 1 {
|
||||||
|
t.Errorf("last failed:\n+++ got: %d elements\n--- want: %d elements",
|
||||||
|
len(got), 1)
|
||||||
|
}
|
||||||
|
|
||||||
|
if got[0] != 5.0 {
|
||||||
|
t.Errorf("last failed:\n+++ got: %f\n--- want: %f",
|
||||||
|
got, 5.0)
|
||||||
|
}
|
||||||
|
|
||||||
|
if s.Len() != 1 {
|
||||||
|
t.Errorf("stack modified after last()")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestAll(t *testing.T) {
|
||||||
|
t.Run("all", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
list := []float64{2, 4, 6, 8}
|
||||||
|
|
||||||
|
for _, item := range list {
|
||||||
|
s.Push(item)
|
||||||
|
}
|
||||||
|
|
||||||
|
got := s.All()
|
||||||
|
|
||||||
|
if len(got) != len(list) {
|
||||||
|
t.Errorf("all failed:\n+++ got: %d elements\n--- want: %d elements",
|
||||||
|
len(got), len(list))
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 1; i < len(list); i++ {
|
||||||
|
if got[i] != list[i] {
|
||||||
|
t.Errorf("all failed (element %d):\n+++ got: %f\n--- want: %f",
|
||||||
|
i, got[i], list[i])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if s.Len() != len(list) {
|
||||||
|
t.Errorf("stack modified after last()")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBackupRestore(t *testing.T) {
|
||||||
|
t.Run("shift", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
s.Push(5)
|
||||||
|
s.Backup()
|
||||||
|
s.Clear()
|
||||||
|
s.Restore()
|
||||||
|
|
||||||
|
if s.Len() != 1 {
|
||||||
|
t.Errorf("stack not correctly restored()")
|
||||||
|
}
|
||||||
|
|
||||||
|
a := s.Pop()
|
||||||
|
if a != 5.0 {
|
||||||
|
t.Errorf("stack not identical to old revision:\n+++ got: %f\n--- want: %f",
|
||||||
|
a, 5.0)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestReverse(t *testing.T) {
|
||||||
|
t.Run("reverse", func(t *testing.T) {
|
||||||
|
s := NewStack()
|
||||||
|
list := []float64{2, 4, 6}
|
||||||
|
reverse := []float64{6, 4, 2}
|
||||||
|
|
||||||
|
for _, item := range list {
|
||||||
|
s.Push(item)
|
||||||
|
}
|
||||||
|
|
||||||
|
s.Reverse()
|
||||||
|
|
||||||
|
got := s.All()
|
||||||
|
|
||||||
|
if len(got) != len(list) {
|
||||||
|
t.Errorf("all failed:\n+++ got: %d elements\n--- want: %d elements",
|
||||||
|
len(got), len(list))
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 1; i < len(reverse); i++ {
|
||||||
|
if got[i] != reverse[i] {
|
||||||
|
t.Errorf("reverse failed (element %d):\n+++ got: %f\n--- want: %f",
|
||||||
|
i, got[i], list[i])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
32
util_test.go
Normal file
32
util_test.go
Normal file
@@ -0,0 +1,32 @@
|
|||||||
|
/*
|
||||||
|
Copyright © 2023 Thomas von Dein
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestContains(t *testing.T) {
|
||||||
|
list := []string{"a", "b", "c"}
|
||||||
|
|
||||||
|
t.Run("contains", func(t *testing.T) {
|
||||||
|
if !contains(list, "a") {
|
||||||
|
t.Errorf("a in [a,b,c] not found")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user