精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

負載均衡技術全解析:Pulsar 分布式系統的優秀實踐

開發 前端
對于無狀態的服務來說,理論上我們只需要做好負載算法即可(輪訓、一致性哈希、低負載優先等)就可以很好的平衡各個節點之間的負載。而對于有狀態的服務來說,負載均衡就是將負載較高節點中的數據轉移到負載低的節點中。

背景

Pulsar 有提供一個查詢 Broker 負載的接口:

/**
     * Get load for this broker.
     *
     * @return
     * @throws PulsarAdminException
     */
LoadManagerReport getLoadReport() throws PulsarAdminException;

public interface LoadManagerReport extends ServiceLookupData {  
  
    ResourceUsage getCpu();  
  
    ResourceUsage getMemory();  
  
    ResourceUsage getDirectMemory();  
  
    ResourceUsage getBandwidthIn();  
  
    ResourceUsage getBandwidthOut();
}

可以返回一些 broker 的負載數據,比如 CPU、內存、流量之類的數據。

我目前碰到的問題是目前會遇到部分節點的負債不平衡,導致資源占用不均衡,所以想要手動查詢所有節點的負載數據,然后人工進行負載。

理論上這些數據是在運行時實時計算的數據,如果對于單機的倒還好說,每次請求這個接口直接實時計算一次就可以了。

但對于集群的服務來說會有多個節點,目前 Pulsar 提供的這個接口只能查詢指定節點的負載數據,也就是說每次得傳入目標節點的 IP 和端口。

所以我的預期是可以提供一個查詢所有節點負載的接口,已經提了 issue,最近準備寫 Purpose 把這個需求解決了。

實現這個需求的方案有兩種:

  • 拿到所有 broker 也就是服務節點信息,依次遍歷調用接口,然后自己組裝信息。
  • 從 zookeeper 中獲取負載信息。

理論上第二種更好,第一種實現雖然更簡單,但每次都發起一次 http 請求,多少有些浪費。

第二種方案直接從源頭獲取負載信息,只需要請求一次就可以了。

而正好社區提供了一個命令行工具可以直接打印所有的 broker 負載數據:

pulsar-perf monitor-brokers --connect-string <zookeeper host:port>

分布式系統常用組件

提供的命令行工具其實就是直接從 zookeeper 中查詢的數據。

在分布式系統中需要一個集中的組件來管理各種數據,比如:

  • 可以利用該組件來選舉 leader 節點
  • 使用該組件來做分布式鎖
  • 為分布式系統同步數據
  • 統一的存放和讀取某些數據

可以提供該功能的組件其實也不少:

  • zookeeper
  • etcd
  • oxia

Zookeeper 是老牌的分布式協調組件,可以做 leader 選舉、配置中心、分布式鎖、服務注冊與發現等功能。

在許多中間件和系統中都有應用,比如:

  • Apache Pulsar 中作為協調中心
  • Kafka 中也有類似的作用。
  • 在 Dubbo 中作為服務注冊發現組件。

etcd 的功能與 zookeeper 類似,可以用作服務注冊發現,也可以作為 Key Value 鍵值對存儲系統;在 kubernetes 中扮演了巨大作用,經歷了各種考驗,穩定性已經非常可靠了。

Oxia 則是 StreamNative 開發的一個用于替換 Zookeeper 的中間件,功能也與 Zookeeper 類似;目前已經可以在 Pulsar 中替換 Zookeeper,只是還沒有大規模的使用。

Pulsar 中的應用

下面以 Pulsar 為例(使用 zookeeper),看看在這類大型分布式系統中是如何處理負載均衡的。

再開始之前先明確下負載均衡大體上會做哪些事情。

  • 首先上報自己節點的負載數據
  • Leader 節點需要定時收集所有節點的負載數據。
  1. CPU、堆內存、堆外內存等通用數據的使用量
  2. 流出、流入流量
  3. 一些系統特有的數據,比如在 Pulsar 中就是:
  4. 每個 broker 中的 topic、consumer、producer、bundle 等數據。
  5. 這些負載數據中包括:
  • 再由 leader 節點讀取到這些數據后選擇負載較高的節點,將數據遷移到負載較低的節點。

