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

驚呆了,Spring中竟然有12種定義Bean的方法

開發 架構
在龐大的java體系中,spring有著舉足輕重的地位,它給每位開發者帶來了極大的便利和驚喜。我們都知道spring是創建和管理bean的工廠,它提供了多種定義bean的方式,能夠滿足我們日常工作中的多種業務場景。

[[409379]]

本文轉載自微信公眾號「蘇三說技術」,作者因為熱愛所以堅持ing 。轉載本文請聯系蘇三說技術公眾號。

前言

在龐大的java體系中,spring有著舉足輕重的地位,它給每位開發者帶來了極大的便利和驚喜。我們都知道spring是創建和管理bean的工廠,它提供了多種定義bean的方式,能夠滿足我們日常工作中的多種業務場景。

那么問題來了,你知道spring中有哪些方式可以定義bean?

我估計很多人會說出以下三種:

沒錯,但我想說的是以上三種方式只是開胃小菜,實際上spring的功能遠比你想象中更強大。

各位看官如果不信,請繼續往下看。

1. xml文件配置bean

我們先從xml配置bean開始,它是spring最早支持的方式。后來,隨著springboot越來越受歡迎,該方法目前已經用得很少了,但我建議我們還是有必要了解一下。

1.1 構造器

如果你之前有在bean.xml文件中配置過bean的經歷,那么對如下的配置肯定不會陌生:

  1. <bean id="personService" class="com.sue.cache.service.test7.PersonService"
  2. </bean> 

這種方式是以前使用最多的方式,它默認使用了無參構造器創建bean。

當然我們還可以使用有參的構造器,通過標簽來完成配置。

  1. <bean id="personService" class="com.sue.cache.service.test7.PersonService"
  2.    <constructor-arg index="0" value="susan"></constructor-arg> 
  3.    <constructor-arg index="1" ref="baseInfo"></constructor-arg> 
  4. </bean> 

其中:

  • index表示下標,從0開始。
  • value表示常量值
  • ref表示引用另一個bean

1.2 setter方法

除此之外,spring還提供了另外一種思路:通過setter方法設置bean所需參數,這種方式耦合性相對較低,比有參構造器使用更為廣泛。

