MySQL Shell is a command-line shell for MySQL Server that has the capability for
interactive and batch code execution. It also offers a wealth of APIs that make it easier and more efficient to work with and manage MySQL servers. In 8.0.13, we made an effort to make those APIs easily accessible straight from the command line. We call it the API command line integration and believe that this new way of interacting with Shell global objects will be quite useful for developers, DBAs or anyone wanting to embed built-in shell commands within their own scripts.
Before this API integration, calling methods from MySQL Shell global objects via the command-line interface had to be done using the --execute
(-e
) option. Doing so can be a bit tricky because of the quoting and escaping that can be necessary.
For instance look at this example of how you would create a cluster with the -e
option.
1 |
$ mysqlsh root:@localhost:3301 -e "dba.createCluster('Cluster1', {multiPrimary:true, force:true, memberWeight:80, ipWhitelist:'127.0.0.1,192.168.0.0/24'})" |
With the new syntax the call can be rewritten in a command line friendly way:
1 |
$ mysqlsh root:@localhost:3301 -- dba create-cluster Cluster1 --multiPrimary=true --force=true --memberWeight=80 --ipWhitelist=127.0.0.1,192.168.0.0/24 |
This simple example showcases the advantages of the new syntax. It requires fewer quoting and escaping (sometimes none at all) and by doing so it is less cumbersome and less error-prone to integrate MySQL Shell into your automation scripts. These advantages are more noticeable as examples become more complex.
API Command Line Integration Syntax
The API Command Line Integration introduces a new syntax for invoking built-in shell commands:
mysqlsh [OPTIONS] [URI] -- <object_name> <method_name> [ argument_list ]
The double dashes “--
” indicate that an API command will be executed. Parameters to its left are interpreted as parameters for the shell (i.e. connection data) and the parameters to its right are interpreted as parameters for the API call as follows:
- object_name – a case-sensitive string that used to specify the MySQL Shell object to interact with. The supported objects are dba, cluster, shell, shell.options and util.
- method_name – a case-sensitive string with the name of the method to be called on the object specified by object_name in alternative command line typing friendly format, i.e., all lower case, words separated by hyphens. Javascript and Python formats are also supported.
- argument_list – the arguments passed to the call of the method_name method.
If an invalid object_name or method_name is provided, the shell will exit with return code 10.
Argument List Syntax
On this new syntax, both object_name and method_name are mandatory case-sensitive strings and have no further rules. The argument_list, on the other hand, is optional and has a syntax to follow. There are two types of arguments that can be used on the argument_list: positional arguments and named arguments. Their usage must adhere to the following syntax:
[ positional_argument ]* [ { named_argument* } ]* [ named_argument ]*
- all parts of the syntax are optional and can be given in any order.
- nesting of curly brackets is forbidden.
- all the named_arguments have to have unique key names inside their scope. The scope is either ungrouped or in a group (inside the curly brackets).
These arguments are then converted into the arguments passed to the method call in the following way:
- all ungrouped named arguments independent to where they appear are tied together as a single dictionary and passed as the last parameter to the method
- named arguments grouped inside curly brackets are tied together into a single dictionary
- positional arguments and dictionaries resulting from grouped named arguments are inserted into the Argument_list in the order they appear on the command line
This information and more can be accessed on the MySQL Shell built- in help:
1 |
mysql-js> \? cmdline |
Examples
With this new API integration, calling built-in shell commands is easier and less cumbersome than with the -e
option. Below are some examples that try to demonstrate it.
Checking if a server can be upgraded
Before 8.0.13:
1 |
$ mysqlsh -e "util.checkForServerUpgrade({user:'root', host:'localhost', port:3301}, {password:'', outputFormat:'JSON'})" |
After:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
$ mysqlsh -- util check-for-server-upgrade { --user=root --host=localhost --port=3301 } --password='' --outputFormat=JSON { "serverAddress": "localhost:3301", "serverVersion": "5.7.25-enterprise-commercial-advanced-log - MySQL Enterprise Server - Advanced Edition (Commercial)", "targetVersion": "8.0.14", "errorCount": 0, "warningCount": 0, "noticeCount": 0, "summary": "No known compatibility errors or issues were found.\n", ... { "id": "checkTableOutput", "title": "Issues reported by 'check table x for upgrade' command", "status": "OK", "detectedProblems": [] } ] } |
Importing JSON document to a server
The importing of JSON documents is also a new feature of MySQL Shell 8.0.13. There are two alternative formats for the command line invocation. You can use the Shell API command line integration syntax, which accepts input only from a file, or the --import
command, which accepts input from standard input or a file. With the Shell API command line integration syntax, you invoke the utility as follows:
1
2
3
4
5
6
7
8
|
$ mysqlsh root@localhost:33010 -- util import-json /home/nelson/Downloads/data.json --collection='zip codes' --schema='json_test' Please provide the password for 'root@localhost:33010': Save password for 'root@localhost:33010'? [Y]es/[N]o/Ne[v]er (default No): Importing from file "/home/nelson/Downloads/data.json" to collection `json_test`.`zip codes` in MySQL Server at localhost:33010 .. 6879.. 13776.. 20721.. 27683.. 29353.. 29353 Processed 3.15 MB in 29353 documents in 1.3289 sec (22.09K documents/s) Total successfully imported documents 29353 (22.09K documents/s) |
Creating a sandbox
In order to create a sandbox you would have had to do the following:
1
2
3
4
5
|
$ mysqlsh -e "dba.deploySandboxInstance(4000, {password: 'foo'});" Deploying new MySQL instance... Instance localhost:4000 successfully deployed and started. Use shell.connect('root@localhost:4000'); to connect to the instance. |
After 8.0.13 with the new syntax:
1 |
$ mysqlsh -- dba deploy-sandbox-instance 4000 --password=foo |
Checking if an instance is correctly configured for InnoDB cluster
Before 8.0.13
1
2
|
$ mysqlsh -e "dba.checkInstanceConfiguration({port:3303, host:'localhost', password:'root', user:'root'}, {mycnfPath:'/home/nelson/mysql sandboxes/3303/my.cnf'}) " |
With the new syntax:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
|
$ mysqlsh -- dba check-instance-configuration { --port=3303 --host=localhost --password=root --user=root } --mycnfPath='/home/nelson/mysql sandboxes/3303/my.cnf' Validating local MySQL instance listening at port 3303 for use in an InnoDB cluster... This instance reports its own address as T460.lan Clients and other cluster members will communicate with it through this address by default. If this is not correct, the report_host MySQL system variable should be changed. Checking whether existing tables comply with Group Replication requirements... No incompatible tables detected Checking instance configuration... Configuration file /home/nelson/mysql sandboxes/3303/my.cnf will also be checked. Some configuration options need to be fixed: +----------------------------------+---------------+----------------+------------------------------------------------+ | Variable | Current Value | Required Value | Note | +----------------------------------+---------------+----------------+------------------------------------------------+ | binlog_checksum | CRC32 | NONE | Update the server variable and the config file | | binlog_format | <not set> | ROW | Update the config file | | enforce_gtid_consistency | OFF | ON | Update the config file and restart the server | | gtid_mode | OFF | ON | Update the config file and restart the server | | log_slave_updates | <not set> | ON | Update the config file | | master_info_repository | <not set> | TABLE | Update the config file | | relay_log_info_repository | <not set> | TABLE | Update the config file | | report_port | <not set> | 3303 | Update the config file | | server_id | 1 | <unique ID> | Update the config file and restart the server | | transaction_write_set_extraction | <not set> | XXHASH64 | Update the config file | +----------------------------------+---------------+----------------+------------------------------------------------+ Some variables need to be changed, but cannot be done dynamically on the server. Please use the dba.configureInstance() command to repair these issues. ... |
Checking the status of a cluster
Before 8.0.13:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
$ mysqlsh root@localhost:3301 --cluster -e "print(cluster.status())" Please provide the password for 'root@localhost:3301': Save password for 'root@localhost:3301'? [Y]es/[N]o/Ne[v]er (default No): { "clusterName": "Cluster1", "defaultReplicaSet": { "name": "default", "ssl": "REQUIRED", "status": "OK_NO_TOLERANCE", "statusText": "Cluster is NOT tolerant to any failures.", "topology": { "localhost:3301": { "address": "localhost:3301", "mode": "R/W", "readReplicas": {}, "role": "HA", "status": "ONLINE" } } }, "groupInformationSourceMember": "T460.lan:3301" } |
After:
1 |
$ mysqlsh root@localhost:3301 -- cluster status |
Adding an instance to a cluster
Before 8.0.13:
1 |
$ mysqlsh root@localhost:3301 --cluster -e "cluster.addInstance('root@localhost:3302', {password:'', memberWeight:90})" |
After:
1
2
3
4
5
6
7
8
9
10
|
mysqlsh root@localhost:3301 -- cluster add-instance root@localhost:3302 --password="" --memberWeight=90 Please provide the password for 'root@localhost:3301': Save password for 'root@localhost:3301'? [Y]es/[N]o/Ne[v]er (default No): Validating instance at localhost:3303... Instance detected as a sandbox. Please note that sandbox instances are only suitable for deploying test clusters for use within the same host. This instance reports its own address as T460.lan Instance configuration is suitable. |
Try it now and send us your feedback
MySQL Shell 8.0.13 GA is available for download from the following links.
- MySQL developers website: https://dev.mysql.com/downloads/shell/
- MySQL Shell is also available on GitHub: https://github.com/mysql/mysql-shell
The documentation of MySQL Shell can be found here: https://dev.mysql.com/doc/mysql-shell/8.0/en/
Enjoy, and Thank you for using MySQL!