以上就是一個完整的負載均衡的流程,下面我們依次看看在 Pulsar 中是如何實現這些邏輯的。

在 Pulsar 中提供了多種負載均衡策略,以下是加載負載均衡器的邏輯:

static LoadManager create(final PulsarService pulsar) {  
    try {  
        final ServiceConfiguration conf = pulsar.getConfiguration();  
        // Assume there is a constructor with one argument of PulsarService.  
        final Object loadManagerInstance = Reflections.createInstance(conf.getLoadManagerClassName(),  
                Thread.currentThread().getContextClassLoader());  
        if (loadManagerInstance instanceof LoadManager) {  
            final LoadManager casted = (LoadManager) loadManagerInstance;  
            casted.initialize(pulsar);  
            return casted;  
        } else if (loadManagerInstance instanceof ModularLoadManager) {  
            final LoadManager casted = new ModularLoadManagerWrapper((ModularLoadManager) loadManagerInstance);  
            casted.initialize(pulsar);  
            return casted;  
        }  
    } catch (Exception e) {  
        LOG.warn("Error when trying to create load manager: ", e);  
    }  
    // If we failed to create a load manager, default to SimpleLoadManagerImpl.  
    return new SimpleLoadManagerImpl(pulsar);  
}

默認使用的是 ModularLoadManagerImpl, 如果出現異常那就會使用 SimpleLoadManagerImpl 作為兜底。

他們兩個的區別是 ModularLoadManagerImpl 的功能更全,可以做更為細致的負載策略。

接下來以默認的 ModularLoadManagerImpl 為例講解上述的流程。

上報負載數據

在負載均衡器啟動的時候就會收集節點數據然后進行上報:

public void start() throws PulsarServerException {
        try {

            String brokerId = pulsar.getBrokerId();
            brokerZnodePath = LoadManager.LOADBALANCE_BROKERS_ROOT + "/" + brokerId;
            // 收集本地負載數據
            updateLocalBrokerData();

   // 上報 zookeeper
            brokerDataLock = brokersData.acquireLock(brokerZnodePath, localData).join();
        } catch (Exception e) {
            log.error("Unable to acquire lock for broker: [{}]", brokerZnodePath, e);
            throw new PulsarServerException(e);
        }
    }

首先獲取到當前 broker 的 Id 然后拼接一個 zookeeper 節點的路徑,將生成的 localData 上傳到 zookeeper 中。

// 存放 broker 的節點信息
ls /loadbalance/brokers

[broker-1:8080, broker-2:8080]

// 根據節點信息查詢負載數據
get /loadbalance/brokers/broker-1:8080

上報的數據:

{"webServiceUrl":"http://broker-1:8080","pulsarServiceUrl":"pulsar://broker-1:6650","persistentTopicsEnabled":true,"nonPersistentTopicsEnabled":true,"cpu":{"usage":7.311714728372232,"limit":800.0},"memory":{"usage":124.0,"limit":2096.0},"directMemory":{"usage":36.0,"limit":256.0},"bandwidthIn":{"usage":0.8324254085661579,"limit":1.0E7},"bandwidthOut":{"usage":0.7155446715644209,"limit":1.0E7},"msgThroughputIn":0.0,"msgThroughputOut":0.0,"msgRateIn":0.0,"msgRateOut":0.0,"lastUpdate":1690979816792,"lastStats":{"my-tenant/my-namespace/0x4ccccccb_0x66666664":{"msgRateIn":0.0,"msgThroughputIn":0.0,"msgRateOut":0.0,"msgThroughputOut":0.0,"consumerCount":2,"producerCount":0,"topics":1,"cacheSize":0}},"numTopics":1,"numBundles":1,"numConsumers":2,"numProducers":0,"bundles":["my-tenant/my-namespace/0x4ccccccb_0x66666664"],"lastBundleGains":[],"lastBundleLosses":[],"brokerVersionString":"3.1.0-SNAPSHOT","protocols":{},"advertisedListeners":{"internal":{"brokerServiceUrl":"pulsar://broker-1:6650"}},"loadManagerClassName":"org.apache.pulsar.broker.loadbalance.impl.ModularLoadManagerImpl","startTimestamp":1690940955211,"maxResourceUsage":0.140625,"loadReportType":"LocalBrokerData"}