先定義Person實體:

  1. @Data 
  2. public class Person { 
  3.     private String name
  4.     private int age; 

它里面包含:成員變量name和age,getter/setter方法。

然后在bean.xml文件中配置bean時,加上<:property>標簽設置bean所需參數。

  1. <bean id="person" class="com.sue.cache.service.test7.Person"
  2.    <property name="name" value="susan"></constructor-arg> 
  3.    <property name="age" value="18"></constructor-arg> 
  4. </bean> 

1.3 靜態工廠

這種方式的關鍵是需要定義一個工廠類,它里面包含一個創建bean的靜態方法。例如:

  1. public class SusanBeanFactory { 
  2.     public static Person createPerson(String nameint age) { 
  3.         return new Person(name, age); 
  4.     } 

接下來定義Person類如下:

  1. @AllArgsConstructor 
  2. @NoArgsConstructor 
  3. @Data 
  4. public class Person { 
  5.     private String name
  6.     private int age; 

它里面包含:成員變量name和age,getter/setter方法,無參構造器和全參構造器。

然后在bean.xml文件中配置bean時,通過factory-method參數指定靜態工廠方法,同時通過設置相關參數。

  1. <bean class="com.sue.cache.service.test7.SusanBeanFactory" factory-method="createPerson"
  2.    <constructor-arg index="0" value="susan"></constructor-arg> 
  3.    <constructor-arg index="1" value="18"></constructor-arg> 
  4. </bean> 

1.4 實例工廠方法

這種方式也需要定義一個工廠類,但里面包含非靜態的創建bean的方法。

  1. public class SusanBeanFactory { 
  2.     public Person createPerson(String nameint age) { 
  3.         return new Person(name, age); 
  4.     } 

Person類跟上面一樣,就不多說了。

然后bean.xml文件中配置bean時,需要先配置工廠bean。然后在配置實例bean時,通過factory-bean參數指定該工廠bean的引用。

  1. <bean id="susanBeanFactory" class="com.sue.cache.service.test7.SusanBeanFactory"
  2. </bean> 
  3. <bean factory-bean="susanBeanFactory" factory-method="createPerson"
  4.    <constructor-arg index="0" value="susan"></constructor-arg> 
  5.    <constructor-arg index="1" value="18"></constructor-arg> 
  6. </bean> 

1.5 FactoryBean

不知道大家有沒有發現,上面的實例工廠方法每次都需要創建一個工廠類,不方面統一管理。

這時我們可以使用FactoryBean接口。

  1. public class UserFactoryBean implements FactoryBean<User> { 
  2.     @Override 
  3.     public User getObject() throws Exception { 
  4.         return new User(); 
  5.     } 
  6.  
  7.     @Override 
  8.     public Class<?> getObjectType() { 
  9.         return User.class; 
  10.     } 

在它的getObject方法中可以實現我們自己的邏輯創建對象,并且在getObjectType方法中我們可以定義對象的類型。

然后在bean.xml文件中配置bean時,只需像普通的bean一樣配置即可。

  1. <bean id="userFactoryBean" class="com.sue.async.service.UserFactoryBean"
  2. </bean> 

輕松搞定,so easy。

注意:getBean("userFactoryBean");獲取的是getObject方法中返回的對象。而getBean("&userFactoryBean");獲取的才是真正的UserFactoryBean對象。

我們通過上面五種方式,在bean.xml文件中把bean配置好之后,spring就會自動掃描和解析相應的標簽,并且幫我們創建和實例化bean,然后放入spring容器中。

雖說基于xml文件的方式配置bean,簡單而且非常靈活,比較適合一些小項目。但如果遇到比較復雜的項目,則需要配置大量的bean,而且bean之間的關系錯綜復雜,這樣久而久之會導致xml文件迅速膨脹,非常不利于bean的管理。

2. Component注解

為了解決bean太多時,xml文件過大,從而導致膨脹不好維護的問題。在spring2.5中開始支持:@Component、@Repository、@Service、@Controller等注解定義bean。

如果你有看過這些注解的源碼的話,就會驚奇得發現:其實后三種注解也是@Component。

@Component系列注解的出現,給我們帶來了極大的便利。我們不需要像以前那樣在bean.xml文件中配置bean了,現在只用在類上加Component、Repository、Service、Controller,這四種注解中的任意一種,就能輕松完成bean的定義。

  1. @Service 
  2. public class PersonService { 
  3.     public String get() { 
  4.         return "data"
  5.     } 

其實,這四種注解在功能上沒有特別的區別,不過在業界有個不成文的約定:

  • Controller 一般用在控制層
  • Service 一般用在業務層
  • Repository 一般用在數據層
  • Component 一般用在公共組件上

太棒了,簡直一下子解放了我們的雙手。

不過,需要特別注意的是,通過這種@Component掃描注解的方式定義bean的前提是:需要先配置掃描路徑。

目前常用的配置掃描路徑的方式如下:

在applicationContext.xml文件中使用標簽。例如:

  1. <context:component-scan base-package="com.sue.cache" /> 

在springboot的啟動類上加上@ComponentScan注解,例如:

  1. @ComponentScan(basePackages = "com.sue.cache"
  2. @SpringBootApplication 
  3. public class Application { 
  4.  
  5.     public static void main(String[] args) { 
  6.         new SpringApplicationBuilder(Application.class).web(WebApplicationType.SERVLET).run(args); 
  7.     } 

直接在SpringBootApplication注解上加,它支持ComponentScan功能:

  1. @SpringBootApplication(scanBasePackages = "com.sue.cache"
  2. public class Application { 
  3.      
  4.     public static void main(String[] args) { 
  5.         new SpringApplicationBuilder(Application.class).web(WebApplicationType.SERVLET).run(args); 
  6.     } 

當然,如果你需要掃描的類跟springboot的入口類,在同一級或者子級的包下面,無需指定scanBasePackages參數,spring默認會從入口類的同一級或者子級的包去找。

  1. @SpringBootApplication 
  2. public class Application { 
  3.      
  4.     public static void main(String[] args) { 
  5.         new SpringApplicationBuilder(Application.class).web(WebApplicationType.SERVLET).run(args); 
  6.     } 

此外,除了上述四種@Component注解之外,springboot還增加了@RestController注解,它是一種特殊的@Controller注解,所以也是@Component注解。

@RestController還支持@ResponseBody注解的功能,即將接口響應數據的格式自動轉換成json。

@Component系列注解已經讓我們愛不釋手了,它目前是我們日常工作中最多的定義bean的方式。

3. JavaConfig

@Component系列注解雖說使用起來非常方便,但是bean的創建過程完全交給spring容器來完成,我們沒辦法自己控制。

spring從3.0以后,開始支持JavaConfig的方式定義bean。它可以看做spring的配置文件,但并非真正的配置文件,我們需要通過編碼java代碼的方式創建bean。例如:

  1. public class MyConfiguration { 
  2.  
  3.     @Bean 
  4.     public Person person() { 
  5.         return new Person(); 
  6.     } 

在JavaConfig類上加@Configuration注解,相當于配置了標簽。而在方法上加@Bean注解,相當于配置了標簽。

此外,springboot還引入了一些列的@Conditional注解,用來控制bean的創建。

  1. @Configuration 
  2. public class MyConfiguration { 
  3.  
  4.     @ConditionalOnClass(Country.class) 
  5.     @Bean 
  6.     public Person person() { 
  7.         return new Person(); 
  8.     } 

@ConditionalOnClass注解的功能是當項目中存在Country類時,才實例化Person類。換句話說就是,如果項目中不存在Country類,就不實例化Person類。

這個功能非常有用,相當于一個開關控制著Person類,只有滿足一定條件才能實例化。

spring中使用比較多的Conditional還有:

  • ConditionalOnBean
  • ConditionalOnProperty
  • ConditionalOnMissingClass
  • ConditionalOnMissingBean
  • ConditionalOnWebApplication

如果你對這些功能比較感興趣,可以看看《spring中那些讓你愛不釋手的代碼技巧(續集)》,這是我之前寫的一篇文章,里面做了更詳細的介紹。

下面用一張圖整體認識一下@Conditional家族:

nice,有了這些功能,我們終于可以告別麻煩的xml時代了。

4. Import注解

通過前面介紹的@Configuration和@Bean相結合的方式,我們可以通過代碼定義bean。但這種方式有一定的局限性,它只能創建該類中定義的bean實例,不能創建其他類的bean實例,如果我們想創建其他類的bean實例該怎么辦呢?

這時可以使用@Import注解導入。

4.1 普通類

spring4.2之后@Import注解可以實例化普通類的bean實例。例如:

先定義了Role類:

  1. @Data 
  2. public class Role { 
  3.     private Long id; 
  4.     private String name

接下來使用@Import注解導入Role類:

  1. @Import(Role.class) 
  2. @Configuration 
  3. public class MyConfig { 

然后在調用的地方通過@Autowired注解注入所需的bean。

  1. @RequestMapping("/"
  2. @RestController 
  3. public class TestController { 
  4.  
  5.     @Autowired 
  6.     private Role role; 
  7.  
  8.     @GetMapping("/test"
  9.     public String test() { 
  10.         System.out.println(role); 
  11.         return "test"
  12.     } 

聰明的你可能會發現,我沒有在任何地方定義過Role的bean,但spring卻能自動創建該類的bean實例,這是為什么呢?

這也許正是@Import注解的強大之處。

此時,有些朋友可能會問:@Import注解能定義單個類的bean,但如果有多個類需要定義bean該怎么辦呢?

恭喜你,這是個好問題,因為@Import注解也支持。

  1. @Import({Role.class, User.class}) 
  2. @Configuration 
  3. public class MyConfig { 

甚至,如果你想偷懶,不想寫這種MyConfig類,springboot也歡迎。

  1. @Import({Role.class, User.class}) 
  2. @SpringBootApplication(exclude = {DataSourceAutoConfiguration.class, 
  3.         DataSourceTransactionManagerAutoConfiguration.class}) 
  4. public class Application { 
  5.  
  6.     public static void main(String[] args) { 
  7.         new SpringApplicationBuilder(Application.class).web(WebApplicationType.SERVLET).run(args); 
  8.     } 

可以將@Import加到springboot的啟動類上。

這樣也能生效?

springboot的啟動類一般都會加@SpringBootApplication注解,該注解上加了@SpringBootConfiguration注解。

而@SpringBootConfiguration注解,上面又加了@Configuration注解。

所以,springboot啟動類本身帶有@Configuration注解的功能。

意不意外?驚不驚喜?

4.2 Configuration類

上面介紹了@Import注解導入普通類的方法,它同時也支持導入Configuration類。

先定義一個Configuration類:

  1. @Configuration 
  2. public class MyConfig2 { 
  3.  
  4.     @Bean 
  5.     public User user() { 
  6.         return  new User(); 
  7.     } 
  8.  
  9.     @Bean 
  10.     public Role role() { 
  11.         return new Role(); 
  12.     } 

然后在另外一個Configuration類中引入前面的Configuration類:

  1. @Import({MyConfig2.class}) 
  2. @Configuration 
  3. public class MyConfig { 

這種方式,如果MyConfig2類已經在spring指定的掃描目錄或者子目錄下,則MyConfig類會顯得有點多余。因為MyConfig2類本身就是一個配置類,它里面就能定義bean。

但如果MyConfig2類不在指定的spring掃描目錄或者子目錄下,則通過MyConfig類的導入功能,也能把MyConfig2類識別成配置類。這就有點厲害了喔。

其實下面還有更高端的玩法。

swagger作為一個優秀的文檔生成框架,在spring項目中越來越受歡迎。接下來,我們以swagger2為例,介紹一下它是如何導入相關類的。

眾所周知,我們引入swagger相關jar包之后,只需要在springboot的啟動類上加上@EnableSwagger2注解,就能開啟swagger的功能。

其中@EnableSwagger2注解中導入了Swagger2DocumentationConfiguration類。

該類是一個Configuration類,它又導入了另外兩個類:

  • SpringfoxWebMvcConfiguration
  • SwaggerCommonConfiguration

SpringfoxWebMvcConfiguration類又會導入新的Configuration類,并且通過@ComponentScan注解掃描了一些其他的路徑。

SwaggerCommonConfiguration同樣也通過@ComponentScan注解掃描了一些額外的路徑。

如此一來,我們通過一個簡單的@EnableSwagger2注解,就能輕松的導入swagger所需的一系列bean,并且擁有swagger的功能。

還有什么好說的,狂起點贊,簡直完美。

4.3 ImportSelector

上面提到的Configuration類,它的功能非常強大。但怎么說呢,它不太適合加復雜的判斷條件,根據某些條件定義這些bean,根據另外的條件定義那些bean。

那么,這種需求該怎么實現呢?

這時就可以使用ImportSelector接口了。

首先定義一個類實現ImportSelector接口:

  1. public class DataImportSelector implements ImportSelector { 
  2.     @Override 
  3.     public String[] selectImports(AnnotationMetadata importingClassMetadata) { 
  4.         return new String[]{"com.sue.async.service.User""com.sue.async.service.Role"}; 
  5.     } 

重寫selectImports方法,在該方法中指定需要定義bean的類名,注意要包含完整路徑,而非相對路徑。

然后在MyConfig類上@Import導入這個類即可:

  1. @Import({DataImportSelector.class}) 
  2. @Configuration 
  3. public class MyConfig { 

朋友們是不是又發現了一個新大陸?

不過,這個注解還有更牛逼的用途。

@EnableAutoConfiguration注解中導入了AutoConfigurationImportSelector類,并且里面包含系統參數名稱:spring.boot.enableautoconfiguration。

AutoConfigurationImportSelector類實現了ImportSelector接口。

并且重寫了selectImports方法,該方法會根據某些注解去找所有需要創建bean的類名,然后返回這些類名。其中在查找這些類名之前,先調用isEnabled方法,判斷是否需要繼續查找。

該方法會根據ENABLED_OVERRIDE_PROPERTY的值來作為判斷條件。

而這個值就是spring.boot.enableautoconfiguration。

換句話說,這里能根據系統參數控制bean是否需要被實例化,優秀。

我個人認為實現ImportSelector接口的好處主要有以下兩點:

  • 把某個功能的相關類,可以放到一起,方面管理和維護。
  • 重寫selectImports方法時,能夠根據條件判斷某些類是否需要被實例化,或者某個條件實例化這些bean,其他的條件實例化那些bean等。我們能夠非常靈活的定制化bean的實例化。

4.4 ImportBeanDefinitionRegistrar

我們通過上面的這種方式,確實能夠非常靈活的自定義bean。

但它的自定義能力,還是有限的,它沒法自定義bean的名稱和作用域等屬性。

有需求,就有解決方案。

接下來,我們一起看看ImportBeanDefinitionRegistrar接口的神奇之處。

先定義CustomImportSelector類實現ImportBeanDefinitionRegistrar接口:

  1. public class CustomImportSelector implements ImportBeanDefinitionRegistrar { 
  2.  
  3.     @Override 
  4.     public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) { 
  5.         RootBeanDefinition roleBeanDefinition = new RootBeanDefinition(Role.class); 
  6.         registry.registerBeanDefinition("role", roleBeanDefinition); 
  7.  
  8.         RootBeanDefinition userBeanDefinition = new RootBeanDefinition(User.class); 
  9.         userBeanDefinition.setScope(ConfigurableBeanFactory.SCOPE_PROTOTYPE); 
  10.         registry.registerBeanDefinition("user", userBeanDefinition); 
  11.     } 

重寫registerBeanDefinitions方法,在該方法中我們可以獲取BeanDefinitionRegistry對象,通過它去注冊bean。不過在注冊bean之前,我們先要創建BeanDefinition對象,它里面可以自定義bean的名稱、作用域等很多參數。

然后在MyConfig類上導入上面的類:

  1. @Import({CustomImportSelector.class}) 
  2. @Configuration 
  3. public class MyConfig { 

我們所熟悉的fegin功能,就是使用ImportBeanDefinitionRegistrar接口實現的:

具體細節就不多說了,有興趣的朋友可以加我微信找我私聊。

5. PostProcessor

除此之外,spring還提供了專門注冊bean的接口:BeanDefinitionRegistryPostProcessor。

該接口的方法postProcessBeanDefinitionRegistry上有這樣一段描述:

修改應用程序上下文的內部bean定義注冊表標準初始化。所有常規bean定義都將被加載,但是還沒有bean被實例化。這允許進一步添加在下一個后處理階段開始之前定義bean。

如果用這個接口來定義bean,我們要做的事情就變得非常簡單了。只需定義一個類實現BeanDefinitionRegistryPostProcessor接口。

  1. @Component 
  2. public class MyRegistryPostProcessor implements BeanDefinitionRegistryPostProcessor { 
  3.     @Override 
  4.     public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException { 
  5.         RootBeanDefinition roleBeanDefinition = new RootBeanDefinition(Role.class); 
  6.         registry.registerBeanDefinition("role", roleBeanDefinition); 
  7.  
  8.         RootBeanDefinition userBeanDefinition = new RootBeanDefinition(User.class); 
  9.         userBeanDefinition.setScope(ConfigurableBeanFactory.SCOPE_PROTOTYPE); 
  10.         registry.registerBeanDefinition("user", userBeanDefinition); 
  11.     } 
  12.  
  13.     @Override 
  14.     public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException { 
  15.     } 

重寫postProcessBeanDefinitionRegistry方法,在該方法中能夠獲取BeanDefinitionRegistry對象,它負責bean的注冊工作。

不過細心的朋友可能會發現,里面還多了一個postProcessBeanFactory方法,沒有做任何實現。

這個方法其實是它的父接口:BeanFactoryPostProcessor里的方法。

在應用程序上下文的標準bean工廠之后修改其內部bean工廠初始化。所有bean定義都已加載,但沒有bean將被實例化。這允許重寫或添加屬性甚至可以初始化bean。

  1. @Component 
  2. public class MyPostProcessor implements BeanFactoryPostProcessor { 
  3.  
  4.     @Override 
  5.     public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException { 
  6.         DefaultListableBeanFactory registry = (DefaultListableBeanFactory)beanFactory; 
  7.         RootBeanDefinition roleBeanDefinition = new RootBeanDefinition(Role.class); 
  8.         registry.registerBeanDefinition("role", roleBeanDefinition); 
  9.  
  10.         RootBeanDefinition userBeanDefinition = new RootBeanDefinition(User.class); 
  11.         userBeanDefinition.setScope(ConfigurableBeanFactory.SCOPE_PROTOTYPE); 
  12.         registry.registerBeanDefinition("user", userBeanDefinition); 
  13.     } 

既然這兩個接口都能注冊bean,那么他們有什么區別?

  • BeanDefinitionRegistryPostProcessor 更側重于bean的注冊
  • BeanFactoryPostProcessor 更側重于對已經注冊的bean的屬性進行修改,雖然也可以注冊bean。

此時,有些朋友可能會問:既然拿到BeanDefinitionRegistry對象就能注冊bean,那通過BeanFactoryAware的方式是不是也能注冊bean呢?

從下面這張圖能夠看出DefaultListableBeanFactory就實現了BeanDefinitionRegistry接口。

這樣一來,我們如果能夠獲取DefaultListableBeanFactory對象的實例,然后調用它的注冊方法,不就可以注冊bean了?

說時遲那時快,定義一個類實現BeanFactoryAware接口:

  1. @Component 
  2. public class BeanFactoryRegistry implements BeanFactoryAware { 
  3.     @Override 
  4.     public void setBeanFactory(BeanFactory beanFactory) throws BeansException { 
  5.         DefaultListableBeanFactory registry = (DefaultListableBeanFactory) beanFactory; 
  6.         RootBeanDefinition rootBeanDefinition = new RootBeanDefinition(User.class); 
  7.         registry.registerBeanDefinition("user", rootBeanDefinition); 
  8.  
  9.         RootBeanDefinition userBeanDefinition = new RootBeanDefinition(User.class); 
  10.         userBeanDefinition.setScope(ConfigurableBeanFactory.SCOPE_PROTOTYPE); 
  11.         registry.registerBeanDefinition("user", userBeanDefinition); 
  12.     } 

重寫setBeanFactory方法,在該方法中能夠獲取BeanFactory對象,它能夠強制轉換成DefaultListableBeanFactory對象,然后通過該對象的實例注冊bean。

當你滿懷喜悅的運行項目時,發現竟然報錯了:

為什么會報錯?

spring中bean的創建過程順序,大致如下:

BeanFactoryAware接口是在bean創建成功,并且完成依賴注入之后,在真正初始化之前才被調用的。在這個時候去注冊bean意義不大,因為這個接口是給我們獲取bean的,并不建議去注冊bean,會引發很多問題。

此外,ApplicationContextRegistry和ApplicationListener接口也有類似的問題,我們可以用他們獲取bean,但不建議用它們注冊bean。

 

責任編輯:武曉燕 來源: 蘇三說技術
相關推薦

2022-02-14 12:04:43

前綴SpringJpa

2020-07-07 07:37:36

Integer源碼Java

2025-11-04 02:00:00

2019-09-18 15:20:16

MyBatisSQL數據庫

2020-11-03 06:57:10

MyBatis數據庫

2020-04-02 07:31:53

RPC超時服務端

2024-07-05 11:47:43

2020-11-27 09:16:21

BlockingQue

2022-09-04 12:43:03

算法裁員Meta

2020-01-06 09:14:59

Java程序員線程

2009-06-17 17:04:37

BeanFactorySpring

2019-06-14 08:48:46

Tomcat日志SpringBoot

2021-03-17 11:47:37

tomcatJavaServerJava

2015-05-19 14:30:48

加密視頻加密億賽通

2015-07-20 15:26:56

WiFi感知

2023-07-27 08:14:29

2021-11-02 11:31:47

Go代碼模式

2021-12-13 22:52:37

iphone iOSHTML

2021-05-28 10:09:22

GC詳解Java JVM

2022-06-24 14:52:34

AI模型
點贊
收藏

51CTO技術棧公眾號

成人资源视频网站免费| 日韩中文字幕不卡视频| 日韩av一二三四区| 成年人视频网站在线| 狠狠色丁香婷婷综合久久片| 欧美成人在线免费| 久操视频免费看| 57pao成人永久免费| 亚洲成人一区在线| 偷拍盗摄高潮叫床对白清晰| 神马午夜精品95| 蜜桃久久久久久| 海角国产乱辈乱精品视频| 亚洲无人区码一码二码三码的含义 | 最新国产精品亚洲| 在线观看亚洲免费视频| 97超碰在线免费| 国产精品国产三级国产aⅴ原创| 91a在线视频| 免费在线观看a级片| 亚洲国产网址| 精品久久久三级丝袜| 国产精品一区二区小说| 日韩电影免费看| 亚洲综合精品自拍| 一卡二卡3卡四卡高清精品视频| 亚洲欧美一二三区| 亚洲精品影院在线观看| 久久久av亚洲男天堂| 无码少妇一区二区| 自拍欧美一区| 日韩经典中文字幕| 亚洲一区二区三区四区av| 色999韩欧美国产综合俺来也| 中文字幕一区二区三区在线不卡| 国产日韩在线观看av| 日韩久久久久久久久| 亚洲欧美色图| 日韩一区二区福利| 四虎地址8848| 色琪琪久久se色| 一区二区三区无码高清视频| 91精品国产自产| 九九热hot精品视频在线播放| 欧美日韩综合视频| 免费一级特黄毛片| 亚洲丝袜精品| 伊人一区二区三区| 国产制服91一区二区三区制服| 人妻少妇精品无码专区| 国产电影一区在线| 91黄色精品| 亚洲爆乳无码一区二区三区| 国产精品一区二区黑丝| 91精品久久久久久久久| 国产精品无码久久av| 激情综合色综合久久| 91精品视频免费观看| 国产三级视频在线播放| 国产毛片精品视频| 不卡日韩av| 午夜视频在线播放| 久久久亚洲精品石原莉奈| 欧美午夜精品理论片a级大开眼界| 亚洲中文字幕在线一区| 久久99国产精品久久99果冻传媒| 久久久久久久久久久亚洲| 久久婷婷综合国产| 国产精品久久久久久模特| 欧洲s码亚洲m码精品一区| 国产伦精品一区二区三区视频我| 牛牛国产精品| 久久久之久亚州精品露出| 国产精品theporn动漫| 国产亚洲精品自拍| 国产精品久久久久久久久久99| 麻豆精品一区二区三区视频| 91精品一区国产高清在线gif | 国产无套粉嫩白浆在线2022年| 国产综合久久久久久鬼色| 亚洲最大成人免费视频| 色wwwwww| 欧美国产乱子伦 | 欧美另类69xxxxx| 最近2019中文字幕第三页视频| 久久久久久久无码| 欧美精品系列| 久久伊人精品天天| 成人精品免费在线观看| 秋霞午夜鲁丝一区二区老狼| 91九色蝌蚪国产| 亚洲色图另类小说| 综合久久久久久| 你真棒插曲来救救我在线观看| 色女人在线视频| 黄色一区二区三区| 污污网站在线观看视频| 色吊丝一区二区| 久久精品国产亚洲一区二区| 免费观看一区二区三区毛片| 精品在线观看免费| 久久免费99精品久久久久久| 菠萝菠萝蜜在线视频免费观看| 中文在线资源观看网站视频免费不卡 | 欧亚av在线| 欧美日本乱大交xxxxx| 午夜视频在线观看国产| 日韩精品午夜| 69国产精品成人在线播放| 国产精品一区二区黑人巨大| 久久综合色播五月| 久久久久久久久久伊人| 中文.日本.精品| 欧美精品一区二区三区蜜桃| 中日韩一级黄色片| 亚洲一区二区三区高清| 亚洲综合精品伊人久久| 91网在线播放| 色欧美日韩亚洲| 星空大象在线观看免费播放| 女主播福利一区| 国产日韩欧美另类| 蝌蚪视频在线播放| 精品毛片网大全| 国产一级免费片| 夜间精品视频| 亚洲一区中文字幕| 香蕉视频免费在线播放| 色老汉一区二区三区| 欧美双性人妖o0| 国内精品福利| 97久久精品午夜一区二区| 日韩理伦片在线| 欧美亚洲图片小说| 色哟哟精品观看| 久久精品人人| 蜜桃日韩视频| 蜜桃视频在线网站| 亚洲国产欧美一区| 日韩精品久久久久久久| 从欧美一区二区三区| 欧美美女黄色网| 精品国产一区二| 久久精品久久久久电影| 国产伦精品一区二区三区免.费| 国产成人在线视频网址| 国产高清免费在线| 日韩毛片免费看| 久久精品免费播放| aaa国产视频| 一区二区三区.www| 伊人久久久久久久久| 欧美精品网站| 国产一区免费视频| 小视频免费在线观看| 亚洲女人被黑人巨大进入al| 亚洲色成人www永久网站| 久久久精品免费观看| 免费国产成人av| 成人一二三区| 91麻豆国产精品| 欧美午夜大胆人体| 日韩av有码在线| 日韩黄色片网站| 国产精品萝li| 免费观看黄网站| 激情偷拍久久| 免费日韩av电影| 成人看片网页| 久久久国产在线视频| 亚洲精品成人电影| 欧美性猛交xxxx免费看漫画| 国精产品一区二区三区| 久久成人av少妇免费| 超碰超碰超碰超碰超碰| 久久a爱视频| 国产精品美女999| 成人在线免费看黄| 亚洲黄色成人网| 最新在线中文字幕| 一区二区三区91| 在线免费观看麻豆| 国产综合成人久久大片91| www.av毛片| 成人av资源电影网站| 亚洲影院高清在线| 26uuu亚洲电影| 久久这里只有精品视频首页| 天堂av一区二区三区| 欧美色爱综合网| 豆国产97在线 | 亚洲| 国产女人aaa级久久久级| 99热这里只有精品2| 日韩国产欧美一区二区三区| 91成人在线视频观看| 婷婷综合福利| 亚洲最大福利视频网| 欧美a级在线观看| 久久久久北条麻妃免费看| 午夜视频1000| 日韩无一区二区| 久久久999久久久| 亚洲动漫第一页| 最新av电影网站| 久久久一区二区| 色欲欲www成人网站| 日韩不卡免费视频| 九色自拍视频在线观看| 99久精品视频在线观看视频| 久久久99国产精品免费| 免费观看在线一区二区三区| 国产成人福利网站| 超碰91在线观看| 欧美成人免费小视频| av色图一区| 亚洲精品视频中文字幕| 亚洲老妇色熟女老太| 欧美日韩激情在线| 无码日韩精品一区二区| 亚洲国产日韩精品| 美国黄色小视频| 亚洲丝袜美腿综合| 国产wwwwxxxx| 国产欧美一区二区三区沐欲| 538国产视频| 成人精品国产一区二区4080| 日本77777| 精品一区二区在线免费观看| 国产日韩一区二区在线观看| 日韩一级在线| 777av视频| 伊人久久成人| 精品久久久久久无码中文野结衣| 先锋影音国产精品| 精品国产免费一区二区三区| aiss精品大尺度系列| 99爱精品视频| 4438全国亚洲精品观看视频| 99re热精品| 亚洲国产欧美国产第一区| 91美女片黄在线观| 国产精品日韩精品在线播放| 国产美女91呻吟求| 91国产一区| 91在线高清视频| 秋霞一区二区三区| 古典武侠综合av第一页| 亚洲一区二区三区中文字幕在线观看| 久久久久久97| 9lporm自拍视频区在线| 午夜精品久久久久久久男人的天堂| 国内在线免费高清视频| 亚洲欧美制服中文字幕| 国产永久免费高清在线观看视频| 91麻豆精品国产综合久久久久久 | 日本中文字幕在线播放| 丝袜亚洲另类欧美重口| 黄色网址视频在线观看| 欧美日韩国产成人| 国产高清视频色在线www| 欧美最猛性xxxxx亚洲精品| 精品免费av一区二区三区| 国产精品亚洲一区二区三区| 亚洲成人1区| 成人激情av| 亚洲免费观看高清完整版在线观| 91国产在线播放| 啪啪激情综合网| 日韩精品久久一区| 欧美不卡高清| 国产精品无码av在线播放| 国产精品毛片| 不卡的av中文字幕| 国产很黄免费观看久久| 国产又黄又粗又猛又爽的视频| 国产老肥熟一区二区三区| 制服丝袜在线第一页| 99久久国产综合精品麻豆| 无码一区二区三区在线| 亚洲人成电影网站色mp4| 精品无码免费视频| 日本道色综合久久| 99热这里只有精品在线观看| 亚洲第一区第二区| www.视频在线.com| 欧美激情a在线| 国产成人精品一区二三区在线观看| 国产91精品视频在线观看| 成人免费一区| 91视频国产精品| 亚洲区小说区图片区qvod按摩| 国产一区二区三区高清| 国产麻豆精品久久| 台湾无码一区二区| 欧美a级理论片| 北京富婆泄欲对白| 18欧美乱大交hd1984| 亚洲综合一二三| 制服.丝袜.亚洲.中文.综合| 天天操天天干天天干| 久久亚洲综合国产精品99麻豆精品福利| 天堂аⅴ在线地址8| 高清在线视频日韩欧美| www.久久久.com| 欧美亚州在线观看| 亚洲国产婷婷| www.成人黄色| 国产欧美日本一区视频| 国产成人精品a视频一区| 欧美高清hd18日本| 加勒比一区二区三区在线| 欧美激情xxxx性bbbb| 亚洲18在线| 日韩高清dvd| 国产精品久久久久久久久久妞妞| 欧美黑人经典片免费观看| 六月丁香综合在线视频| 欧美一区二区免费在线观看| 亚洲欧美电影一区二区| 中文字幕一区二区免费| 亚洲男人天堂网| 国内激情视频在线观看| 春色成人在线视频| 亚洲91中文字幕无线码三区| 黄色三级视频片| 久久久亚洲欧洲日产国码αv| 亚洲a∨无码无在线观看| 精品国产1区2区| 深夜福利视频网站| 欧美激情高清视频| 欧美高清hd| 日韩一级片一区二区| 九一九一国产精品| 欧美色图17p| 欧美人动与zoxxxx乱| 1024国产在线| 国产欧美日韩91| 婷婷激情图片久久| 天堂av8在线| 亚洲欧美怡红院| 国产精品久久久久久久免费| 日韩视频免费在线| 国产精品免费精品自在线观看| 久久国产精品久久| 亚洲日本久久| 特级西西人体4444xxxx| 欧美日韩国产精品| 男同在线观看| 国产精品久久久av久久久| 欧美色婷婷久久99精品红桃| 大香煮伊手机一区| 国产亲近乱来精品视频 | 欧美日韩国产色视频| 免费看国产片在线观看| 午夜精品久久17c| 成人三级av在线| 麻豆tv在线播放| 2019国产精品| 久久久国产免费| 日韩中文字幕欧美| 欧洲一区在线| 毛片在线播放视频| 久久久不卡影院| 国产又粗又黄又爽| 欧美大片免费观看| 欧美天堂社区| 久久精品免费网站| 亚洲欧美自拍偷拍色图| 亚洲国产精品国自产拍久久| 久久久久久久国产精品视频| 日本午夜精品久久久| 妞干网在线免费视频| 国产精品福利电影一区二区三区四区 | 欧美日韩理论片| 亚洲无人区一区| 黄色网址在线播放| 国产精品欧美日韩一区二区| 亚洲91精品| 黄色a一级视频| 69成人精品免费视频| 蜜臀av在线| 日产国产精品精品a∨| 国产一区久久久| 日本三级一区二区| 久久精品电影网站| 久久精品66| 日本不卡一区二区在线观看| 亚洲综合偷拍欧美一区色| 国际av在线| 国产精品久久久久久久小唯西川| 亚洲精品成人| 日本少妇色视频| 欧美一区二区啪啪| 色香欲www7777综合网| 300部国产真实乱| 国产欧美日韩久久| 粉嫩av一区二区夜夜嗨| 国产精品女人网站| 国产精品腿扒开做爽爽爽挤奶网站| 欧类av怡春院|