Uploaded image for project: 'Jenkins'
  1. Jenkins
  2. JENKINS-48561

JNLP agent doesn't take into account -Dhttp.nonProxyHosts

    • Icon: Bug Bug
    • Resolution: Fixed
    • Icon: Major Major
    • core, remoting
    • None
    • Jenkins 2.73.3 with remoting 3.10.2 on OracleJDK 1.8

      This is a followup of JENKINS-32326 and JENKINS-32326 which aimed to implement full support of proxy and exclusions list in remoting lib.

       

      Our network is behind a corporate proxy which requires us to properly configure our tools to access Internet.

      For most of our CLI tools, we rely on the no_proxy environment variables to set the list of exclusions. Unfortunately, this variable (and the associated logic) does not support wildcard and can only contain a limited number of chars. That means that we can only whitelist some IP addresses and FQDN.

      For Java-based tool, we use the system property http.nonProxyHosts which is much more convenient since it supports wildcard and regex.

      Our Jenkins agents are executed in environment which contain the aforementioned environment variables, in a JVM with the corresponding system properties as well.

      Some part of the remoting lib seems to give precedence to environment variables over system properties. Meaning that if the master IP address is in the system property but not in the env var, the agent will try to go through the proxy and timeout.

      Test case

      • Command: java -cp /path/to/remoting.jar hudson.remoting.jnlp.Main -headless -url http://172.17.0.1:8080 <agent_secret> <agent_name>
      • System properties:
        • -Dhttp.proxyHost=200.xxx.xxx.xxx
        • -Dhttp.proxyPort=80
        • -Dhttp.nonProxyHosts=172.17.0.1
      • Environment variables:

      Expected behavior

      Agent connects to the master since its IP address is in the exclusion list defined by a system property which has precedence over the corresponding environment variable.

      Issue

      Agent successfully validates the provided credentials and checks that the master is up and running, but timeout when trying to open the JNLP channel.

      Analysis

      ProxySelector.getDefault() resolves to sun.net.spi.DefaultProxySelector which is a basic helper to retrieve all available proxy connections defined with system properties and/or provided by the operating system.

      DefaultProxySelector.select() will return a list of Proxy object which are relevant to the provided URL in argument (e.g. http://172.17.0.1).

      The most important information of the Proxy object is its type which can either be:

      • Type.DIRECT: direct connection to the URL without going through a proxy
      • Type.HTTP: connection through a HTTP proxy
      • Type.SOCKS: connection through a SOCK proxy

      By default, a Proxy has a DIRECT type. The static variable Proxy.NO_PROXY is an alias to the default constructor.

      In JnlpAgentEndpointResolver, when the returned proxy is of type DIRECT, the while loop is terminated: JnlpAgentEndpointResolver#338. When exiting the loop, no value has been assigned to targetAddress which is still equal to null.

      At JnlpAgentEndpointResolver#354, the script fallbacks to the proxy environment variables if targetAddress is still null.

      Unfortunately in our case, DefaultProxySelector.select() will return a unique proxy of type DIRECT because the system property http.nonProxyHosts does contain the URL in argument (172.17.0.1).

      Even if you don't go through the entire logic of DefaultProxySelector.select(), it is fairly easy to draw general conclusion from this test: ProxySelector.getDefault().select(URI.create("http://172.17.0.1:80")) will return:

      • Proxy.NO_PROXY when the system property is not set
      • Proxy.NO_PROXY when the system property is http.nonProxyHosts=172.17.0.1
      • "HTTP @ 200.xxx.xxx.xxx:80" when the system property is http.nonProxyHosts=127.0.0.1

          [JENKINS-48561] JNLP agent doesn't take into account -Dhttp.nonProxyHosts

          Etienne Bec added a comment -

          Etienne Bec added a comment - https://github.com/jenkinsci/remoting/pull/243

          Code changed in jenkins
          User: etiennebec
          Path:
          src/main/java/org/jenkinsci/remoting/engine/JnlpAgentEndpointResolver.java
          http://jenkins-ci.org/commit/remoting/eb2b2d965abae05e32aaadd34cdb197e5984aea5
          Log:
          [FIXED JENKINS-48561] Give precedence to proxy exclusion list system property over env var

          SCM/JIRA link daemon added a comment - Code changed in jenkins User: etiennebec Path: src/main/java/org/jenkinsci/remoting/engine/JnlpAgentEndpointResolver.java http://jenkins-ci.org/commit/remoting/eb2b2d965abae05e32aaadd34cdb197e5984aea5 Log: [FIXED JENKINS-48561] Give precedence to proxy exclusion list system property over env var

          Daniel Beck added a comment -

          Merged into core towards 2.112.

          Daniel Beck added a comment - Merged into core towards 2.112.

            etiennebec Etienne Bec
            etiennebec Etienne Bec
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

              Created:
              Updated:
              Resolved: