mirror of
https://github.com/signalapp/Signal-Android.git
synced 2026-05-08 09:18:39 +01:00
Add foreign key constraint details to Spinner.
This commit is contained in:
@@ -4,6 +4,9 @@ function init() {
|
||||
console.log('clicked');
|
||||
elem.classList.toggle('active');
|
||||
document.getElementById(elem.dataset.for).classList.toggle('hidden');
|
||||
document.dispatchEvent(new CustomEvent('header-toggle', {
|
||||
detail: document.getElementById(elem.dataset.for)
|
||||
}))
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -14,8 +14,8 @@
|
||||
|
||||
{{> partials/prefix isOverview=true}}
|
||||
|
||||
<h1 class="collapse-header active" data-for="table-creates">Tables</h1>
|
||||
<div id="table-creates">
|
||||
<h1 class="collapse-header" data-for="table-creates">Tables</h1>
|
||||
<div id="table-creates" class="hidden">
|
||||
{{#if tables}}
|
||||
{{#each tables}}
|
||||
<h2 class="collapse-header" data-for="table-create-{{@index}}">{{name}}</h2>
|
||||
@@ -26,8 +26,8 @@
|
||||
{{/if}}
|
||||
</div>
|
||||
|
||||
<h1 class="collapse-header active" data-for="index-creates">Indices</h1>
|
||||
<div id="index-creates">
|
||||
<h1 class="collapse-header" data-for="index-creates">Indices</h1>
|
||||
<div id="index-creates" class="hidden">
|
||||
{{#if indices}}
|
||||
{{#each indices}}
|
||||
<h2 class="collapse-header active" data-for="index-create-{{@index}}">{{name}}</h2>
|
||||
@@ -38,8 +38,8 @@
|
||||
{{/if}}
|
||||
</div>
|
||||
|
||||
<h1 class="collapse-header active" data-for="trigger-creates">Triggers</h1>
|
||||
<div id="trigger-creates">
|
||||
<h1 class="collapse-header" data-for="trigger-creates">Triggers</h1>
|
||||
<div id="trigger-creates" class="hidden">
|
||||
{{#if triggers}}
|
||||
{{#each triggers}}
|
||||
<h2 class="collapse-header active" data-for="trigger-create-{{@index}}">{{name}}</h2>
|
||||
@@ -50,6 +50,58 @@
|
||||
{{/if}}
|
||||
</div>
|
||||
|
||||
|
||||
<h1 class="collapse-header" data-for="foreign-key-creates">Foreign Keys</h1>
|
||||
<div id="foreign-key-creates" class="hidden">
|
||||
{{#if foreignKeys}}
|
||||
<table>
|
||||
<tr>
|
||||
<th>Column</th>
|
||||
<th>Depends On</th>
|
||||
<th>On Delete</th>
|
||||
</tr>
|
||||
{{#each foreignKeys}}
|
||||
<tr>
|
||||
<td>{{table}}.{{column}}</td>
|
||||
<td>{{dependsOnTable}}.{{dependsOnColumn}}</td>
|
||||
<td>{{onDelete}}</td>
|
||||
</tr>
|
||||
{{/each}}
|
||||
</table>
|
||||
|
||||
<h2>Without Labels</h2>
|
||||
<pre class="mermaid">
|
||||
flowchart LR
|
||||
{{#each foreignKeys}}
|
||||
id_{{table}}[{{table}}] --> id_{{dependsOnTable}}[{{dependsOnTable}}]
|
||||
{{/each}}
|
||||
</pre>
|
||||
|
||||
<h2>With Labels</h2>
|
||||
<pre class="mermaid">
|
||||
flowchart LR
|
||||
{{#each foreignKeys}}
|
||||
id_{{table}}[{{table}}] -- "{{column}} 🠖 {{dependsOnColumn}}" --> id_{{dependsOnTable}}[{{dependsOnTable}}]
|
||||
{{/each}}
|
||||
</pre>
|
||||
|
||||
{{else}}
|
||||
None.
|
||||
{{/if}}
|
||||
</div>
|
||||
|
||||
|
||||
<script type="module">
|
||||
import mermaid from 'https://cdn.jsdelivr.net/npm/mermaid@9/dist/mermaid.esm.min.mjs';
|
||||
mermaid.initialize({ startOnLoad: false });
|
||||
|
||||
document.addEventListener('header-toggle', (e) => {
|
||||
if (e.detail.id === 'foreign-key-creates') {
|
||||
mermaid.init('.mermaid')
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
{{> partials/suffix }}
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -2,6 +2,10 @@ package org.signal.spinner
|
||||
|
||||
import android.database.Cursor
|
||||
import androidx.sqlite.db.SupportSQLiteDatabase
|
||||
import org.signal.core.util.SqlUtil
|
||||
import org.signal.core.util.readToList
|
||||
import org.signal.core.util.requireNonNullString
|
||||
import org.signal.core.util.requireString
|
||||
|
||||
fun SupportSQLiteDatabase.getTableNames(): List<String> {
|
||||
val out = mutableListOf<String>()
|
||||
@@ -26,6 +30,22 @@ fun SupportSQLiteDatabase.getTriggers(): Cursor {
|
||||
return this.query("SELECT * FROM sqlite_master WHERE type='trigger' ORDER BY name ASC")
|
||||
}
|
||||
|
||||
fun SupportSQLiteDatabase.getForeignKeys(): List<ForeignKeyConstraint> {
|
||||
return SqlUtil.getAllTables(this)
|
||||
.map { table ->
|
||||
this.query("PRAGMA foreign_key_list($table)").readToList { cursor ->
|
||||
ForeignKeyConstraint(
|
||||
table = table,
|
||||
column = cursor.requireNonNullString("from"),
|
||||
dependsOnTable = cursor.requireNonNullString("table"),
|
||||
dependsOnColumn = cursor.requireNonNullString("to"),
|
||||
onDelete = cursor.requireString("on_delete") ?: "NOTHING"
|
||||
)
|
||||
}
|
||||
}
|
||||
.flatten()
|
||||
}
|
||||
|
||||
fun SupportSQLiteDatabase.getTableRowCount(table: String): Int {
|
||||
return this.query("SELECT COUNT(*) FROM $table").use {
|
||||
if (it.moveToFirst()) {
|
||||
@@ -35,3 +55,11 @@ fun SupportSQLiteDatabase.getTableRowCount(table: String): Int {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
data class ForeignKeyConstraint(
|
||||
val table: String,
|
||||
val column: String,
|
||||
val dependsOnTable: String,
|
||||
val dependsOnColumn: String,
|
||||
val onDelete: String
|
||||
)
|
||||
|
||||
@@ -105,6 +105,7 @@ internal class SpinnerServer(
|
||||
tables = db.getTables().use { it.toTableInfo() },
|
||||
indices = db.getIndexes().use { it.toIndexInfo() },
|
||||
triggers = db.getTriggers().use { it.toTriggerInfo() },
|
||||
foreignKeys = db.getForeignKeys(),
|
||||
queryResult = db.getTables().use { it.toQueryResult() }
|
||||
)
|
||||
)
|
||||
@@ -410,6 +411,7 @@ internal class SpinnerServer(
|
||||
val tables: List<TableInfo>,
|
||||
val indices: List<IndexInfo>,
|
||||
val triggers: List<TriggerInfo>,
|
||||
val foreignKeys: List<ForeignKeyConstraint>,
|
||||
val queryResult: QueryResult? = null
|
||||
) : PrefixPageData
|
||||
|
||||
|
||||
Reference in New Issue
Block a user