Addresses #2, more work is needed to finalize management of existing records

This commit is contained in:
2025-06-29 23:05:07 -05:00
parent 10af09b4ec
commit 0848a3b938
10 changed files with 186 additions and 82 deletions

4
.gitignore vendored
View File

@ -22,4 +22,6 @@ dist-ssr
*.njsproj *.njsproj
*.sln *.sln
*.sw? *.sw?
.env .env
*api*/

View File

@ -1,5 +1,5 @@
{ {
"name": "my-vue-app", "name": "kingdom",
"private": true, "private": true,
"version": "0.0.0", "version": "0.0.0",
"type": "module", "type": "module",
@ -11,14 +11,14 @@
}, },
"dependencies": { "dependencies": {
"envy": "^2.0.0", "envy": "^2.0.0",
"react": "^18.3.1", "react": "19",
"react-dom": "^18.3.1", "react-dom": "19",
"react-router-dom": "6" "react-router-dom": "6"
}, },
"devDependencies": { "devDependencies": {
"@eslint/js": "^9.17.0", "@eslint/js": "^9.17.0",
"@types/react": "^18.3.18", "@types/react": "19",
"@types/react-dom": "^18.3.5", "@types/react-dom": "19",
"@vitejs/plugin-react": "^4.3.4", "@vitejs/plugin-react": "^4.3.4",
"eslint": "^9.17.0", "eslint": "^9.17.0",
"eslint-plugin-react": "^7.37.2", "eslint-plugin-react": "^7.37.2",

View File

@ -35,7 +35,10 @@ input {
margin: 8px 0; margin: 8px 0;
box-sizing: border-box; box-sizing: border-box;
} }
input[type="radio"] {
margin-top: -1px;
vertical-align: middle;
}
select { select {
width: 100%; width: 100%;
} }

View File

@ -1 +0,0 @@
console.log(4)

View File

@ -1,10 +0,0 @@
import './piholeClient'
import './nginxClient'
function registerApp(props){
alert(JSON.stringify(props))
const formData = props
}
export default registerApp;

View File

@ -0,0 +1,8 @@
import pihole from './piholeClient.jsx'
// import './nginxClient'
const registerApp = (fqdn, cnameTarget, targetHost, upstreamPort, protocol) => {
console.log('Register App data: ',fqdn, cnameTarget, targetHost, upstreamPort, protocol)
pihole(fqdn, cnameTarget)
}
export default registerApp;

View File

@ -0,0 +1,71 @@
const piholeURL = `${import.meta.env.VITE_PIHOLE_URL}/api`
const piholeAuth = async () => {
const session = await fetch(`${piholeURL}/auth`, {
method: "POST",
body: JSON.stringify({ "password": import.meta.env.VITE_PIHOLE_PASSWORD })
})
.then(response => {
if (response.ok) {
return response.json()
}
else console.log(response.status) && console.log(response.statusText)
})
.then(data => data.session)
.catch(error => console.log(error))
return session
}
const getRecords = async (session) => {
const configDNS = await fetch(`${piholeURL}/config/dns/cnameRecords`, {
method: "GET",
headers: {"sid": session.sid}
})
.then(response => {
if (response.ok) {
return response.json()
}
else console.log(response.status) && console.log(response.statusText)
})
.then(data => {
// console.log('getRecords: return data',data)
return data
})
.catch(error => console.log(error))
return {configDNS, session}
}
const makeRecord = async (data, session, fqdn, cnameTarget) => {
const putRecord = await fetch(`${piholeURL}/config/dns/cnameRecords/${fqdn},${cnameTarget}`, {
method: "PUT",
headers: {"sid": session.sid}
})
.then(response => {
if (response.status === 201){
// console.log(`Response: ${response.status}`)
return response.json()
}
if (!response.ok){
// console.log(`Response: ${response.status} ${response.statusText}`)
return response.json()
}
else console.log(response.status) && console.log(response.statusText)
})
.then(data => {
if (data.error){console.log(data.error.message, data.error.hint)}
return data
})
.catch(console.error)
return putRecord
}
const pihole = (fqdn, cnameTarget) => {
const pi = piholeAuth()
pi.then(s => getRecords(s))
.then((a) => {
// console.log('pihole after getRecords', a.configDNS, a.session)
makeRecord(a.configDNS, a.session, fqdn, cnameTarget)
})
}
export default pihole

View File

@ -1,72 +1,114 @@
import { useState } from 'react'; import { useState } from 'react';
import registerApp from '../assets/orchestration' import registerApp from '../assets/orchestration.jsx'
function MyForm() { function Form() {
const [inputs, setInputs] = useState({}); const envCnameTarget = import.meta.env.VITE_CNAME_TARGET_DEFAULT || ''
const [fqdn, setFQDN] = useState('');
const [cnameTarget, setCnameTarget] = useState(envCnameTarget);
const [targetHost, setTargetHost] = useState('');
const [upstreamPort, setUpstreamPort] = useState('');
const [protocol, setProtocol] = useState('http');
const handleChange = (event) => {
const name = event.target.name;
const value = event.target.value;
setInputs(values => ({ ...values, [name]: value }))
}
return ( return (
<> <>
<form className='card'> <form className='card' id="create-service" action={
() => registerApp(fqdn, cnameTarget, targetHost, upstreamPort, protocol)}>
<h4>DNS</h4> <h4>DNS</h4>
<label>FQDN <label>
<input type="text" name="fqdn" value={inputs.fqdn} onChange={handleChange} placeholder='Target DNS name.' required autoFocus/> FQDN
<input
type="text"
name="fqdn"
value={fqdn}
onChange={e => setFQDN(e.target.value)}
placeholder='Target DNS name.'
required
autoFocus />
</label> </label>
<br /> <br />
<label>CNAME Target <label>
<input type="text" name="cname_target" value={inputs.cname_target} onChange={handleChange} placeholder='cygnus.int.jonb.io' required/> CNAME Target
<input
type="text"
name="cnameTarget"
value={cnameTarget}
onChange={e => setCnameTarget(e.target.value)}
placeholder='Backend server DNS CNAME'
required />
</label> </label>
<br /> <br />
<h4>Reverse Proxy</h4> <h4>Reverse Proxy</h4>
<label>FQDN <label>
<input type="text" value={inputs.fqdn} onChange={handleChange} disabled placeholder='Automatically filled, Target DNS name'/> FQDN
<input
type="text"
value={fqdn}
disabled
placeholder='Target DNS name' />
</label> </label>
<br /> <br />
<label>Target Host <label>
<input type="text" name="target_host" value={inputs.target_host} onChange={handleChange} placeholder='Network host Domain or IP' required/> Target Host
<input
type="text"
name="targetHost"
value={targetHost}
onChange={e => setTargetHost(e.target.value)}
placeholder='Network host Domain or IP'
required />
</label> </label>
<br /> <br />
<label>Upstream Port <label>
<input type="number" name="upstream_port" value={inputs.upstream_port} onChange={handleChange} placeholder='Port the target service is listening on.' required/> Upstream Port
<input
type="number"
name="upstreamPort"
value={upstreamPort}
onChange={e => setUpstreamPort(e.target.value)}
placeholder='Port the target service is listening on.'
required />
</label> </label>
<br /> <br />
<label>Protocol <select
<select name="protocol" value={inputs.protocol || "http"} onChange={handleChange}> name="protocol"
<option value="http" selected>HTTP</option> value={protocol}
<option value="https">HTTPS</option> onChange={e => setProtocol(e.target.value)}>
</select> <option value="http">http</option>
</label> <option value="https">https</option>
</select>
<br /> <br />
<button className="button" type="submit" onChange={handleChange} onClick={() => registerApp({inputs})}>Submit</button> <button
className="button"
type="submit">
Create
</button>
</form> </form>
</> </>
) )
} }
function Home() { function Home() {
return (<><h2>Deploy New App</h2> return (
<MyForm /> <>
</> <h2>Deploy New App</h2>
<Form />
</>
) )
} }

View File

@ -562,22 +562,16 @@
resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.15.tgz#596a1747233694d50f6ad8a7869fcb6f56cf5841" resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.15.tgz#596a1747233694d50f6ad8a7869fcb6f56cf5841"
integrity sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA== integrity sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==
"@types/prop-types@*": "@types/react-dom@19":
version "15.7.14" version "19.1.6"
resolved "https://registry.yarnpkg.com/@types/prop-types/-/prop-types-15.7.14.tgz#1433419d73b2a7ebfc6918dcefd2ec0d5cd698f2" resolved "https://registry.yarnpkg.com/@types/react-dom/-/react-dom-19.1.6.tgz#4af629da0e9f9c0f506fc4d1caa610399c595d64"
integrity sha512-gNMvNH49DJ7OJYv+KAKn0Xp45p8PLl6zo2YnvDIbTd4J6MER2BmWN49TG7n9LvkyihINxeKW8+3bfS2yDC9dzQ== integrity sha512-4hOiT/dwO8Ko0gV1m/TJZYk3y0KBnY9vzDh7W+DH17b2HFSOGgdj33dhihPeuy3l0q23+4e+hoXHV6hCC4dCXw==
"@types/react-dom@^18.3.5": "@types/react@19":
version "18.3.7" version "19.1.8"
resolved "https://registry.yarnpkg.com/@types/react-dom/-/react-dom-18.3.7.tgz#b89ddf2cd83b4feafcc4e2ea41afdfb95a0d194f" resolved "https://registry.yarnpkg.com/@types/react/-/react-19.1.8.tgz#ff8395f2afb764597265ced15f8dddb0720ae1c3"
integrity sha512-MEe3UeoENYVFXzoXEWsvcpg6ZvlrFNlOQ7EOsvhI3CfAXwzPfO8Qwuxd40nepsYKqyyVQnTdEfv68q91yLcKrQ== integrity sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g==
"@types/react@^18.3.18":
version "18.3.20"
resolved "https://registry.yarnpkg.com/@types/react/-/react-18.3.20.tgz#b0dccda9d2f1bc24d2a04b1d0cb5d0b9a3576ad3"
integrity sha512-IPaCZN7PShZK/3t6Q87pfTkRm6oLTd4vztyoj+cbHUF1g3FfVb2tFIL79uCRKEfv16AhqDMBywP2VW3KIZUvcg==
dependencies: dependencies:
"@types/prop-types" "*"
csstype "^3.0.2" csstype "^3.0.2"
"@vitejs/plugin-react@^4.3.4": "@vitejs/plugin-react@^4.3.4":
@ -1709,7 +1703,7 @@ lodash.merge@^4.6.2:
resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a"
integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==
loose-envify@^1.1.0, loose-envify@^1.4.0: loose-envify@^1.4.0:
version "1.4.0" version "1.4.0"
resolved "https://registry.yarnpkg.com/loose-envify/-/loose-envify-1.4.0.tgz#71ee51fa7be4caec1a63839f7e682d8132d30caf" resolved "https://registry.yarnpkg.com/loose-envify/-/loose-envify-1.4.0.tgz#71ee51fa7be4caec1a63839f7e682d8132d30caf"
integrity sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q== integrity sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==
@ -1934,13 +1928,12 @@ quick-lru@^1.0.0:
resolved "https://registry.yarnpkg.com/quick-lru/-/quick-lru-1.1.0.tgz#4360b17c61136ad38078397ff11416e186dcfbb8" resolved "https://registry.yarnpkg.com/quick-lru/-/quick-lru-1.1.0.tgz#4360b17c61136ad38078397ff11416e186dcfbb8"
integrity sha512-tRS7sTgyxMXtLum8L65daJnHUhfDUgboRdcWW2bR9vBfrj2+O5HSMbQOJfJJjIVSPFqbBCF37FpwWXGitDc5tA== integrity sha512-tRS7sTgyxMXtLum8L65daJnHUhfDUgboRdcWW2bR9vBfrj2+O5HSMbQOJfJJjIVSPFqbBCF37FpwWXGitDc5tA==
react-dom@^18.3.1: react-dom@19:
version "18.3.1" version "19.1.0"
resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-18.3.1.tgz#c2265d79511b57d479b3dd3fdfa51536494c5cb4" resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-19.1.0.tgz#133558deca37fa1d682708df8904b25186793623"
integrity sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw== integrity sha512-Xs1hdnE+DyKgeHJeJznQmYMIBG3TKIHJJT95Q58nHLSrElKlGQqDTR2HQ9fx5CN/Gk6Vh/kupBTDLU11/nDk/g==
dependencies: dependencies:
loose-envify "^1.1.0" scheduler "^0.26.0"
scheduler "^0.23.2"
react-is@^16.13.1: react-is@^16.13.1:
version "16.13.1" version "16.13.1"
@ -1967,12 +1960,10 @@ react-router@6.30.0:
dependencies: dependencies:
"@remix-run/router" "1.23.0" "@remix-run/router" "1.23.0"
react@^18.3.1: react@19:
version "18.3.1" version "19.1.0"
resolved "https://registry.yarnpkg.com/react/-/react-18.3.1.tgz#49ab892009c53933625bd16b2533fc754cab2891" resolved "https://registry.yarnpkg.com/react/-/react-19.1.0.tgz#926864b6c48da7627f004795d6cce50e90793b75"
integrity sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ== integrity sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==
dependencies:
loose-envify "^1.1.0"
reflect.getprototypeof@^1.0.6, reflect.getprototypeof@^1.0.9: reflect.getprototypeof@^1.0.6, reflect.getprototypeof@^1.0.9:
version "1.0.10" version "1.0.10"
@ -2071,12 +2062,10 @@ safe-regex-test@^1.1.0:
es-errors "^1.3.0" es-errors "^1.3.0"
is-regex "^1.2.1" is-regex "^1.2.1"
scheduler@^0.23.2: scheduler@^0.26.0:
version "0.23.2" version "0.26.0"
resolved "https://registry.yarnpkg.com/scheduler/-/scheduler-0.23.2.tgz#414ba64a3b282892e944cf2108ecc078d115cdc3" resolved "https://registry.yarnpkg.com/scheduler/-/scheduler-0.26.0.tgz#4ce8a8c2a2095f13ea11bf9a445be50c555d6337"
integrity sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ== integrity sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA==
dependencies:
loose-envify "^1.1.0"
semver@^6.3.1: semver@^6.3.1:
version "6.3.1" version "6.3.1"