mirror of
https://github.com/featurebasedb/featurebase.git
synced 2026-10-08 20:07:51 +00:00
Add new webui design from Joe
This commit is contained in:
parent
92ec0a0cb0
commit
60c8ba238c
9 changed files with 389 additions and 221 deletions
BIN
webui/assets/chevron-down.png
Normal file
BIN
webui/assets/chevron-down.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 3.6 KiB |
|
|
@ -1,63 +0,0 @@
|
|||
.output {
|
||||
overflow: auto;
|
||||
padding: 0 8px;
|
||||
}
|
||||
|
||||
.output .query {
|
||||
font-family: monospace;
|
||||
}
|
||||
|
||||
.output .response {
|
||||
font-family: monospace;
|
||||
}
|
||||
|
||||
.input-bar {
|
||||
padding-right: 2em;
|
||||
background-color: #eeeeee;
|
||||
}
|
||||
|
||||
.input-textarea {
|
||||
font-family: monospace;
|
||||
font-size: 14px;
|
||||
background-color: #dddddd;
|
||||
width: 100%;
|
||||
border: 0;
|
||||
outline: 0;
|
||||
margin: 1em;
|
||||
}
|
||||
|
||||
body {
|
||||
padding-top: 5rem;
|
||||
}
|
||||
|
||||
.controls {
|
||||
padding: 1em;
|
||||
}
|
||||
|
||||
.output {
|
||||
padding: 1em;
|
||||
}
|
||||
|
||||
.result {
|
||||
background-color: #eeeeee;
|
||||
padding: 1em;
|
||||
margin-top: 1em;
|
||||
}
|
||||
.result > .tab-content > .tab-pane {
|
||||
padding: 1em;
|
||||
}
|
||||
|
||||
.query {
|
||||
background-color: #dddddd;
|
||||
padding: 0.5em
|
||||
}
|
||||
|
||||
#exTab3 .nav-pills > li > a {
|
||||
border-radius: 4px 4px 0 0 ;
|
||||
}
|
||||
|
||||
#exTab3 .tab-content {
|
||||
color : white;
|
||||
background-color: #428bca;
|
||||
padding : 5px 15px;
|
||||
}
|
||||
|
|
@ -1,114 +0,0 @@
|
|||
class REPL {
|
||||
constructor(input, output) {
|
||||
this.input = input
|
||||
this.output = output
|
||||
this.history = []
|
||||
this.history_index = 0
|
||||
this.history_buffer = ''
|
||||
this.result_number = 0
|
||||
}
|
||||
bind_events() {
|
||||
const repl = this
|
||||
const keys = {
|
||||
ENTER: 13,
|
||||
UP_ARROW: 38,
|
||||
DOWN_ARROW: 40
|
||||
}
|
||||
|
||||
this.input.addEventListener("keydown", (e) => {
|
||||
if (e.keyCode == keys.UP_ARROW) {
|
||||
e.preventDefault()
|
||||
if (this.input.value.substring(0, this.input.selectionStart).indexOf('\n') == '-1') {
|
||||
if (this.history_index == 0) {
|
||||
return
|
||||
} else {
|
||||
if (this.history_index == this.history.length) {
|
||||
this.history_buffer = this.input.value
|
||||
}
|
||||
this.history_index--
|
||||
this.input.value = this.history[this.history_index]
|
||||
this.input.setSelectionRange(this.input.value.length, this.input.value.length)
|
||||
}
|
||||
}
|
||||
}
|
||||
if (e.keyCode == keys.DOWN_ARROW) {
|
||||
e.preventDefault()
|
||||
if (this.input.value.substring(this.input.selectionEnd, this.input.length).indexOf('\n') == '-1') {
|
||||
if (this.history_index == this.history.length) {
|
||||
return
|
||||
} else {
|
||||
this.history_index++
|
||||
if (this.history_index == this.history.length) {
|
||||
this.input.value = this.history_buffer
|
||||
} else {
|
||||
this.input.value = this.history[this.history_index]
|
||||
}
|
||||
this.input.setSelectionRange(this.input.value.length, this.input.value.length)
|
||||
}
|
||||
}
|
||||
}
|
||||
if (e.keyCode == keys.ENTER && !e.shiftKey) {
|
||||
e.preventDefault()
|
||||
this.history_buffer = ''
|
||||
this.history_index = this.history.length
|
||||
this.history[this.history_index] = this.input.value
|
||||
this.history_index++
|
||||
this.process_query(this.input.value)
|
||||
this.input.value = ""
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
process_query(query) {
|
||||
var xhr = new XMLHttpRequest();
|
||||
var dbname = 'foo'; // todo: get db name from dropdown menu
|
||||
xhr.open('POST', '/db/' + dbname + '/query');
|
||||
xhr.setRequestHeader('Content-Type', 'application/text');
|
||||
|
||||
const repl = this
|
||||
xhr.onload = function() {
|
||||
repl.result_number++
|
||||
//const entry = document.createElement('p')
|
||||
const result = (
|
||||
'<div class="container result">' +
|
||||
'<ul class="nav nav-tabs" role="tablist">' +
|
||||
'<li class="nav-item">' +
|
||||
'<a class="nav-link active" data-toggle="tab" href="#result' + repl.result_number + '" role="tab">Result</a>' +
|
||||
'</li>' +
|
||||
'<li class="nav-item">' +
|
||||
'<a class="nav-link" data-toggle="tab" href="#raw' + repl.result_number + '" role="tab">Raw</a>' +
|
||||
'</li>' +
|
||||
'</ul>' +
|
||||
'' +
|
||||
'<div class="tab-content">' +
|
||||
'<div class="tab-pane active" id="result' + repl.result_number + '" role="tabpanel">' +
|
||||
'<p class="query">' +
|
||||
query +
|
||||
'</p>' +
|
||||
'<p>Response</p>' +
|
||||
'<p class="response">' +
|
||||
xhr.responseText +
|
||||
'</p>' +
|
||||
'</div>' +
|
||||
'<div class="tab-pane" id="raw' + repl.result_number + '" role="tabpanel">' +
|
||||
'<table class="table table-inverse"><tbody>' +
|
||||
'<tr><th>Response code</th><td>' + xhr.status + '</td></tr>' +
|
||||
'<tr><th>Response text</th><td>' + xhr.responseText + '</td></tr>' +
|
||||
'<tr><th>Response URL</th><td>' + xhr.responseURL + '</td></tr>' +
|
||||
'</tbody></table>' +
|
||||
'</div>' +
|
||||
'</div>' +
|
||||
'</div>')
|
||||
// TODO: remove jquery
|
||||
$(repl.output).prepend($(result))
|
||||
};
|
||||
xhr.send(query);
|
||||
}
|
||||
}
|
||||
|
||||
function startup() {
|
||||
const input = document.querySelector('.input-textarea')
|
||||
const output = document.querySelector('.output')
|
||||
repl = new REPL(input, output)
|
||||
repl.bind_events()
|
||||
}
|
||||
1
webui/assets/nav_cluster.svg
Normal file
1
webui/assets/nav_cluster.svg
Normal file
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100.75 36.67"><defs><style>.cls-1{fill:#1db598;}.cls-2{fill:none;stroke:#fff;stroke-miterlimit:10;stroke-width:5px;}</style></defs><title>nav_cluster_1</title><g id="Layer_2" data-name="Layer 2"><g id="Layer_1-2" data-name="Layer 1"><circle class="cls-1" cx="55.14" cy="18.24" r="9.61"/><circle class="cls-1" cx="18.33" cy="18.33" r="9.61"/><circle class="cls-1" cx="91.14" cy="18.24" r="9.61"/><circle class="cls-2" cx="18.33" cy="18.33" r="15.83"/></g></g></svg>
|
||||
|
After Width: | Height: | Size: 517 B |
1
webui/assets/nav_console.svg
Normal file
1
webui/assets/nav_console.svg
Normal file
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 78.47 48.95"><defs><style>.cls-1{fill:none;stroke:#3c5f8d;stroke-miterlimit:10;stroke-width:6px;}.cls-2{fill:#1db598;}</style></defs><title>nav_console</title><g id="Layer_2" data-name="Layer 2"><g id="Layer_1-2" data-name="Layer 1"><rect class="cls-1" x="3" y="3" width="72.47" height="42.95"/><circle class="cls-2" cx="39.25" cy="25.92" r="9.61"/></g></g></svg>
|
||||
|
After Width: | Height: | Size: 416 B |
1
webui/assets/nav_documentation.svg
Normal file
1
webui/assets/nav_documentation.svg
Normal file
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 70 44.5"><defs><style>.cls-1{fill:none;stroke:#fff;stroke-miterlimit:10;stroke-width:5px;}.cls-2{fill:#1db598;}</style></defs><title>documentation</title><g id="Layer_2" data-name="Layer 2"><g id="Layer_1-2" data-name="Layer 1"><line class="cls-1" y1="2.5" x2="70" y2="2.5"/><line class="cls-1" y1="20" x2="70" y2="20"/><line class="cls-1" y1="38.5" x2="52.82" y2="38.5"/><circle class="cls-2" cx="63.5" cy="38.5" r="6"/></g></g></svg>
|
||||
|
After Width: | Height: | Size: 488 B |
1
webui/assets/nav_item1.svg
Normal file
1
webui/assets/nav_item1.svg
Normal file
|
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 75.47 45.95"><defs><style>.cls-1{fill:none;stroke:#3c5f8d;stroke-miterlimit:10;stroke-width:3px;}.cls-2{fill:#1db598;}</style></defs><title>nav_item1</title><g id="Layer_2" data-name="Layer 2"><g id="Layer_1-2" data-name="Layer 1"><rect class="cls-1" x="1.5" y="1.5" width="72.47" height="42.95"/><circle class="cls-2" cx="37.75" cy="24.42" r="9.61"/></g></g></svg>
|
||||
|
After Width: | Height: | Size: 418 B |
220
webui/assets/style.css
Normal file
220
webui/assets/style.css
Normal file
|
|
@ -0,0 +1,220 @@
|
|||
*{
|
||||
-webkit-box-sizing: border-box;
|
||||
-moz-box-sizing: border-box;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
body{
|
||||
font-family: sans-serif;
|
||||
background-color: #fbfcfd;
|
||||
margin: 0;
|
||||
color: #102445;
|
||||
}
|
||||
h2{
|
||||
margin-bottom: 30px;
|
||||
}
|
||||
|
||||
h5{
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
line-height: 1.21;
|
||||
margin: 0;
|
||||
}
|
||||
a{
|
||||
line-height: 1.38;
|
||||
letter-spacing: 0.2px;
|
||||
text-decoration: none;
|
||||
color: #102445;
|
||||
}
|
||||
|
||||
|
||||
a:hover{
|
||||
color: #1db598;
|
||||
}
|
||||
|
||||
textarea{
|
||||
width: 100%;
|
||||
margin-bottom: 10px;
|
||||
border-radius: 2px;
|
||||
background-color: #fbfcfd;
|
||||
border: solid 1.5px #e4eff4;
|
||||
font-family: monospace;
|
||||
font-size: 16px;
|
||||
line-height: 1.5;
|
||||
letter-spacing: 1.1px;
|
||||
outline: none;
|
||||
padding: 30px;
|
||||
}
|
||||
|
||||
|
||||
select{
|
||||
/*-webkit-appearance: none;
|
||||
-moz-appearance: none;
|
||||
appearance: none;
|
||||
background: url("img/chevron-down.png") no-repeat calc(100% - 10px) !important;*/
|
||||
border-radius: 3px;
|
||||
background-color: #fbfcfd;
|
||||
width: 187px;
|
||||
height: 50px;
|
||||
border: solid 1.5px #e4eff4;
|
||||
font-size: 18px;
|
||||
font-weight: bold;
|
||||
line-height: 1.39;
|
||||
letter-spacing: 0.2px;
|
||||
color: #102445;
|
||||
padding: 10.5px;
|
||||
|
||||
}
|
||||
|
||||
button{
|
||||
width: 165px;
|
||||
height: 50px;
|
||||
border-radius: 3px;
|
||||
background-color: #1db598;
|
||||
outline: none;
|
||||
border: none;
|
||||
font-size: 16px;
|
||||
color: white;
|
||||
}
|
||||
|
||||
em{
|
||||
font-style: normal;
|
||||
opacity: 0.5;
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
letter-spacing: 0.2px;
|
||||
color: #102445;
|
||||
}
|
||||
|
||||
.header{
|
||||
height: 92px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
width: 90%;
|
||||
margin: auto;
|
||||
}
|
||||
|
||||
.container{
|
||||
display: flex;
|
||||
height:100%;
|
||||
min-height: 100vh;
|
||||
}
|
||||
.nav{
|
||||
color: white;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 150px;
|
||||
background: #3c5f8d;
|
||||
}
|
||||
|
||||
.nav-item{
|
||||
height:150px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
flex-direction: column;
|
||||
border-bottom: 3px solid #2a4871;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-active{
|
||||
background: #f2f7f9;
|
||||
font-weight: bold;
|
||||
color: #1db598;
|
||||
}
|
||||
|
||||
|
||||
|
||||
.interface{
|
||||
display: flex;
|
||||
flex: 1;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
background: #f2f7f9;
|
||||
}
|
||||
|
||||
.query{
|
||||
margin-bottom: 30px;
|
||||
}
|
||||
.query,
|
||||
.output-container{
|
||||
width: 75%;
|
||||
}
|
||||
|
||||
.output{
|
||||
margin-bottom: 30px;
|
||||
}
|
||||
|
||||
.input-controls{
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.tabs{
|
||||
display: flex;
|
||||
background: #eaf2f6;
|
||||
}
|
||||
.active-tab{
|
||||
background: white;
|
||||
font-weight: bold;
|
||||
color: #1db598;
|
||||
|
||||
}
|
||||
|
||||
.tab{
|
||||
height:60px;
|
||||
width: 100px;
|
||||
border-top-right-radius: 5px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
visibility: visible;
|
||||
cursor: pointer;
|
||||
|
||||
}
|
||||
|
||||
.pane{
|
||||
background: white;
|
||||
padding: 30px;
|
||||
display: none;
|
||||
}
|
||||
|
||||
.active{
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
|
||||
.result-io-header{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin-bottom: 15px;
|
||||
}
|
||||
|
||||
.result-input,
|
||||
.result-ouput{
|
||||
border-radius: 2px;
|
||||
background-color: #fafafa;
|
||||
border: solid 1.5px #e4eff4;
|
||||
font-family: monospace;
|
||||
font-size: 16px;
|
||||
line-height: 1.5;
|
||||
letter-spacing: 1.1px;
|
||||
color: #102445;
|
||||
padding: 15px;
|
||||
margin-bottom: 15px;
|
||||
}
|
||||
|
||||
|
||||
.result-ouput{
|
||||
background-color: #edf9f7;
|
||||
border-left: solid 4px #1db598;
|
||||
}
|
||||
|
||||
|
||||
.raw{
|
||||
height: 253px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
209
webui/index.html
209
webui/index.html
|
|
@ -1,51 +1,172 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-alpha.6/css/bootstrap.min.css" integrity="sha384-rwoIResjU2yc3z8GV/NPeZWAv56rSmLldC3R/AZzGRnGxQQKnKkoFVhFQhNUwEyJ" crossorigin="anonymous">
|
||||
<link rel="stylesheet" href="/assets/main.css">
|
||||
</head>
|
||||
<body>
|
||||
<nav class="navbar navbar-toggleable-md navbar-inverse bg-inverse fixed-top">
|
||||
<button class="navbar-toggler navbar-toggler-right" type="button" data-toggle="collapse" data-target="#navbarsExampleDefault" aria-controls="navbarsExampleDefault" aria-expanded="false" aria-label="Toggle navigation">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
<a class="navbar-brand" href="#">Pilosa</a>
|
||||
|
||||
<div class="collapse navbar-collapse" id="navbarsExampleDefault">
|
||||
<ul class="navbar-nav mr-auto">
|
||||
<li class="nav-item active">
|
||||
<a class="nav-link" href="#">Query <span class="sr-only">(current)</span></a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/stats">Cluster Status</a>
|
||||
</li>
|
||||
</ul>
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<link rel="stylesheet" href="/assets/style.css">
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge">
|
||||
<title>Pilosa Console</title>
|
||||
</head>
|
||||
<body>
|
||||
<div class="header">
|
||||
<img src="https://dc3kpxyuw05cb.cloudfront.net/img/logo.svg" width="110" alt="">
|
||||
<a href='/' >Support</a>
|
||||
</div>
|
||||
<div class="container">
|
||||
<div class="nav">
|
||||
<div class="nav-item nav-active">
|
||||
<img style='margin-bottom:10px;' height='40px' src="/assets/nav_console.svg" alt="">
|
||||
Console
|
||||
</div>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<div class="input-bar">
|
||||
<div class="dropdown">
|
||||
<button class="btn btn-secondary dropdown-toggle" type="button" id="dropdownMenuButton" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
|
||||
Database
|
||||
</button>
|
||||
<div class="dropdown-menu" aria-labelledby="dropdownMenuButton">
|
||||
<a class="dropdown-item" href="#">1</a>
|
||||
<a class="dropdown-item" href="#">2</a>
|
||||
</div>
|
||||
</div>
|
||||
<textarea class="input-textarea"></textarea>
|
||||
<div class="nav-item">
|
||||
<img style='margin-bottom:10px;' height='20px' src="/assets/nav_cluster.svg" alt="">
|
||||
Cluster Admin
|
||||
</div>
|
||||
<div class="nav-item">
|
||||
<img style='margin-bottom:10px;' height='30px' src="/assets/nav_documentation.svg" alt="">
|
||||
Documentation
|
||||
</div>
|
||||
</div>
|
||||
<div class="container output"></div>
|
||||
<div class="interface">
|
||||
|
||||
<!-- todo: remove jquery and bootstrap -->
|
||||
<script src="https://code.jquery.com/jquery-3.1.1.slim.min.js" integrity="sha384-A7FZj7v+d/sdmMqp/nOQwliLvUsJfDHW+k9Omg/a/EheAdgtzNs3hpfag6Ed950n" crossorigin="anonymous"></script>
|
||||
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-alpha.6/js/bootstrap.min.js" integrity="sha384-vBWWzlZJ8ea9aCX4pEW3rVHjgjt7zpkNpZk+02D9phzyeVkE+jo0ieGizqPLForn" crossorigin="anonymous"></script>
|
||||
<script src="/assets/main.js"></script>
|
||||
<script>
|
||||
startup()
|
||||
</script>
|
||||
</body>
|
||||
<div class="query">
|
||||
<h2>Query</h2>
|
||||
<textarea name="name" id='query' rows="5" required></textarea>
|
||||
<div class='input-controls'>
|
||||
|
||||
<select class="" name="">
|
||||
<option value="">Index</option>
|
||||
</select>
|
||||
|
||||
<button id='query-btn'>Run Query</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="output-container">
|
||||
|
||||
<h2>Output</h2>
|
||||
<div id="outputs">
|
||||
|
||||
<!-- results -->
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
|
||||
|
||||
//helpers
|
||||
function prependChild(parent, newFirstChild) {
|
||||
parent.insertBefore(newFirstChild, parent.firstChild)
|
||||
}
|
||||
|
||||
var createSingleOutput = function(res){
|
||||
var node = document.createElement("div");
|
||||
node.classList.add('output');
|
||||
var markup =`
|
||||
|
||||
<div class="panes">
|
||||
<div class="pane active">
|
||||
<div class="result-io">
|
||||
<div class="result-io-header">
|
||||
<h5>Input</h5>
|
||||
|
||||
<em>Source: Index</em>
|
||||
</div>
|
||||
<div class="result-input">
|
||||
${res.input}
|
||||
</div>
|
||||
</div>
|
||||
<div class="result-io">
|
||||
<div class="result-io-header">
|
||||
<h5>output</h5>
|
||||
|
||||
<em>.42 ms</em>
|
||||
</div>
|
||||
<div class="result-ouput">
|
||||
${res.output}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="pane">
|
||||
<div class="raw">
|
||||
|
||||
<a href="${res.url}">Export raw .csv</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
`
|
||||
node.innerHTML = markup;
|
||||
|
||||
prependChild(document.getElementById("outputs"),node);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// mock data load
|
||||
var results=[
|
||||
{
|
||||
id:1,
|
||||
input:'Union(Bitmap(id=1, frame=“foo”), Bitmap(id=1), frame=“bar”))',
|
||||
output: '{“results”:[{“attrs”:bits”:[1,2,3,4,5,12,13,14]}]}',
|
||||
},
|
||||
{
|
||||
id:2,
|
||||
input:'SetBitmapAttrs(Bitmap(id=1, frame=“foo”), Bitmap(id=1), frame=“bar”))”))',
|
||||
output: 'null',
|
||||
}
|
||||
]
|
||||
for (var i = 0; i < results.length; i++){
|
||||
createSingleOutput(results[i]);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
//mock api
|
||||
function callAPI(){
|
||||
return {
|
||||
input:document.getElementById("query").value,
|
||||
output: `${queryBox.value} +1`
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//events
|
||||
var button = document.getElementById('query-btn');
|
||||
var queryBox = document.getElementById("query")
|
||||
|
||||
button.onclick = function(){
|
||||
var res = callAPI()
|
||||
createSingleOutput(res);
|
||||
}
|
||||
|
||||
|
||||
queryBox.addEventListener("keyup", function(event) {
|
||||
event.preventDefault();
|
||||
if (event.key == 'Enter') {
|
||||
button.click();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue