Rumah >Java >javaTutorial >Cara Melaksanakan Pengehadan Kadar dalam API Boot Spring Menggunakan Pengaturcaraan Berorientasikan Aspek

Cara Melaksanakan Pengehadan Kadar dalam API Boot Spring Menggunakan Pengaturcaraan Berorientasikan Aspek

WBOY
WBOYasal
2024-09-09 16:31:021027semak imbas

How to Implement Rate Limiting in Spring Boot APIs Using Aspect-Oriented Programming

Apa yang saya pelajari semasa membuat projek sampingan…

Pengenalan: Pengaturcaraan Berorientasikan Aspek (AOP) ialah teknik yang berkuasa dalam Spring Boot untuk memisahkan kebimbangan silang daripada logik aplikasi utama. Satu kes penggunaan biasa AOP ialah melaksanakan pengehadan kadar dalam API, di mana anda mengehadkan bilangan permintaan yang boleh dibuat oleh pelanggan dalam tempoh tertentu. Dalam artikel ini, kami akan meneroka cara memanfaatkan AOP untuk melaksanakan pengehadan kadar dalam Spring Boot API, memastikan prestasi optimum dan penggunaan sumber.

Jadual Kandungan:

  1. Memahami Pengaturcaraan Berorientasikan Aspek (AOP)
  2. Melaksanakan Pengehadan Kadar dengan AOP dalam But Spring
  3. Contoh: Pengehadan Kadar dalam API But Spring
  4. Kesimpulan

1. Memahami Pengaturcaraan Berorientasikan Aspek (AOP)

Pengaturcaraan Berorientasikan Aspek ialah paradigma pengaturcaraan yang bertujuan untuk memodulasi kebimbangan silang dalam pembangunan perisian. Kebimbangan silang adalah aspek program yang mempengaruhi berbilang modul dan sukar untuk dimodulasi menggunakan pendekatan tradisional. Contohnya termasuk pengelogan, keselamatan dan pengurusan transaksi.

AOP memperkenalkan konsep aspek, yang merangkumi kebimbangan silang. Aspek ialah unit modular yang boleh digunakan merentasi bahagian aplikasi yang berbeza tanpa mengubah logik teras. Rangka kerja AOP, seperti Spring AOP, menyediakan mekanisme untuk mentakrifkan aspek dan menerapkannya pada titik gabungan tertentu dalam aliran pelaksanaan aplikasi.

2. Melaksanakan Pengehadan Kadar dengan AOP dalam But Spring

Penghadan kadar ialah keperluan biasa dalam API web untuk mencegah penyalahgunaan dan memastikan penggunaan sumber yang adil. Dengan AOP dalam Spring Boot, kami boleh melaksanakan pengehadan kadar dengan memintas seruan kaedah dan menguatkuasakan sekatan ke atas bilangan permintaan yang dibenarkan dalam tempoh masa tertentu.

Untuk melaksanakan pengehadan kadar dengan AOP dalam Spring Boot, kami biasanya mengikuti langkah berikut:

  • Tentukan anotasi tersuai untuk menandakan kaedah yang sepatutnya dihadkan kadar.
  • Buat kelas aspek yang memintas penyebutan kaedah beranotasi dengan anotasi tersuai.
  • Gunakan komponen pengehad kadar untuk menjejak dan menguatkuasakan had kadar.
  • Kendalikan had kadar melebihi senario dengan anggun, seperti dengan membuang pengecualian tersuai.

3. Contoh: Pengehadan Kadar dalam API Spring Boot

Melaksanakan pengehadan kadar dalam Spring Boot API boleh dicapai menggunakan pelbagai teknik. Satu pendekatan biasa ialah menggunakan Spring AOP (Aspect-Oriented Programming) untuk memintas permintaan masuk dan menguatkuasakan had kadar.

Langkah 1 - Tentukan Konfigurasi Had Kadar: Buat kelas konfigurasi di mana anda menentukan parameter had kadar seperti bilangan permintaan yang dibenarkan dan tempoh masa.

@Configuration
public class RateLimitConfig {
    @Value("${rate.limit.requests}")
    private int requests;

    @Value("${rate.limit.seconds}")
    private int seconds;

    // Getters and setters
}

Langkah 2 — Buat Aspek Mengehadkan Kadar: Laksanakan aspek menggunakan Spring AOP untuk memintas panggilan kaedah dan menguatkuasakan had kadar.

@Aspect
@Component
public class RateLimitAspect {
    @Autowired
    private RateLimitConfig rateLimitConfig;

    @Autowired
    private RateLimiter rateLimiter;

    @Around("@annotation(RateLimited)")
    public Object enforceRateLimit(ProceedingJoinPoint joinPoint) throws Throwable {
        String key = getKey(joinPoint);
        if (!rateLimiter.tryAcquire(key, rateLimitConfig.getRequests(), rateLimitConfig.getSeconds())) {
            throw new RateLimitExceededException("Rate limit exceeded");
        }
        return joinPoint.proceed();
    }

    private String getKey(ProceedingJoinPoint joinPoint) {
        // Generate a unique key for the method being called
        // Example: method signature, user ID, IP address, etc.
        // You can customize this based on your requirements
    }
}

Langkah 3 — Tentukan Anotasi RateLimited: Buat anotasi tersuai untuk menandakan kaedah yang sepatutnya dihadkan kadar.

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
  public @interface RateLimited {
}

