mirror of
https://github.com/clap-rs/clap
synced 2024-12-14 23:02:31 +00:00
commit
ce724d8f61
6 changed files with 185 additions and 22 deletions
33
CHANGELOG.md
33
CHANGELOG.md
|
@ -1,3 +1,36 @@
|
||||||
|
<a name="v2.6.0"></a>
|
||||||
|
## v2.6.0 (2016-06-14)
|
||||||
|
|
||||||
|
|
||||||
|
#### Improvements
|
||||||
|
|
||||||
|
* removes extra newline from help output ([86e61d19](https://github.com/kbknapp/clap-rs/commit/86e61d19a748fb9870fcf1175308984e51ca1115))
|
||||||
|
* allows printing version to any io::Write object ([921f5f79](https://github.com/kbknapp/clap-rs/commit/921f5f7916597f1d028cd4a65bfe76a01c801724))
|
||||||
|
* removes extra newline when printing version ([7e2e2cbb](https://github.com/kbknapp/clap-rs/commit/7e2e2cbb4a8a0f050bb8072a376f742fc54b8589))
|
||||||
|
* **Aliases:** improves readability of asliases in help messages ([ca511de7](https://github.com/kbknapp/clap-rs/commit/ca511de71f5b8c2ac419f1b188658e8c63b67846), closes [#526](https://github.com/kbknapp/clap-rs/issues/526), [#529](https://github.com/kbknapp/clap-rs/issues/529))
|
||||||
|
* **Usage Strings:** improves the default usage string when only a single positional arg is present ([ec86f2da](https://github.com/kbknapp/clap-rs/commit/ec86f2dada1545a63fc72355e22fcdc4c466c215), closes [#518](https://github.com/kbknapp/clap-rs/issues/518))
|
||||||
|
|
||||||
|
#### Features
|
||||||
|
|
||||||
|
* **Help:** allows wrapping at specified term width (Even on Windows!) ([1761dc0d](https://github.com/kbknapp/clap-rs/commit/1761dc0d27d0d621229d792be40c36fbf65c3014), closes [#451](https://github.com/kbknapp/clap-rs/issues/451))
|
||||||
|
* **Settings:**
|
||||||
|
* adds new setting to stop delimiting values with -- or TrailingVarArg ([fc3e0f5a](https://github.com/kbknapp/clap-rs/commit/fc3e0f5afda6d24cdb3c4676614beebe13e1e870), closes [#511](https://github.com/kbknapp/clap-rs/issues/511))
|
||||||
|
* one can now set an AppSetting which is propogated down through child subcommands ([e2341835](https://github.com/kbknapp/clap-rs/commit/e23418351a3b98bf08dfd7744bc14377c70d59ee), closes [#519](https://github.com/kbknapp/clap-rs/issues/519))
|
||||||
|
* **Subcommands:** adds support for visible aliases ([7b10e7f8](https://github.com/kbknapp/clap-rs/commit/7b10e7f8937a07fdb8d16a6d8df79ce78d080cd3), closes [#522](https://github.com/kbknapp/clap-rs/issues/522))
|
||||||
|
|
||||||
|
#### Bug Fixes
|
||||||
|
|
||||||
|
* fixes bug where args are printed out of order with templates ([05abb534](https://github.com/kbknapp/clap-rs/commit/05abb534864764102031a0d402e64ac65867aa87))
|
||||||
|
* fixes bug where one can't override version or help flags ([90d7d6a2](https://github.com/kbknapp/clap-rs/commit/90d7d6a2ea8240122dd9bf8d82d3c4f5ebb5c703), closes [#514](https://github.com/kbknapp/clap-rs/issues/514))
|
||||||
|
* fixes issue where before_help wasn't printed ([b3faff60](https://github.com/kbknapp/clap-rs/commit/b3faff6030f76a23f26afcfa6a90169002ed7106))
|
||||||
|
* **Help:** `App::before_help` and `App::after_help` now correctly wrap ([1f4da767](https://github.com/kbknapp/clap-rs/commit/1f4da7676e6e71aa8dda799f3eeefad105a47819), closes [#516](https://github.com/kbknapp/clap-rs/issues/516))
|
||||||
|
* **Settings:** fixes bug where new color settings couldn't be converted from strs ([706a7c11](https://github.com/kbknapp/clap-rs/commit/706a7c11b0900be594de6d5a3121938eff197602))
|
||||||
|
* **Subcommands:** subcommands with aliases now display help of the aliased subcommand ([5354d14b](https://github.com/kbknapp/clap-rs/commit/5354d14b51f189885ba110e01e6b76cca3752992), closes [#521](https://github.com/kbknapp/clap-rs/issues/521))
|
||||||
|
* **Windows:** fixes a failing windows build ([01e7dfd6](https://github.com/kbknapp/clap-rs/commit/01e7dfd6c07228c0be6695b3c7bf9370d82860d4))
|
||||||
|
* **YAML:** adds missing YAML methods for App and Arg ([e468faf3](https://github.com/kbknapp/clap-rs/commit/e468faf3f05950fd9f72d84b69aa2061e91c6c64), closes [#528](https://github.com/kbknapp/clap-rs/issues/528))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<a name="v2.5.2"></a>
|
<a name="v2.5.2"></a>
|
||||||
### v2.5.2 (2016-05-31)
|
### v2.5.2 (2016-05-31)
|
||||||
|
|
||||||
|
|
25
README.md
25
README.md
|
@ -38,6 +38,24 @@ Created by [gh-md-toc](https://github.com/ekalinin/github-markdown-toc)
|
||||||
|
|
||||||
## What's New
|
## What's New
|
||||||
|
|
||||||
|
Here's the highlights for v2.6.0
|
||||||
|
|
||||||
|
* **Global Settings:** One can now set an `AppSetting` which is propogated down through child subcommands
|
||||||
|
* **Terminal Wrapping:** Allows wrapping at specified term width (Even on Windows!) (can now set an absolute width to "smart" wrap at)
|
||||||
|
* **SubCommands/Aliases:** adds support for visible aliases for subcommands (i.e. aliases that are dipslayed in the help message)
|
||||||
|
* **Subcommands/Aliases:** when viewing the help of an alias, it now display help of the aliased subcommand
|
||||||
|
* Improves the default usage string when only a single positional arg is present
|
||||||
|
* Adds new setting to stop delimiting values with `--` or `AppSettings::TrailingVarArg`
|
||||||
|
* `App::before_help` and `App::after_help` now correctly wrap
|
||||||
|
* Fixes bug where positional args are printed out of order when using templates
|
||||||
|
* Fixes bug where one can't override the auto-generated version or help flags
|
||||||
|
* Fixes issue where `App::before_help` wasn't printed
|
||||||
|
* Fixes a failing windows build
|
||||||
|
* Fixes bug where new color settings couldn't be converted from strings
|
||||||
|
* Adds missing YAML methods for App and Arg
|
||||||
|
* Allows printing version to any io::Write object
|
||||||
|
* Removes extra newline from help and version output
|
||||||
|
|
||||||
Here's what's new in v.2.5.2
|
Here's what's new in v.2.5.2
|
||||||
|
|
||||||
* Removes trailing newlines from help and version output
|
* Removes trailing newlines from help and version output
|
||||||
|
@ -86,8 +104,6 @@ An example of the optional colored help:
|
||||||
|
|
||||||
Here's the highlights from v2.2.0
|
Here's the highlights from v2.2.0
|
||||||
|
|
||||||
#### Features
|
|
||||||
|
|
||||||
* **Help text auto wraps and aligns at term width!** - Long help strings will now properly wrap and align to term width on Linux and OS X (and presumably Unix too). This can be turned off as well.
|
* **Help text auto wraps and aligns at term width!** - Long help strings will now properly wrap and align to term width on Linux and OS X (and presumably Unix too). This can be turned off as well.
|
||||||
* **Can customize the order of opts, flags, and subcommands in help messages** - Instead of using the default alphabetical order, you can now re-arrange the order of your args and subcommands in help message. This helps to emphasize more popular or important options.
|
* **Can customize the order of opts, flags, and subcommands in help messages** - Instead of using the default alphabetical order, you can now re-arrange the order of your args and subcommands in help message. This helps to emphasize more popular or important options.
|
||||||
* **Can auto-derive the order from declaration order** - Have a bunch of args or subcommmands to re-order? You can now just derive the order from the declaration order!
|
* **Can auto-derive the order from declaration order** - Have a bunch of args or subcommmands to re-order? You can now just derive the order from the declaration order!
|
||||||
|
@ -101,13 +117,8 @@ An example of the help text wrapping at term width:
|
||||||
|
|
||||||
In v2.1.2
|
In v2.1.2
|
||||||
|
|
||||||
#### New Features
|
|
||||||
|
|
||||||
* **Default Values**: Args can now specify default values
|
* **Default Values**: Args can now specify default values
|
||||||
* **Next Line Help**: Args can have help strings on the line following the argument (useful for long arguments, or those with many values). This can be set command-wide or for individual args
|
* **Next Line Help**: Args can have help strings on the line following the argument (useful for long arguments, or those with many values). This can be set command-wide or for individual args
|
||||||
|
|
||||||
#### Improvements
|
|
||||||
|
|
||||||
* **Documentation Examples**: The examples in the documentation have been vastly improved
|
* **Documentation Examples**: The examples in the documentation have been vastly improved
|
||||||
|
|
||||||
For full details, see [CHANGELOG.md](https://github.com/kbknapp/clap-rs/blob/master/CHANGELOG.md)
|
For full details, see [CHANGELOG.md](https://github.com/kbknapp/clap-rs/blob/master/CHANGELOG.md)
|
||||||
|
|
103
src/app/help.rs
103
src/app/help.rs
|
@ -80,7 +80,7 @@ pub struct Help<'a> {
|
||||||
writer: &'a mut Write,
|
writer: &'a mut Write,
|
||||||
next_line_help: bool,
|
next_line_help: bool,
|
||||||
hide_pv: bool,
|
hide_pv: bool,
|
||||||
term_w: Option<usize>,
|
term_w: usize,
|
||||||
color: bool,
|
color: bool,
|
||||||
cizer: Colorizer,
|
cizer: Colorizer,
|
||||||
}
|
}
|
||||||
|
@ -88,13 +88,16 @@ pub struct Help<'a> {
|
||||||
// Public Functions
|
// Public Functions
|
||||||
impl<'a> Help<'a> {
|
impl<'a> Help<'a> {
|
||||||
/// Create a new `Help` instance.
|
/// Create a new `Help` instance.
|
||||||
pub fn new(w: &'a mut Write, next_line_help: bool, hide_pv: bool, color: bool, cizer: Colorizer) -> Self {
|
pub fn new(w: &'a mut Write, next_line_help: bool, hide_pv: bool, color: bool, cizer: Colorizer, term_w: Option<usize>) -> Self {
|
||||||
debugln!("fn=Help::new;");
|
debugln!("fn=Help::new;");
|
||||||
Help {
|
Help {
|
||||||
writer: w,
|
writer: w,
|
||||||
next_line_help: next_line_help,
|
next_line_help: next_line_help,
|
||||||
hide_pv: hide_pv,
|
hide_pv: hide_pv,
|
||||||
term_w: term::dimensions().map(|(w, _)| w),
|
term_w: match term_w {
|
||||||
|
Some(width) => width,
|
||||||
|
None => term::dimensions().map(|(w, _)| w).unwrap_or(120),
|
||||||
|
},
|
||||||
color: color,
|
color: color,
|
||||||
cizer: cizer,
|
cizer: cizer,
|
||||||
}
|
}
|
||||||
|
@ -132,7 +135,7 @@ impl<'a> Help<'a> {
|
||||||
use_stderr: stderr,
|
use_stderr: stderr,
|
||||||
when: parser.color(),
|
when: parser.color(),
|
||||||
};
|
};
|
||||||
Self::new(w, nlh, hide_v, color, cizer).write_help(parser)
|
Self::new(w, nlh, hide_v, color, cizer, parser.meta.term_w).write_help(parser)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Writes the parser help to the wrapped stream.
|
/// Writes the parser help to the wrapped stream.
|
||||||
|
@ -324,6 +327,89 @@ impl<'a> Help<'a> {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn write_before_after_help<'b, 'c>(&mut self, h: &str) -> io::Result<()> {
|
||||||
|
debugln!("fn=before_help;");
|
||||||
|
let mut help = String::new();
|
||||||
|
// determine if our help fits or needs to wrap
|
||||||
|
let width = self.term_w;
|
||||||
|
debugln!("Term width...{}", width);
|
||||||
|
let too_long = str_width(h) >= width;
|
||||||
|
debugln!("Too long...{:?}", too_long);
|
||||||
|
|
||||||
|
debug!("Too long...");
|
||||||
|
if too_long {
|
||||||
|
sdebugln!("Yes");
|
||||||
|
help.push_str(h);
|
||||||
|
debugln!("help: {}", help);
|
||||||
|
debugln!("help width: {}", str_width(&*help));
|
||||||
|
// Determine how many newlines we need to insert
|
||||||
|
debugln!("Usable space: {}", width);
|
||||||
|
let longest_w = {
|
||||||
|
let mut lw = 0;
|
||||||
|
for l in help.split(' ').map(|s| str_width(s)) {
|
||||||
|
if l > lw {
|
||||||
|
lw = l;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
lw
|
||||||
|
};
|
||||||
|
debugln!("Longest word...{}", longest_w);
|
||||||
|
debug!("Enough space to wrap...");
|
||||||
|
if longest_w < width {
|
||||||
|
sdebugln!("Yes");
|
||||||
|
let mut indices = vec![];
|
||||||
|
let mut idx = 0;
|
||||||
|
loop {
|
||||||
|
idx += width - 1;
|
||||||
|
if idx >= help.len() {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// 'a' arbitrary non space char
|
||||||
|
if help.chars().nth(idx).unwrap_or('a') != ' ' {
|
||||||
|
idx = find_idx_of_space(&*help, idx);
|
||||||
|
}
|
||||||
|
debugln!("Adding idx: {}", idx);
|
||||||
|
debugln!("At {}: {:?}", idx, help.chars().nth(idx));
|
||||||
|
indices.push(idx);
|
||||||
|
if str_width(&help[idx..]) <= width {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (i, idx) in indices.iter().enumerate() {
|
||||||
|
debugln!("iter;i={},idx={}", i, idx);
|
||||||
|
let j = idx + (2 * i);
|
||||||
|
debugln!("removing: {}", j);
|
||||||
|
debugln!("at {}: {:?}", j, help.chars().nth(j));
|
||||||
|
help.remove(j);
|
||||||
|
help.insert(j, '{');
|
||||||
|
help.insert(j + 1, 'n');
|
||||||
|
help.insert(j + 2, '}');
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
sdebugln!("No");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
sdebugln!("No");
|
||||||
|
}
|
||||||
|
let help = if !help.is_empty() {
|
||||||
|
&*help
|
||||||
|
} else {
|
||||||
|
help.push_str(h);
|
||||||
|
&*help
|
||||||
|
};
|
||||||
|
if help.contains("{n}") {
|
||||||
|
if let Some(part) = help.split("{n}").next() {
|
||||||
|
try!(write!(self.writer, "{}", part));
|
||||||
|
}
|
||||||
|
for part in help.split("{n}").skip(1) {
|
||||||
|
try!(write!(self.writer, "\n{}", part));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
try!(write!(self.writer, "{}", help));
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
/// Writes argument's help to the wrapped stream.
|
/// Writes argument's help to the wrapped stream.
|
||||||
fn help<'b, 'c>(&mut self, arg: &ArgWithDisplay<'b, 'c>, longest: usize) -> io::Result<()> {
|
fn help<'b, 'c>(&mut self, arg: &ArgWithDisplay<'b, 'c>, longest: usize) -> io::Result<()> {
|
||||||
debugln!("fn=help;");
|
debugln!("fn=help;");
|
||||||
|
@ -336,10 +422,9 @@ impl<'a> Help<'a> {
|
||||||
longest + 12
|
longest + 12
|
||||||
};
|
};
|
||||||
// determine if our help fits or needs to wrap
|
// determine if our help fits or needs to wrap
|
||||||
let width = self.term_w.unwrap_or(0);
|
let width = self.term_w;
|
||||||
debugln!("Term width...{}", width);
|
debugln!("Term width...{}", width);
|
||||||
let too_long = self.term_w.is_some() &&
|
let too_long = spcs + str_width(h) + str_width(&*spec_vals) >= width;
|
||||||
(spcs + str_width(h) + str_width(&*spec_vals) >= width);
|
|
||||||
debugln!("Too long...{:?}", too_long);
|
debugln!("Too long...{:?}", too_long);
|
||||||
|
|
||||||
// Is help on next line, if so newline + 2x tab
|
// Is help on next line, if so newline + 2x tab
|
||||||
|
@ -603,7 +688,7 @@ impl<'a> Help<'a> {
|
||||||
pub fn write_default_help(&mut self, parser: &Parser) -> ClapResult<()> {
|
pub fn write_default_help(&mut self, parser: &Parser) -> ClapResult<()> {
|
||||||
debugln!("fn=write_default_help;");
|
debugln!("fn=write_default_help;");
|
||||||
if let Some(h) = parser.meta.pre_help {
|
if let Some(h) = parser.meta.pre_help {
|
||||||
try!(write!(self.writer, "{}", h));
|
try!(self.write_before_after_help(h));
|
||||||
try!(self.writer.write(b"\n\n"));
|
try!(self.writer.write(b"\n\n"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -638,7 +723,7 @@ impl<'a> Help<'a> {
|
||||||
if flags || opts || pos || subcmds {
|
if flags || opts || pos || subcmds {
|
||||||
try!(self.writer.write(b"\n\n"));
|
try!(self.writer.write(b"\n\n"));
|
||||||
}
|
}
|
||||||
try!(write!(self.writer, "{}", h));
|
try!(self.write_before_after_help(h));
|
||||||
}
|
}
|
||||||
|
|
||||||
self.writer.flush().map_err(Error::from)
|
self.writer.flush().map_err(Error::from)
|
||||||
|
|
|
@ -13,6 +13,7 @@ pub struct AppMeta<'b> {
|
||||||
pub usage: Option<String>,
|
pub usage: Option<String>,
|
||||||
pub help_str: Option<&'b str>,
|
pub help_str: Option<&'b str>,
|
||||||
pub disp_ord: usize,
|
pub disp_ord: usize,
|
||||||
|
pub term_w: Option<usize>,
|
||||||
pub template: Option<&'b str>,
|
pub template: Option<&'b str>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -32,6 +33,7 @@ impl<'b> Default for AppMeta<'b> {
|
||||||
disp_ord: 999,
|
disp_ord: 999,
|
||||||
template: None,
|
template: None,
|
||||||
aliases: None,
|
aliases: None,
|
||||||
|
term_w: None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -61,6 +63,7 @@ impl<'b> Clone for AppMeta<'b> {
|
||||||
disp_ord: self.disp_ord,
|
disp_ord: self.disp_ord,
|
||||||
template: self.template,
|
template: self.template,
|
||||||
aliases: self.aliases.clone(),
|
aliases: self.aliases.clone(),
|
||||||
|
term_w: self.term_w,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -482,6 +482,35 @@ impl<'a, 'b> App<'a, 'b> {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Sets the terminal width at which to wrap help messages. Defaults to `120`.
|
||||||
|
///
|
||||||
|
/// `clap` automatically tries to determine the terminal width on Unix, Linux, and OSX if the
|
||||||
|
/// `wrap_help` cargo "feature" has been used while compiling. If the terminal width cannot be
|
||||||
|
/// determined, `clap` defaults to `120`.
|
||||||
|
///
|
||||||
|
/// **NOTE:** This setting applies globally and *not* on a per-command basis.
|
||||||
|
///
|
||||||
|
/// **NOTE:** This setting must be set **before** any subcommands are added!
|
||||||
|
///
|
||||||
|
/// # Platform Specific
|
||||||
|
///
|
||||||
|
/// Only Unix, Linux, and OSX support automatic determination of terminal width. Even on those
|
||||||
|
/// platforms, this setting is useful if for any reason the terminal width cannot be
|
||||||
|
/// determined.
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```no_run
|
||||||
|
/// # use clap::App;
|
||||||
|
/// App::new("myprog")
|
||||||
|
/// .set_term_width(80)
|
||||||
|
/// # ;
|
||||||
|
/// ```
|
||||||
|
pub fn set_term_width(mut self, width: usize) -> Self {
|
||||||
|
self.p.meta.term_w = Some(width);
|
||||||
|
self
|
||||||
|
}
|
||||||
|
|
||||||
/// Adds an [argument] to the list of valid possibilties.
|
/// Adds an [argument] to the list of valid possibilties.
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
|
@ -640,7 +669,7 @@ impl<'a, 'b> App<'a, 'b> {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Allows adding a [`SubCommand`] alias that functions exactly like those defined with
|
/// Allows adding a [`SubCommand`] alias that functions exactly like those defined with
|
||||||
/// [`App::alias`], except that they are visible inside the help message.
|
/// [`App::alias`], except that they are visible inside the help message.
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
|
@ -664,7 +693,7 @@ impl<'a, 'b> App<'a, 'b> {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Allows adding multiple [`SubCommand`] aliases that functions exactly like those defined
|
/// Allows adding multiple [`SubCommand`] aliases that functions exactly like those defined
|
||||||
/// with [`App::aliases`], except that they are visible inside the help message.
|
/// with [`App::aliases`], except that they are visible inside the help message.
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
|
|
|
@ -195,6 +195,8 @@ impl<'a, 'b> Parser<'a, 'b>
|
||||||
|
|
||||||
pub fn add_subcommand(&mut self, mut subcmd: App<'a, 'b>) {
|
pub fn add_subcommand(&mut self, mut subcmd: App<'a, 'b>) {
|
||||||
debugln!("fn=Parser::add_subcommand;");
|
debugln!("fn=Parser::add_subcommand;");
|
||||||
|
debugln!("Term widnth...{:?}", self.p.meta.term_w);
|
||||||
|
subcmd.p.meta.term_w = self.meta.term_w;
|
||||||
debug!("Is help...");
|
debug!("Is help...");
|
||||||
if subcmd.p.meta.name == "help" {
|
if subcmd.p.meta.name == "help" {
|
||||||
sdebugln!("Yes");
|
sdebugln!("Yes");
|
||||||
|
@ -532,14 +534,14 @@ impl<'a, 'b> Parser<'a, 'b>
|
||||||
}
|
}
|
||||||
} else if let Some(c) = sc.subcommands
|
} else if let Some(c) = sc.subcommands
|
||||||
.iter()
|
.iter()
|
||||||
.filter(|s|
|
.filter(|s|
|
||||||
if let Some(ref als) = s.p
|
if let Some(ref als) = s.p
|
||||||
.meta
|
.meta
|
||||||
.aliases {
|
.aliases {
|
||||||
als.iter()
|
als.iter()
|
||||||
.any(|&(a, _)| &a == &&*cmd.to_string_lossy())
|
.any(|&(a, _)| &a == &&*cmd.to_string_lossy())
|
||||||
} else {
|
} else {
|
||||||
false
|
false
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
.next()
|
.next()
|
||||||
|
|
Loading…
Reference in a new issue