Merge branch 'main' into dev

This commit is contained in:
Owen
2025-08-13 10:58:04 -07:00
3 changed files with 1012 additions and 161 deletions

1063
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@@ -70,7 +70,7 @@
"cors": "2.8.5", "cors": "2.8.5",
"crypto-js": "^4.2.0", "crypto-js": "^4.2.0",
"drizzle-orm": "0.44.4", "drizzle-orm": "0.44.4",
"eslint": "9.32.0", "eslint": "9.33.0",
"eslint-config-next": "15.4.6", "eslint-config-next": "15.4.6",
"express": "5.1.0", "express": "5.1.0",
"express-rate-limit": "7.5.1", "express-rate-limit": "7.5.1",
@@ -82,7 +82,7 @@
"jmespath": "^0.16.0", "jmespath": "^0.16.0",
"js-yaml": "4.1.0", "js-yaml": "4.1.0",
"jsonwebtoken": "^9.0.2", "jsonwebtoken": "^9.0.2",
"lucide-react": "0.536.0", "lucide-react": "0.539.0",
"moment": "2.30.1", "moment": "2.30.1",
"next": "15.4.6", "next": "15.4.6",
"next-intl": "^4.3.4", "next-intl": "^4.3.4",
@@ -128,23 +128,23 @@
"@types/jsonwebtoken": "^9.0.10", "@types/jsonwebtoken": "^9.0.10",
"@types/node": "^24", "@types/node": "^24",
"@types/nodemailer": "6.4.17", "@types/nodemailer": "6.4.17",
"@types/pg": "8.15.4", "@types/pg": "8.15.5",
"@types/react": "19.1.9", "@types/react": "19.1.10",
"@types/react-dom": "19.1.7", "@types/react-dom": "19.1.7",
"@types/semver": "^7.7.0", "@types/semver": "^7.7.0",
"@types/swagger-ui-express": "^4.1.8", "@types/swagger-ui-express": "^4.1.8",
"@types/ws": "8.18.1", "@types/ws": "8.18.1",
"@types/yargs": "17.0.33", "@types/yargs": "17.0.33",
"drizzle-kit": "0.31.4", "drizzle-kit": "0.31.4",
"esbuild": "0.25.6", "esbuild": "0.25.9",
"esbuild-node-externals": "1.18.0", "esbuild-node-externals": "1.18.0",
"postcss": "^8", "postcss": "^8",
"react-email": "4.2.8", "react-email": "4.2.8",
"tailwindcss": "^4.1.4", "tailwindcss": "^4.1.4",
"tsc-alias": "1.8.16", "tsc-alias": "1.8.16",
"tsx": "4.20.3", "tsx": "4.20.4",
"typescript": "^5", "typescript": "^5",
"typescript-eslint": "^8.39.0" "typescript-eslint": "^8.39.1"
}, },
"overrides": { "overrides": {
"emblor": { "emblor": {

View File

@@ -107,7 +107,8 @@ export default function Page() {
}), }),
method: z.enum(["newt", "wireguard", "local"]), method: z.enum(["newt", "wireguard", "local"]),
copied: z.boolean(), copied: z.boolean(),
clientAddress: z.string().optional() clientAddress: z.string().optional(),
acceptClients: z.boolean()
}) })
.refine( .refine(
(data) => { (data) => {
@@ -170,6 +171,8 @@ export default function Page() {
const [wgConfig, setWgConfig] = useState(""); const [wgConfig, setWgConfig] = useState("");
const [createLoading, setCreateLoading] = useState(false); const [createLoading, setCreateLoading] = useState(false);
const [acceptClients, setAcceptClients] = useState(false);
const [newtVersion, setNewtVersion] = useState("latest");
const [siteDefaults, setSiteDefaults] = const [siteDefaults, setSiteDefaults] =
useState<PickSiteDefaultsResponse | null>(null); useState<PickSiteDefaultsResponse | null>(null);
@@ -199,55 +202,59 @@ PersistentKeepalive = 5`;
id: string, id: string,
secret: string, secret: string,
endpoint: string, endpoint: string,
version: string version: string,
acceptClients: boolean = false
) => { ) => {
const acceptClientsFlag = acceptClients ? " --accept-clients" : "";
const acceptClientsEnv = acceptClients ? "\n - ACCEPT_CLIENTS=true" : "";
const commands = { const commands = {
mac: { mac: {
"Apple Silicon (arm64)": [ "Apple Silicon (arm64)": [
`curl -L -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_darwin_arm64" && chmod +x ./newt`, `curl -L -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_darwin_arm64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
"Intel x64 (amd64)": [ "Intel x64 (amd64)": [
`curl -L -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_darwin_amd64" && chmod +x ./newt`, `curl -L -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_darwin_amd64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
linux: { linux: {
amd64: [ amd64: [
`wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_amd64" && chmod +x ./newt`, `wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_amd64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
arm64: [ arm64: [
`wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm64" && chmod +x ./newt`, `wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
arm32: [ arm32: [
`wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm32" && chmod +x ./newt`, `wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm32" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
arm32v6: [ arm32v6: [
`wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm32v6" && chmod +x ./newt`, `wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_arm32v6" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
riscv64: [ riscv64: [
`wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_riscv64" && chmod +x ./newt`, `wget -O newt "https://github.com/fosrl/newt/releases/download/${version}/newt_linux_riscv64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
freebsd: { freebsd: {
amd64: [ amd64: [
`fetch -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_freebsd_amd64" && chmod +x ./newt`, `fetch -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_freebsd_amd64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
arm64: [ arm64: [
`fetch -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_freebsd_arm64" && chmod +x ./newt`, `fetch -o newt "https://github.com/fosrl/newt/releases/download/${version}/newt_freebsd_arm64" && chmod +x ./newt`,
`./newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `./newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
windows: { windows: {
x64: [ x64: [
`curl -o newt.exe -L "https://github.com/fosrl/newt/releases/download/${version}/newt_windows_amd64.exe"`, `curl -o newt.exe -L "https://github.com/fosrl/newt/releases/download/${version}/newt_windows_amd64.exe"`,
`newt.exe --id ${id} --secret ${secret} --endpoint ${endpoint}` `newt.exe --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
docker: { docker: {
@@ -260,10 +267,10 @@ PersistentKeepalive = 5`;
environment: environment:
- PANGOLIN_ENDPOINT=${endpoint} - PANGOLIN_ENDPOINT=${endpoint}
- NEWT_ID=${id} - NEWT_ID=${id}
- NEWT_SECRET=${secret}` - NEWT_SECRET=${secret}${acceptClientsEnv}`
], ],
"Docker Run": [ "Docker Run": [
`docker run -dit fosrl/newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `docker run -dit fosrl/newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
podman: { podman: {
@@ -276,7 +283,7 @@ ContainerName=newt
Image=docker.io/fosrl/newt Image=docker.io/fosrl/newt
Environment=PANGOLIN_ENDPOINT=${endpoint} Environment=PANGOLIN_ENDPOINT=${endpoint}
Environment=NEWT_ID=${id} Environment=NEWT_ID=${id}
Environment=NEWT_SECRET=${secret} Environment=NEWT_SECRET=${secret}${acceptClients ? "\nEnvironment=ACCEPT_CLIENTS=true" : ""}
# Secret=newt-secret,type=env,target=NEWT_SECRET # Secret=newt-secret,type=env,target=NEWT_SECRET
[Service] [Service]
@@ -286,15 +293,15 @@ Restart=always
WantedBy=default.target` WantedBy=default.target`
], ],
"Podman Run": [ "Podman Run": [
`podman run -dit docker.io/fosrl/newt --id ${id} --secret ${secret} --endpoint ${endpoint}` `podman run -dit docker.io/fosrl/newt --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
}, },
nixos: { nixos: {
x86_64: [ x86_64: [
`nix run 'nixpkgs#fosrl-newt' -- --id ${id} --secret ${secret} --endpoint ${endpoint}` `nix run 'nixpkgs#fosrl-newt' -- --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
], ],
aarch64: [ aarch64: [
`nix run 'nixpkgs#fosrl-newt' -- --id ${id} --secret ${secret} --endpoint ${endpoint}` `nix run 'nixpkgs#fosrl-newt' -- --id ${id} --secret ${secret} --endpoint ${endpoint}${acceptClientsFlag}`
] ]
} }
}; };
@@ -393,7 +400,8 @@ WantedBy=default.target`
name: "", name: "",
copied: false, copied: false,
method: "newt", method: "newt",
clientAddress: "" clientAddress: "",
acceptClients: false
} }
}); });
@@ -469,7 +477,7 @@ WantedBy=default.target`
const load = async () => { const load = async () => {
setLoadingPage(true); setLoadingPage(true);
let newtVersion = "latest"; let currentNewtVersion = "latest";
try { try {
const response = await fetch( const response = await fetch(
@@ -484,7 +492,8 @@ WantedBy=default.target`
} }
const data = await response.json(); const data = await response.json();
const latestVersion = data.tag_name; const latestVersion = data.tag_name;
newtVersion = latestVersion; currentNewtVersion = latestVersion;
setNewtVersion(latestVersion);
} catch (error) { } catch (error) {
console.error( console.error(
t("newtErrorFetchLatest", { t("newtErrorFetchLatest", {
@@ -530,7 +539,8 @@ WantedBy=default.target`
newtId, newtId,
newtSecret, newtSecret,
env.app.dashboardUrl, env.app.dashboardUrl,
newtVersion currentNewtVersion,
acceptClients
); );
hydrateWireGuardConfig( hydrateWireGuardConfig(
@@ -653,6 +663,48 @@ WantedBy=default.target`
)} )}
/> />
)} )}
{form.watch("method") ===
"newt" && (
<FormField
control={form.control}
name="acceptClients"
render={({ field }) => (
<FormItem>
<div className="flex items-center space-x-2">
<Checkbox
id="acceptClients"
checked={field.value}
onCheckedChange={(checked) => {
const value = checked as boolean;
field.onChange(value);
setAcceptClients(value);
// Re-hydrate commands with new acceptClients value
if (newtId && newtSecret) {
hydrateCommands(
newtId,
newtSecret,
env.app.dashboardUrl,
newtVersion,
value
);
}
}}
/>
<label
htmlFor="acceptClients"
className="text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70"
>
Accept client connections
</label>
</div>
<FormDescription>
Allow other devices to connect through this newt instance as a gateway.
</FormDescription>
<FormMessage />
</FormItem>
)}
/>
)}
</form> </form>
</Form> </Form>
</SettingsSectionForm> </SettingsSectionForm>