source: gs2-extensions/tipple-bridge/trunk/src/src/main/java/sqlCli.java@ 34885

Last change on this file since 34885 was 34885, checked in by davidb, 3 years ago

Updated to have default values from 'port' and 'database' options. Prints out the connection URL formed

File size: 7.8 KB
Line 
1import com.google.gson.JsonArray;
2import picocli.CommandLine;
3import picocli.CommandLine.Command;
4import picocli.CommandLine.Option;
5
6import java.sql.*;
7import java.util.HashMap;
8import com.google.gson.Gson;
9import java.io.FileWriter;
10
11/*
12TODO:
13for the CLI:
14- Error handling
15- Subcommands?
16
17 */
18
19//-u su41Tipple -p --port 3306 --dbname tippleTest1
20//@/home/su41/configFileTest
21
22/*
23The mixinStandardHelpOptions = true adds in --help and --version options
24 */
25@Command (name="sqlCli", description = "Arguments for database connection", mixinStandardHelpOptions = true)
26public class sqlCli implements Runnable {
27 //our cli arguments
28
29 @Option(names = {"-u", "--user"}, description = "The user name")
30 String userName;
31
32 //interactive allows the user to omit the argument value and instead enter it as a prompt
33 /*
34 NOTE: if you are running an interactive option on an IDE, most likely will be using something
35 like the javaw.exe library which tries to mimic the terminal.
36 The point is that interactive option would usually make whatever you enter hidden (it doesn't
37 echo back) but on the IDE it will echo back.
38 */
39 @Option(names = {"-p", "--password"}, description = "User's password", interactive = true)
40 String password;
41
42 @Option(names = {"--port"}, description="Port number", defaultValue="3306")
43 int portNo;
44
45 @Option(names = {"--dbname"}, description="Name of the database", defaultValue="tippleTest")
46 String dbName;
47
48 @Option(names = {"--projectID"}, description = "ID number of the project")
49 String projectID;
50
51 //defaultValue in case the user doesn't enter in an option for it
52 @Option(names = {"--fileName"}, description = "Name of the db",
53 required = true, defaultValue = "myData.json")
54 String fileName;
55
56 @Option(names = {"--host"}, description = "Type of host e.g. localhost ",
57 required = true, defaultValue = "localhost")
58 String host;
59
60
61 public void run() {
62 System.out.println("Hello, " + userName);
63 databaseConnect(userName, password, portNo, dbName, projectID, fileName, host);
64 }
65
66 public static void main(String... args) {
67 int exitCode = new CommandLine(new sqlCli()).execute(args);
68 System.exit(exitCode);
69 }
70
71
72 private static void databaseConnect(String user, String pass, int port, String dbName,
73 String projectID, String filename, String host){
74 Connection conn;
75 Statement stmt;
76
77 // String dbUrl = "jdbc:mysql://localhost:" + port +"/"+ dbName;
78
79 //TODO: are we changing / putting the type of database into a variable too?
80 String dbUrl = "jdbc:mysql://" + host + ":" + port +"/"+ dbName;
81
82 //originally in the try ()
83 // FileWriter file = new FileWriter("tippleData.json")
84 try (FileWriter file = new FileWriter(filename)){
85 //register the jdbc driver
86 Class.forName("com.mysql.cj.jdbc.Driver");
87 //opening the connection
88 System.out.println("Connecting to database:");
89 System.out.println(" " + dbUrl);
90
91 conn = DriverManager.getConnection(dbUrl, user, pass);
92
93 //create and execute query
94 stmt = conn.createStatement();
95 //remember to put in the projectId parameter instead of hardcoding it
96 String sql = "SELECT name, id, typeId, created from td_ContentItem where projectId="+projectID;
97/*
98 String sql = "select td_Document.id, td_Document.content " +
99 "from td_Document, td_ContentItem, td_ContentItem_Document " +
100 "where td_ContentItem.projectId=" + projectID + " and td_ContentItem.id =
101 td_ContentItem_Document.ContentItemId " +
102 "and td_ContentItem_Document.documentId = td_Document.id;";
103*/
104 ResultSet myResult = stmt.executeQuery(sql);
105 ResultSetMetaData resultMetaData = myResult.getMetaData();
106
107 int dbColumn = resultMetaData.getColumnCount();
108 System.out.println("columns " + dbColumn);
109
110 Gson myGSon = new Gson();
111 file.write("[");
112
113 //does nothing, assuming the try catch picks up the error first,
114 if(!myResult.next()){
115 System.out.println("Access denied");
116 }
117
118 while(myResult.next()){
119 //string/object as key/value pair
120 HashMap<String, Object> dbRow = new HashMap<String, Object>(dbColumn);
121
122 //maybe use some kind of arrayList?
123 // ArrayList<Map<String, Object>> dbRowArray = new ArrayList<>(dbColumn);
124
125 for(int i = 1; i <= dbColumn; i++){
126 /*
127 doing checking this way would mean we have to have a case
128 for every data type,
129 if a data type changes in the database that's probably fine, but
130 if a new data type is sent in, the code may not handle it
131 */
132 /*
133 Without this kind of check though, the output would throw a pretty nasty
134 warning about illegal reflective access. Though it would still print the
135 date out fine. Think it switched to using some other java option?
136
137 WARNING: An illegal reflective access operation has occurred
138WARNING: Illegal reflective access by com.google.gson.internal.bind.ReflectiveTypeAdapterFactory (file:/home/su41/.gradle/caches/modules-2/files-2.1/com.google.code.gson/gson/2.7/751f548c85fa49f330cecbb1875893f971b33c4e/gson-2.7.jar) to field java.time.LocalDateTime.date
139WARNING: Please consider reporting this to the maintainers of com.google.gson.internal.bind.ReflectiveTypeAdapterFactory
140WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
141WARNING: All illegal access operations will be denied in a future release
142 */
143 if(resultMetaData.getColumnTypeName(i).equals("DATETIME")){
144 dbRow.put(resultMetaData.getColumnName(i), myResult.getDate(i));
145 //System.out.println("has a datetime");
146
147 }
148
149 else{
150 dbRow.put(resultMetaData.getColumnName(i), myResult.getObject(i));
151 // System.out.println("no datetime datetime");
152 }
153 }
154 //JsonObject jsonObject = myGSon.toJsonTree(dbRow).getAsJsonObject();
155
156 // using a hashmap wont work with this as its not an array
157 // JsonArray jsonArray = myGSon.toJsonTree(dbRow).getAsJsonArray();
158 String dbRowAsJson = myGSon.toJson(dbRow);
159
160 //printing statements for checking output
161 // System.out.println("As normal: " + dbRow);
162 // System.out.println("====");
163 //System.out.println("As JSON: " + anObject);
164
165 //saving to json file
166
167 file.write(dbRowAsJson);
168 //file.write(jsonArray.toString());
169 //Adding commas between each row that we write to our file, as we need it to be valid json
170 if(!myResult.isLast()){
171 file.write(",");
172 }
173 }
174 //write the closing bracket, and flush the writer
175 file.write("]");
176 file.flush();
177 file.close();
178 //System.out.println(myList);
179 System.out.println("Closing connection...");
180 myResult.close();
181 stmt.close();
182 conn.close();
183 }
184 catch(Exception e){
185 //catch for class.name
186 e.printStackTrace();
187 //print out wrong username or password instead of the stack trace?
188 System.out.println("encountered error");
189 }
190 }
191}
Note: See TracBrowser for help on using the repository browser.