স্প্রিং এমভিসি কন্ট্রোলারে কল পাবেন কীভাবে আইপি ঠিকানা?


93

আমি স্প্রিং এমভিসি কন্ট্রোলার প্রকল্পে কাজ করছি যেখানে আমি ব্রাউজার থেকে একটি জিইটি ইউআরএল কল করছি -

নীচে url এর মাধ্যমে আমি ব্রাউজার থেকে একটি জিইটি কল করছি -

http://127.0.0.1:8080/testweb/processing?workflow=test&conf=20140324&dc=all

এবং নীচে নীচে কোডটি রয়েছে যেখানে ব্রাউজারে আঘাত করার পরে কল আসে -

@RequestMapping(value = "processing", method = RequestMethod.GET)
public @ResponseBody ProcessResponse processData(@RequestParam("workflow") final String workflow,
    @RequestParam("conf") final String value, @RequestParam("dc") final String dc) {

        System.out.println(workflow);
        System.out.println(value);
        System.out.println(dc);

        // some other code
    }

সমস্যা বিবৃতি:-

এখন কোন উপায় আছে, আমি কিছু শিরোলেখ থেকে আইপি ঠিকানা বের করতে পারি? অর্থ আমি জানতে চাই কোন আইপি ঠিকানা থেকে, কল আসছে, যার অর্থ যে কেউ ইউআরএল উপরে কল করছে, তাদের আইপি ঠিকানা আমার জানা দরকার। এটা কি সম্ভব?


স্প্রিং এওপি ব্যবহার করে এবং এইচটিটিপি সার্ভলেটআরউকেস্ট পরিচালনা করার চেষ্টা করুন। stackoverflow.com/questions/19271807/…
দিলিপ জি

উত্তর:


148

সমাধানটি হ'ল

@RequestMapping(value = "processing", method = RequestMethod.GET)
public @ResponseBody ProcessResponse processData(@RequestParam("workflow") final String workflow,
    @RequestParam("conf") final String value, @RequestParam("dc") final String dc, HttpServletRequest request) {

        System.out.println(workflow);
        System.out.println(value);
        System.out.println(dc);
        System.out.println(request.getRemoteAddr());
        // some other code
    }

যোগ HttpServletRequest requestআপনার পদ্ধতি সংজ্ঞা এবং তারপর সার্ভলেট API- টি ব্যবহার

স্প্রিং ডকুমেন্টেশন এখানে বলেছেন

15.3.2.3 সমর্থিত হ্যান্ডলার পদ্ধতির যুক্তি এবং রিটার্নের ধরণগুলি

Handler methods that are annotated with @RequestMapping can have very flexible signatures.
Most of them can be used in arbitrary order (see below for more details).

Request or response objects (Servlet API). Choose any specific request or response type,
for example ServletRequest or HttpServletRequest

4
সহায়তার জন্য কুইটোয়ার ধন্যবাদ একটি তাত্ক্ষণিক প্রশ্ন, ধরুন যদি কলটি নির্দিষ্ট মেশিনের পরিবর্তে লোড ব্যালেন্সার থেকে আসে তবে এটি কি কাজ করবে? আমার ধারণা নেই ..
জন

না, এটি লোড ব্যালেন্সারে কিছু কনফিগারেশন রয়েছে যা আইপি প্রেরণ করতে পারে কারণ সেটির অস্তিত্ব নেই, সম্ভবত এটি আপনার ক্ষেত্রে
কোয়েটোয়ার

সম্ভবত লোড ব্যালান্সার এই মানগুলি একটি শিরোনামে প্রেরণ করতে পারে তা চেক করুন, সুতরাং এইচটিটিপি সার্ভলেটআরকুয়েস্টের getHeader পদ্ধতি ব্যবহার করে বিবেচনা করুন।
কুইটোয়ার

কুইটোয়ার এটি পুরোপুরি কাজ করে !! তবে এইচটিটিপি সার্ভেলেটরেখেষ্টের পরিবর্তে অন্য কোনও উপায় নেই।
হর্ষাল পাতিল

4
এটি অবচয় করা হয়েছে।
Gewure

112

আমি এখানে দেরিতে আছি, তবে এটির উত্তর খুঁজতে কাউকে সহায়তা করতে পারে। সাধারণত servletRequest.getRemoteAddr()কাজ করে।

