All checks were successful
continuous-integration/drone/push Build is passing
252 lines
6.1 KiB
TypeScript
252 lines
6.1 KiB
TypeScript
/**
|
|
* A CLI option. Supports basic comparative, and set-based validation.
|
|
* @class
|
|
*/
|
|
export abstract class CLIOption<T> {
|
|
|
|
/**
|
|
* Do we use the whitelist?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected useWhitelist = false
|
|
|
|
/**
|
|
* Do we use the blacklist?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected useBlacklist = false
|
|
|
|
/**
|
|
* Do we use the less-than comparison?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected useLessThan = false
|
|
|
|
/**
|
|
* Do we use the greater-than comparison?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected useGreaterThan = false
|
|
|
|
/**
|
|
* Do we use the equality operator?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected useEquality = false
|
|
|
|
/**
|
|
* Is this option optional?
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected isOptional = false
|
|
|
|
/**
|
|
* Whitelisted values.
|
|
* @type {Array<*>}
|
|
* @private
|
|
*/
|
|
protected whitelistItems: T[] = []
|
|
|
|
/**
|
|
* Blacklisted values.
|
|
* @type {Array<*>}
|
|
* @private
|
|
*/
|
|
protected blacklistItems: T[] = []
|
|
|
|
/**
|
|
* Value to be compared in less than.
|
|
* @type {*}
|
|
* @private
|
|
*/
|
|
protected lessThanValue?: T
|
|
|
|
/**
|
|
* If true, the less than will be less than or equal to.
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected lessThanBit = false
|
|
|
|
/**
|
|
* Value to be compared in greater than.
|
|
* @type {*}
|
|
* @private
|
|
*/
|
|
protected greaterThanValue?: T
|
|
|
|
/**
|
|
* If true, the greater than will be greater than or equal to.
|
|
* @type {boolean}
|
|
* @private
|
|
*/
|
|
protected greaterThanBit = false
|
|
|
|
/**
|
|
* The value to be used to check equality.
|
|
* @type {*}
|
|
* @private
|
|
*/
|
|
protected equalityValue?: T
|
|
|
|
/**
|
|
* Whitelist the specified item or items and enable the whitelist.
|
|
* @param {...*} items - the items to whitelist
|
|
*/
|
|
whitelist(...items: T[]): this {
|
|
this.useWhitelist = true
|
|
items.forEach(item => this.whitelistItems.push(item))
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Blacklist the specified item or items and enable the blacklist.
|
|
* @param {...*} items - the items to blacklist
|
|
*/
|
|
blacklist(...items: T[]): this {
|
|
this.useBlacklist = true
|
|
items.forEach(item => this.blacklistItems.push(item))
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Specifies the value to be used in less-than comparison and enables less-than comparison.
|
|
* @param {*} value
|
|
*/
|
|
lessThan(value: T): this {
|
|
this.useLessThan = true
|
|
this.lessThanValue = value
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Specifies the value to be used in less-than or equal-to comparison and enables that comparison.
|
|
* @param {*} value
|
|
*/
|
|
lessThanOrEqualTo(value: T): this {
|
|
this.lessThanBit = true
|
|
this.lessThan(value)
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Specifies the value to be used in greater-than comparison and enables that comparison.
|
|
* @param {*} value
|
|
*/
|
|
greaterThan(value: T): this {
|
|
this.useGreaterThan = true
|
|
this.greaterThanValue = value
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Specifies the value to be used in greater-than or equal-to comparison and enables that comparison.
|
|
* @param {*} value
|
|
*/
|
|
greaterThanOrEqualTo(value: T): this {
|
|
this.greaterThanBit = true
|
|
this.greaterThan(value)
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Specifies the value to be used in equality comparison and enables that comparison.
|
|
* @param {*} value
|
|
*/
|
|
equals(value: T): this {
|
|
this.useEquality = true
|
|
this.equalityValue = value
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Checks if the specified value passes the configured comparisons.
|
|
* @param value
|
|
* @returns {boolean}
|
|
*/
|
|
validate(value: T): boolean {
|
|
let isValid = true
|
|
if ( this.useEquality ) {
|
|
isValid = isValid && (this.equalityValue === value)
|
|
}
|
|
|
|
if ( this.useLessThan && typeof this.lessThanValue !== 'undefined' ) {
|
|
if ( this.lessThanBit ) {
|
|
isValid = isValid && (value <= this.lessThanValue)
|
|
} else {
|
|
isValid = isValid && (value < this.lessThanValue)
|
|
}
|
|
}
|
|
|
|
if ( this.useGreaterThan && typeof this.greaterThanValue !== 'undefined' ) {
|
|
if ( this.greaterThanBit ) {
|
|
isValid = isValid && (value >= this.greaterThanValue)
|
|
} else {
|
|
isValid = isValid && (value > this.greaterThanValue)
|
|
}
|
|
}
|
|
|
|
if ( this.useWhitelist ) {
|
|
isValid = isValid && this.whitelistItems.some(x => {
|
|
return x === value
|
|
})
|
|
}
|
|
|
|
if ( this.useBlacklist ) {
|
|
isValid = isValid && !(this.blacklistItems.some(x => x === value))
|
|
}
|
|
|
|
return isValid
|
|
}
|
|
|
|
/**
|
|
* Sets the Option as optional.
|
|
*/
|
|
optional(): this {
|
|
this.isOptional = true
|
|
return this
|
|
}
|
|
|
|
/**
|
|
* Get the argument name. Should be overridden by child classes.
|
|
* @returns {string}
|
|
*/
|
|
abstract getArgumentName(): string
|
|
|
|
/**
|
|
* Get an array of strings denoting the human-readable requirements for this option to be valid.
|
|
* @returns {Array<string>}
|
|
*/
|
|
getRequirementDisplays(): string[] {
|
|
const clauses = []
|
|
|
|
if ( this.useBlacklist ) {
|
|
clauses.push(`must not be one of: ${this.blacklistItems.map(x => String(x)).join(', ')}`)
|
|
}
|
|
|
|
if ( this.useWhitelist ) {
|
|
clauses.push(`must be one of: ${this.whitelistItems.map(x => String(x)).join(', ')}`)
|
|
}
|
|
|
|
if ( this.useGreaterThan ) {
|
|
clauses.push(`must be greater than${this.greaterThanBit ? ' or equal to' : ''}: ${String(this.greaterThanValue)}`)
|
|
}
|
|
|
|
if ( this.useLessThan ) {
|
|
clauses.push(`must be less than${this.lessThanBit ? ' or equal to' : ''}: ${String(this.lessThanValue)}`)
|
|
}
|
|
|
|
if ( this.useEquality ) {
|
|
clauses.push(`must be equal to: ${String(this.equalityValue)}`)
|
|
}
|
|
|
|
return clauses
|
|
}
|
|
}
|