WIP SQL console: enable flag; better table output

This commit is contained in:
Francesco 2023-10-22 16:13:58 +02:00
parent c9a9dc6e4c
commit ee58fa0d77
6 changed files with 90 additions and 15 deletions

View File

@ -19,9 +19,6 @@
package tech.ailef.dbadmin.external; package tech.ailef.dbadmin.external;
import java.util.HashMap;
import java.util.Map;
import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.boot.context.properties.ConfigurationProperties;
/** /**
@ -50,6 +47,11 @@ public class DbAdminProperties {
*/ */
private boolean testMode = false; private boolean testMode = false;
/**
* Whether the SQL console feature is enabled
*/
private boolean sqlConsoleEnabled = true;
/** /**
* Whether Spring Boot Database Admin is enabled * Whether Spring Boot Database Admin is enabled
* @return * @return
@ -62,6 +64,14 @@ public class DbAdminProperties {
this.enabled = enabled; this.enabled = enabled;
} }
public boolean isSqlConsoleEnabled() {
return sqlConsoleEnabled;
}
public void setSqlConsoleEnabled(boolean sqlConsoleEnabled) {
this.sqlConsoleEnabled = sqlConsoleEnabled;
}
/** /**
* Returns the prefix that is prepended to all routes registered by Spring Boot Database Admin. * Returns the prefix that is prepended to all routes registered by Spring Boot Database Admin.
* @return * @return
@ -94,14 +104,15 @@ public class DbAdminProperties {
this.testMode = testMode; this.testMode = testMode;
} }
public Map<String, String> toMap() { // public Map<String, String> toMap() {
Map<String, String> conf = new HashMap<>(); // Map<String, String> conf = new HashMap<>();
conf.put("enabled", enabled + ""); // conf.put("enabled", enabled + "");
conf.put("baseUrl", baseUrl); // conf.put("baseUrl", baseUrl);
conf.put("modelsPackage", modelsPackage); // conf.put("modelsPackage", modelsPackage);
conf.put("testMode", testMode + ""); // conf.put("testMode", testMode + "");
return conf; // conf.put("sqlConsoleEnabled", sqlConsoleEnabled + "");
} // return conf;
// }
} }

View File

@ -551,6 +551,10 @@ public class DefaultDbAdminController {
@GetMapping("/console/new") @GetMapping("/console/new")
public String consoleNew(Model model) { public String consoleNew(Model model) {
if (!properties.isSqlConsoleEnabled()) {
throw new DbAdminException("SQL console not enabled");
}
model.addAttribute("activePage", "console"); model.addAttribute("activePage", "console");
ConsoleQuery q = new ConsoleQuery(); ConsoleQuery q = new ConsoleQuery();
@ -560,6 +564,10 @@ public class DefaultDbAdminController {
@GetMapping("/console") @GetMapping("/console")
public String console(Model model) { public String console(Model model) {
if (!properties.isSqlConsoleEnabled()) {
throw new DbAdminException("SQL console not enabled");
}
List<ConsoleQuery> tabs = consoleQueryRepository.findAll(); List<ConsoleQuery> tabs = consoleQueryRepository.findAll();
if (tabs.isEmpty()) { if (tabs.isEmpty()) {
@ -574,6 +582,10 @@ public class DefaultDbAdminController {
@PostMapping("/console/delete/{queryId}") @PostMapping("/console/delete/{queryId}")
public String consoleDelete(@PathVariable String queryId, Model model) { public String consoleDelete(@PathVariable String queryId, Model model) {
if (!properties.isSqlConsoleEnabled()) {
throw new DbAdminException("SQL console not enabled");
}
consoleQueryRepository.deleteById(queryId); consoleQueryRepository.deleteById(queryId);
return "redirect:/" + properties.getBaseUrl() + "/console"; return "redirect:/" + properties.getBaseUrl() + "/console";
} }
@ -584,6 +596,10 @@ public class DefaultDbAdminController {
public String consoleRun(Model model, @RequestParam(required = false) String query, public String consoleRun(Model model, @RequestParam(required = false) String query,
@RequestParam(required = false) String queryTitle, @RequestParam(required = false) String queryTitle,
@PathVariable String queryId) { @PathVariable String queryId) {
if (!properties.isSqlConsoleEnabled()) {
throw new DbAdminException("SQL console not enabled");
}
ConsoleQuery activeQuery = consoleQueryRepository.findById(queryId).orElseThrow(() -> { ConsoleQuery activeQuery = consoleQueryRepository.findById(queryId).orElseThrow(() -> {
return new DbAdminNotFoundException("Query with ID " + queryId + " not found."); return new DbAdminNotFoundException("Query with ID " + queryId + " not found.");
}); });

View File

@ -59,6 +59,7 @@ public class GlobalController {
model.addAttribute("dbadmin_userConf", userConf); model.addAttribute("dbadmin_userConf", userConf);
model.addAttribute("dbadmin_baseUrl", getBaseUrl()); model.addAttribute("dbadmin_baseUrl", getBaseUrl());
model.addAttribute("dbadmin_version", dbAdmin.getVersion()); model.addAttribute("dbadmin_version", dbAdmin.getVersion());
model.addAttribute("dbadmin_properties", props);
return "other/error"; return "other/error";
} }
@ -70,6 +71,7 @@ public class GlobalController {
model.addAttribute("dbadmin_userConf", userConf); model.addAttribute("dbadmin_userConf", userConf);
model.addAttribute("dbadmin_baseUrl", getBaseUrl()); model.addAttribute("dbadmin_baseUrl", getBaseUrl());
model.addAttribute("dbadmin_version", dbAdmin.getVersion()); model.addAttribute("dbadmin_version", dbAdmin.getVersion());
model.addAttribute("dbadmin_properties", props);
response.setStatus(404); response.setStatus(404);
return "other/error"; return "other/error";
} }
@ -118,5 +120,11 @@ public class GlobalController {
public UserConfiguration getUserConf() { public UserConfiguration getUserConf() {
return userConf; return userConf;
} }
@ModelAttribute("dbadmin_properties")
public DbAdminProperties getProps() {
return props;
}
} }

View File

@ -41,20 +41,52 @@ public class DbQueryOutputField {
return dbField != null && dbField.isPrimaryKey(); return dbField != null && dbField.isPrimaryKey();
} }
/**
* Returns true if this field is a foreign key, only in the case
* the field has been mapped to a table
*/
public boolean isForeignKey() { public boolean isForeignKey() {
return dbField != null && dbField.isForeignKey(); return dbField != null && dbField.isForeignKey();
} }
/**
* Returns true if this field is a binary field (BLOB, etc.), only in the case
* the field has been mapped to a table
* @return
*/
public boolean isBinary() { public boolean isBinary() {
return dbField != null && dbField.isBinary(); return dbField != null && dbField.isBinary();
} }
/**
* Returns true if this field is mapped to a table
* @return
*/
public boolean isMapped() {
return dbField != null;
}
/**
* Returns the type of the field, only in the case the field
* has been mapped to a table
* @return
*/
public String getType() { public String getType() {
if (dbField != null) if (dbField != null)
return dbField.getType().toString(); return dbField.getType().toString();
return "-"; return "-";
} }
public String getJavaName() {
if (dbField == null) return null;
return dbField.getJavaName();
}
public String getEntityClassName() {
if (dbField == null) return null;
return dbField.getSchema().getClassName();
}
@Override @Override
public int hashCode() { public int hashCode() {
return Objects.hash(name, table); return Objects.hash(name, table);

View File

@ -12,8 +12,15 @@
<!-- data-row-field fragment --> <!-- data-row-field fragment -->
<th:block th:fragment="data_row_field(field, object)"> <th:block th:fragment="data_row_field(field, object)">
<th:block th:if="${field.isBinary()}">
<th:block th:if="${object.get(field)}">
<span class="font-monospace null-label">BINARY</span>
</th:block>
</th:block>
<th:block th:if="${!field.isBinary()}">
<span th:text="${object.get(field)}"></span> <span th:text="${object.get(field)}"></span>
</th:block> </th:block>
</th:block>
<!-- end data-row-field fragment --> <!-- end data-row-field fragment -->
</body> </body>
</html> </html>

View File

@ -83,7 +83,8 @@
</a> </a>
</li> </li>
<li th:class="${#strings.equals(activePage, 'console') ? 'active' : ''}"> <li th:if="${dbadmin_properties.isSqlConsoleEnabled()}"
th:class="${#strings.equals(activePage, 'console') ? 'active' : ''}">
<a th:href="|/${dbadmin_baseUrl}/console|"> <a th:href="|/${dbadmin_baseUrl}/console|">
<div class="d-flex align-items-center"> <div class="d-flex align-items-center">
<div class="menu-icon"> <div class="menu-icon">