অনেক ক্ষেত্রে আপনার অ্যাপ্লিকেশন ব্যবহারকারীরা প্রক্সি সার্ভারের মাধ্যমে আপনার ওয়েব সার্ভারটি অ্যাক্সেস করছেন বা সম্ভবত আপনার অ্যাপ্লিকেশন কোনও লোড ব্যালান্সারের পিছনে রয়েছে।

সুতরাং আপনার ক্ষেত্রে এক্স-ফরওয়ার্ড-ফর এইচডিপি শিরোনামটি ব্যবহারকারীর আইপি ঠিকানা পেতে অ্যাক্সেস করা উচিত ।

যেমন String ipAddress = request.getHeader("X-FORWARDED-FOR");

আশাকরি এটা সাহায্য করবে.


11
নোট করুন যে X-Forwarded-Forসাধারণত আইপিএসের একটি কমা-বিচ্ছিন্ন তালিকা, চেইনের প্রতিটি প্রক্সি সহ তালিকায় এটি প্রত্যন্ত ঠিকানা যুক্ত করে। সুতরাং একটি ভাল বাস্তবায়নের ক্ষেত্রে বিশ্বস্ত প্রক্সিগুলির একটি তালিকা থাকে এবং এই শিরোনামটি ডান থেকে বামে পড়ার সময় সেই আইপিকে "এড়িয়ে যান"।
রমন

111.111.111.111/X হিসাবে আইপি ঠিকানা পেতে কিভাবে
মুনিব মীর্জা

26

আমি এটি করার জন্য এই জাতীয় পদ্ধতি ব্যবহার করি

public class HttpReqRespUtils {

    private static final String[] IP_HEADER_CANDIDATES = {
        "X-Forwarded-For",
        "Proxy-Client-IP",
        "WL-Proxy-Client-IP",
        "HTTP_X_FORWARDED_FOR",
        "HTTP_X_FORWARDED",
        "HTTP_X_CLUSTER_CLIENT_IP",
        "HTTP_CLIENT_IP",
        "HTTP_FORWARDED_FOR",
        "HTTP_FORWARDED",
        "HTTP_VIA",
        "REMOTE_ADDR"
    };

    public static String getClientIpAddressIfServletRequestExist() {

        if (RequestContextHolder.getRequestAttributes() == null) {
            return "0.0.0.0";
        }

        HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        for (String header: IP_HEADER_CANDIDATES) {
            String ipList = request.getHeader(header);
            if (ipList != null && ipList.length() != 0 && !"unknown".equalsIgnoreCase(ipList)) {
                String ip = ipList.split(",")[0];
                return ip;
            }
        }

        return request.getRemoteAddr();
    }
}

4
আমি এটি কোথায় ব্যবহার করব?
মাইফি উল আসাদ

12

আপনি RequestContextHolderনীচের হিসাবে স্থিতিশীলভাবে আইপি ঠিকানা পেতে পারেন :

HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes())
        .getRequest();

String ip = request.getRemoteAddr();

4

আপনার বেসকন্ট্রোলারে এই পদ্ধতিটি রাখুন:

@SuppressWarnings("ConstantConditions")
protected String fetchClientIpAddr() {
    HttpServletRequest request = ((ServletRequestAttributes) (RequestContextHolder.getRequestAttributes())).getRequest();
    String ip = Optional.ofNullable(request.getHeader("X-FORWARDED-FOR")).orElse(request.getRemoteAddr());
    if (ip.equals("0:0:0:0:0:0:0:1")) ip = "127.0.0.1";
    Assert.isTrue(ip.chars().filter($ -> $ == '.').count() == 3, "Illegal IP: " + ip);
    return ip;
}

4