采集數據

public static SystemResourceUsage getSystemResourceUsage(final BrokerHostUsage brokerHostUsage) {  
    SystemResourceUsage systemResourceUsage = brokerHostUsage.getBrokerHostUsage();  
  
    // Override System memory usage and limit with JVM heap usage and limit  
    double maxHeapMemoryInBytes = Runtime.getRuntime().maxMemory();  
    double memoryUsageInBytes = Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory();  
    double memoryUsage = memoryUsageInBytes / MIBI;  
    double memoryLimit = maxHeapMemoryInBytes / MIBI;  
    systemResourceUsage.setMemory(new ResourceUsage(memoryUsage, memoryLimit));  
  
    // Collect JVM direct memory  
    systemResourceUsage.setDirectMemory(new ResourceUsage((double) (getJvmDirectMemoryUsed() / MIBI),  
            (double) (DirectMemoryUtils.jvmMaxDirectMemory() / MIBI)));  
  
    return systemResourceUsage;  
}

會在運行時獲取一些 JVM 和 堆外內存的數據。

收集所有節點數據

作為 leader 節點還需要收集所有節點的負載數據,然后根據一些規則選擇將負載較高的節點移動到負債較低的節點中。

private void updateAllBrokerData() {
     // 從 zookeeper 中獲取所有節點
        final Set<String> activeBrokers = getAvailableBrokers();
        final Map<String, BrokerData> brokerDataMap = loadData.getBrokerData();
        for (String broker : activeBrokers) {
            try {
                String key = String.format("%s/%s", LoadManager.LOADBALANCE_BROKERS_ROOT, broker);
                // 依次讀取各個節點的負載數據
                Optional<LocalBrokerData> localData = brokersData.readLock(key).get();
                if (!localData.isPresent()) {
                    brokerDataMap.remove(broker);
                    log.info("[{}] Broker load report is not present", broker);
                    continue;
                }

                if (brokerDataMap.containsKey(broker)) {
                    // Replace previous local broker data.
                    brokerDataMap.get(broker).setLocalData(localData.get());
                } else {
                    // Initialize BrokerData object for previously unseen
                    // brokers.
                    // 將數據寫入到本地緩存
                    brokerDataMap.put(broker, new BrokerData(localData.get()));
                }
            } catch (Exception e) {
                log.warn("Error reading broker data from cache for broker - [{}], [{}]", broker, e.getMessage());
            }
        }
        // Remove obsolete brokers.
        for (final String broker : brokerDataMap.keySet()) {
            if (!activeBrokers.contains(broker)) {
                brokerDataMap.remove(broker);
            }
        }
    }

會從 zookeeper 的節點中獲取到所有的 broker 列表(broker 會在啟動時將自身的信息注冊到 zookeeper 中。)

然后依次讀取各自節點的負載數據,也就是在負載均衡器啟動的時候上報的數據。

篩選出所有 broker 中需要 unload 的 bundle

在 Pulsar 中 topic 是最核心的概念,而為了方便管理大量 topic,提出了一個 Bundle 的概念;Bundle 是一批 topic 的集合,管理 Bundle 自然會比 topic 更佳容易。

所以在 Pulsar 中做負載均衡最主要的就是將負載較高節點中的 bundle 轉移到低負載的 broker 中。