Langkah 4 — Laksanakan Pengehad Kadar: Buat komponen pengehad kadar untuk mengurus had kadar menggunakan algoritma baldi token atau mana-mana algoritma lain yang sesuai.

@Component
public class RateLimiter {
    private final Map<String,RateLimitedSemaphore> semaphores = new ConcurrentHashMap<>();

    public boolean tryAcquire(String key, int requests, int seconds) {
        // Get the current timestamp
        long currentTime = System.currentTimeMillis();

        // Calculate the start time of the time window (in milliseconds)
        long startTime = currentTime - seconds * 1000;

        // Remove expired entries from the semaphore map
        cleanupExpiredEntries(startTime);

        // Get or create the semaphore for the given key
        RateLimitedSemaphore semaphore = semaphores.computeIfAbsent(key, k -> {
            RateLimitedSemaphore newSemaphore = new RateLimitedSemaphore(requests);
            newSemaphore.setLastAcquireTime(currentTime); // Set last acquire time
            return newSemaphore;
        });

        // Check if the semaphore allows acquiring a permit
        boolean acquired = semaphore.tryAcquire();
        if (acquired) {
            semaphore.setLastAcquireTime(currentTime); // Update last acquire time
        }
        return acquired;
    }

    private void cleanupExpiredEntries(long startTime) {
        Iterator<Map.Entry<String, RateLimitedSemaphore>> iterator = semaphores.entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry<String, RateLimitedSemaphore> entry = iterator.next();
            String key = entry.getKey();
            RateLimitedSemaphore semaphore = entry.getValue();
            if (semaphore.getLastAcquireTime() < startTime) {
                iterator.remove();
            }
        }
    }

    private class RateLimitedSemaphore extends Semaphore {
        private volatile long lastAcquireTime;

        public RateLimitedSemaphore(int permits) {
            super(permits);
        }

        public long getLastAcquireTime() {
            return lastAcquireTime;
        }

        public void setLastAcquireTime(long lastAcquireTime) {
            this.lastAcquireTime = lastAcquireTime;
        }
    }
}

Langkah 5 — Anotasi Kaedah Pengawal: Anotasi kaedah pengawal yang sepatutnya dihadkan kadar dengan @RateLimited.

@RestController
public class MyController {
    @RateLimited
    @GetMapping("/api/resource")
    public ResponseEntity<String> getResource() {
        // Implementation
    }
}

Langkah 6 — Konfigurasikan Sifat Had Kadar: Konfigurasikan sifat had kadar dalam application.properties atau application.yml anda.

rate.limit.requests=10
rate.limit.seconds=60

Tambahan pula…

Untuk mengehadkan permintaan mengikut alamat IP, anda boleh mengekstrak alamat IP daripada permintaan masuk dan menggunakannya sebagai kunci untuk mengehadkan kadar. Begini cara anda boleh mengubah suai kaedah getKey untuk menghasilkan kunci unik berdasarkan alamat IP:

private String getKey(HttpServletRequest request) {
    // Get the IP address of the client making the request
    String ipAddress = request.getRemoteAddr();
    return ipAddress; // Use IP address as the key
}

Anda juga perlu mengubah suai kaedah enforceRateLimit dalam kelas RateLimitAspect untuk menghantar objek HttpServletRequest ke kaedah getKey:

@Around("@annotation(RateLimited)")
public Object enforceRateLimit(ProceedingJoinPoint joinPoint) throws Throwable {
    // Get the current request from the JoinPoint
    ServletRequestAttributes requestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
    HttpServletRequest request = requestAttributes.getRequest();

    String key = getKey(request);
    if (!rateLimiter.tryAcquire(key, rateLimitConfig.getRequests(), rateLimitConfig.getSeconds())) {
        throw new RateLimitExceededException("Rate limit exceeded");
    }
    return joinPoint.proceed();
}

Dalam contoh ini, kami mentakrifkan anotasi tersuai @RateLimited untuk menandakan kaedah yang sepatutnya dihadkan kadar. Kami kemudian membuat aspek RateLimitAspect yang memintas panggilan kaedah yang dianotasi dengan @RateLimited. Di dalam aspek tersebut, kami menguatkuasakan had kadar menggunakan komponen RateLimiter.

4. Kesimpulan

Dalam artikel ini, kami telah meneroka cara melaksanakan pengehadan kadar dalam Spring Boot API menggunakan Pengaturcaraan Berorientasikan Aspek (AOP). Dengan memisahkan kebimbangan silang seperti pengehadan kadar daripada logik aplikasi teras, kami boleh memastikan modulariti, kebolehselenggaraan dan kebolehskalaan yang lebih baik bagi aplikasi kami. AOP menyediakan mekanisme yang berkuasa untuk menangani kebimbangan sedemikian, membolehkan pembangun menumpukan pada membina API yang teguh dan cekap.

Dengan mengikut langkah-langkah yang digariskan dalam artikel ini dan memanfaatkan keupayaan AOP dalam Spring Boot, pembangun boleh melaksanakan pengehadan kadar dengan mudah dan kebimbangan lain dalam aplikasi mereka, yang membawa kepada API yang lebih berdaya tahan dan berprestasi tinggi.

Atas ialah kandungan terperinci Cara Melaksanakan Pengehadan Kadar dalam API Boot Spring Menggunakan Pengaturcaraan Berorientasikan Aspek. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn