{"record":{"id":"4abbf9f50547ae56","repo":"abhigyanpatwari/GitNexus","slug":"azure-devops-url-is-configured-over-cleartext-http","errorCode":null,"errorMessage":"AZURE_DEVOPS_URL is configured over cleartext http:// — the Azure DevOps PAT will be sent unencrypted. Prefer https:// where your instance supports it.","messagePattern":"AZURE_DEVOPS_URL is configured over cleartext http:// — the Azure DevOps PAT will be sent unencrypted\\. Prefer https:// where your instance supports it\\.","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"gitnexus/src/server/git-clone.ts","lineNumber":294,"sourceCode":"    return host === 'dev.azure.com' || host.endsWith('.visualstudio.com');\n  } catch {\n    return false;\n  }\n}\n\n/**\n * One-time startup warning when AZURE_DEVOPS_URL is configured over cleartext\n * http:// — the Azure DevOps PAT would then be sent unencrypted on every\n * clone. Self-hosted instances that only serve http are still supported (we\n * do not refuse), but operators rarely read request-time logs, so surface it\n * at boot too. Call once from server startup.\n */\nexport function warnIfInsecureAzureConfig(): void {\n  const base = process.env.AZURE_DEVOPS_URL;\n  if (!base) return;\n  try {\n    if (new URL(base).protocol === 'http:') {\n      logger.warn(\n        'AZURE_DEVOPS_URL is configured over cleartext http:// — the Azure DevOps PAT will be sent unencrypted. Prefer https:// where your instance supports it.',\n      );\n    }\n  } catch {\n    /* invalid AZURE_DEVOPS_URL — isAzureDevOpsUrl already tolerates this */\n  }\n}\n\nexport function buildCloneArgs(url: string, targetDir: string): string[] {\n  return ['clone', '--depth', '1', '--', url, targetDir];\n}\n\n/**\n * Normalize a git URL into a comparable form.\n *\n * Two URLs are considered the same repository when their normalized forms\n * are identical: lowercased hostname, no trailing `.git`, no trailing\n * slashes on the path, default port stripped. Path comparison stays","sourceCodeStart":276,"sourceCodeEnd":312,"githubUrl":"https://github.com/abhigyanpatwari/GitNexus/blob/aac7515d2a8c50a1f8f923c6fb77218b333560d6/gitnexus/src/server/git-clone.ts#L276-L312","documentation":"At server startup, warnIfInsecureAzureConfig inspects AZURE_DEVOPS_URL; if it parses and its scheme is http:, this one-time warning fires because the Azure DevOps PAT used for clones would cross the wire unencrypted on every request. The configuration is deliberately not refused (self-hosted instances that only serve http remain supported), but the risk is surfaced at boot because operators rarely read request-time logs.","triggerScenarios":"Setting AZURE_DEVOPS_URL to any cleartext URL (e.g. http://tfs.internal:8080) and starting the server: every subsequent authenticated Azure DevOps clone sends the PAT base64-encoded but unencrypted. An invalid URL stays silent here because isAzureDevOpsUrl already tolerates it.","commonSituations":"Self-hosted Azure DevOps Server / TFS on plain http inside the corporate network; a copy-pasted internal URL; TLS terminated at a proxy while the configured base URL still uses http.","solutions":["Serve the instance over https and set AZURE_DEVOPS_URL to the https:// base","Put a TLS-terminating reverse proxy in front of the http instance and point AZURE_DEVOPS_URL at the https endpoint","If cleartext is intentional on an isolated trusted network, accept the advisory warning: the clone still proceeds"],"exampleFix":"# before\nexport AZURE_DEVOPS_URL=http://tfs.internal:8080/\n\n# after\nexport AZURE_DEVOPS_URL=https://tfs.internal/","handlingStrategy":"validation","validationCode":"const base = process.env.AZURE_DEVOPS_URL;\nif (base) {\n  const u = new URL(base); // throws on invalid, mirroring the tolerant path\n  if (u.protocol === 'http:') {\n    throw new Error('AZURE_DEVOPS_URL must use https:// when a PAT will be sent');\n  }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Default credentialed endpoints to https bases","Treat this boot warning as a security finding in review, not log noise","Remember the PAT header is base64 — encoding, not encryption"],"tags":["security","azure-devops","http","pat","configuration","env-var"],"backgroundTag":"cleartext-http-credential-exposure","analyzedSha":"aac7515d2a8c50a1f8f923c6fb77218b333560d6","analyzedAt":"2026-08-20T23:29:22.980Z","schemaVersion":2},"datasetVersion":"2026-08-22T20:17:22.307Z"}