নিচে দেখ. এই কোডটি স্প্রিং-বুট এবং স্প্রিং-বুট + অ্যাপাচি সিএক্সএফ / এসওএপি সহ কাজ করে।

    // in your class RequestUtil
    private static final String[] IP_HEADER_NAMES = { 
                                                        "X-Forwarded-For",
                                                        "Proxy-Client-IP",
                                                        "WL-Proxy-Client-IP",
                                                        "HTTP_X_FORWARDED_FOR",
                                                        "HTTP_X_FORWARDED",
                                                        "HTTP_X_CLUSTER_CLIENT_IP",
                                                        "HTTP_CLIENT_IP",
                                                        "HTTP_FORWARDED_FOR",
                                                        "HTTP_FORWARDED",
                                                        "HTTP_VIA",
                                                        "REMOTE_ADDR"
                                                    };

    public static String getRemoteIP(RequestAttributes requestAttributes)
    {
        if (requestAttributes == null)
        {
            return "0.0.0.0";
        }
        HttpServletRequest request = ((ServletRequestAttributes) requestAttributes).getRequest();
        String ip = Arrays.asList(IP_HEADER_NAMES)
            .stream()
            .map(request::getHeader)
            .filter(h -> h != null && h.length() != 0 && !"unknown".equalsIgnoreCase(h))
            .map(h -> h.split(",")[0])
            .reduce("", (h1, h2) -> h1 + ":" + h2);
        return ip + request.getRemoteAddr();
    }

    //... in service class:
    String remoteAddress = RequestUtil.getRemoteIP(RequestContextHolder.currentRequestAttributes());

:)


3

ক্লাসে autowiredঅনুরোধ বিন সহ বসন্তের নীচে @Controller:

@Autowired 
private HttpServletRequest request;

System.out.println(request.getRemoteHost());

4
এটি একাধিক থ্রেড জুড়ে নিয়ামকের একযোগে ব্যবহারে সমস্যা সৃষ্টি করতে পারে। শুধু singletons মধ্যে উচিত ইনজেকশনের @Controllerব্যবহার দৃষ্টান্ত @Autowired। অন্যথায়, @Scope(BeanDefinition.SCOPE_PROTOTYPE)প্রতিটি অনুরোধের সাথে নিয়ামকের একটি নতুন উদাহরণ তৈরি করা হয়েছে তা নিশ্চিত করতে আপনাকে অবশ্যই নিয়ামক শ্রেণিতে ব্যবহার করতে হবে । এটি কম দক্ষ, তবে আপনি যদি নিয়ামক শ্রেণীর কাছে সম্পত্তি হিসাবে কিছু ইনজেক্ট করতেই হয় তবে তা কার্যকর নয়।
অ্যান্ডি

1

আমার ক্ষেত্রে, আমি নিম্নলিখিত কনফিগারেশন সহ আমার অ্যাপ্লিকেশনটির সামনে এনগিনেক্স ব্যবহার করছিলাম:

location / {
     proxy_pass        http://localhost:8080/;
     proxy_set_header  X-Real-IP $remote_addr;
     proxy_set_header  X-Forwarded-For $proxy_add_x_forwarded_for;
     proxy_set_header  Host $http_host;
     add_header Content-Security-Policy 'upgrade-insecure-requests';
}

সুতরাং আমার অ্যাপ্লিকেশনটিতে আমি বাস্তব ব্যবহারকারী আইপি পেয়েছি:

String clientIP = request.getHeader("X-Real-IP");

0
private static final String[] IP_HEADER_CANDIDATES = {
            "X-Forwarded-For",
            "Proxy-Client-IP",
            "WL-Proxy-Client-IP",
            "HTTP_X_FORWARDED_FOR",
            "HTTP_X_FORWARDED",
            "HTTP_X_CLUSTER_CLIENT_IP",
            "HTTP_CLIENT_IP",
            "HTTP_FORWARDED_FOR",
            "HTTP_FORWARDED",
            "HTTP_VIA",
            "REMOTE_ADDR"
    };

    public static String getIPFromRequest(HttpServletRequest request) {
        String ip = null;
        if (request == null) {
            if (RequestContextHolder.getRequestAttributes() == null) {
                return null;
            }
            request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        }

        try {
            ip = InetAddress.getLocalHost().getHostAddress();
        } catch (Exception e) {
            e.printStackTrace();
        }
        if (!StringUtils.isEmpty(ip))
            return ip;

        for (String header : IP_HEADER_CANDIDATES) {
            String ipList = request.getHeader(header);
            if (ipList != null && ipList.length() != 0 && !"unknown".equalsIgnoreCase(ipList)) {
                return ipList.split(",")[0];
            }
        }

        return request.getRemoteAddr();
    }

আমি এই কোডটির সাথে উপরের কোডটি বেশিরভাগ ক্ষেত্রেই কাজ করি। HttpServletRequest requestআপনি এপিআই থেকে প্রাপ্ত পদ্ধতিতে পাস করুন

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.