All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.apache.camel.component.webhook.WebhookConfiguration Maven / Gradle / Ivy

The newest version!
/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.camel.component.webhook;

import java.net.UnknownHostException;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Base64;

import org.apache.camel.RuntimeCamelException;
import org.apache.camel.spi.Metadata;
import org.apache.camel.spi.RestConfiguration;
import org.apache.camel.spi.UriParam;
import org.apache.camel.spi.UriParams;
import org.apache.camel.spi.UriPath;
import org.apache.camel.util.HostUtils;
import org.apache.camel.util.ObjectHelper;

/**
 * Configuration class for the webhook component.
 */
@UriParams
public class WebhookConfiguration implements Cloneable {

    private transient RestConfiguration restConfiguration;

    /*
     * Note: all properties start with the 'webhook' prefix to avoid collision with the delegate endpoint.
     */

    @UriPath
    @Metadata(required = true)
    private String endpointUri;

    @UriParam
    private String webhookComponentName;

    @UriParam
    private String webhookExternalUrl;

    @UriParam
    private String webhookBasePath;

    @UriParam
    private String webhookPath;

    @UriParam(defaultValue = "true")
    private boolean webhookAutoRegister = true;

    public WebhookConfiguration() {
    }

    public String getWebhookComponentName() {
        return webhookComponentName;
    }

    /**
     * Returns a copy of this configuration
     */
    public WebhookConfiguration copy() {
        try {
            return (WebhookConfiguration) clone();
        } catch (CloneNotSupportedException e) {
            throw new RuntimeCamelException(e);
        }
    }

    // cannot use getter/setter as its not a regular option
    public void storeConfiguration(RestConfiguration restConfiguration) {
        this.restConfiguration = restConfiguration;
    }

    // cannot use getter/setter as its not a regular option
    public RestConfiguration retrieveRestConfiguration() {
        return restConfiguration;
    }

    /**
     * Computes the external URL of the webhook as seen by the remote webhook provider.
     *
     * @return the webhook external URL
     */
    public String computeFullExternalUrl() throws UnknownHostException {
        String externalServerUrl = this.webhookExternalUrl;
        if (externalServerUrl == null) {
            externalServerUrl = computeServerUriPrefix();
        }
        String path = computeFullPath(true);
        return externalServerUrl + path;
    }

    /**
     * Computes the path part of the webhook.
     *
     * @param  external indicates if it's the path seen by the external provider or the internal one.
     * @return          the webhook full path
     */
    public String computeFullPath(boolean external) {
        // calculate the url to the rest service
        String path = webhookPath;
        if (path == null) {
            path = computeDefaultPath(endpointUri);
        } else if (!path.startsWith("/")) {
            path = "/" + path;
        }

        if (webhookBasePath != null) {
            if (!webhookBasePath.startsWith("/")) {
                path = "/" + webhookBasePath + path;
            } else {
                path = webhookBasePath + path;
            }
        }

        if (external) {
            String contextPath = restConfiguration.getContextPath();
            if (contextPath != null) {
                if (!contextPath.startsWith("/")) {
                    path = "/" + contextPath + path;
                } else {
                    path = contextPath + path;
                }
            }
        }

        return path;
    }

    /**
     * Computes the URL of the webhook that should be used to bind the REST endpoint locally.
     */
    public String computeServerUriPrefix() throws UnknownHostException {
        // if no explicit port/host configured, then use port from rest configuration
        String scheme = "http";
        String host = "";
        int port = 80;

        if (restConfiguration.getScheme() != null) {
            scheme = restConfiguration.getScheme();
        }
        if (restConfiguration.getHost() != null) {
            host = restConfiguration.getHost();
        }
        int num = restConfiguration.getPort();
        if (num > 0) {
            port = num;
        }

        // if no explicit hostname set then resolve the hostname
        if (ObjectHelper.isEmpty(host)) {
            if (restConfiguration.getHostNameResolver() == RestConfiguration.RestHostNameResolver.allLocalIp) {
                host = "0.0.0.0";
            } else if (restConfiguration.getHostNameResolver() == RestConfiguration.RestHostNameResolver.localHostName) {
                host = HostUtils.getLocalHostName();
            } else if (restConfiguration.getHostNameResolver() == RestConfiguration.RestHostNameResolver.localIp) {
                host = HostUtils.getLocalIp();
            }
        }

        return scheme + "://" + host + (port != 80 ? ":" + port : "");
    }

    /**
     * A default path is computed for the webhook if not provided by the user. It uses a hash of the delegate endpoint
     * in order for it to be reproducible.
     *
     * This is not random on purpose.
     */
    public static String computeDefaultPath(String uri) {
        try {
            MessageDigest md = MessageDigest.getInstance("SHA-256");
            md.update(uri.getBytes(StandardCharsets.UTF_8));
            byte[] digest = md.digest();

            return "/" + Base64.getUrlEncoder().encodeToString(digest);
        } catch (NoSuchAlgorithmException e) {
            throw new RuntimeCamelException("Cannot compute default webhook path", e);
        }
    }

    public String getEndpointUri() {
        return endpointUri;
    }

    /**
     * The delegate uri. Must belong to a component that supports webhooks.
     */
    public void setEndpointUri(String endpointUri) {
        this.endpointUri = endpointUri;
    }

    /**
     * The Camel Rest component to use for the REST transport, such as netty-http.
     */
    public void setWebhookComponentName(String webhookComponentName) {
        this.webhookComponentName = webhookComponentName;
    }

    public String getWebhookExternalUrl() {
        return webhookExternalUrl;
    }

    /**
     * The URL of the current service as seen by the webhook provider
     */
    public void setWebhookExternalUrl(String webhookExternalUrl) {
        this.webhookExternalUrl = webhookExternalUrl;
    }

    public String getWebhookBasePath() {
        return webhookBasePath;
    }

    /**
     * The first (base) path element where the webhook will be exposed. It's a good practice to set it to a random
     * string, so that it cannot be guessed by unauthorized parties.
     */
    public void setWebhookBasePath(String webhookBasePath) {
        this.webhookBasePath = webhookBasePath;
    }

    public String getWebhookPath() {
        return webhookPath;
    }

    /**
     * The path where the webhook endpoint will be exposed (relative to basePath, if any)
     */
    public void setWebhookPath(String webhookPath) {
        this.webhookPath = webhookPath;
    }

    public boolean isWebhookAutoRegister() {
        return webhookAutoRegister;
    }

    /**
     * Automatically register the webhook at startup and unregister it on shutdown.
     */
    public void setWebhookAutoRegister(boolean webhookAutoRegister) {
        this.webhookAutoRegister = webhookAutoRegister;
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy