fix: Handle quoted password hash and improve temp directory setup
continuous-integration/drone/push Build is passing

- Strip surrounding quotes from ADMIN_PASSWORD_HASH (Portainer adds them)
- Rewrite temp directory initialization with better fallback logic
- Ensure /app/temp directory exists with correct permissions in Docker
This commit is contained in:
Paul Nothaft
2026-01-05 22:30:59 +01:00
parent 6beb4ae03c
commit 82d4c37294
3 changed files with 53 additions and 41 deletions
+2 -2
View File
@@ -52,8 +52,8 @@ RUN addgroup -g 1001 -S nodejs && \
adduser -S nodejs -u 1001
# Create necessary directories with proper permissions
RUN mkdir -p logs temp /tmp/minio-webui-temp /run/nginx && \
chown -R nodejs:nodejs /app logs temp /tmp/minio-webui-temp && \
RUN mkdir -p /app/logs /app/temp /tmp/minio-webui-temp /run/nginx && \
chown -R nodejs:nodejs /app /tmp/minio-webui-temp && \
chown -R nodejs:nodejs /var/lib/nginx /var/log/nginx /run/nginx
# Create startup script
+7 -2
View File
@@ -26,7 +26,12 @@ class AuthService {
async verifyPassword(password) {
try {
const hash = config.auth.adminPasswordHash;
let hash = config.auth.adminPasswordHash;
// Clean up hash - remove surrounding quotes that Portainer/Docker may add
if (hash) {
hash = hash.trim().replace(/^["']|["']$/g, '');
}
// Debug logging for troubleshooting
logger.debug('Password verification attempt', {
@@ -46,7 +51,7 @@ class AuthService {
if (!hash.match(/^\$2[aby]\$\d{2}\$/)) {
logger.error('Invalid bcrypt hash format - hash may be corrupted by environment variable interpolation', {
hashPrefix: hash.substring(0, 20),
expectedFormat: '$2b$12$...'
expectedFormat: '$2b$12$... or $2y$10$...'
});
return false;
}
+44 -37
View File
@@ -14,46 +14,53 @@ const execAsync = util.promisify(exec);
class MinIOService {
constructor(alias = config.minio.defaultAlias) {
this.alias = alias;
// Use Docker-prepared temp directory first, then fallback options
this.tempDir = process.env.TEMP_DIR || '/tmp/minio-webui-temp';
this.ensureTempDir();
// Initialize temp directory asynchronously
this.tempDir = null;
this.tempDirReady = this.initTempDir();
}
async initTempDir() {
// Try directories in order of preference
const candidates = [
process.env.TEMP_DIR,
'/app/temp',
path.join(process.cwd(), 'temp'),
'/tmp/minio-webui-temp',
path.join(os.tmpdir(), 'minio-webui-temp')
].filter(Boolean);
for (const dir of candidates) {
if (await this.tryTempDir(dir)) {
this.tempDir = dir;
logger.info(`Using temp directory: ${this.tempDir}`);
this.cleanupTempFiles();
return;
}
}
// Last resort - use current directory
this.tempDir = path.join(process.cwd(), '.temp');
await fs.mkdir(this.tempDir, { recursive: true }).catch(() => {});
logger.warn(`Fallback to temp directory: ${this.tempDir}`);
}
async tryTempDir(dir) {
try {
await fs.mkdir(dir, { recursive: true, mode: 0o755 });
const testFile = path.join(dir, `.write-test-${Date.now()}-${Math.random()}`);
await fs.writeFile(testFile, 'test', { mode: 0o644 });
await fs.unlink(testFile);
return true;
} catch (error) {
logger.debug(`Temp directory ${dir} not usable: ${error.message}`);
return false;
}
}
async ensureTempDir() {
try {
await fs.mkdir(this.tempDir, { recursive: true, mode: 0o755 });
// Test write permissions
const testFile = path.join(this.tempDir, `.write-test-${Date.now()}`);
await fs.writeFile(testFile, 'test');
await fs.unlink(testFile);
logger.info(`Using temp directory: ${this.tempDir}`);
// Clean up old temp files (older than 1 hour)
this.cleanupTempFiles();
} catch (error) {
logger.error(`Failed to create or write to temp directory ${this.tempDir}:`, error);
// Try alternative local temp directory
const alternativeTempDir = path.join(process.cwd(), 'temp');
try {
await fs.mkdir(alternativeTempDir, { recursive: true, mode: 0o755 });
const testFile = path.join(alternativeTempDir, `.write-test-${Date.now()}`);
await fs.writeFile(testFile, 'test');
await fs.unlink(testFile);
this.tempDir = alternativeTempDir;
logger.info(`Using alternative temp directory: ${this.tempDir}`);
} catch (altError) {
logger.error('Failed to use alternative temp directory:', altError);
// Last resort: use OS temp directory
this.tempDir = path.join(os.tmpdir(), 'minio-webui-temp');
try {
await fs.mkdir(this.tempDir, { recursive: true, mode: 0o755 });
logger.warn(`Using OS temp directory (may have permission issues): ${this.tempDir}`);
} catch (fallbackError) {
logger.error('Failed to create OS temp directory:', fallbackError);
// Use current directory as last resort
this.tempDir = path.join(process.cwd(), '.temp');
logger.error(`Using current directory for temp files: ${this.tempDir}`);
}
}
// Wait for initialization if not complete
if (!this.tempDir) {
await this.tempDirReady;
}
}