require 'uuid' require_relative 'collection/split_route_collection' require_relative 'rules' require_relative 'resolver' require_relative 'collection/route_collection' require_relative 'middleware' class SiteHub class ForwardProxyBuilder include Middleware include Rules, Resolver class InvalidDefinitionException < Exception; end attr_reader :mapped_path, :default_proxy, :routes, :middlewares, :splits, :sitehub_cookie_name def initialize(url: nil, mapped_path:, rule:nil, sitehub_cookie_name: nil, &block) @mapped_path = mapped_path @middlewares = [] @splits = Collection::SplitRouteCollection.new @routes = Collection::RouteCollection.new @sitehub_cookie_name = sitehub_cookie_name rule(rule) if rule default(url: url) if url if block instance_eval(&block) raise InvalidDefinitionException unless valid? end end def valid? return true if @default_proxy endpoints.valid? end def endpoints collection=nil return @endpoints || Collection::RouteCollection.new unless collection raise InvalidDefinitionException, 'you cant register routes and splits at the same level' if @endpoints && @endpoints != collection @endpoints = collection end def split(percentage:, url:, label:, &block) endpoints(splits) endpoints.add label.to_sym, forward_proxy(label: label, url: url), percentage end def route url:nil, label:nil, rule: nil, &block endpoints(routes) if block raise InvalidDefinitionException, 'rule must be specified when supplying a block'unless rule builder = self.class.new(mapped_path: mapped_path, rule: rule, &block).build endpoints.add UUID.generate(:compact), builder else endpoints.add label.to_sym, forward_proxy(url: url, label: label, rule: rule) end end def default(url:) @default_proxy = forward_proxy(label: :default, url: url) end def sitehub_cookie_path path=nil return @sitehub_cookie_path unless path @sitehub_cookie_path = path end def build endpoints.transform do |proxy| apply_middleware(proxy).tap do |wrapped_proxy| wrapped_proxy.extend(Rules) wrapped_proxy.extend(Resolver) unless wrapped_proxy.is_a?(Resolver) wrapped_proxy.rule(proxy.rule) end end @default_proxy = apply_middleware(default_proxy) if default_proxy self end def resolve(id: nil, env:) id = id.to_s.to_sym endpoints[id] || endpoints.resolve(env: env) || default_proxy end def == other other.is_a?(ForwardProxyBuilder) && self.default_proxy == other.default_proxy && self.endpoints == other.endpoints end def forward_proxy(label:, url:, rule: nil) ForwardProxy.new(url: url, id: label.to_sym, mapped_path: mapped_path, sitehub_cookie_path: sitehub_cookie_path, sitehub_cookie_name: sitehub_cookie_name, rule: rule) end end end