Message on Whatsapp 8879355057 for DSA(OA + Interview) + Fullstack Dev Training + 1-1 Personalized Mentoring to get 10+LPA Job
0 like 0 dislike
581 views
in Interview-Experiences by Expert (116,030 points) | 581 views

2 Answers

0 like 0 dislike

// Implement simple circuit breaker given a rpc method.
// please consider the generic circuit breaker options like the following:
//
// * timeWindowSec - (10s) time sliding window size.
// * failureRatioThreshhold - (50%) failure ratio threshold in which the circuit open
// * circuitCloseTimeSec - (5s) required time to circuit re-close
// * min requests - 10

 

// Main class should be named 'Solution' and should not be public

 

package com.example.designpatterns.circuitbreaker;


import com.example.designpatterns.circuitbreaker.handler.MethodHandler;
import com.example.designpatterns.circuitbreaker.model.Method;
import com.example.designpatterns.circuitbreaker.model.Request;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;

import java.util.Map;
import java.util.UUID;
import java.util.concurrent.atomic.AtomicBoolean;


@Slf4j
@AllArgsConstructor
public class CircuitBreaker {
    Map<String, MethodHandler> methodHandlerMap;

    public void addMethod(String name) {
        Method method = new Method(UUID.randomUUID().toString(), name, new AtomicBoolean(false));
        MethodHandler methodHandler = new MethodHandler(method);
        methodHandlerMap.put(name, methodHandler);
        log.info("Added hystrix for this method");
    }

    public void sendRequest(String name, Request request) {

        MethodHandler methodHandler = methodHandlerMap.get(name);
        if (methodHandler == null) {
            log.info("Hystrix not available in this method");
            return;
        }
        if (methodHandler.getMethod().checkIfCircuitOpen()) {
            log.info("Dropping this request as circuit is open");
            return;
        }
        log.info("sending request to method {}", name);
        methodHandler.getMethod().addRequest(request);
        log.info(String.valueOf(methodHandler.getMethod().getListOfRequest().size()));
        methodHandler.run();

    }
}

package com.example.designpatterns.circuitbreaker.model;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.extern.slf4j.Slf4j;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;


@Getter
@Data
@Slf4j
public class Method {
    String id;
    String name;
    AtomicBoolean isCircuitOpen;
    List<Request> listOfRequest;
    ReentrantLock reentrantLock = new ReentrantLock();
    Condition condition = reentrantLock.newCondition();

    public Method(String _id, String _name, AtomicBoolean _isCircuitOpen) {
        id = _id;
        name = _name;
        isCircuitOpen = _isCircuitOpen;
        listOfRequest = new ArrayList<>();
    }


    public void addRequest(Request request) {
        reentrantLock.lock();
        if (isCircuitOpen.get() == true) {
            log.error("Circuit is open. Cannot send request");
        } else {
            listOfRequest.add(request);
        }
        reentrantLock.unlock();
    }

    public void circuitOpen() {
        reentrantLock.lock();
        isCircuitOpen.compareAndSet(isCircuitOpen.get(), true);
        reentrantLock.unlock();
    }

    public void circuitClose() {
        reentrantLock.lock();
        isCircuitOpen.compareAndSet(isCircuitOpen.get(), false);
        log.info("Closing circuit");
        reentrantLock.unlock();
    }

    public boolean checkIfCircuitOpen() {
        return isCircuitOpen.get();
    }

}


package com.example.designpatterns.circuitbreaker.model;

import com.example.designpatterns.circuitbreaker.commons.ResponseCode;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.Getter;

@AllArgsConstructor
@Getter
@Data
@Builder
public class Request {
    String requestId;
    ResponseCode responseCode;
    long time;
}




package com.example.designpatterns.circuitbreaker.handler;

import com.example.designpatterns.circuitbreaker.commons.ResponseCode;
import com.example.designpatterns.circuitbreaker.model.Method;
import com.example.designpatterns.circuitbreaker.model.Request;
import com.example.designpatterns.messegingQueue.model.Message;
import lombok.Builder;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;

import java.util.List;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

@Data
@Slf4j
public class MethodHandler {
    Method method;
    ReentrantLock reentrantLock;
    Condition condition;

    public MethodHandler(Method _method) {
        method = _method;
        reentrantLock = new ReentrantLock();
        condition = reentrantLock.newCondition();
    }

    public void run() {
        reentrantLock.lock();
        List<Request> requestList = method.getListOfRequest();
        long fromTime = System.currentTimeMillis() - 10000;
        long toTime = System.currentTimeMillis();
        long totalErrors = 0;
        long totalRequest = 0;
        log.info("from time {}, to Time {}", fromTime, toTime);
        for (Request request : requestList) {
           log.info(String.valueOf(request.getTime()));
            if (request.getTime() >= fromTime && request.getTime() <= toTime) {
                if (!request.getResponseCode().equals(ResponseCode.OK)) {
                    totalErrors++;
                }
                totalRequest++;
            }
        }
        log.info("Total Request {}, Error request{} ,{}",totalRequest,totalErrors, (double)totalErrors/totalRequest);
        if (totalRequest >= 2 && ((double)totalErrors/totalRequest >= 0.5)) {
            log.info("Opening Circuit for 5 seconds");
            method.circuitOpen();
            new Thread(() -> {
                try {
                    Thread.sleep(5000);
                    method.circuitClose();
                } catch (Exception e) {

                }
            }).start();
        }
        reentrantLock.unlock();
    }
}


package com.example.designpatterns.circuitbreaker.commons;

public enum ResponseCode {
    OK,
    INTERNAL_SERVER_ERROR,
    BAD_REQUEST
}
by Expert (116,030 points)
0 like 0 dislike

Given two cells, source(x1,y1) and destination(x2, y2) in an infinite grid.
Find the total no of paths with minimum no of steps between source and destination. (You can go only 4 directions at each cell).

by Expert (116,030 points)

Get best answers to any doubt/query/question related to programming , jobs, gate, internships and tech-companies. Feel free to ask a question and you will receive the best advice/suggestion related to anything you ask about software-engineering , development and programming problems .