private void updateAllBrokerData() {
        final Set<String> activeBrokers = getAvailableBrokers();
        final Map<String, BrokerData> brokerDataMap = loadData.getBrokerData();
        for (String broker : activeBrokers) {
            try {
                String key = String.format("%s/%s", LoadManager.LOADBALANCE_BROKERS_ROOT, broker);
                Optional<LocalBrokerData> localData = brokersData.readLock(key).get();
                if (!localData.isPresent()) {
                    brokerDataMap.remove(broker);
                    log.info("[{}] Broker load report is not present", broker);
                    continue;
                }

                if (brokerDataMap.containsKey(broker)) {
                    // Replace previous local broker data.
                    brokerDataMap.get(broker).setLocalData(localData.get());
                } else {
                    // Initialize BrokerData object for previously unseen
                    // brokers.
                    brokerDataMap.put(broker, new BrokerData(localData.get()));
                }
            } catch (Exception e) {
                log.warn("Error reading broker data from cache for broker - [{}], [{}]", broker, e.getMessage());
            }
        }
        // Remove obsolete brokers.
        for (final String broker : brokerDataMap.keySet()) {
            if (!activeBrokers.contains(broker)) {
                brokerDataMap.remove(broker);
            }
        }
    }

負載均衡器在啟動的時候就會查詢所有節點的數據,然后寫入到 brokerDataMap 中。

同時也會注冊相關的 zookeeper 事件,當注冊的節點發生變化時(一般是新增或者刪減了 broker 節點)就會更新內存中緩存的負載數據。

之后 leader 節點會定期調用 org.apache.pulsar.broker.loadbalance.impl.ModularLoadManagerImpl#doLoadShedding 函數查詢哪些數據需要卸載,然后進行重新負載。

final Multimap<String, String> bundlesToUnload = loadSheddingStrategy.findBundlesForUnloading(loadData, conf);

最核心的就是調用這個 findBundlesForUnloading 函數,會返回需要卸載 bundle 集合,最終會遍歷這個集合調用 admin API 進行卸載和重平衡。

而這個函數會有多種實現,本質上就是根據傳入的各個節點的負載數據,然后根據自定義的規則返回一批需要卸載的數據。

以默認的 org.apache.pulsar.broker.loadbalance.impl.ThresholdShedder 規則為例:

它是根據帶寬、內存、流量等各個指標的權重算出每個節點的負載值,之后為整個集群計算出一個平均負載值。

以上圖為例:超過 ShedBundles 的數據就需要被卸載掉,然后轉移到低負載的節點中。

所以最左邊節點和超出的 bundle 部分就需要被返回。

具體的計算邏輯如下:

private void filterAndSelectBundle(LoadData loadData, Map<String, Long> recentlyUnloadedBundles, String broker,
                                       LocalBrokerData localData, double minimumThroughputToOffload) {
        MutableDouble trafficMarkedToOffload = new MutableDouble(0);
        MutableBoolean atLeastOneBundleSelected = new MutableBoolean(false);
        loadData.getBundleDataForLoadShedding().entrySet().stream()
                .map((e) -> {
                    String bundle = e.getKey();
                    BundleData bundleData = e.getValue();
                    TimeAverageMessageData shortTermData = bundleData.getShortTermData();
                    double throughput = shortTermData.getMsgThroughputIn() + shortTermData.getMsgThroughputOut();
                    return Pair.of(bundle, throughput);
                }).filter(e ->
                        !recentlyUnloadedBundles.containsKey(e.getLeft())
                ).filter(e ->
                        localData.getBundles().contains(e.getLeft())
                ).sorted((e1, e2) ->
                        Double.compare(e2.getRight(), e1.getRight())
                ).forEach(e -> {
                    if (trafficMarkedToOffload.doubleValue() < minimumThroughputToOffload
                            || atLeastOneBundleSelected.isFalse()) {
                        selectedBundlesCache.put(broker, e.getLeft());
                        trafficMarkedToOffload.add(e.getRight());
                        atLeastOneBundleSelected.setTrue();
                    }
                });
    }

從代碼里看的出來就是在一個備選集合中根據各種閾值和判斷條件篩選出需要卸載的 bundle。

