Yes! 'mvn dependency:tree' showed I get an old jline bundle 
(org.apache.servicemix.bundles.jline:jar:0.9.94_1) via my Neo4j client 
dependency.
Adding an exclusion to the dependency and my example does work.

  package org.example;

  import jline.TerminalFactory;
  import org.apache.karaf.shell.commands.Command;
  import org.apache.karaf.shell.console.OsgiCommandSupport;

  @Command(scope = "example", name = "term-wdith", description = "get the terminal 
width")
  public class TermWidthCmd extends OsgiCommandSupport{

      protected Object doExecute() throws Exception {
          int w = TerminalFactory.get().getWidth();
          System.out.println("w="+w);

          return null;
      }
  }

Thanks a lot Guillaume!
-Max


On 12/07/2016 11:58 AM, Guillaume Nodet wrote:
Can you run a "mvn dependency:tree" on your bundle  ? I do suspect you have a 
jline 1.x somewhere, as found by the maven bundle plugin when computing the package 
version.

2016-12-07 20:06 GMT+01:00 Max Spring <[email protected] 
<mailto:[email protected]>>:

    Yes, I probably have here some build issue going on.

    I've got the jline bundle v2.13.0 in my container:

    | karaf@root()> list -s -t 0 | grep jline
    |  22 | Active   |  30 | 2.13.0           | jline
    |
    | karaf@root()> bundle:headers 22
    |
    | JLine (22)
    | ----------
    | Archiver-Version = Plexus Archiver
    | Originally-Created-By = Apache Maven Bundle Plugin
    | Created-By = Apache Maven Bundle Plugin
    | Manifest-Version = 1.0
    | Bnd-LastModified = 1439224319120
    | Build-Jdk = 1.8.0_45
    | Built-By = gnodet
    | Tool = Bnd-2.4.1.201501161923
    |
    | Bundle-License = http://www.opensource.org/licenses/bsd-license.php 
<http://www.opensource.org/licenses/bsd-license.php>
    | Bundle-ManifestVersion = 2
    | Bundle-SymbolicName = jline
    | Bundle-Version = 2.13.0
    | Bundle-Name = JLine
    | Bundle-Description = Sonatype helps open source projects to set up Maven 
repositories on https://oss.sonatype.org/
    |
    | Require-Capability =
    |       osgi.ee <http://osgi.ee>;filter:=(&(osgi.ee 
<http://osgi.ee>=JavaSE)(version=1.5))
    |
    | Export-Package =
    |       jline;uses:=jline.internal;version=2.13.0,
    |       jline.console;uses:="jline,jline.console.completer,jline.co 
<http://jline.co>nsole.history";version=2.13.0,
    |       jline.console.completer;uses:=jline.console;version=2.13.0,
    |       jline.console.history;version=2.13.0,
    |       jline.console.internal;version=2.13.0,
    |       jline.internal;version=2.13.0,
    |       org.fusesource.jansi;version=1.11

    The Maven artifact with version 2.13 is identical to the cached bundle (not 
sure why the Maven artifact doesn't have the micro version, though):

    | $ diff karaf/data/cache/bundle22/version0.0/bundle.jar 
~/.m2/repository/jline/jline/2.13/jline-2.13.jar; echo $?
    | 0

    If I do this in my POM

    |   <dependencies>
    |     ...
    |     <dependency>
    |       <groupId>jline</groupId>
    |       <artifactId>jline</artifactId>
    |       <version>2.13</version>
    |     </dependency>
    |     ...
    |   </dependencies>
    |
    |   <build>
    |     <plugins>
    |       <plugin>
    |         <groupId>org.apache.felix</groupId>
    |         <artifactId>maven-bundle-plugin</artifactId>
    |         <inherited>true</inherited>
    |         <extensions>true</extensions>
    |         <configuration>
    |           <instructions>
    |             
<Bundle-SymbolicName>${project.artifactId}</Bundle-SymbolicName>
    |           </instructions>
    |         </configuration>
    |       </plugin>
    |     </plugins>
    |   </build>

    then when I try to install my feature which references my bundle with the 
example command, I get:

    | karaf@root()> feature:install my-feature
    | no such process "maven/boot" to wait for
    | Error executing command: Can't install feature my-feature/0.0.0:
    | Could not start bundle mvn:org.example/example-bundle/1.0.0-SNAPSHOT in feature(s) 
example-bundle-1.0.0-SNAPSHOT: Unresolved constraint in bundle example-bundle [195]: 
Unable to resolve 195.0: missing requirement [195.0] osgi.wiring.package; 
(&(osgi.wiring.package=jline)(version>=0.9.0)(!(version>=1.0.0)))

    But when I explicitly specify the version of the jline package, my bundle 
does install:

    |   <dependencies>
    |     ...
    |     <dependency>
    |       <groupId>jline</groupId>
    |       <artifactId>jline</artifactId>
    |       <version>2.13</version>
    |     </dependency>
    |     ...
    |   </dependencies>
    |
    |   <build>
    |     <plugins>
    |       <plugin>
    |         <groupId>org.apache.felix</groupId>
    |         <artifactId>maven-bundle-plugin</artifactId>
    |         <inherited>true</inherited>
    |         <extensions>true</extensions>
    |         <configuration>
    |           <instructions>
    |             
<Bundle-SymbolicName>${project.artifactId}</Bundle-SymbolicName>
    |              <Import-Package>
    |                jline*;version="2.13.0",
    |                *
    |              </Import-Package>
    |           </instructions>
    |         </configuration>
    |       </plugin>
    |     </plugins>
    |   </build>

    I guess this leads to my bundle not finding the correct Terminal classes.

    -Max


    On 12/07/2016 10:42 AM, Guillaume Nodet wrote:

        The second approach should definitely work, see
          
https://github.com/apache/karaf/blob/karaf-3.0.x/shell/commands/src/main/java/org/apache/karaf/shell/commands/impl/MoreAction.java#L40
 
<https://github.com/apache/karaf/blob/karaf-3.0.x/shell/commands/src/main/java/org/apache/karaf/shell/commands/impl/MoreAction.java#L40>

        The exception is a bit unexpected.  Maybe you're compiling against a 
very old version of jline ? In JLine 1.x, the Terminal was an abstract class, 
but it has been changed to an interface in jline 2.x.

        2016-12-07 19:16 GMT+01:00 Max Spring <[email protected] 
<mailto:[email protected]> <mailto:[email protected] 
<mailto:[email protected]>>>:


            Is there a way to get the actual jline terminal object in a Karaf 
command?
            I want to format the command output depending on the terminal width.
            I'm on Ubuntu 16.04, Java 1.8.0_60-x64, and Karaf 3.0.5.

            This one

              package org.example;

              import jline.TerminalFactory;
              import org.apache.karaf.shell.commands.Command;
              import org.apache.karaf.shell.console.OsgiCommandSupport;

              @Command(scope = "example", name = "term-wdith", description = "get 
the terminal width")
              public class TermWidthCmd extends OsgiCommandSupport{

                  protected Object doExecute() throws Exception {
                      int w = TerminalFactory.get().getTerminalWidth();

                      return null;
                  }
              }

            gives:

            | 2016-12-07 10:10:17,443 | ERROR | l for user karaf | ShellUtil    
                    | 27 - org.apache.karaf.shell.console - 3.0.5 | Exception 
caught while executing command
            | java.lang.IncompatibleClassChangeError: Found interface 
jline.Terminal, but class was expected
            |       at org.example.TermWidthCmd.doExecute(TermWidthCmd.java:11)
            |       at 
org.apache.karaf.shell.console.AbstractAction.execute(AbstractAction.java:33)
            |       at 
org.apache.karaf.shell.console.OsgiCommandSupport.execute(OsgiCommandSupport.java:39)
            |       at 
org.apache.karaf.shell.commands.basic.AbstractCommand.execute(AbstractCommand.java:33)
            |       at 
Proxy68e7a8f7_5f52_4001_8cfa_f4b37a3fc958.execute(Unknown Source)
            |       at 
Proxy68e7a8f7_5f52_4001_8cfa_f4b37a3fc958.execute(Unknown Source)
            |       at 
org.apache.felix.gogo.runtime.CommandProxy.execute(CommandProxy.java:78)
            |       at 
org.apache.felix.gogo.runtime.Closure.executeCmd(Closure.java:480)
            |       at 
org.apache.felix.gogo.runtime.Closure.executeStatement(Closure.java:406)
            |       at org.apache.felix.gogo.runtime.Pipe.run(Pipe.java:108)
            |       at 
org.apache.felix.gogo.runtime.Closure.execute(Closure.java:182)
            |       at 
org.apache.felix.gogo.runtime.Closure.execute(Closure.java:119)
            |       at 
org.apache.felix.gogo.runtime.CommandSessionImpl.execute(CommandSessionImpl.java:94)
            |       at 
org.apache.karaf.shell.console.impl.jline.ConsoleImpl.run(ConsoleImpl.java:210)
            |       at 
org.apache.karaf.shell.console.impl.jline.LocalConsoleManager$2$1$1.run(LocalConsoleManager.java:109)
            |       at java.security.AccessController.doPrivileged(Native 
Method)[:1.8.0_60]
            |       at 
org.apache.karaf.jaas.modules.JaasHelper.doAs(JaasHelper.java:57)[28:org.apache.karaf.jaas.modules:3.0.5]
            |       at 
org.apache.karaf.shell.console.impl.jline.LocalConsoleManager$2$1.run(LocalConsoleManager.java:102)[27:org.apache.karaf.shell.console:3.0.5]

            The 2nd approach

              package org.example;

              import jline.NoInterruptUnixTerminal;
              import jline.Terminal;
              import org.apache.karaf.shell.commands.Command;
              import org.apache.karaf.shell.console.OsgiCommandSupport;

              @Command(scope = "example", name = "term-wdith", description = "get 
the terminal width")
              public class TermWidthCmd extends OsgiCommandSupport{

                  protected Object doExecute() throws Exception {
                      Terminal term = session != null ? (Terminal) 
session.get(".jline.terminal") : null;
                      NoInterruptUnixTerminal uterm = 
(NoInterruptUnixTerminal)term;
                      int w = term.getTerminalWidth();

                      return null;
                  }
              }

            basically gives the same exception:

            | 2016-12-07 10:09:11,964 | ERROR | l for user karaf | ShellUtil    
                    | 27 - org.apache.karaf.shell.console - 3.0.5 | Exception 
caught while executing command
            | java.lang.IncompatibleClassChangeError: Found interface 
jline.Terminal, but class was expected
            |       at org.example.TermWidthCmd.doExecute(TermWidthCmd.java:14)
            |       at 
org.apache.karaf.shell.console.AbstractAction.execute(AbstractAction.java:33)
            |       at 
org.apache.karaf.shell.console.OsgiCommandSupport.execute(OsgiCommandSupport.java:39)
            |       at 
org.apache.karaf.shell.commands.basic.AbstractCommand.execute(AbstractCommand.java:33)
            |       at 
Proxy1c55bc35_2cb4_47b2_b9f4_f593e49a68ce.execute(Unknown Source)
            |       at 
Proxy1c55bc35_2cb4_47b2_b9f4_f593e49a68ce.execute(Unknown Source)
            |       at 
org.apache.felix.gogo.runtime.CommandProxy.execute(CommandProxy.java:78)
            |       at 
org.apache.felix.gogo.runtime.Closure.executeCmd(Closure.java:480)
            |       at 
org.apache.felix.gogo.runtime.Closure.executeStatement(Closure.java:406)
            |       at org.apache.felix.gogo.runtime.Pipe.run(Pipe.java:108)
            |       at 
org.apache.felix.gogo.runtime.Closure.execute(Closure.java:182)
            |       at 
org.apache.felix.gogo.runtime.Closure.execute(Closure.java:119)
            |       at 
org.apache.felix.gogo.runtime.CommandSessionImpl.execute(CommandSessionImpl.java:94)
            |       at 
org.apache.karaf.shell.console.impl.jline.ConsoleImpl.run(ConsoleImpl.java:210)
            |       at 
org.apache.karaf.shell.console.impl.jline.LocalConsoleManager$2$1$1.run(LocalConsoleManager.java:109)
            |       at java.security.AccessController.doPrivileged(Native 
Method)[:1.8.0_60]
            |       at 
org.apache.karaf.jaas.modules.JaasHelper.doAs(JaasHelper.java:57)[28:org.apache.karaf.jaas.modules:3.0.5]
            |       at 
org.apache.karaf.shell.console.impl.jline.LocalConsoleManager$2$1.run(LocalConsoleManager.java:102)[27:org.apache.karaf.shell.console:3.0.5]

            What am I missing?

            Thanks!
            -Max




        --
        ------------------------
        Guillaume Nodet
        ------------------------
        Red Hat, Open Source Integration

        Email: [email protected] <mailto:[email protected]> <mailto:[email protected] 
<mailto:[email protected]>>
        Web: http://fusesource.com <http://fusesource.com/>
        Blog: http://gnodet.blogspot.com/





--
------------------------
Guillaume Nodet
------------------------
Red Hat, Open Source Integration

Email: [email protected] <mailto:[email protected]>
Web: http://fusesource.com <http://fusesource.com/>
Blog: http://gnodet.blogspot.com/


Reply via email to