mirror of
https://github.com/arsvendg/Stirling-PDF.git
synced 2026-07-15 19:10:47 +02:00
Desktop self-hosted connection logging (#5410)
Also added in automotic protocol addition if missing. Defaults to https:// --------- Co-authored-by: Anthony Stirling <[email protected]>
This commit is contained in:
co-authored by
Anthony Stirling
parent
a284dbfc15
commit
72389f5872
@@ -20,36 +20,67 @@ export const ServerSelection: React.FC<ServerSelectionProps> = ({ onSelect, load
|
||||
const handleSubmit = async (e: React.FormEvent) => {
|
||||
e.preventDefault();
|
||||
|
||||
// Normalize URL: trim and remove trailing slashes
|
||||
const url = customUrl.trim().replace(/\/+$/, '');
|
||||
// Normalize and validate URL
|
||||
let url = customUrl.trim().replace(/\/+$/, '');
|
||||
|
||||
if (!url) {
|
||||
setTestError(t('setup.server.error.emptyUrl', 'Please enter a server URL'));
|
||||
return;
|
||||
}
|
||||
|
||||
// Auto-add https:// if no protocol specified
|
||||
if (!url.startsWith('http://') && !url.startsWith('https://')) {
|
||||
console.log('[ServerSelection] No protocol specified, adding https://');
|
||||
url = `https://${url}`;
|
||||
setCustomUrl(url); // Update the input field
|
||||
}
|
||||
|
||||
// Validate URL format
|
||||
try {
|
||||
const urlObj = new URL(url);
|
||||
console.log('[ServerSelection] Valid URL:', {
|
||||
protocol: urlObj.protocol,
|
||||
hostname: urlObj.hostname,
|
||||
port: urlObj.port,
|
||||
pathname: urlObj.pathname,
|
||||
});
|
||||
} catch (err) {
|
||||
console.error('[ServerSelection] Invalid URL format:', err);
|
||||
setTestError(t('setup.server.error.invalidUrl', 'Invalid URL format. Please enter a valid URL like https://your-server.com'));
|
||||
return;
|
||||
}
|
||||
|
||||
// Test connection before proceeding
|
||||
setTesting(true);
|
||||
setTestError(null);
|
||||
setSecurityDisabled(false);
|
||||
|
||||
try {
|
||||
const isReachable = await connectionModeService.testConnection(url);
|
||||
console.log(`[ServerSelection] Testing connection to: ${url}`);
|
||||
|
||||
if (!isReachable) {
|
||||
setTestError(t('setup.server.error.unreachable', 'Could not connect to server'));
|
||||
try {
|
||||
const testResult = await connectionModeService.testConnection(url);
|
||||
|
||||
if (!testResult.success) {
|
||||
console.error('[ServerSelection] Connection test failed:', testResult);
|
||||
setTestError(testResult.error || t('setup.server.error.unreachable', 'Could not connect to server'));
|
||||
setTesting(false);
|
||||
return;
|
||||
}
|
||||
|
||||
console.log('[ServerSelection] ✅ Connection test successful');
|
||||
|
||||
// Fetch OAuth providers and check if login is enabled
|
||||
const enabledProviders: SSOProviderConfig[] = [];
|
||||
try {
|
||||
console.log('[ServerSelection] Fetching login configuration...');
|
||||
const response = await fetch(`${url}/api/v1/proprietary/ui-data/login`);
|
||||
|
||||
// Check if security is disabled (status 403 or error response)
|
||||
if (!response.ok) {
|
||||
console.warn(`[ServerSelection] Login config request failed with status ${response.status}`);
|
||||
|
||||
if (response.status === 403 || response.status === 401) {
|
||||
console.log('[ServerSelection] Security is disabled on this server');
|
||||
setSecurityDisabled(true);
|
||||
setTesting(false);
|
||||
return;
|
||||
@@ -65,10 +96,11 @@ export const ServerSelection: React.FC<ServerSelectionProps> = ({ onSelect, load
|
||||
}
|
||||
|
||||
const data = await response.json();
|
||||
console.log('Login UI data:', data);
|
||||
console.log('[ServerSelection] Login UI data:', data);
|
||||
|
||||
// Check if the response indicates security is disabled
|
||||
if (data.enableLogin === false || data.securityEnabled === false) {
|
||||
console.log('[ServerSelection] Security is explicitly disabled in config');
|
||||
setSecurityDisabled(true);
|
||||
setTesting(false);
|
||||
return;
|
||||
@@ -90,32 +122,39 @@ export const ServerSelection: React.FC<ServerSelectionProps> = ({ onSelect, load
|
||||
});
|
||||
});
|
||||
|
||||
console.log('[ServerSelection] Detected OAuth providers:', enabledProviders);
|
||||
console.log('[ServerSelection] ✅ Detected OAuth providers:', enabledProviders);
|
||||
} catch (err) {
|
||||
console.error('[ServerSelection] Failed to fetch login configuration', err);
|
||||
console.error('[ServerSelection] ❌ Failed to fetch login configuration:', err);
|
||||
|
||||
// Check if it's a security disabled error
|
||||
if (err instanceof Error && (err.message.includes('403') || err.message.includes('401'))) {
|
||||
console.log('[ServerSelection] Security is disabled (error-based detection)');
|
||||
setSecurityDisabled(true);
|
||||
setTesting(false);
|
||||
return;
|
||||
}
|
||||
|
||||
// For any other error (network, CORS, invalid JSON, etc.), show error and don't proceed
|
||||
const errorMessage = err instanceof Error ? err.message : 'Unknown error';
|
||||
console.error('[ServerSelection] Configuration fetch error details:', errorMessage);
|
||||
|
||||
setTestError(
|
||||
t('setup.server.error.configFetch', 'Failed to fetch server configuration. Please check the URL and try again.')
|
||||
t('setup.server.error.configFetch', 'Failed to fetch server configuration: {{error}}', {
|
||||
error: errorMessage
|
||||
})
|
||||
);
|
||||
setTesting(false);
|
||||
return;
|
||||
}
|
||||
|
||||
// Connection successful - pass URL and OAuth providers
|
||||
console.log('[ServerSelection] ✅ Server selection complete, proceeding to login');
|
||||
onSelect({
|
||||
url,
|
||||
enabledOAuthProviders: enabledProviders.length > 0 ? enabledProviders : undefined,
|
||||
});
|
||||
} catch (error) {
|
||||
console.error('Connection test failed:', error);
|
||||
console.error('[ServerSelection] ❌ Unexpected error during connection test:', error);
|
||||
setTestError(
|
||||
error instanceof Error
|
||||
? error.message
|
||||
|
||||
@@ -101,7 +101,12 @@ export const SetupWizard: React.FC<SetupWizardProps> = ({ onComplete }) => {
|
||||
};
|
||||
|
||||
const handleSelfHostedLogin = async (username: string, password: string) => {
|
||||
console.log('[SetupWizard] 🔐 Starting self-hosted login');
|
||||
console.log(`[SetupWizard] Server: ${serverConfig?.url}`);
|
||||
console.log(`[SetupWizard] Username: ${username}`);
|
||||
|
||||
if (!serverConfig) {
|
||||
console.error('[SetupWizard] ❌ No server configured');
|
||||
setError('No server configured');
|
||||
return;
|
||||
}
|
||||
@@ -110,19 +115,35 @@ export const SetupWizard: React.FC<SetupWizardProps> = ({ onComplete }) => {
|
||||
setLoading(true);
|
||||
setError(null);
|
||||
|
||||
console.log('[SetupWizard] Step 1: Authenticating with server...');
|
||||
await authService.login(serverConfig.url, username, password);
|
||||
console.log('[SetupWizard] ✅ Authentication successful');
|
||||
|
||||
console.log('[SetupWizard] Step 2: Switching to self-hosted mode...');
|
||||
await connectionModeService.switchToSelfHosted(serverConfig);
|
||||
console.log('[SetupWizard] ✅ Switched to self-hosted mode');
|
||||
|
||||
console.log('[SetupWizard] Step 3: Initializing external backend...');
|
||||
await tauriBackendService.initializeExternalBackend();
|
||||
console.log('[SetupWizard] ✅ External backend initialized');
|
||||
|
||||
console.log('[SetupWizard] ✅ Setup complete, calling onComplete()');
|
||||
onComplete();
|
||||
} catch (err) {
|
||||
console.error('Self-hosted login failed:', err);
|
||||
setError(err instanceof Error ? err.message : 'Self-hosted login failed');
|
||||
console.error('[SetupWizard] ❌ Self-hosted login failed:', err);
|
||||
const errorMessage = err instanceof Error ? err.message : 'Self-hosted login failed';
|
||||
console.error('[SetupWizard] Error message:', errorMessage);
|
||||
setError(errorMessage);
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
const handleSelfHostedOAuthSuccess = async (_userInfo: UserInfo) => {
|
||||
console.log('[SetupWizard] 🔐 OAuth login successful, completing setup');
|
||||
console.log(`[SetupWizard] Server: ${serverConfig?.url}`);
|
||||
|
||||
if (!serverConfig) {
|
||||
console.error('[SetupWizard] ❌ No server configured');
|
||||
setError('No server configured');
|
||||
return;
|
||||
}
|
||||
@@ -131,13 +152,22 @@ export const SetupWizard: React.FC<SetupWizardProps> = ({ onComplete }) => {
|
||||
setLoading(true);
|
||||
setError(null);
|
||||
|
||||
// OAuth already completed by authService.loginWithOAuth
|
||||
console.log('[SetupWizard] Step 1: OAuth already completed');
|
||||
console.log('[SetupWizard] Step 2: Switching to self-hosted mode...');
|
||||
await connectionModeService.switchToSelfHosted(serverConfig);
|
||||
console.log('[SetupWizard] ✅ Switched to self-hosted mode');
|
||||
|
||||
console.log('[SetupWizard] Step 3: Initializing external backend...');
|
||||
await tauriBackendService.initializeExternalBackend();
|
||||
console.log('[SetupWizard] ✅ External backend initialized');
|
||||
|
||||
console.log('[SetupWizard] ✅ Setup complete, calling onComplete()');
|
||||
onComplete();
|
||||
} catch (err) {
|
||||
console.error('Self-hosted OAuth login completion failed:', err);
|
||||
setError(err instanceof Error ? err.message : 'Failed to complete login');
|
||||
console.error('[SetupWizard] ❌ Self-hosted OAuth login completion failed:', err);
|
||||
const errorMessage = err instanceof Error ? err.message : 'Failed to complete login';
|
||||
console.error('[SetupWizard] Error message:', errorMessage);
|
||||
setError(errorMessage);
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user