而 SimpleLoadManagerImpl 的實現如下:

synchronized (currentLoadReports) {
 for (Map.Entry<ResourceUnit, LoadReport> entry : currentLoadReports.entrySet()) {
  ResourceUnit overloadedRU = entry.getKey();
  LoadReport lr = entry.getValue();
  // 所有數據做一個簡單的篩選,超過閾值的數據需要被 unload
  if (isAboveLoadLevel(lr.getSystemResourceUsage(), overloadThreshold)) {
   ResourceType bottleneckResourceType = lr.getBottleneckResourceType();
   Map<String, NamespaceBundleStats> bundleStats = lr.getSortedBundleStats(bottleneckResourceType);
   if (bundleStats == null) {
    log.warn("Null bundle stats for bundle {}", lr.getName());
    continue;

   }

就是很簡單的通過將判斷節點的負載是否超過了閾值 isAboveLoadLevel,然后做一個簡單的排序就返回了。

從這里也看得出來 SimpleLoadManagerImpl 和 ModularLoadManager 的區別,SimpleLoadManagerImpl 更簡單,并沒有提供多個 doLoadShedding 的篩選實現。

總結

總的來說對于無狀態的服務來說,理論上我們只需要做好負載算法即可(輪訓、一致性哈希、低負載優先等)就可以很好的平衡各個節點之間的負載。

而對于有狀態的服務來說,負載均衡就是將負載較高節點中的數據轉移到負載低的節點中。

其中的關鍵就是需要存儲各個節點的負載數據(業界常用的是存儲到 zookeeper 中),然后再由一個 leader 節點從這些節點中根據某種負載算法選擇出負載較高的節點以及負載較低的節點,最終把數據遷移過去即可。

責任編輯:姜華 來源: crossoverJie
相關推薦

2019-07-17 22:23:01

分布式系統負載均衡架構

2014-06-11 09:17:39

負載均衡

2014-05-23 10:30:25

負載均衡分布式架構

2019-07-12 09:14:07

分布式系統負載均衡

2025-07-21 01:00:00

2013-03-01 09:55:28

負載均衡分布式存儲集群

2025-06-12 09:48:46

2021-01-27 09:45:17

負載均衡

2017-09-26 15:24:48

分布式集群均衡

2023-11-03 08:13:35

ZAB協議負載均衡

2019-03-27 08:43:17

Nginx負載均衡服務器

2022-03-21 19:44:30

CitusPostgreSQ執行器

2024-07-08 07:30:47

2023-10-26 18:10:43

分布式并行技術系統

2024-09-27 09:19:30

2022-04-07 17:13:09

緩存算法服務端

2019-05-07 11:57:26

分布式架構負載均衡

2024-06-03 14:17:00

2019-10-10 09:16:34

Zookeeper架構分布式

2012-07-06 09:27:02

云計算分布式服務器負載均衡
點贊
收藏

51CTO技術棧公眾號

欧美在线一卡| 精品午夜福利在线观看| a欧美人片人妖| 中文字幕免费不卡| 亚洲在线www| 欧美一二三区视频| 91免费精品| 亚洲成人精品在线| 国产wwwxx| 日本三级韩国三级欧美三级| 91老司机福利 在线| 国产精品偷伦视频免费观看国产 | 日韩亚洲欧美视频| 青青草视频免费在线观看| 久久精品国产**网站演员| 久久久久国产精品免费| 国产午夜精品久久久久久久久| 欧美久久一区二区三区| 欧美性猛交xxxxx免费看| 欧美 另类 交| 国产视频精品久久| 国产 日韩 欧美大片| 国产精品偷伦一区二区| 中文字幕视频网| 欧美日本一区二区高清播放视频| 亚洲美女久久久| 蜜臀视频在线观看| 日韩久久一区| 欧美性三三影院| 97国产在线播放| 羞羞的视频在线看| 亚洲欧洲精品一区二区三区| 久久久综合香蕉尹人综合网| 国产黄色一区二区| 国产综合久久久久影院| 国产精品69av| 一级免费在线观看| 在线视频观看日韩| 欧美激情综合色综合啪啪五月| 999久久久国产| 国产一区二区三区四区五区传媒| 欧美精品一区二区久久久| 欧美性猛交xxxx乱大交91| 丁香婷婷久久| 欧美三日本三级三级在线播放| 日韩人妻精品无码一区二区三区| 男插女视频久久久| 亚洲在线中文字幕| 免费的一级黄色片| 成人a在线视频免费观看| 国产精品你懂的在线欣赏| 青青草成人激情在线| 美丽的姑娘在线观看免费动漫| 不卡的看片网站| 精品国产免费久久久久久尖叫| www.国产.com| 成人美女视频在线观看18| 1卡2卡3卡精品视频| 精品女同一区二区三区| 国产成人免费视频精品含羞草妖精| 91久久精品国产| 国产欧美综合视频| 国产·精品毛片| 精品免费一区二区三区蜜桃| 五月激情婷婷网| 久久综合999| 日本一区二区在线视频观看| 啊v在线视频| 1000精品久久久久久久久| 一区二区三区在线视频111| 久热国产在线| 一区二区三区毛片| 无码人妻精品一区二区三区在线| 中文字幕资源网在线观看免费| 色狠狠一区二区三区香蕉| 亚洲欧美另类动漫| 国产一区二区三区免费在线| 欧美成人综合网站| 国内精品久久99人妻无码| 久久99蜜桃| 美女啪啪无遮挡免费久久网站| 免费一级肉体全黄毛片| 蘑菇福利视频一区播放| 国产色综合天天综合网| 精品人妻av一区二区三区| 99久久er热在这里只有精品15| 日本在线免费观看一区| 成人video亚洲精品| 精品国产户外野外| 网站一区二区三区| 99香蕉久久| 在线性视频日韩欧美| 日本黄色小说视频| 久久中文字幕一区二区三区| 国产精品自拍视频| 亚洲AV无码成人片在线观看| 久久久亚洲精品石原莉奈| 熟女熟妇伦久久影院毛片一区二区| 激情网站在线| 欧美视频在线播放| 天天躁日日躁狠狠躁av| 国产一区二区三区不卡视频网站 | 欧美激情20| 欧美理论电影在线| 日韩免费高清一区二区| 欧美肥老太太性生活| 国模视频一区二区| 91成年人视频| 国产校园另类小说区| 日本中文字幕一级片| 成人自拍av| 精品国产sm最大网站免费看| 午夜黄色福利视频| 香蕉久久夜色精品国产| 99一区二区| 日本www在线观看| 日韩欧美国产免费播放| 男人女人拔萝卜视频| 欧美系列电影免费观看| 91av网站在线播放| 亚洲第一黄色片| 亚洲欧洲www| 香港日本韩国三级网站| 色婷婷av一区二区三区丝袜美腿| 欧美成人合集magnet| 中文字幕日本视频| 久久久精品中文字幕麻豆发布| 久久艹国产精品| 精品成人18| 久久夜精品香蕉| 中文字幕欧美人妻精品| 久久久久国产精品麻豆ai换脸 | 日韩欧美中文一区二区| 在线看片中文字幕| 老牛国产精品一区的观看方式| 国产嫩草一区二区三区在线观看| 米奇精品一区二区三区| 欧美午夜寂寞影院| 夫妇交换中文字幕| 免费黄网站欧美| 婷婷四月色综合| 欧美大片高清| 亚洲精选一区二区| 国产又粗又爽视频| 2014亚洲片线观看视频免费| 拔插拔插海外华人免费| 日韩精品久久久久久久软件91| 久久久精品国产亚洲| 国产视频一二三四区| 国产精品盗摄一区二区三区| 潘金莲激情呻吟欲求不满视频| 欧美美女视频| 成人h猎奇视频网站| 天堂地址在线www| 欧美日韩精品欧美日韩精品一| 永久免费毛片在线观看| 蜜臀av性久久久久av蜜臀妖精 | 成人中心免费视频| 国产在线观看免费麻豆| 91精品国产综合久久久蜜臀图片 | 国产精品欧美日韩| 尤物网址在线观看| 欧美一区二区三区的| 久久久久亚洲AV成人| 国产传媒久久文化传媒| 成人在线播放网址| 婷婷综合一区| 国产精品视频地址| а√资源新版在线天堂| 欧美不卡123| 国产精品自拍99| 欧美韩国日本不卡| 三上悠亚 电影| 亚洲另类自拍| 日本不卡久久| 成人av在线播放| 久久久免费电影| 邻居大乳一区二区三区| 欧美日韩小视频| 青青草手机在线观看| 91原创在线视频| 日本爱爱免费视频| 欧美黄色一级视频| 欧美另类网站| av在线亚洲一区| 韩剧1988免费观看全集| 国产在线你懂得| 日韩一区二区在线看| 亚洲男人第一av| 最新热久久免费视频| 国模无码视频一区| 免费成人在线网站| 欧美乱大交xxxxx潮喷l头像| 国产欧美日韩在线观看视频| 91久久国产婷婷一区二区| 免费一二一二在线视频| 最近中文字幕日韩精品| 懂色av一区二区三区四区| 欧洲视频一区二区| 午夜写真片福利电影网| 国产片一区二区三区| 师生出轨h灌满了1v1| 视频在线在亚洲| 国产 欧美 日韩 一区| 欧洲三级视频| 国产一区高清视频| 成人在线分类| 国产精品av电影| 日本不卡1234视频| 欧美国产亚洲视频| 麻豆传媒免费在线观看| 亚洲欧美变态国产另类| 亚洲乱色熟女一区二区三区| 欧美三级午夜理伦三级中视频| 日本在线观看中文字幕| 亚洲欧美在线视频| 午夜在线观看一区| 91在线视频官网| 四虎永久免费观看| 久久99精品久久久久| 久久久久久久少妇| 99香蕉国产精品偷在线观看| 97在线免费视频观看| 日韩欧美一区二区三区在线视频| 久久久久久亚洲精品不卡4k岛国| 1204国产成人精品视频| 91欧美精品午夜性色福利在线| 国模一区二区| 日韩美女福利视频| 女海盗2成人h版中文字幕| 久久久久久久电影一区| av在线看片| 久久亚洲精品国产亚洲老地址| 第九色区av在线| 亚洲最新av网址| 国产在线视频网| 一区二区亚洲欧洲国产日韩| 欧美色综合一区二区三区| 亚洲激情视频在线播放| 黑人乱码一区二区三区av| 精品国产免费人成电影在线观看四季| 国产伦理一区二区| 3751色影院一区二区三区| 国产一区二区三区四区视频| 精品视频1区2区| 中文字幕码精品视频网站| 欧美视频一二三区| 亚洲图片中文字幕| 6080午夜不卡| 国产aⅴ爽av久久久久成人| 777精品伊人久久久久大香线蕉| 91精品国自产| 欧美一区二区三区视频在线 | 懂色av中文字幕一区二区三区| 日韩av福利在线观看| 国产一二精品视频| gogo亚洲国模私拍人体| 不卡av免费在线观看| 亚洲一区二区乱码| 久久久久久久久久久久久久久99| 在线免费观看日韩av| 国产婷婷色一区二区三区四区 | 亚洲国产一区二区在线播放| 国产一国产二国产三| 激情久久av一区av二区av三区 | 欧美日韩国产成人在线91| 92久久精品一区二区| 日韩欧美中文字幕精品| 色婷婷av一区二区三区之e本道| 日韩电视剧免费观看网站| 国产中文字幕在线看| 日韩一二三在线视频播| 欧美男男video| 日韩av成人在线| 国产精品诱惑| 国产99在线播放| 啪啪亚洲精品| 欧洲美女和动交zoz0z| 亚洲欧洲日本mm| 最新中文字幕免费视频| 国产精品综合二区| 亚洲一区二区三区四区五区六区 | 青青草手机视频在线观看| 精品av在线播放| 在线免费观看一区二区| 精品美女一区二区| 国产免费av在线| 欧美成人精品在线| 免费成人美女女| 亚洲在线免费观看| 性人久久久久| 免费观看国产视频在线| 美女被久久久| 在线观看视频你懂得| 26uuu色噜噜精品一区二区| 老司机精品免费视频| 午夜视频一区在线观看| 中文字幕在线日亚洲9| 亚洲国产成人一区| 麻豆视频免费在线观看| 欧美中在线观看| 欧美特黄不卡| 日韩精品一线二线三线| 亚洲国产专区| 亚洲综合在线一区二区| 国产欧美日韩另类一区| 日本三级2019| 91精品久久久久久久久99蜜臂 | 欧美成人精品一区二区三区| 日韩精品99| 国产综合色一区二区三区| 天天做天天爱天天综合网| 欧美极品欧美精品欧美| 精品一区二区三区不卡| 三上悠亚影音先锋| 亚洲mv在线观看| 亚洲av无码国产精品久久不卡| 色偷偷9999www| 丝袜美腿诱惑一区二区三区| 高清国产在线一区| 91tv官网精品成人亚洲| 爱情岛论坛亚洲首页入口章节| 91亚洲国产成人精品一区二区三| 青娱乐国产在线视频| 91精品国产91久久久久久一区二区| 九色国产在线观看| 欧美一级bbbbb性bbbb喷潮片| 色妞ww精品视频7777| 婷婷久久综合九色综合绿巨人| 免费在线a视频| 成人性生交大片免费看视频在线| 99自拍偷拍视频| 欧美性大战久久久久久久蜜臀| 男同在线观看| 国产91精品高潮白浆喷水| 国产福利一区二区精品秒拍| 4444在线观看| 国产伦精品一区二区三区免费迷| www中文在线| 欧美日韩在线精品一区二区三区激情 | 91国偷自产一区二区开放时间| 天堂av在线播放| 2019中文字幕在线免费观看| 久久亚洲黄色| a级黄色一级片| 91在线免费播放| 免费观看成人毛片| 亚洲片在线观看| 欧美舌奴丨vk视频| 日韩欧美在线观看强乱免费| 日日夜夜免费精品视频| xxxx日本黄色| 欧美性做爰猛烈叫床潮| 国产69精品久久app免费版| 国产精品久久久久久久久久ktv| 亚洲涩涩av| 另类小说第一页| 国产精品久久久久国产精品日日| 在线黄色av网站| 欧美精品在线视频观看| 98视频精品全部国产| 天天夜碰日日摸日日澡性色av| 99re在线精品| 特级西西444www大胆免费看| 色婷婷综合成人av| 久久影院一区二区三区| 人人妻人人澡人人爽欧美一区| av在线这里只有精品| 二区视频在线观看| 在线观看日韩av| 久久的色偷偷| 极品美女扒开粉嫩小泬| 久久久噜噜噜久噜久久综合| 中文字幕激情视频| 欧美疯狂xxxx大交乱88av| 黄色免费大全亚洲| 激情内射人妻1区2区3区| 日韩理论片中文av| 人妻妺妺窝人体色www聚色窝| 国产成人av在线播放| 国产精品久久久久久| 成年女人免费视频| 欧美在线播放高清精品| 亚洲国产精品精华素| 欧美h视频在线| 国产一区在线不卡| av黄色在线看| 久久九九有精品国产23| 九色丨蝌蚪丨成人| 中文字幕av专区| 亚洲国产日韩精品| 成人在线二区| 国产精品视频免费一区| 免费看欧美女人艹b| 国产一级做a爱免费视频| 国产亚洲精品久久| aiai久久| 国产成年人视频网站| 舔着乳尖日韩一区| 尤物视频在线看|