blob: 027598828a44e528142158b84a1325a272cd6002 [file]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package cli
import groovy.test.GroovyTestCase
abstract class CliBuilderTestCase extends GroovyTestCase {
abstract String getImportCliBuilder()
void testAnnotationsInterface() {
assertScript """
import cli.GreeterI
$importCliBuilder
// tag::annotationInterface[]
// import CliBuilder not shown
def cli = new CliBuilder(usage: 'groovy Greeter') // <1>
def argz = '--audience Groovologist'.split()
def options = cli.parseFromSpec(GreeterI, argz) // <2>
assert options.audience() == 'Groovologist' // <3>
argz = '-h Some Other Args'.split()
options = cli.parseFromSpec(GreeterI, argz) // <4>
assert options.help()
assert options.remaining() == ['Some', 'Other', 'Args'] // <5>
// end::annotationInterface[]
"""
}
void testAnnotationsClass() {
assertScript """
import cli.GreeterC
$importCliBuilder
// tag::annotationClass[]
// import CliBuilder not shown
def cli = new CliBuilder(usage: 'groovy Greeter [option]') // <1>
def options = new GreeterC() // <2>
def argz = '--audience Groovologist foo'.split()
cli.parseFromInstance(options, argz) // <3>
assert options.audience == 'Groovologist' // <4>
assert options.remaining == ['foo'] // <5>
// end::annotationClass[]
"""
}
// performs toString comparison of usage help - this isn't because we guarantee any specific output
// (hence expected is provided as a parameter) but we want to know when it changes significantly and
// in particular we want to ensure that no information that we expect to be there just disappears
protected void doTestAnnotationsInterfaceToString(String key, String expected) {
assertScript """
import cli.GreeterI
$importCliBuilder
def cli = new CliBuilder($key: 'groovy Greeter')
def options = cli.parseFromSpec(GreeterI, ['-h', 'Some', 'Other', 'Args'] as String[])
assert options.help()
assert options.remaining() == ['Some', 'Other', 'Args']
StringWriter sw = new StringWriter()
cli.writer = new PrintWriter(sw)
cli.usage()
assert '''$expected'''.normalize() == sw.toString().normalize()
"""
}
void testParseScript() {
def argz = '--audience Groovologist foo'.split()
new GroovyShell().run("""
$importCliBuilder
// tag::annotationScript[]
// import CliBuilder not shown
import groovy.cli.OptionField
import groovy.cli.UnparsedField
@OptionField String audience
@OptionField Boolean help
@UnparsedField List remaining
new CliBuilder().parseFromInstance(this, args)
assert audience == 'Groovologist'
assert remaining == ['foo']
// end::annotationScript[]
""", 'TestScript.groovy', argz)
}
void testWithArgument() {
assertScript """
$importCliBuilder
// tag::withArgument[]
// import CliBuilder not shown
def cli = new CliBuilder()
cli.a(args: 0, 'a arg') // <1>
cli.b(args: 1, 'b arg') // <2>
cli.c(args: 1, optionalArg: true, 'c arg') // <3>
def options = cli.parse('-a -b foo -c bar baz'.split()) // <4>
assert options.a == true
assert options.b == 'foo'
assert options.c == 'bar'
assert options.arguments() == ['baz']
options = cli.parse('-a -c -b foo bar baz'.split()) // <5>
assert options.a == true
assert options.c == true
assert options.b == 'foo'
assert options.arguments() == ['bar', 'baz']
// end::withArgument[]
"""
}
void testMultipleArgsAndOptionalValueSeparator() {
assertScript """
$importCliBuilder
// tag::multipleArgs[]
// import CliBuilder not shown
def cli = new CliBuilder()
cli.a(args: 2, 'a-arg')
cli.b(args: '2', valueSeparator: ',', 'b-arg') // <1>
cli.c(args: '+', valueSeparator: ',', 'c-arg') // <2>
def options = cli.parse('-a 1 2 3 4'.split()) // <3>
assert options.a == '1' // <4>
assert options.as == ['1', '2'] // <5>
assert options.arguments() == ['3', '4']
options = cli.parse('-a1 -a2 3'.split()) // <6>
assert options.as == ['1', '2']
assert options.arguments() == ['3']
options = cli.parse(['-b1,2']) // <7>
assert options.bs == ['1', '2']
options = cli.parse(['-c', '1'])
assert options.cs == ['1']
options = cli.parse(['-c1'])
assert options.cs == ['1']
options = cli.parse(['-c1,2,3'])
assert options.cs == ['1', '2', '3']
// end::multipleArgs[]
"""
}
void testWithArgumentInterface() {
assertScript """
import cli.WithArgsI
$importCliBuilder
// tag::withArgumentInterface[]
def cli = new CliBuilder()
def options = cli.parseFromSpec(WithArgsI, '-a -b foo -c bar baz'.split())
assert options.a()
assert options.b() == 'foo'
assert options.c() == ['bar']
assert options.remaining() == ['baz']
options = cli.parseFromSpec(WithArgsI, '-a -c -b foo bar baz'.split())
assert options.a()
assert options.c() == []
assert options.b() == 'foo'
assert options.remaining() == ['bar', 'baz']
// end::withArgumentInterface[]
"""
}
void testMultipleArgsAndOptionalValueSeparatorInterface() {
assertScript """
import cli.ValSepI
$importCliBuilder
// tag::multipleArgsInterface[]
def cli = new CliBuilder()
def options = cli.parseFromSpec(ValSepI, '-a 1 2 3 4'.split())
assert options.a() == ['1', '2']
assert options.remaining() == ['3', '4']
options = cli.parseFromSpec(ValSepI, '-a1 -a2 3'.split())
assert options.a() == ['1', '2']
assert options.remaining() == ['3']
options = cli.parseFromSpec(ValSepI, ['-b1,2'] as String[])
assert options.b() == ['1', '2']
options = cli.parseFromSpec(ValSepI, ['-c', '1'] as String[])
assert options.c() == ['1']
options = cli.parseFromSpec(ValSepI, ['-c1'] as String[])
assert options.c() == ['1']
options = cli.parseFromSpec(ValSepI, ['-c1,2,3'] as String[])
assert options.c() == ['1', '2', '3']
// end::multipleArgsInterface[]
"""
}
void testType() {
assertScript """
import java.math.RoundingMode
$importCliBuilder
// tag::withType[]
def argz = '''-a John -b -d 21 -e 1980 -f 3.5 -g 3.14159
-h cv.txt -i DOWN and some more'''.split()
def cli = new CliBuilder()
cli.a(type: String, 'a-arg')
cli.b(type: boolean, 'b-arg')
cli.c(type: Boolean, 'c-arg')
cli.d(type: int, 'd-arg')
cli.e(type: Long, 'e-arg')
cli.f(type: Float, 'f-arg')
cli.g(type: BigDecimal, 'g-arg')
cli.h(type: File, 'h-arg')
cli.i(type: RoundingMode, 'i-arg')
def options = cli.parse(argz)
assert options.a == 'John'
assert options.b
assert !options.c
assert options.d == 21
assert options.e == 1980L
assert options.f == 3.5f
assert options.g == 3.14159
assert options.h == new File('cv.txt')
assert options.i == RoundingMode.DOWN
assert options.arguments() == ['and', 'some', 'more']
// end::withType[]
"""
}
void testTypeMultiple() {
assertScript """
$importCliBuilder
// tag::withTypeMultiple[]
def argz = '''-j 3 4 5 -k1.5,2.5,3.5 and some more'''.split()
def cli = new CliBuilder()
cli.j(args: 3, type: int[], 'j-arg')
cli.k(args: '+', valueSeparator: ',', type: BigDecimal[], 'k-arg')
def options = cli.parse(argz)
assert options.js == [3, 4, 5] // <1>
assert options.j == [3, 4, 5] // <1>
assert options.k == [1.5, 2.5, 3.5]
assert options.arguments() == ['and', 'some', 'more']
// end::withTypeMultiple[]
"""
}
void testConvert() {
assertScript """
$importCliBuilder
// tag::withConvert[]
def argz = '''-a John -b Mary -d 2016-01-01 and some more'''.split()
def cli = new CliBuilder()
def lower = { it.toLowerCase() }
cli.a(convert: lower, 'a-arg')
cli.b(convert: { it.toUpperCase() }, 'b-arg')
cli.d(convert: { Date.parse('yyyy-MM-dd', it) }, 'd-arg')
def options = cli.parse(argz)
assert options.a == 'john'
assert options.b == 'MARY'
assert options.d.format('dd-MM-yyyy') == '01-01-2016'
assert options.arguments() == ['and', 'some', 'more']
// end::withConvert[]
"""
}
void testConvertInterface() {
assertScript """
import cli.WithConvertI
$importCliBuilder
// tag::withConvertInterface[]
Date newYears = Date.parse("yyyy-MM-dd", "2016-01-01")
def argz = '''-a John -b Mary -d 2016-01-01 and some more'''.split()
def cli = new CliBuilder()
def options = cli.parseFromSpec(WithConvertI, argz)
assert options.a() == 'john'
assert options.b() == 'MARY'
assert options.d() == newYears
assert options.remaining() == ['and', 'some', 'more']
// end::withConvertInterface[]
"""
}
void testDefaultValue() {
assertScript """
$importCliBuilder
// tag::withDefaultValue[]
def cli = new CliBuilder()
cli.f longOpt: 'from', type: String, args: 1, defaultValue: 'one', 'f option'
cli.t longOpt: 'to', type: int, defaultValue: '35', 't option'
def options = cli.parse('-f two'.split())
assert options.hasOption('f')
assert options.f == 'two'
assert !options.hasOption('t')
assert options.t == 35
options = cli.parse('-t 45'.split())
assert !options.hasOption('from')
assert options.from == 'one'
assert options.hasOption('to')
assert options.to == 45
// end::withDefaultValue[]
"""
}
void testDefaultValueInterface() {
assertScript """
$importCliBuilder
import cli.WithDefaultValueI
// tag::withDefaultValueInterface[]
def cli = new CliBuilder()
def options = cli.parseFromSpec(WithDefaultValueI, '-f two'.split())
assert options.from() == 'two'
assert options.to() == 35
options = cli.parseFromSpec(WithDefaultValueI, '-t 45'.split())
assert options.from() == 'one'
assert options.to() == 45
// end::withDefaultValueInterface[]
"""
}
void testTypeCheckedInterfaceRunner() {
assertScript """
$importCliBuilder
import cli.TypeCheckedI
import groovy.transform.TypeChecked
// tag::withTypeCheckedInterface[]
@TypeChecked
void testTypeCheckedInterface() {
def argz = "--name John --age 21 and some more".split()
def cli = new CliBuilder()
def options = cli.parseFromSpec(TypeCheckedI, argz)
String n = options.name()
int a = options.age()
assert n == 'John' && a == 21
assert options.remaining() == ['and', 'some', 'more']
}
// end::withTypeCheckedInterface[]
testTypeCheckedInterface()
"""
}
void testTypeCheckedRunner() {
assertScript """
$importCliBuilder
// tag::withTypeChecked[]
import groovy.cli.TypedOption
import groovy.transform.TypeChecked
@TypeChecked
void testTypeChecked() {
def cli = new CliBuilder()
TypedOption<String> name = cli.option(String, opt: 'n', longOpt: 'name', 'name option')
TypedOption<Integer> age = cli.option(Integer, longOpt: 'age', 'age option')
def argz = "--name John --age 21 and some more".split()
def options = cli.parse(argz)
String n = options[name]
int a = options[age]
assert n == 'John' && a == 21
assert options.arguments() == ['and', 'some', 'more']
}
// end::withTypeChecked[]
testTypeChecked()
"""
}
}