small frontend fix

This commit is contained in:
d34dscene
2024-10-03 21:55:47 +02:00
parent 0c0347c41f
commit 7bed0552b0
7 changed files with 78 additions and 26 deletions

View File

@@ -4,7 +4,7 @@ on:
push:
branches:
- main
jobs:
build:
runs-on: ubuntu-latest

View File

@@ -25,10 +25,10 @@ var backupCron *cron.Cron
// BackupData is the structure for the full manual backup
type BackupData struct {
Profiles []db.Profile `json:"profiles"`
Configs []*traefik.Dynamic `json:"configs"`
Providers []db.Provider `json:"providers"`
Settings []db.Setting `json:"settings"`
Users []db.User `json:"users"`
Configs []*traefik.Dynamic `json:"configs"`
}
func DumpBackup(ctx context.Context) (*BackupData, error) {
@@ -44,12 +44,37 @@ func DumpBackup(ctx context.Context) (*BackupData, error) {
if err != nil {
return nil, fmt.Errorf("failed to get configs: %w", err)
}
// We're only interested in the our local provider
for _, config := range configs {
dynamic, err := traefik.DecodeConfig(config)
if err != nil {
return nil, fmt.Errorf("failed to decode config: %w", err)
}
data.Configs = append(data.Configs, dynamic)
newDynamic := &traefik.Dynamic{
ProfileID: config.ProfileID,
Routers: make(map[string]traefik.Router),
Services: make(map[string]traefik.Service),
Middlewares: make(map[string]traefik.Middleware),
}
for i, router := range dynamic.Routers {
if router.Provider == "http" {
newDynamic.Routers[i] = router
}
}
for i, service := range dynamic.Services {
if service.Provider == "http" {
newDynamic.Services[i] = service
}
}
for i, middleware := range dynamic.Middlewares {
if middleware.Provider == "http" {
newDynamic.Middlewares[i] = middleware
}
}
data.Configs = append(data.Configs, newDynamic)
}
data.Providers, err = db.Query.ListProviders(ctx)

View File

@@ -450,7 +450,7 @@ func GetTraefikConfig() {
// Sync periodically syncs the Traefik configuration
func Sync(ctx context.Context) {
ticker := time.NewTicker(time.Second * 60)
ticker := time.NewTicker(time.Second * 10)
defer ticker.Stop()
GetTraefikConfig()

View File

@@ -127,7 +127,6 @@
const validate = () => {
try {
middleware.headers = headersSchema.parse(middleware.headers);
console.log(middleware.headers.stsSeconds);
errors = {};
} catch (err) {
if (err instanceof z.ZodError) {

View File

@@ -83,7 +83,6 @@
$: isNameTaken = $middlewares.some((m) => m.name === middleware.name + '@' + middleware.provider);
onMount(async () => {
console.log(middleware);
checkType();
form = await LoadMiddlewareForm(middleware);
});

View File

@@ -14,7 +14,7 @@
toggleMiddleware,
toggleDNSProvider
} from '$lib/api';
import { newRouter, type Router } from '$lib/types/config';
import { type Router } from '$lib/types/config';
import RuleEditor from '../utils/ruleEditor.svelte';
import ArrayInput from '../ui/array-input/array-input.svelte';
import logo from '$lib/images/logo.svg';
@@ -25,23 +25,39 @@
export let router: Router;
export let disabled = false;
const formSchema = z.object({
name: z.string({ required_error: 'Name is required' }).min(1).max(255),
provider: z.string().optional(),
status: z.string().optional(),
routerType: z
.string()
.toLowerCase()
.regex(/^(http|tcp|udp)$/),
dnsProvider: z.coerce.number().int().nonnegative().optional(),
entrypoints: z.array(z.string()).optional(),
middlewares: z.array(z.string()).optional(),
rule: z.string({ required_error: 'Rule is required' }).min(1, { message: 'Rule is required' }),
priority: z.coerce.number().int().nonnegative().optional(),
tls: z.object({
certResolver: z.string().trim().optional()
const formSchema = z
.object({
name: z.string().trim().min(1, 'Name is required').max(255),
provider: z.string().trim().optional(),
status: z.string().trim().optional(),
routerType: z
.string()
.toLowerCase()
.regex(/^(http|tcp|udp)$/),
dnsProvider: z.coerce.number().int().nonnegative().optional(),
entrypoints: z.array(z.string()).optional(),
middlewares: z.array(z.string()).optional(),
rule: z.string().trim().optional(),
priority: z.coerce.number().int().nonnegative().optional(),
tls: z
.object({
certResolver: z.string().trim().optional()
})
.optional()
})
});
.refine(
(data) => {
// Conditionally check if `rule` is required for `http` or `tcp`
if (['http', 'tcp'].includes(data.routerType) && !data.rule) {
return false;
}
return true;
},
{
message: 'Rule is required for HTTP and TCP routers',
path: ['rule'] // This points to the 'rule' field
}
);
let errors: Record<any, string[] | undefined> = {};
export const validate = () => {
@@ -298,6 +314,9 @@
<!-- Rule -->
{#if router.routerType === 'http' || router.routerType === 'tcp'}
{#if errors.rule}
<div class="col-span-4 text-right text-sm text-red-500">{errors.rule}</div>
{/if}
<RuleEditor bind:rule={router.rule} bind:type={router.routerType} {disabled} />
{/if}
</Card.Content>

View File

@@ -24,7 +24,19 @@
.regex(/^(http|tcp|udp)$/),
serverStatus: z.record(z.string()).optional(),
loadBalancer: z.object({
servers: z.array(z.object({ url: z.string() }).or(z.object({ address: z.string() }))),
servers: z
.array(
z
.object({
url: z.string().trim().optional(),
address: z.string().trim().optional()
})
.refine((data) => data.url || data.address, {
message: 'At least one server is required',
path: ['servers'] // Points to the 'servers' array in case of error
})
)
.nonempty('At least one server is required'),
passHostHeader: z.boolean().optional()
})
});
@@ -33,7 +45,6 @@
export const validate = () => {
try {
serviceSchema.parse({ ...service });
errors = {};
return true;
} catch (err) {
@@ -45,7 +56,6 @@
};
const update = () => {
validate();
if (service.loadBalancer === undefined) service.loadBalancer = { servers: [] };
service.loadBalancer.passHostHeader = passHostHeader;