Skip to content

Commit

Permalink
Merge pull request #40457 from gayaldassanayake/bal-tool2
Browse files Browse the repository at this point in the history
Improvements/ bug fixes for bal tool feature
  • Loading branch information
gayaldassanayake authored May 18, 2023
2 parents 427f58d + b7aace6 commit a67704c
Show file tree
Hide file tree
Showing 11 changed files with 106 additions and 117 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -54,4 +54,7 @@ public class Constants {
public static final String START_DEBUG_ADAPTER_COMMAND = "start-debugger-adapter";
public static final String HELP_COMMAND = "help";
public static final String HOME_COMMAND = "home";

public static final String TOML_EXT = ".toml";
public static final String DIST_TOOL_TOML_PREFIX = "dist-";
}
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@
import java.util.Optional;
import java.util.stream.Stream;

import static io.ballerina.cli.cmd.Constants.DIST_TOOL_TOML_PREFIX;
import static io.ballerina.cli.cmd.Constants.TOML_EXT;
import static io.ballerina.cli.cmd.Constants.TOOL_COMMAND;
import static io.ballerina.projects.util.ProjectConstants.BALA_DIR_NAME;
import static io.ballerina.projects.util.ProjectConstants.BAL_TOOLS_TOML;
Expand Down Expand Up @@ -80,7 +82,8 @@ public class ToolCommand implements BLauncherCmd {
private final PrintStream outStream;
private final PrintStream errStream;

private final String distSpecificToolsTomlName = "dist-" + RepoUtils.getBallerinaShortVersion() + ".toml";
private final String distSpecificToolsTomlName = DIST_TOOL_TOML_PREFIX + RepoUtils.getBallerinaShortVersion()
+ TOML_EXT;
Path distSpecificToolsTomlPath = Path.of(
System.getProperty(CommandUtil.USER_HOME), HOME_REPO_DEFAULT_DIRNAME, CONFIG_DIR,
distSpecificToolsTomlName);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,52 +17,15 @@
*/
package io.ballerina.cli.launcher;

import io.ballerina.cli.BLauncherCmd;
import io.ballerina.runtime.api.values.BError;
import picocli.CommandLine;

import java.io.IOException;
import java.io.PrintStream;
import java.nio.file.Files;
import java.nio.file.LinkOption;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

import static io.ballerina.cli.cmd.Constants.ADD_COMMAND;
import static io.ballerina.cli.cmd.Constants.ASYNCAPI_COMMAND;
import static io.ballerina.cli.cmd.Constants.BINDGEN_COMMAND;
import static io.ballerina.cli.cmd.Constants.BUILD_COMMAND;
import static io.ballerina.cli.cmd.Constants.CLEAN_COMMAND;
import static io.ballerina.cli.cmd.Constants.DEPRECATE_COMMAND;
import static io.ballerina.cli.cmd.Constants.DIST_COMMAND;
import static io.ballerina.cli.cmd.Constants.DOC_COMMAND;
import static io.ballerina.cli.cmd.Constants.FORMAT_COMMAND;
import static io.ballerina.cli.cmd.Constants.GRAPHQL_COMMAND;
import static io.ballerina.cli.cmd.Constants.GRAPH_COMMAND;
import static io.ballerina.cli.cmd.Constants.GRPC_COMMAND;
import static io.ballerina.cli.cmd.Constants.HELP_COMMAND;
import static io.ballerina.cli.cmd.Constants.HOME_COMMAND;
import static io.ballerina.cli.cmd.Constants.INIT_COMMAND;
import static io.ballerina.cli.cmd.Constants.NEW_COMMAND;
import static io.ballerina.cli.cmd.Constants.OPENAPI_COMMAND;
import static io.ballerina.cli.cmd.Constants.PACK_COMMAND;
import static io.ballerina.cli.cmd.Constants.PERSIST_COMMAND;
import static io.ballerina.cli.cmd.Constants.PULL_COMMAND;
import static io.ballerina.cli.cmd.Constants.PUSH_COMMAND;
import static io.ballerina.cli.cmd.Constants.RUN_COMMAND;
import static io.ballerina.cli.cmd.Constants.SEARCH_COMMAND;
import static io.ballerina.cli.cmd.Constants.SEMVER_COMMAND;
import static io.ballerina.cli.cmd.Constants.SHELL_COMMAND;
import static io.ballerina.cli.cmd.Constants.START_DEBUG_ADAPTER_COMMAND;
import static io.ballerina.cli.cmd.Constants.START_LANG_SERVER_COMMAND;
import static io.ballerina.cli.cmd.Constants.TEST_COMMAND;
import static io.ballerina.cli.cmd.Constants.TOOL_COMMAND;
import static io.ballerina.cli.cmd.Constants.UPDATE_COMMAND;
import static io.ballerina.cli.cmd.Constants.VERSION_COMMAND;

/**
* Contains utility methods for executing a Ballerina program.
Expand Down Expand Up @@ -131,11 +94,6 @@ static String makeFirstLetterLowerCase(String s) {
return new String(c);
}

public static <K extends Comparable<? super K>, V> Iterable<V> sortValuesByKeys(Map<K, V> map) {
TreeMap<K, V> sortedMap = new TreeMap<>(map);
return sortedMap.values();
}

static String wrapString(String str, int wrapLength, int indent) {
StringBuilder wrappedStr = new StringBuilder();
int i = 0;
Expand Down Expand Up @@ -166,56 +124,4 @@ static String wrapString(String str, int wrapLength, int indent) {
return wrappedStr.toString();
}

static String generateGeneralHelp(Map<String, CommandLine> subCommands) {
List<String> coreCommands = Arrays.asList(
BUILD_COMMAND, RUN_COMMAND, TEST_COMMAND, DOC_COMMAND, PACK_COMMAND);
List<String> packageCommands = Arrays.asList(NEW_COMMAND, INIT_COMMAND, ADD_COMMAND, PULL_COMMAND,
PUSH_COMMAND, SEARCH_COMMAND, SEMVER_COMMAND, GRAPH_COMMAND, DEPRECATE_COMMAND);
List<String> otherCommands = Arrays.asList(CLEAN_COMMAND, FORMAT_COMMAND, GRPC_COMMAND, GRAPHQL_COMMAND,
OPENAPI_COMMAND, ASYNCAPI_COMMAND, PERSIST_COMMAND, BINDGEN_COMMAND, SHELL_COMMAND, VERSION_COMMAND);
List<String> excludedCommands = Arrays.asList(TOOL_COMMAND, DIST_COMMAND, UPDATE_COMMAND,
START_LANG_SERVER_COMMAND, START_DEBUG_ADAPTER_COMMAND, HELP_COMMAND, HOME_COMMAND);

StringBuilder helpBuilder = new StringBuilder();
StringBuilder coreCmdsHelpBuilder = new StringBuilder("\n Core Commands:\n");
StringBuilder pkgCmdsHelpBuilder = new StringBuilder("\n Package Commands:\n");
// StringBuilder toolCmdsHelpBuilder = new StringBuilder("\n Tool Commands:\n");
StringBuilder otherCmdHelpBuilder = new StringBuilder("\n Other Commands:\n");

helpBuilder.append(BLauncherCmd.getCommandUsageInfo(HELP_COMMAND));

for (CommandLine cmd : LauncherUtils.sortValuesByKeys(subCommands)) {
String cmdName = cmd.getCommandName();
if (coreCommands.contains(cmdName)) {
LauncherUtils.generateCommandDescription(cmd, coreCmdsHelpBuilder);
} else if (packageCommands.contains(cmdName)) {
LauncherUtils.generateCommandDescription(cmd, pkgCmdsHelpBuilder);
} else if (otherCommands.contains(cmdName)) {
LauncherUtils.generateCommandDescription(cmd, otherCmdHelpBuilder);
} else if (excludedCommands.contains(cmdName)) {
// do nothing
// } else {
// LauncherUtils.generateCommandDescription(cmd, toolCmdsHelpBuilder);
}
}
helpBuilder.append(coreCmdsHelpBuilder);
helpBuilder.append(pkgCmdsHelpBuilder);
// helpBuilder.append(toolCmdsHelpBuilder);
helpBuilder.append(otherCmdHelpBuilder);
return helpBuilder.toString();
}

private static void generateCommandDescription(CommandLine command, StringBuilder stringBuilder) {
String commandName = command.getCommandName();
BLauncherCmd bCmd = (BLauncherCmd) command.getCommandSpec().userObject();
CommandLine.Command annotation = bCmd.getClass().getAnnotation(CommandLine.Command.class);
String commandDescription = "";
if (annotation != null) {
String[] descValues = annotation.description();
if (descValues != null && descValues.length > 0) {
commandDescription = wrapString(descValues[0], 60, 29);
}
}
stringBuilder.append("\t").append(String.format("%-20s %s", commandName, commandDescription)).append("\n");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@
import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import java.util.ServiceLoader;
Expand Down Expand Up @@ -212,24 +211,21 @@ private static class HelpCmd implements BLauncherCmd {
private CommandLine parentCmdParser;

public void execute() {
Map<String, CommandLine> subCommands = parentCmdParser.getSubcommands();

if (helpCommands == null) {
String generalHelp = LauncherUtils.generateGeneralHelp(subCommands);
outStream.println(generalHelp);
printUsageInfo(BallerinaCliCommands.HELP);
return;

} else if (helpCommands.size() > 1) {
throw LauncherUtils.createUsageExceptionWithHelp("too many arguments given");
}

String userCommand = helpCommands.get(0);
if (subCommands.get(userCommand) == null) {
if (parentCmdParser.getSubcommands().get(userCommand) == null) {
throw LauncherUtils.createUsageExceptionWithHelp("unknown help topic `" + userCommand + "`");
}
StringBuilder commandUsageInfo = new StringBuilder();
BLauncherCmd cmd = subCommands.get(userCommand).getCommand();
cmd.printLongDesc(commandUsageInfo);
outStream.println(commandUsageInfo);

String commandUsageInfo = BLauncherCmd.getCommandUsageInfo(userCommand);
errStream.println(commandUsageInfo);
}

@Override
Expand Down Expand Up @@ -391,9 +387,8 @@ public void execute() {
printUsageInfo(argList.get(0));
return;
}
Map<String, CommandLine> subCommands = parentCmdParser.getSubcommands();
String generalHelp = LauncherUtils.generateGeneralHelp(subCommands);
outStream.println(generalHelp);

printUsageInfo(BallerinaCliCommands.HELP);
}

@Override
Expand Down
32 changes: 32 additions & 0 deletions cli/ballerina-cli/src/main/resources/cli-help/ballerina-help.help
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,35 @@ OPTIONS
COMMANDS
The available subcommands are:

Core Commands:
build Compile the current package
run Compile and run the current package
test Run package tests
doc Generate current package's documentation
pack Create distribution format of the current package

Package Commands:
new Create a new Ballerina package
add Add a new Ballerina module to the current package
pull Pull a package from Ballerina Central
push Publish a package to Ballerina Central
search Search Ballerina Central for packages
semver Show SemVer compatibility and local package changes against
published packages in Ballerina Central
graph Print the dependency graph in the console
deprecate Deprecate a package in Ballerina Central

Other Commands:
clean Clean the artifacts generated during the build
format Format Ballerina source files
grpc Generate the Ballerina sources for a given Protocol
Buffer definition
graphql Generate the Ballerina client sources for a GraphQL config file
and generate the GraphQL schema for a Ballerina GraphQL service.
openapi Generate the Ballerina sources for a given OpenAPI
definition and vice versa
asyncapi Generate the Ballerina sources for a given AsyncAPI definition
persist Manage data persistence
bindgen Generate the Ballerina bindings for Java APIs
shell Run Ballerina interactive REPL
version Print the Ballerina version
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,5 @@ OPTIONS
DESCRIPTION
List the tool-id and the version of all locally available tools.

When there are multiple versions of the same tool, a row is printed
for each version.
When multiple versions of the same tool exist, the latest version
will be listed.
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@ DESCRIPTION
as a command in the bal tool chain.

If the tool version is specified, that specific version will be fetched.
If the version is not specified, the latest version of the tool will
get pulled.
If the tool version is not specified, the latest version will be
fetched.

When there are multiple versions of the same tool pulled, the latest
version will be used.
When there are multiple versions of the same tool available locally, the
latest version will be used.
Original file line number Diff line number Diff line change
Expand Up @@ -15,5 +15,5 @@ DESCRIPTION
If the version is not specified, all versions of the tool will be
removed.

When the latest version of the tool is removed, the next latest version
available will be used as the latest version.
If the most recent version of the tool is removed, the next most recent
version available will be used as the active version.
Original file line number Diff line number Diff line change
Expand Up @@ -935,7 +935,7 @@ public PackageSearchResult searchPackage(String query, String supportedPlatform,
}

/**
* Search packages in registry.
* Search tools in central.
*/
public ToolSearchResult searchTool(String keyword, String supportedPlatform, String ballerinaVersion)
throws CentralClientException {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,10 @@ private static String read(Path balToolsTomlPath) {
StringBuilder content = new StringBuilder();
if (!balToolsTomlPath.toFile().exists()) {
try {
Path parentDirectory = balToolsTomlPath.getParent();
if (parentDirectory != null && !parentDirectory.toFile().exists()) {
Files.createDirectories(parentDirectory);
}
Files.createFile(balToolsTomlPath);
} catch (IOException e) {
throw new RuntimeException("Error while creating bal-tools.toml :" + e);
Expand Down
46 changes: 46 additions & 0 deletions distribution/zip/jballerina/bin/bal.bat
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,52 @@ set BALLERINA_CLASSPATH=!BALLERINA_CLASSPATH!;%BALLERINA_HOME%\bre\lib\*
set BALLERINA_CLASSPATH=!BALLERINA_CLASSPATH!;%BALLERINA_HOME%\lib\tools\lang-server\lib\*
set BALLERINA_CLASSPATH=!BALLERINA_CLASSPATH!;%BALLERINA_HOME%\lib\tools\debug-adapter\lib\*

rem ----- load bal tool jars to classpath ---------------------------------------
set "bal_version_file=%USERPROFILE%\.ballerina\ballerina-version"
if exist "!bal_version_file!" (
for /F "usebackq delims=" %%A in ("%bal_version_file%") do (
for /F "tokens=2 delims=-" %%B in ("%%A") do (
set "bal_version=%%B"
)
)

set "BAL_TOOLS_FILE=%USERPROFILE%\.ballerina\.config\dist-!bal_version!.toml"
if exist "!BAL_TOOLS_FILE!" (
set "org="
set "name="
set "version="
for /F "usebackq tokens=*" %%B in ("!BAL_TOOLS_FILE!") do (
set "line=%%B"
echo !line! | findstr /C:"org =" > nul 2>&1
if not errorlevel 1 (
for /F "tokens=2 delims== " %%C in ("!line!") do set "org=%%C"
set "org=!org:"=!"
) else (
echo !line! | findstr /C:"name =" > nul 2>&1
if not errorlevel 1 (
for /F "tokens=2 delims== " %%C in ("!line!") do set "name=%%C"
set "name=!name:"=!"
) else (
echo !line! | findstr /C:"version =" > nul 2>&1
if not errorlevel 1 (
for /F "tokens=2 delims== " %%C in ("!line!") do set "version=%%C"
set "version=!version:"=!"
)
)
)
if defined org if defined name if defined version (
set "libs=%USERPROFILE%\.ballerina\repositories\central.ballerina.io\bala\!org!\!name!\!version!\any\tool\libs\"
for /f "delims=" %%F in ('dir /b /s /a-d "!libs!\*.jar"') do (
set "BALLERINA_CLASSPATH=!BALLERINA_CLASSPATH!;%%F"
)
set "org="
set "name="
set "version="
)
)
)
)

set BALLERINA_CLI_HEIGHT=
set BALLERINA_CLI_WIDTH=
for /F "tokens=2 delims=:" %%a in ('mode con') do for %%b in (%%a) do (
Expand Down

0 comments on commit a67704c

Please sign in to comment.