JAVA implements a simple F5 load balancing function. F5 load balancer is very expensive and not suitable for small entrepreneurial companies. Here is a small piece of pure JAVA code to implement the load balancing function of an HTTP server. It has basic load balancing functions and is enough for daily use. ServerF5.java package F5Server; import java.math.BigInteger; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; public class ServerF5 { private int currentIndex = -1;// last selected server private int currentWeight = 0;// Current plan weight private int maxWeight = 0; // maximum weight private int gcdWeight = 0; //Greatest common divisor of all server weights private int serverCount = 0; //number of servers private List<Server> serverList; //List of server collections private static ServerF5 context; /** * Initialize the F5 context */ public static ServerF5 getContext() { if (context == null) { context = new ServerF5(); } return ServerF5.context; } /** * returns the greatest common divisor */ private static int gcd(int a, int b) { BigInteger b1 = new BigInteger(String.valueOf(a)); BigInteger b2 = new BigInteger(String.valueOf(b)); BigInteger gcd = b1.gcd(b2); return gcd.intValue(); } /** * Returns the greatest common divisor of all server weights */ private static int getGCDForServers(List<Server> serverList) { int w = 0; if (serverList.size() == 1) { w = gcd(w, serverList.get(0).weight); } for (int i = 0, len = serverList.size(); i < len - 1; i++) { if (w == 0) { w = gcd(serverList.get(i).weight, serverList.get(i + 1).weight); } else { w = gcd(w, serverList.get(i + 1).weight); } } return w; } /** * Returns the highest weight of all servers. */ public static int getMaxWeightForServers(List<Server> serverList) { int w = 0; if (serverList.size() == 1) { w = Math.max(w, serverList.get(0).weight); } for (int i = 0, len = serverList.size(); i < len - 1; i++) { if (w == 0) { w = Math.max(serverList.get(i).weight, serverList.get(i + 1).weight); } else { w = Math.max(w, serverList.get(i + 1).weight); } } return w; } /** * Algorithm processing: * Suppose we have a set of servers. S = {S0, S1, ..., Sn-1} * There is a corresponding weight, and the variable currentIndex indicates the last selected server. * Weight currentWeight is initialized to 0, currentIndex is initialized to -1, and the server with the largest weight is returned for the first time, * Find a suitable server to return, and keep reducing the weight until the weight returns to 0 after the polling ends. */ public Server GetServer() { while (true) { currentIndex = (currentIndex + 1) % serverCount; if (currentIndex == 0) { currentWeight = currentWeight - gcdWeight; if (currentWeight <= 0) { currentWeight = maxWeight; if (currentWeight == 0) return null; } } if (serverList.get(currentIndex).weight >= currentWeight) { return serverList.get(currentIndex); } } } /* * Initializes the F5 property of the URL list. * */ public void init(List list) { if (serverList != null) { serverList.clear(); } else { serverList = new ArrayList<Server>(); } for (int i = 0; i < list.size(); i++) { String url[] = list.get(i).toString().split(":"); String ip = url[0]; int port = Integer.parseInt(url[1]); Server server = new Server(ip, 1, port); serverList.add(server); } currentIndex = -1; currentWeight = 0; serverCount = serverList.size(); maxWeight = getMaxWeightForServers(serverList); gcdWeight = getGCDForServers(serverList); } class Server { public String ip; public int weight;//current server weight public int port; public Server(String ip, int weight, int port) { super(); this.ip = ip; this.weight = weight; this.port = port; } public String getIp() { return ip; } public void setIp(String ip) { this.ip = ip; } public int getWeight() { return weight; } public void setWeight(int weight) { this.weight = weight; } public int getPort() { return port; } public void setPort(int port) { this.port = port; } } /* * Test and view results * */ public static void main(String[] args) { ServerF5 obj = new ServerF5(); List list = new ArrayList(); list.add("11.2.43.4:8080"); list.add("11.2.43.5:8081"); list.add("11.2.43.6:8082"); obj.init(list); Map<String, Integer> countResult = new HashMap<String, Integer>(); for (int i = 0; i < 100; i++) { Server s = obj.GetServer(); String log = "ip:" + s.ip + ";weight:" + s.weight; if (countResult.containsKey(log)) { countResult.put(log, countResult.get(log) + 1); } else { countResult.put(log, 1); } System.out.println(log); } for (Map.Entry<String, Integer> map : countResult.entrySet()) { System.out.println("Server " + map.getKey() + " request count: " + map.getValue()); } } } This is the implementation class of the basic F5 load balancing algorithm,Let’s take a look at the actual calling tool class of F5 load balancing. //We need to import it here. httpcore-4.1.4.jar httpclient-4.1.3.jar ServerF5Utils.java package F5Server; import org.apache.http.HttpHost; import org.apache.http.client.HttpClient; import org.apache.http.conn.ClientConnectionRequest; import org.apache.http.conn.ManagedClientConnection; import org.apache.http.conn.routing.HttpRoute; import org.apache.http.impl.client.DefaultHttpClient; import org.apache.http.params.BasicHttpParams; import org.apache.http.protocol.BasicHttpContext; import java.net.ConnectException; import java.util.ArrayList; import java.util.List; import java.util.Timer; import java.util.TimerTask; import java.util.concurrent.TimeUnit; public class ServerF5Utils { private static ServerF5Utils context; private static List aliveUrlList; private Timer timer; private static ServerF5 serverF5; static { serverF5 = ServerF5.getContext(); } public void updateAliveList(List urlLists) { try { //List of active URLs. aliveUrlList = new ArrayList(); //List of client configuration URLs. for (int i = 0; i < urlLists.size(); i++) { String[] urlport = urlLists.get(i).toString().split(":"); String ipaddr = urlport[0]; int port = Integer.parseInt(urlport[1]); HttpClient httpClient = new DefaultHttpClient(); HttpRoute route = new HttpRoute(new HttpHost(ipaddr, port)); ClientConnectionRequest connRequest = httpClient.getConnectionManager().requestConnection(route, null); ManagedClientConnection conn = connRequest.getConnection(10, TimeUnit.SECONDS); try { //Open a connection using the client-configured list of URLs. conn.open(route, new BasicHttpContext(), new BasicHttpParams()); } catch (ConnectException e) { System.out.println("AliveList init refuse:[" + ipaddr + ":" + port + "]"); continue; } if (conn.isOpen()) { //If the test connection is successful, the connection is added to the list of active links. aliveUrlList.add(urlLists.get(i).toString()); System.out.println("AliveList init Success:[" + this.aliveUrlList + "]"); conn.releaseConnection(); continue; } else { continue; } } } catch (Exception e) { System.out.println("HttpConnection Alive Url List init fail,please check Http URL,Exception:" + e.toString()); } System.out.println("HttpConnection Alive Url List List =[" + aliveUrlList + "]"); //List of active links offered to F5 services for selection. serverF5.init(aliveUrlList); } /** * Available URL links are algorithmically selected and returned. */ public String getServerUrl() { ServerF5.Server server = serverF5.GetServer(); String ip = server.getIp(); int port = server.getPort(); String url = ip + ":" + port; return url; } /** * Initializes the context of the F5 utility class so that the user can invoke it. */ public static ServerF5Utils getContext(final List urlLists) { if (context == null) { context = new ServerF5Utils(); context.updateAliveList(urlLists); context.timer = new Timer(); context.timer.schedule(new TimerTask() { @Override public void run() { context.updateAliveList(urlLists); } }, 50000, 300000); } return ServerF5Utils.context; } //Test public static void main(String[] args) { List<String> urls= new ArrayList<>(); urls.add("11.2.43.3:8080"); urls.add("11.2.43.4:8080"); urls.add("11.2.43.5:8080"); String shotUrl = ServerF5Utils.getContext(urls).getServerUrl(); System.out.println("shotUrl="+shotUrl); } } The Test and Invoke methods pass the server-built list of selected URLs to the F5 tool class context. After F5 Load Balancing initialization is successful, returns the selected URL link available to the caller. 文章导航 JAVA代码实现的一个简单的F5负载均衡功能 Mysql表有外键关联时如何初始化自增ID