func parseConfig()

in cmd/root.go [787:971]


func parseConfig(cmd *Command, conf *proxy.Config, args []string) error {
	// If no instance connection names were provided AND FUSE isn't enabled,
	// error.
	if len(args) == 0 && conf.FUSEDir == "" {
		return newBadCommandError("missing instance uri (e.g., projects/$PROJECT/locations/$LOCATION/clusters/$CLUSTER/instances/$INSTANCE)")
	}

	if conf.FUSEDir != "" {
		if conf.RunConnectionTest {
			return newBadCommandError("cannot run connection tests in FUSE mode")
		}

		if err := proxy.SupportsFUSE(); err != nil {
			return newBadCommandError(
				fmt.Sprintf("--fuse is not supported: %v", err),
			)
		}
	}

	if len(args) == 0 && conf.FUSEDir == "" && conf.FUSETempDir != "" {
		return newBadCommandError("cannot specify --fuse-tmp-dir without --fuse")
	}

	if userHasSetLocal(cmd, "address") && userHasSetLocal(cmd, "unix-socket") {
		return newBadCommandError("cannot specify --unix-socket and --address together")
	}
	if userHasSetLocal(cmd, "port") && userHasSetLocal(cmd, "unix-socket") {
		return newBadCommandError("cannot specify --unix-socket and --port together")
	}
	// First, validate global config.
	if ip := net.ParseIP(conf.Addr); ip == nil {
		return newBadCommandError(fmt.Sprintf("not a valid IP address: %q", conf.Addr))
	}

	// If more than one auth method is set, error.
	if conf.Token != "" && conf.CredentialsFile != "" {
		return newBadCommandError("cannot specify --token and --credentials-file flags at the same time")
	}
	if conf.Token != "" && conf.GcloudAuth {
		return newBadCommandError("cannot specify --token and --gcloud-auth flags at the same time")
	}
	if conf.CredentialsFile != "" && conf.GcloudAuth {
		return newBadCommandError("cannot specify --credentials-file and --gcloud-auth flags at the same time")
	}
	if conf.CredentialsJSON != "" && conf.Token != "" {
		return newBadCommandError("cannot specify --json-credentials and --token flags at the same time")
	}
	if conf.CredentialsJSON != "" && conf.CredentialsFile != "" {
		return newBadCommandError("cannot specify --json-credentials and --credentials-file flags at the same time")
	}
	if conf.CredentialsJSON != "" && conf.GcloudAuth {
		return newBadCommandError("cannot specify --json-credentials and --gcloud-auth flags at the same time")
	}

	if userHasSetLocal(cmd, "alloydbadmin-api-endpoint") {
		_, err := url.Parse(conf.APIEndpointURL)
		if err != nil {
			return newBadCommandError(fmt.Sprintf(
				"provided value for --alloydbadmin-api-endpoint is not a valid url, %v",
				conf.APIEndpointURL,
			))
		}

		// Remove trailing '/' if included
		conf.APIEndpointURL = strings.TrimSuffix(conf.APIEndpointURL, "/")
		cmd.logger.Infof("Using API Endpoint %v", conf.APIEndpointURL)
	}

	if userHasSetGlobal(cmd, "http-port") && !userHasSetLocal(cmd, "prometheus") && !userHasSetLocal(cmd, "health-check") {
		cmd.logger.Infof("Ignoring --http-port because --prometheus or --health-check was not set")
	}

	if !userHasSetLocal(cmd, "telemetry-project") && userHasSetLocal(cmd, "telemetry-prefix") {
		cmd.logger.Infof("Ignoring --telementry-prefix as --telemetry-project was not set")
	}
	if !userHasSetLocal(cmd, "telemetry-project") && userHasSetLocal(cmd, "disable-metrics") {
		cmd.logger.Infof("Ignoring --disable-metrics as --telemetry-project was not set")
	}
	if !userHasSetLocal(cmd, "telemetry-project") && userHasSetLocal(cmd, "disable-traces") {
		cmd.logger.Infof("Ignoring --disable-traces as --telemetry-project was not set")
	}

	if userHasSetLocal(cmd, "user-agent") {
		defaultUserAgent += " " + cmd.conf.OtherUserAgents
		conf.UserAgent = defaultUserAgent
	}

	var ics []proxy.InstanceConnConfig
	for _, a := range args {
		// split into instance uri and query parameters
		res := strings.SplitN(a, "?", 2)
		_, _, _, _, err := proxy.ParseInstanceURI(res[0])
		if err != nil {
			return newBadCommandError(fmt.Sprintf("could not parse instance uri: %q", res[0]))
		}
		ic := proxy.InstanceConnConfig{Name: res[0]}
		// If there are query params, update instance config.
		if len(res) > 1 {
			q, err := url.ParseQuery(res[1])
			if err != nil {
				return newBadCommandError(fmt.Sprintf("could not parse query: %q", res[1]))
			}

			a, aok := q["address"]
			p, pok := q["port"]
			u, uok := q["unix-socket"]
			up, upok := q["unix-socket-path"]

			if aok && uok {
				return newBadCommandError("cannot specify both address and unix-socket query params")
			}
			if pok && uok {
				return newBadCommandError("cannot specify both port and unix-socket query params")
			}
			if aok && upok {
				return newBadCommandError("cannot specify both address and unix-socket-path query params")
			}
			if pok && upok {
				return newBadCommandError("cannot specify both port and unix-socket-path query params")
			}
			if uok && upok {
				return newBadCommandError("cannot specify both unix-socket-path and unix-socket query params")
			}

			if aok {
				if len(a) != 1 {
					return newBadCommandError(fmt.Sprintf("address query param should be only one value: %q", a))
				}
				if ip := net.ParseIP(a[0]); ip == nil {
					return newBadCommandError(
						fmt.Sprintf("address query param is not a valid IP address: %q",
							a[0],
						))
				}
				ic.Addr = a[0]
			}

			if upok {
				if len(up) != 1 {
					return newBadCommandError(fmt.Sprintf("unix-socket-path query param should be only one value: %q", a))
				}
				ic.UnixSocketPath = up[0]
			}

			if pok {
				if len(p) != 1 {
					return newBadCommandError(fmt.Sprintf("port query param should be only one value: %q", a))
				}
				pp, err := strconv.Atoi(p[0])
				if err != nil {
					return newBadCommandError(
						fmt.Sprintf("port query param is not a valid integer: %q",
							p[0],
						))
				}
				ic.Port = pp
			}

			if uok {
				if len(u) != 1 {
					return newBadCommandError(fmt.Sprintf("unix query param should be only one value: %q", a))
				}
				ic.UnixSocket = u[0]

			}

			ic.AutoIAMAuthN, err = parseBoolOpt(q, "auto-iam-authn")
			if err != nil {
				return err
			}
			ic.PublicIP, err = parseBoolOpt(q, "public-ip")
			if err != nil {
				return err
			}
			ic.PSC, err = parseBoolOpt(q, "psc")
			if err != nil {
				return err
			}
		}
		ics = append(ics, ic)
	}

	conf.Instances = ics
	return nil
}