You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@dubbo.apache.org by GitBox <gi...@apache.org> on 2018/08/28 03:15:08 UTC

[GitHub] okotta1 closed pull request #2366: Baiji 274 g6

okotta1 closed pull request #2366: Baiji 274 g6
URL: https://github.com/apache/incubator-dubbo/pull/2366
 
 
   

This is a PR merged from a forked repository.
As GitHub hides the original diff on merge, it is displayed below for
the sake of provenance:

As this is a foreign pull request (from a fork), the diff is supplied
below (as it won't show otherwise due to GitHub magic):

diff --git a/.codecov.yml b/.codecov.yml
index 4b49c86e5e..b6081f29a1 100644
--- a/.codecov.yml
+++ b/.codecov.yml
@@ -1,11 +1,11 @@
-coverage:
-  status:
-    # pull-requests only
-    patch:
-      default:
-        threshold: 0.1%
-ignore:
-  - "dubbo-demo/.*"
-  - "dubbo-common/src/main/java/org/apache/dubbo/common/json/*.java" #  internal JSON impl is deprecate, ignore test coverage for them
-  - "dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/AnnotationBean.java" # Deprecated
+coverage:
+  status:
+    # pull-requests only
+    patch:
+      default:
+        threshold: 0.1%
+ignore:
+  - "dubbo-demo/.*"
+  - "dubbo-common/src/main/java/org/apache/dubbo/common/json/*.java" #  internal JSON impl is deprecate, ignore test coverage for them
+  - "dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/AnnotationBean.java" # Deprecated
   - "dubbo-rpc/dubbo-rpc-thrift/.*"
\ No newline at end of file
diff --git a/.github/ISSUE_TEMPLATE/dubbo-issue-report-template.md b/.github/ISSUE_TEMPLATE/dubbo-issue-report-template.md
index c2ff96a054..164053df70 100644
--- a/.github/ISSUE_TEMPLATE/dubbo-issue-report-template.md
+++ b/.github/ISSUE_TEMPLATE/dubbo-issue-report-template.md
@@ -1,36 +1,36 @@
----
-name: Dubbo issue report template
-about: If you would like to report a issue to Dubbo, please use this template.
-
----
-
-- [ ] I have searched the [issues](https://github.com/apache/incubator-dubbo/issues) of this repository and believe that this is not a duplicate.
-- [ ] I have checked the [FAQ](https://github.com/apache/incubator-dubbo/blob/master/FAQ.md) of this repository and believe that this is not a duplicate.
-
-### Environment
-
-* Dubbo version: xxx
-* Operating System version: xxx
-* Java version: xxx
-
-### Step to reproduce this issue
-
-1. xxx
-2. xxx
-3. xxx
-
-Pls. provide [GitHub address] to reproduce this issue.
-
-### Expected Result
-
-What do you expected from the above steps?
-
-### Actual Result
-
-What is actually happen?
-
-If there is an exception, please attach the exception trace:
-
-```
-Just put your stack trace here!
-```
+---
+name: Dubbo issue report template
+about: If you would like to report a issue to Dubbo, please use this template.
+
+---
+
+- [ ] I have searched the [issues](https://github.com/apache/incubator-dubbo/issues) of this repository and believe that this is not a duplicate.
+- [ ] I have checked the [FAQ](https://github.com/apache/incubator-dubbo/blob/master/FAQ.md) of this repository and believe that this is not a duplicate.
+
+### Environment
+
+* Dubbo version: xxx
+* Operating System version: xxx
+* Java version: xxx
+
+### Step to reproduce this issue
+
+1. xxx
+2. xxx
+3. xxx
+
+Pls. provide [GitHub address] to reproduce this issue.
+
+### Expected Result
+
+What do you expected from the above steps?
+
+### Actual Result
+
+What is actually happen?
+
+If there is an exception, please attach the exception trace:
+
+```
+Just put your stack trace here!
+```
diff --git a/.gitignore b/.gitignore
index a98a8a6945..2caaa1782e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,31 +1,31 @@
-# maven ignore
-target/
-*.jar
-!.mvn/wrapper/*
-*.war
-*.zip
-*.tar
-*.tar.gz
-
-# eclipse ignore
-.settings/
-.project
-.classpath
-
-# idea ignore
-.idea/
-*.ipr
-*.iml
-*.iws
-
-# temp ignore
-*.log
-*.cache
-*.diff
-*.patch
-*.tmp
-
-# system ignore
-.DS_Store
-Thumbs.db
-*.orig
+# maven ignore
+target/
+*.jar
+!.mvn/wrapper/*
+*.war
+*.zip
+*.tar
+*.tar.gz
+
+# eclipse ignore
+.settings/
+.project
+.classpath
+
+# idea ignore
+.idea/
+*.ipr
+*.iml
+*.iws
+
+# temp ignore
+*.log
+*.cache
+*.diff
+*.patch
+*.tmp
+
+# system ignore
+.DS_Store
+Thumbs.db
+*.orig
diff --git a/.travis.yml b/.travis.yml
index fe60e30958..f8da5ac64c 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,19 +1,19 @@
-language: java
-sudo: false # faster builds
-
-jdk:
-  - oraclejdk10
-  - oraclejdk9
-  - oraclejdk8
-
-cache:
-  directories:
-    - '$HOME/.m2/repository'
-
-install: true
-
-script:
-  - travis_wait 30 ./mvnw clean package -DskipTests=false -Dcheckstyle.skip=true -Drat.skip=true -Dmaven.javadoc.skip=true
-
-after_success:
-  - bash <(curl -s https://codecov.io/bash)
+language: java
+sudo: false # faster builds
+
+jdk:
+  - oraclejdk10
+  - oraclejdk9
+  - oraclejdk8
+
+cache:
+  directories:
+    - '$HOME/.m2/repository'
+
+install: true
+
+script:
+  - travis_wait 30 ./mvnw clean package -DskipTests=false -Dcheckstyle.skip=true -Drat.skip=true -Dmaven.javadoc.skip=true
+
+after_success:
+  - bash <(curl -s https://codecov.io/bash)
diff --git a/CHANGES.md b/CHANGES.md
index 7c04d5b87e..f3bd05a9ce 100644
--- a/CHANGES.md
+++ b/CHANGES.md
@@ -1,15 +1,15 @@
-# Release Notes
-
-## 2.6.2
-
-1. Hessian-lite serialization: revert locale serialization for compatibility, #1413
-2. Asset transfer to ASF, includeing pom, license, DISCLAIMER and so on, #1491
-3. Introduce of new dispatcher policy: EagerThreadpool, #1568
-4. Separate monitor data with group and version, #1407
-5. Spring Boot Enhancenment, #1611
-6. Gaceful shutdown enhancement
-   - Remove exporter destroy logic in AnnotationBean.
-   - Waiting for registry notification on consumer side by checking channel state.
-7. Simplify consumer/provider side check in RpcContext, #1444.
-
+# Release Notes
+
+## 2.6.2
+
+1. Hessian-lite serialization: revert locale serialization for compatibility, #1413
+2. Asset transfer to ASF, includeing pom, license, DISCLAIMER and so on, #1491
+3. Introduce of new dispatcher policy: EagerThreadpool, #1568
+4. Separate monitor data with group and version, #1407
+5. Spring Boot Enhancenment, #1611
+6. Gaceful shutdown enhancement
+   - Remove exporter destroy logic in AnnotationBean.
+   - Waiting for registry notification on consumer side by checking channel state.
+7. Simplify consumer/provider side check in RpcContext, #1444.
+
 Issues and Pull Requests, check [milestone-2.6.2](https://github.com/apache/incubator-dubbo/milestone/15).
\ No newline at end of file
diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md
index b7c31c2e8d..3980c49c7d 100644
--- a/CODE_OF_CONDUCT.md
+++ b/CODE_OF_CONDUCT.md
@@ -1,46 +1,46 @@
-# Contributor Covenant Code of Conduct
-
-## Our Pledge
-
-In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation.
-
-## Our Standards
-
-Examples of behavior that contributes to creating a positive environment include:
-
-* Using welcoming and inclusive language
-* Being respectful of differing viewpoints and experiences
-* Gracefully accepting constructive criticism
-* Focusing on what is best for the community
-* Showing empathy towards other community members
-
-Examples of unacceptable behavior by participants include:
-
-* The use of sexualized language or imagery and unwelcome sexual attention or advances
-* Trolling, insulting/derogatory comments, and personal or political attacks
-* Public or private harassment
-* Publishing others' private information, such as a physical or electronic address, without explicit permission
-* Other conduct which could reasonably be considered inappropriate in a professional setting
-
-## Our Responsibilities
-
-Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior.
-
-Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful.
-
-## Scope
-
-This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers.
-
-## Enforcement
-
-Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at dev@dubbo.apache.org. The project team will review and investigate all complaints, and will respond in a way that it deems appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.
-
-Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership.
-
-## Attribution
-
-This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, available at [http://contributor-covenant.org/version/1/4][version]
-
-[homepage]: http://contributor-covenant.org
-[version]: http://contributor-covenant.org/version/1/4/
+# Contributor Covenant Code of Conduct
+
+## Our Pledge
+
+In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation.
+
+## Our Standards
+
+Examples of behavior that contributes to creating a positive environment include:
+
+* Using welcoming and inclusive language
+* Being respectful of differing viewpoints and experiences
+* Gracefully accepting constructive criticism
+* Focusing on what is best for the community
+* Showing empathy towards other community members
+
+Examples of unacceptable behavior by participants include:
+
+* The use of sexualized language or imagery and unwelcome sexual attention or advances
+* Trolling, insulting/derogatory comments, and personal or political attacks
+* Public or private harassment
+* Publishing others' private information, such as a physical or electronic address, without explicit permission
+* Other conduct which could reasonably be considered inappropriate in a professional setting
+
+## Our Responsibilities
+
+Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior.
+
+Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful.
+
+## Scope
+
+This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers.
+
+## Enforcement
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at dev@dubbo.apache.org. The project team will review and investigate all complaints, and will respond in a way that it deems appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.
+
+Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership.
+
+## Attribution
+
+This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, available at [http://contributor-covenant.org/version/1/4][version]
+
+[homepage]: http://contributor-covenant.org
+[version]: http://contributor-covenant.org/version/1/4/
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index bd7dc2022c..c38d231aaa 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -1,66 +1,66 @@
-
-## Contributing to dubbo
-Dubbo is released under the non-restrictive Apache 2.0 license, and follows a very standard Github development process, using Github tracker for issues and merging pull requests into master. If you want to contribute even something trivial please do not hesitate, but follow the guidelines below.
-
-### Sign the Contributor License Agreement
-Before we accept a non-trivial patch or pull request we will need you to sign the Contributor License Agreement. Signing the contributor’s agreement does not grant anyone commit rights to the main repository, but it does mean that we can accept your contributions, and you will get an author credit if we do. Active contributors might be asked to join the core team, and given the ability to merge pull requests.
-
-### Contact
-
-#### Mailing list
-
-The mailing list is the recommended way for discussing almost anything that related to Dubbo. Please refer to this [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide) for detailed documentation on how to subscribe.
-
-- [dev@dubbo.incubator.apache.org](mailto:dev-subscribe@dubbo.incubator.apache.org): the develop mailing list, you can ask question here if you have encountered any problem when using or developing Dubbo.
-- [commits@dubbo.incubator.apache.org](mailto:commits-subscribe@dubbo.incubator.apache.org): all the commits will be sent to this mailing list. You can subscribe to it if you are interested in Dubbo's development.
-- [notification@dubbo.incubator.apache.org](mailto:notification-subscribe@dubbo.incubator.apache.org): all the Github [issue](https://github.com/apache/incubator-dubbo/issues) updates and [pull request](https://github.com/apache/incubator-dubbo/pulls) updates will be sent to this mailing list.
-
-### Reporting issue
-
-Please follow the [template](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md) for reporting any issues.
-
-### Code Conventions
-Our code style is almost in line with the standard java conventions (Popular IDE's default setting satisfy this), with the following additional restricts:  
-* If there are more than 120 characters in current line, start a new line.
-
-* Make sure all new .java files to have a simple Javadoc class comment with at least a @date tag identifying birth, and preferably at least a paragraph on what the class is for.
-
-* Add the ASF license header comment to all new .java files (copy from existing files in the project)
-
-* Make sure no @author tag added to the file you contribute since @author tag is not used at Apache, other ways such as cvs will record all your contributions fairly.
-
-* Add some Javadocs and, if you change the namespace, some XSD doc elements.
-
-* A few unit tests should be added for a new feature or an important bugfix.
-
-* If no-one else is using your branch, please rebase it against the current master (or other target branch in the main project).
-
-* When writing a commit message please follow these conventions, if you are fixing an existing issue please add Fixes #XXX at the end of the commit message (where XXX is the issue number).
-
-### Contribution flow
-
-This is a rough outline of what a contributor's workflow looks like:
-
-* Fork the current repository
-* Create a topic branch from where to base the contribution. This is usually master.
-* Make commits of logical units.
-* Make sure commit messages are in the proper format (see below).
-* Push changes in a topic branch to your forked repository.
-* Follow the checklist in the [pull request template](https://github.com/apache/incubator-dubbo/blob/master/PULL_REQUEST_TEMPLATE.md)
-* Before you sending out the pull request, please sync your forked repository with remote repository, this will make your pull request simple and clear. See guide below:
-```
-git remote add upstream git@github.com:apache/incubator-dubbo.git
-git fetch upstream
-git rebase upstream/master
-git checkout -b your_awesome_patch
-... add some work
-git push origin your_awesome_patch
-```
-* Submit a pull request to apache/incubator-dubbo and wait for the reply.
-
-Thanks for contributing!
-
-### Code style
-
-We provide a template file [dubbo_codestyle_for_idea.xml](https://github.com/apache/incubator-dubbo/tree/master/codestyle/dubbo_codestyle_for_idea.xml) for IntelliJ idea, you can import it to you IDE. 
+
+## Contributing to dubbo
+Dubbo is released under the non-restrictive Apache 2.0 license, and follows a very standard Github development process, using Github tracker for issues and merging pull requests into master. If you want to contribute even something trivial please do not hesitate, but follow the guidelines below.
+
+### Sign the Contributor License Agreement
+Before we accept a non-trivial patch or pull request we will need you to sign the Contributor License Agreement. Signing the contributor’s agreement does not grant anyone commit rights to the main repository, but it does mean that we can accept your contributions, and you will get an author credit if we do. Active contributors might be asked to join the core team, and given the ability to merge pull requests.
+
+### Contact
+
+#### Mailing list
+
+The mailing list is the recommended way for discussing almost anything that related to Dubbo. Please refer to this [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide) for detailed documentation on how to subscribe.
+
+- [dev@dubbo.incubator.apache.org](mailto:dev-subscribe@dubbo.incubator.apache.org): the develop mailing list, you can ask question here if you have encountered any problem when using or developing Dubbo.
+- [commits@dubbo.incubator.apache.org](mailto:commits-subscribe@dubbo.incubator.apache.org): all the commits will be sent to this mailing list. You can subscribe to it if you are interested in Dubbo's development.
+- [notification@dubbo.incubator.apache.org](mailto:notification-subscribe@dubbo.incubator.apache.org): all the Github [issue](https://github.com/apache/incubator-dubbo/issues) updates and [pull request](https://github.com/apache/incubator-dubbo/pulls) updates will be sent to this mailing list.
+
+### Reporting issue
+
+Please follow the [template](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md) for reporting any issues.
+
+### Code Conventions
+Our code style is almost in line with the standard java conventions (Popular IDE's default setting satisfy this), with the following additional restricts:  
+* If there are more than 120 characters in current line, start a new line.
+
+* Make sure all new .java files to have a simple Javadoc class comment with at least a @date tag identifying birth, and preferably at least a paragraph on what the class is for.
+
+* Add the ASF license header comment to all new .java files (copy from existing files in the project)
+
+* Make sure no @author tag added to the file you contribute since @author tag is not used at Apache, other ways such as cvs will record all your contributions fairly.
+
+* Add some Javadocs and, if you change the namespace, some XSD doc elements.
+
+* A few unit tests should be added for a new feature or an important bugfix.
+
+* If no-one else is using your branch, please rebase it against the current master (or other target branch in the main project).
+
+* When writing a commit message please follow these conventions, if you are fixing an existing issue please add Fixes #XXX at the end of the commit message (where XXX is the issue number).
+
+### Contribution flow
+
+This is a rough outline of what a contributor's workflow looks like:
+
+* Fork the current repository
+* Create a topic branch from where to base the contribution. This is usually master.
+* Make commits of logical units.
+* Make sure commit messages are in the proper format (see below).
+* Push changes in a topic branch to your forked repository.
+* Follow the checklist in the [pull request template](https://github.com/apache/incubator-dubbo/blob/master/PULL_REQUEST_TEMPLATE.md)
+* Before you sending out the pull request, please sync your forked repository with remote repository, this will make your pull request simple and clear. See guide below:
+```
+git remote add upstream git@github.com:apache/incubator-dubbo.git
+git fetch upstream
+git rebase upstream/master
+git checkout -b your_awesome_patch
+... add some work
+git push origin your_awesome_patch
+```
+* Submit a pull request to apache/incubator-dubbo and wait for the reply.
+
+Thanks for contributing!
+
+### Code style
+
+We provide a template file [dubbo_codestyle_for_idea.xml](https://github.com/apache/incubator-dubbo/tree/master/codestyle/dubbo_codestyle_for_idea.xml) for IntelliJ idea, you can import it to you IDE. 
 If you use Eclipse you can config manually by referencing the same file.
\ No newline at end of file
diff --git a/FAQ.md b/FAQ.md
index dca1e02836..c3f15879bd 100644
--- a/FAQ.md
+++ b/FAQ.md
@@ -1,25 +1,25 @@
-### Where is dubbo-admin?
-
-dubbo-admin has been moved from core repository to https://github.com/apache/incubator-dubbo-ops since 2.6.1
-
-### Which version should I choose?
-
-Currently, dubbo keeps 3 versions evolve in parallel:
-
-* 2.7.x (master): requires Java 1.8, major feature branch
-
-* 2.6.x: requires Java 1.6, minor feature & bugfix branch, GA, production ready.
-
-* 2.5.x: requires Java 1.6, maintainance branch, only accept security vulnerbility and critical bugfix, expected to be EOL soon
-
-check [this](https://github.com/apache/incubator-dubbo/issues/1208) for detailed version management plan.
-
-For contributors, please make sure all changes on the right branch, that is, most of the pull request should go to 2.7.x, and be backported to 2.6.x and 2.5.x if necessary. If the fix is specific to a branch, please make sure your pull request goes to the right branch.
-
-For committers, make sure select the right label and target branch for every PR, and don't forget to back port the fix to lower version is necessary.
-
-####  How to register ip correctly in docker?  
-
-[Example question](https://github.com/alibaba/dubbo/issues/742)  
-
+### Where is dubbo-admin?
+
+dubbo-admin has been moved from core repository to https://github.com/apache/incubator-dubbo-ops since 2.6.1
+
+### Which version should I choose?
+
+Currently, dubbo keeps 3 versions evolve in parallel:
+
+* 2.7.x (master): requires Java 1.8, major feature branch
+
+* 2.6.x: requires Java 1.6, minor feature & bugfix branch, GA, production ready.
+
+* 2.5.x: requires Java 1.6, maintainance branch, only accept security vulnerbility and critical bugfix, expected to be EOL soon
+
+check [this](https://github.com/apache/incubator-dubbo/issues/1208) for detailed version management plan.
+
+For contributors, please make sure all changes on the right branch, that is, most of the pull request should go to 2.7.x, and be backported to 2.6.x and 2.5.x if necessary. If the fix is specific to a branch, please make sure your pull request goes to the right branch.
+
+For committers, make sure select the right label and target branch for every PR, and don't forget to back port the fix to lower version is necessary.
+
+####  How to register ip correctly in docker?  
+
+[Example question](https://github.com/alibaba/dubbo/issues/742)  
+
 Dubbo support to specify ip/port via system environment varialbles, examples can be found [here](https://github.com/dubbo/dubbo-samples/tree/master/dubbo-samples-docker).
\ No newline at end of file
diff --git a/LICENSE b/LICENSE
index b85622380c..02a4c3ed14 100644
--- a/LICENSE
+++ b/LICENSE
@@ -1,231 +1,231 @@
-
-                                 Apache License
-                           Version 2.0, January 2004
-                        http://www.apache.org/licenses/
-
-   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
-
-   1. Definitions.
-
-      "License" shall mean the terms and conditions for use, reproduction,
-      and distribution as defined by Sections 1 through 9 of this document.
-
-      "Licensor" shall mean the copyright owner or entity authorized by
-      the copyright owner that is granting the License.
-
-      "Legal Entity" shall mean the union of the acting entity and all
-      other entities that control, are controlled by, or are under common
-      control with that entity. For the purposes of this definition,
-      "control" means (i) the power, direct or indirect, to cause the
-      direction or management of such entity, whether by contract or
-      otherwise, or (ii) ownership of fifty percent (50%) or more of the
-      outstanding shares, or (iii) beneficial ownership of such entity.
-
-      "You" (or "Your") shall mean an individual or Legal Entity
-      exercising permissions granted by this License.
-
-      "Source" form shall mean the preferred form for making modifications,
-      including but not limited to software source code, documentation
-      source, and configuration files.
-
-      "Object" form shall mean any form resulting from mechanical
-      transformation or translation of a Source form, including but
-      not limited to compiled object code, generated documentation,
-      and conversions to other media types.
-
-      "Work" shall mean the work of authorship, whether in Source or
-      Object form, made available under the License, as indicated by a
-      copyright notice that is included in or attached to the work
-      (an example is provided in the Appendix below).
-
-      "Derivative Works" shall mean any work, whether in Source or Object
-      form, that is based on (or derived from) the Work and for which the
-      editorial revisions, annotations, elaborations, or other modifications
-      represent, as a whole, an original work of authorship. For the purposes
-      of this License, Derivative Works shall not include works that remain
-      separable from, or merely link (or bind by name) to the interfaces of,
-      the Work and Derivative Works thereof.
-
-      "Contribution" shall mean any work of authorship, including
-      the original version of the Work and any modifications or additions
-      to that Work or Derivative Works thereof, that is intentionally
-      submitted to Licensor for inclusion in the Work by the copyright owner
-      or by an individual or Legal Entity authorized to submit on behalf of
-      the copyright owner. For the purposes of this definition, "submitted"
-      means any form of electronic, verbal, or written communication sent
-      to the Licensor or its representatives, including but not limited to
-      communication on electronic mailing lists, source code control systems,
-      and issue tracking systems that are managed by, or on behalf of, the
-      Licensor for the purpose of discussing and improving the Work, but
-      excluding communication that is conspicuously marked or otherwise
-      designated in writing by the copyright owner as "Not a Contribution."
-
-      "Contributor" shall mean Licensor and any individual or Legal Entity
-      on behalf of whom a Contribution has been received by Licensor and
-      subsequently incorporated within the Work.
-
-   2. Grant of Copyright License. Subject to the terms and conditions of
-      this License, each Contributor hereby grants to You a perpetual,
-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
-      copyright license to reproduce, prepare Derivative Works of,
-      publicly display, publicly perform, sublicense, and distribute the
-      Work and such Derivative Works in Source or Object form.
-
-   3. Grant of Patent License. Subject to the terms and conditions of
-      this License, each Contributor hereby grants to You a perpetual,
-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
-      (except as stated in this section) patent license to make, have made,
-      use, offer to sell, sell, import, and otherwise transfer the Work,
-      where such license applies only to those patent claims licensable
-      by such Contributor that are necessarily infringed by their
-      Contribution(s) alone or by combination of their Contribution(s)
-      with the Work to which such Contribution(s) was submitted. If You
-      institute patent litigation against any entity (including a
-      cross-claim or counterclaim in a lawsuit) alleging that the Work
-      or a Contribution incorporated within the Work constitutes direct
-      or contributory patent infringement, then any patent licenses
-      granted to You under this License for that Work shall terminate
-      as of the date such litigation is filed.
-
-   4. Redistribution. You may reproduce and distribute copies of the
-      Work or Derivative Works thereof in any medium, with or without
-      modifications, and in Source or Object form, provided that You
-      meet the following conditions:
-
-      (a) You must give any other recipients of the Work or
-          Derivative Works a copy of this License; and
-
-      (b) You must cause any modified files to carry prominent notices
-          stating that You changed the files; and
-
-      (c) You must retain, in the Source form of any Derivative Works
-          that You distribute, all copyright, patent, trademark, and
-          attribution notices from the Source form of the Work,
-          excluding those notices that do not pertain to any part of
-          the Derivative Works; and
-
-      (d) If the Work includes a "NOTICE" text file as part of its
-          distribution, then any Derivative Works that You distribute must
-          include a readable copy of the attribution notices contained
-          within such NOTICE file, excluding those notices that do not
-          pertain to any part of the Derivative Works, in at least one
-          of the following places: within a NOTICE text file distributed
-          as part of the Derivative Works; within the Source form or
-          documentation, if provided along with the Derivative Works; or,
-          within a display generated by the Derivative Works, if and
-          wherever such third-party notices normally appear. The contents
-          of the NOTICE file are for informational purposes only and
-          do not modify the License. You may add Your own attribution
-          notices within Derivative Works that You distribute, alongside
-          or as an addendum to the NOTICE text from the Work, provided
-          that such additional attribution notices cannot be construed
-          as modifying the License.
-
-      You may add Your own copyright statement to Your modifications and
-      may provide additional or different license terms and conditions
-      for use, reproduction, or distribution of Your modifications, or
-      for any such Derivative Works as a whole, provided Your use,
-      reproduction, and distribution of the Work otherwise complies with
-      the conditions stated in this License.
-
-   5. Submission of Contributions. Unless You explicitly state otherwise,
-      any Contribution intentionally submitted for inclusion in the Work
-      by You to the Licensor shall be under the terms and conditions of
-      this License, without any additional terms or conditions.
-      Notwithstanding the above, nothing herein shall supersede or modify
-      the terms of any separate license agreement you may have executed
-      with Licensor regarding such Contributions.
-
-   6. Trademarks. This License does not grant permission to use the trade
-      names, trademarks, service marks, or product names of the Licensor,
-      except as required for reasonable and customary use in describing the
-      origin of the Work and reproducing the content of the NOTICE file.
-
-   7. Disclaimer of Warranty. Unless required by applicable law or
-      agreed to in writing, Licensor provides the Work (and each
-      Contributor provides its Contributions) on an "AS IS" BASIS,
-      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
-      implied, including, without limitation, any warranties or conditions
-      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
-      PARTICULAR PURPOSE. You are solely responsible for determining the
-      appropriateness of using or redistributing the Work and assume any
-      risks associated with Your exercise of permissions under this License.
-
-   8. Limitation of Liability. In no event and under no legal theory,
-      whether in tort (including negligence), contract, or otherwise,
-      unless required by applicable law (such as deliberate and grossly
-      negligent acts) or agreed to in writing, shall any Contributor be
-      liable to You for damages, including any direct, indirect, special,
-      incidental, or consequential damages of any character arising as a
-      result of this License or out of the use or inability to use the
-      Work (including but not limited to damages for loss of goodwill,
-      work stoppage, computer failure or malfunction, or any and all
-      other commercial damages or losses), even if such Contributor
-      has been advised of the possibility of such damages.
-
-   9. Accepting Warranty or Additional Liability. While redistributing
-      the Work or Derivative Works thereof, You may choose to offer,
-      and charge a fee for, acceptance of support, warranty, indemnity,
-      or other liability obligations and/or rights consistent with this
-      License. However, in accepting such obligations, You may act only
-      on Your own behalf and on Your sole responsibility, not on behalf
-      of any other Contributor, and only if You agree to indemnify,
-      defend, and hold each Contributor harmless for any liability
-      incurred by, or claims asserted against, such Contributor by reason
-      of your accepting any such warranty or additional liability.
-
-   END OF TERMS AND CONDITIONS
-
-   APPENDIX: How to apply the Apache License to your work.
-
-      To apply the Apache License to your work, attach the following
-      boilerplate notice, with the fields enclosed by brackets "[]"
-      replaced with your own identifying information. (Don't include
-      the brackets!)  The text should be enclosed in the appropriate
-      comment syntax for the file format. We also recommend that a
-      file or class name and description of purpose be included on the
-      same "printed page" as the copyright notice for easier
-      identification within third-party archives.
-
-   Copyright [yyyy] [name of copyright owner]
-
-   Licensed under the Apache License, Version 2.0 (the "License");
-   you may not use this file except in compliance with the License.
-   You may obtain a copy of the License at
-
-       http://www.apache.org/licenses/LICENSE-2.0
-
-   Unless required by applicable law or agreed to in writing, software
-   distributed under the License is distributed on an "AS IS" BASIS,
-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-   See the License for the specific language governing permissions and
-   limitations under the License.
-
-
-Apache Dubbo Submodules:
-
-Apache Dubbo includes a number of submodules with separate copyright notices
-and license terms. Your use of these submodules is subject to the terms and
-conditions of the following licenses.
-
-For the org.apache.dubbo.common.concurrent package:
-
-This product bundles and repackages the following code in Google Guava 16.0.1, which is available under a
-"Apache License 2.0" license. For details, see https://github.com/google/guava/blob/v16.0.1/COPYING.
-
- * com.google.common.util.concurrent.ExecutionList
- * com.google.common.util.concurrent.ListenableFuture
- * com.google.common.util.concurrent.ListenableFutureTask
-
-For the package org.apache.dubbo.common.threadlocal and org.apache.dubbo.common.timer:
-
-This product contains a modified portion of 'Netty', an event-driven asynchronous network application framework also
- under a "Apache License 2.0" license, see https://github.com/netty/netty/blob/4.1/LICENSE.txt:
-
- * io.netty.util.concurrent.FastThreadLocal
- * io.netty.util.internal.InternalThreadLocalMap
- * io.netty.util.Timer
- * io.netty.util.TimerTask
- * io.netty.util.Timeout
- * io.netty.util.HashedWheelTimer
-
+
+                                 Apache License
+                           Version 2.0, January 2004
+                        http://www.apache.org/licenses/
+
+   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+   1. Definitions.
+
+      "License" shall mean the terms and conditions for use, reproduction,
+      and distribution as defined by Sections 1 through 9 of this document.
+
+      "Licensor" shall mean the copyright owner or entity authorized by
+      the copyright owner that is granting the License.
+
+      "Legal Entity" shall mean the union of the acting entity and all
+      other entities that control, are controlled by, or are under common
+      control with that entity. For the purposes of this definition,
+      "control" means (i) the power, direct or indirect, to cause the
+      direction or management of such entity, whether by contract or
+      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+      outstanding shares, or (iii) beneficial ownership of such entity.
+
+      "You" (or "Your") shall mean an individual or Legal Entity
+      exercising permissions granted by this License.
+
+      "Source" form shall mean the preferred form for making modifications,
+      including but not limited to software source code, documentation
+      source, and configuration files.
+
+      "Object" form shall mean any form resulting from mechanical
+      transformation or translation of a Source form, including but
+      not limited to compiled object code, generated documentation,
+      and conversions to other media types.
+
+      "Work" shall mean the work of authorship, whether in Source or
+      Object form, made available under the License, as indicated by a
+      copyright notice that is included in or attached to the work
+      (an example is provided in the Appendix below).
+
+      "Derivative Works" shall mean any work, whether in Source or Object
+      form, that is based on (or derived from) the Work and for which the
+      editorial revisions, annotations, elaborations, or other modifications
+      represent, as a whole, an original work of authorship. For the purposes
+      of this License, Derivative Works shall not include works that remain
+      separable from, or merely link (or bind by name) to the interfaces of,
+      the Work and Derivative Works thereof.
+
+      "Contribution" shall mean any work of authorship, including
+      the original version of the Work and any modifications or additions
+      to that Work or Derivative Works thereof, that is intentionally
+      submitted to Licensor for inclusion in the Work by the copyright owner
+      or by an individual or Legal Entity authorized to submit on behalf of
+      the copyright owner. For the purposes of this definition, "submitted"
+      means any form of electronic, verbal, or written communication sent
+      to the Licensor or its representatives, including but not limited to
+      communication on electronic mailing lists, source code control systems,
+      and issue tracking systems that are managed by, or on behalf of, the
+      Licensor for the purpose of discussing and improving the Work, but
+      excluding communication that is conspicuously marked or otherwise
+      designated in writing by the copyright owner as "Not a Contribution."
+
+      "Contributor" shall mean Licensor and any individual or Legal Entity
+      on behalf of whom a Contribution has been received by Licensor and
+      subsequently incorporated within the Work.
+
+   2. Grant of Copyright License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      copyright license to reproduce, prepare Derivative Works of,
+      publicly display, publicly perform, sublicense, and distribute the
+      Work and such Derivative Works in Source or Object form.
+
+   3. Grant of Patent License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      (except as stated in this section) patent license to make, have made,
+      use, offer to sell, sell, import, and otherwise transfer the Work,
+      where such license applies only to those patent claims licensable
+      by such Contributor that are necessarily infringed by their
+      Contribution(s) alone or by combination of their Contribution(s)
+      with the Work to which such Contribution(s) was submitted. If You
+      institute patent litigation against any entity (including a
+      cross-claim or counterclaim in a lawsuit) alleging that the Work
+      or a Contribution incorporated within the Work constitutes direct
+      or contributory patent infringement, then any patent licenses
+      granted to You under this License for that Work shall terminate
+      as of the date such litigation is filed.
+
+   4. Redistribution. You may reproduce and distribute copies of the
+      Work or Derivative Works thereof in any medium, with or without
+      modifications, and in Source or Object form, provided that You
+      meet the following conditions:
+
+      (a) You must give any other recipients of the Work or
+          Derivative Works a copy of this License; and
+
+      (b) You must cause any modified files to carry prominent notices
+          stating that You changed the files; and
+
+      (c) You must retain, in the Source form of any Derivative Works
+          that You distribute, all copyright, patent, trademark, and
+          attribution notices from the Source form of the Work,
+          excluding those notices that do not pertain to any part of
+          the Derivative Works; and
+
+      (d) If the Work includes a "NOTICE" text file as part of its
+          distribution, then any Derivative Works that You distribute must
+          include a readable copy of the attribution notices contained
+          within such NOTICE file, excluding those notices that do not
+          pertain to any part of the Derivative Works, in at least one
+          of the following places: within a NOTICE text file distributed
+          as part of the Derivative Works; within the Source form or
+          documentation, if provided along with the Derivative Works; or,
+          within a display generated by the Derivative Works, if and
+          wherever such third-party notices normally appear. The contents
+          of the NOTICE file are for informational purposes only and
+          do not modify the License. You may add Your own attribution
+          notices within Derivative Works that You distribute, alongside
+          or as an addendum to the NOTICE text from the Work, provided
+          that such additional attribution notices cannot be construed
+          as modifying the License.
+
+      You may add Your own copyright statement to Your modifications and
+      may provide additional or different license terms and conditions
+      for use, reproduction, or distribution of Your modifications, or
+      for any such Derivative Works as a whole, provided Your use,
+      reproduction, and distribution of the Work otherwise complies with
+      the conditions stated in this License.
+
+   5. Submission of Contributions. Unless You explicitly state otherwise,
+      any Contribution intentionally submitted for inclusion in the Work
+      by You to the Licensor shall be under the terms and conditions of
+      this License, without any additional terms or conditions.
+      Notwithstanding the above, nothing herein shall supersede or modify
+      the terms of any separate license agreement you may have executed
+      with Licensor regarding such Contributions.
+
+   6. Trademarks. This License does not grant permission to use the trade
+      names, trademarks, service marks, or product names of the Licensor,
+      except as required for reasonable and customary use in describing the
+      origin of the Work and reproducing the content of the NOTICE file.
+
+   7. Disclaimer of Warranty. Unless required by applicable law or
+      agreed to in writing, Licensor provides the Work (and each
+      Contributor provides its Contributions) on an "AS IS" BASIS,
+      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+      implied, including, without limitation, any warranties or conditions
+      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+      PARTICULAR PURPOSE. You are solely responsible for determining the
+      appropriateness of using or redistributing the Work and assume any
+      risks associated with Your exercise of permissions under this License.
+
+   8. Limitation of Liability. In no event and under no legal theory,
+      whether in tort (including negligence), contract, or otherwise,
+      unless required by applicable law (such as deliberate and grossly
+      negligent acts) or agreed to in writing, shall any Contributor be
+      liable to You for damages, including any direct, indirect, special,
+      incidental, or consequential damages of any character arising as a
+      result of this License or out of the use or inability to use the
+      Work (including but not limited to damages for loss of goodwill,
+      work stoppage, computer failure or malfunction, or any and all
+      other commercial damages or losses), even if such Contributor
+      has been advised of the possibility of such damages.
+
+   9. Accepting Warranty or Additional Liability. While redistributing
+      the Work or Derivative Works thereof, You may choose to offer,
+      and charge a fee for, acceptance of support, warranty, indemnity,
+      or other liability obligations and/or rights consistent with this
+      License. However, in accepting such obligations, You may act only
+      on Your own behalf and on Your sole responsibility, not on behalf
+      of any other Contributor, and only if You agree to indemnify,
+      defend, and hold each Contributor harmless for any liability
+      incurred by, or claims asserted against, such Contributor by reason
+      of your accepting any such warranty or additional liability.
+
+   END OF TERMS AND CONDITIONS
+
+   APPENDIX: How to apply the Apache License to your work.
+
+      To apply the Apache License to your work, attach the following
+      boilerplate notice, with the fields enclosed by brackets "[]"
+      replaced with your own identifying information. (Don't include
+      the brackets!)  The text should be enclosed in the appropriate
+      comment syntax for the file format. We also recommend that a
+      file or class name and description of purpose be included on the
+      same "printed page" as the copyright notice for easier
+      identification within third-party archives.
+
+   Copyright [yyyy] [name of copyright owner]
+
+   Licensed under the Apache License, Version 2.0 (the "License");
+   you may not use this file except in compliance with the License.
+   You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
+
+Apache Dubbo Submodules:
+
+Apache Dubbo includes a number of submodules with separate copyright notices
+and license terms. Your use of these submodules is subject to the terms and
+conditions of the following licenses.
+
+For the org.apache.dubbo.common.concurrent package:
+
+This product bundles and repackages the following code in Google Guava 16.0.1, which is available under a
+"Apache License 2.0" license. For details, see https://github.com/google/guava/blob/v16.0.1/COPYING.
+
+ * com.google.common.util.concurrent.ExecutionList
+ * com.google.common.util.concurrent.ListenableFuture
+ * com.google.common.util.concurrent.ListenableFutureTask
+
+For the package org.apache.dubbo.common.threadlocal and org.apache.dubbo.common.timer:
+
+This product contains a modified portion of 'Netty', an event-driven asynchronous network application framework also
+ under a "Apache License 2.0" license, see https://github.com/netty/netty/blob/4.1/LICENSE.txt:
+
+ * io.netty.util.concurrent.FastThreadLocal
+ * io.netty.util.internal.InternalThreadLocalMap
+ * io.netty.util.Timer
+ * io.netty.util.TimerTask
+ * io.netty.util.Timeout
+ * io.netty.util.HashedWheelTimer
+
diff --git a/PULL_REQUEST_TEMPLATE.md b/PULL_REQUEST_TEMPLATE.md
index 403cb91358..2b0189cea5 100644
--- a/PULL_REQUEST_TEMPLATE.md
+++ b/PULL_REQUEST_TEMPLATE.md
@@ -1,20 +1,20 @@
-## What is the purpose of the change
-
-XXXXX
-
-## Brief changelog
-
-XXXXX
-
-## Verifying this change
-
-XXXXX
-
-Follow this checklist to help us incorporate your contribution quickly and easily:
-
-- [x] Make sure there is a [GITHUB_issue](https://github.com/apache/incubator-dubbo/issues) filed for the change (usually before you start working on it). Trivial changes like typos do not require a GITHUB issue. Your pull request should address just this issue, without pulling in other changes - one PR resolves one issue.
-- [ ] Format the pull request title like `[Dubbo-XXX] Fix UnknownException when host config not exist #XXX`. Each commit in the pull request should have a meaningful subject line and body.
-- [ ] Write a pull request description that is detailed enough to understand what the pull request does, how, and why.
-- [ ] Write necessary unit-test to verify your logic correction, more mock a little better when cross module dependency exist. If the new feature or significant change is committed, please remember to add integration-test in [test module](https://github.com/apache/incubator-dubbo/tree/master/dubbo-test).
-- [ ] Run `mvn clean install -DskipTests` & `mvn clean test-compile failsafe:integration-test` to make sure unit-test and integration-test pass.
-- [ ] If this contribution is large, please follow the [Software Donation Guide](https://github.com/apache/incubator-dubbo/wiki/Software-donation-guide).
+## What is the purpose of the change
+
+XXXXX
+
+## Brief changelog
+
+XXXXX
+
+## Verifying this change
+
+XXXXX
+
+Follow this checklist to help us incorporate your contribution quickly and easily:
+
+- [x] Make sure there is a [GITHUB_issue](https://github.com/apache/incubator-dubbo/issues) filed for the change (usually before you start working on it). Trivial changes like typos do not require a GITHUB issue. Your pull request should address just this issue, without pulling in other changes - one PR resolves one issue.
+- [ ] Format the pull request title like `[Dubbo-XXX] Fix UnknownException when host config not exist #XXX`. Each commit in the pull request should have a meaningful subject line and body.
+- [ ] Write a pull request description that is detailed enough to understand what the pull request does, how, and why.
+- [ ] Write necessary unit-test to verify your logic correction, more mock a little better when cross module dependency exist. If the new feature or significant change is committed, please remember to add integration-test in [test module](https://github.com/apache/incubator-dubbo/tree/master/dubbo-test).
+- [ ] Run `mvn clean install -DskipTests` & `mvn clean test-compile failsafe:integration-test` to make sure unit-test and integration-test pass.
+- [ ] If this contribution is large, please follow the [Software Donation Guide](https://github.com/apache/incubator-dubbo/wiki/Software-donation-guide).
diff --git a/README.md b/README.md
index ffb16af551..3a8a4e5a8f 100644
--- a/README.md
+++ b/README.md
@@ -1,166 +1,166 @@
-# Apache Dubbo (incubating) Project
-
-[![Build Status](https://travis-ci.org/apache/incubator-dubbo.svg?branch=master)](https://travis-ci.org/apache/incubator-dubbo)
-[![codecov](https://codecov.io/gh/apache/incubator-dubbo/branch/master/graph/badge.svg)](https://codecov.io/gh/apache/incubator-dubbo)
-[![Gitter](https://badges.gitter.im/alibaba/dubbo.svg)](https://gitter.im/alibaba/dubbo?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge)
-![license](https://img.shields.io/github/license/alibaba/dubbo.svg)
-![maven](https://img.shields.io/maven-central/v/com.alibaba/dubbo.svg)
-
-Apache Dubbo (incubating) is a high-performance, java based open source RPC framework. Please visit [official site ](http://dubbo.incubator.apache.org) for quick start and documentations, as well as [Wiki](https://github.com/apache/incubator-dubbo/wiki) for news, FAQ, and release notes.
-
-We are now collecting dubbo user info in order to help us to improve dubbo better, pls. kindly help us by providing yours on [issue#1012: Wanted: who's using dubbo](https://github.com/apache/incubator-dubbo/issues/1012), thanks :)
-
-## Architecture
-
-![Architecture](http://dubbo.apache.org/img/architecture.png)
-
-## Features
-
-* Transparent interface based RPC
-* Intelligent load balancing
-* Automatic service registration and discovery
-* High extensibility
-* Runtime traffic routing
-* Visualized service governance
-
-## Getting started
-
-### Maven dependency
-
-```xml
-<dependency>
-    <groupId>com.alibaba</groupId>
-    <artifactId>dubbo</artifactId>
-    <version>2.6.2</version>
-</dependency>
-```
-
-### Defining service interfaces
-
-```java
-package org.apache.dubbo.demo;
-
-public interface GreetingService {
-    String sayHello(String name);
-}
-```
-
-### Implement interface in service provider
-
-```java
-package org.apache.dubbo.demo.provider;
- 
-import org.apache.dubbo.demo.GreetingService;
- 
-public class GreetingServiceImpl implements GreetingService {
-    public String sayHello(String name) {
-        return "Hello " + name;
-    }
-}
-```
-
-### Starting service provider
-
-```java
-package org.apache.dubbo.demo.provider;
-
-import com.alibaba.dubbo.config.ApplicationConfig;
-import com.alibaba.dubbo.config.RegistryConfig;
-import com.alibaba.dubbo.config.ServiceConfig;
-import org.apache.dubbo.demo.GreetingService;
-
-import java.io.IOException;
- 
-public class Provider {
-
-    public static void main(String[] args) throws IOException {
-        ServiceConfig<GreetingService> serviceConfig = new ServiceConfig<GreetingService>();
-        serviceConfig.setApplication(new ApplicationConfig("first-dubbo-provider"));
-        serviceConfig.setRegistry(new RegistryConfig("multicast://224.5.6.7:1234"));
-        serviceConfig.setInterface(GreetingService.class);
-        serviceConfig.setRef(new GreetingServiceImpl());
-        serviceConfig.export();
-        System.in.read();
-    }
-}
-```
-
-### Call remote service in consumer
-
-```java
-package org.apache.dubbo.demo.consumer;
-
-import com.alibaba.dubbo.config.ApplicationConfig;
-import com.alibaba.dubbo.config.ReferenceConfig;
-import com.alibaba.dubbo.config.RegistryConfig;
-import org.apache.dubbo.demo.GreetingService;
-
-public class Consumer {
-    public static void main(String[] args) {
-        ReferenceConfig<GreetingService> referenceConfig = new ReferenceConfig<GreetingService>();
-        referenceConfig.setApplication(new ApplicationConfig("first-dubbo-consumer"));
-        referenceConfig.setRegistry(new RegistryConfig("multicast://224.5.6.7:1234"));
-        referenceConfig.setInterface(GreetingService.class);
-        GreetingService greetingService = referenceConfig.get();
-        System.out.println(greetingService.sayHello("world"));
-    }
-}
-```
-
-### Next steps
-
-* [Dubbo user manual](http://dubbo.apache.org/#/docs/user/preface/background.md) - How to use Dubbo and all its features.
-* [Dubbo developer guide](http://dubbo.apache.org/#/docs/dev/build.md) - How to invovle in Dubbo development.
-* [Dubbo admin manual](http://dubbo.apache.org/#/docs/admin/install/provider-demo.md) - How to admin and manage Dubbo services.
-
-## Contact
-
-* Mailing list: [dev@dubbo.incubator.apache.org](mailto:[dev-subscribe@dubbo.incubator.apache.org]) (subscription [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide))
-* Bugs: [Issues](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md)
-* Gitter: [Gitter channel](https://gitter.im/alibaba/dubbo) 
-* Twitter: [@ApacheDubbo](https://twitter.com/ApacheDubbo)
-
-## Contributing
-
-See [CONTRIBUTING](https://github.com/apache/incubator-dubbo/blob/master/CONTRIBUTING.md) for details on submitting patches and the contribution workflow.
-
-### How can I contribute?
-
-* Take a look at issues with tag called [`Good first issue`](https://github.com/apache/incubator-dubbo/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22) or [`Help wanted`](https://github.com/apache/incubator-dubbo/issues?q=is%3Aopen+is%3Aissue+label%3A%22help+wanted%22).
-* Join the discussion on mailing list, subscription [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide).
-* Answer questions on [issues](https://github.com/apache/incubator-dubbo/issues).
-* Fix bugs reported on [issues](https://github.com/apache/incubator-dubbo/issues), and send us pull request.
-* Review the existing [pull request](https://github.com/apache/incubator-dubbo/pulls).
-* Improve the [website](https://github.com/apache/incubator-dubbo-website), typically we need
-  * blog post
-  * translation on documentation
-  * use cases about how Dubbo is being used in enterprise system.
-* Improve the [dubbo-ops/dubbo-monitor](https://github.com/apache/incubator-dubbo-ops).
-* Contribute to the projects listed in [ecosystem](https://github.com/dubbo).
-* Any form of contribution that is not mentioned above.
-* If you would like to contribute, please send an email to dev@dubbo.incubator.apache.org to let us know!
-
-## Reporting bugs
-
-Please follow the [template](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md) for reporting any issues.
-
-## Reporting a security vulnerability
-
-Please report security vulnerability to security@dubbo.incubator.apache.org (private mailing list).
-
-## [Ecosystem](https://github.com/dubbo)
-
-* [Dubbo Website](https://github.com/apache/incubator-dubbo-website) - Apache Dubbo (incubating) official website
-* [Dubbo Samples](https://github.com/dubbo/dubbo-samples) - samples for Apache Dubbo (incubating)
-* [Dubbo Spring Boot](https://github.com/apache/incubator-dubbo-spring-boot-project) - Spring Boot Project for Dubbo
-* [Dubbo OPS](https://github.com/apache/incubator-dubbo-ops) - The reference implementation for dubbo ops (dubbo-admin, dubbo-monitor, dubbo-registry-simple, etc.)
-
-#### Language
-
-* [Node.js](https://github.com/dubbo/dubbo2.js)
-* [Python](https://github.com/dubbo/dubbo-client-py)
-* [Php](https://github.com/dubbo/dubbo-php-framework)
-
-## License
-
-Apache Dubbo is under the Apache 2.0 license. See the [LICENSE](https://github.com/apache/incubator-dubbo/blob/master/LICENSE) file for details.
+# Apache Dubbo (incubating) Project
+
+[![Build Status](https://travis-ci.org/apache/incubator-dubbo.svg?branch=master)](https://travis-ci.org/apache/incubator-dubbo)
+[![codecov](https://codecov.io/gh/apache/incubator-dubbo/branch/master/graph/badge.svg)](https://codecov.io/gh/apache/incubator-dubbo)
+[![Gitter](https://badges.gitter.im/alibaba/dubbo.svg)](https://gitter.im/alibaba/dubbo?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge)
+![license](https://img.shields.io/github/license/alibaba/dubbo.svg)
+![maven](https://img.shields.io/maven-central/v/com.alibaba/dubbo.svg)
+
+Apache Dubbo (incubating) is a high-performance, java based open source RPC framework. Please visit [official site ](http://dubbo.incubator.apache.org) for quick start and documentations, as well as [Wiki](https://github.com/apache/incubator-dubbo/wiki) for news, FAQ, and release notes.
+
+We are now collecting dubbo user info in order to help us to improve dubbo better, pls. kindly help us by providing yours on [issue#1012: Wanted: who's using dubbo](https://github.com/apache/incubator-dubbo/issues/1012), thanks :)
+
+## Architecture
+
+![Architecture](http://dubbo.apache.org/img/architecture.png)
+
+## Features
+
+* Transparent interface based RPC
+* Intelligent load balancing
+* Automatic service registration and discovery
+* High extensibility
+* Runtime traffic routing
+* Visualized service governance
+
+## Getting started
+
+### Maven dependency
+
+```xml
+<dependency>
+    <groupId>com.alibaba</groupId>
+    <artifactId>dubbo</artifactId>
+    <version>2.6.2</version>
+</dependency>
+```
+
+### Defining service interfaces
+
+```java
+package org.apache.dubbo.demo;
+
+public interface GreetingService {
+    String sayHello(String name);
+}
+```
+
+### Implement interface in service provider
+
+```java
+package org.apache.dubbo.demo.provider;
+ 
+import org.apache.dubbo.demo.GreetingService;
+ 
+public class GreetingServiceImpl implements GreetingService {
+    public String sayHello(String name) {
+        return "Hello " + name;
+    }
+}
+```
+
+### Starting service provider
+
+```java
+package org.apache.dubbo.demo.provider;
+
+import com.alibaba.dubbo.config.ApplicationConfig;
+import com.alibaba.dubbo.config.RegistryConfig;
+import com.alibaba.dubbo.config.ServiceConfig;
+import org.apache.dubbo.demo.GreetingService;
+
+import java.io.IOException;
+ 
+public class Provider {
+
+    public static void main(String[] args) throws IOException {
+        ServiceConfig<GreetingService> serviceConfig = new ServiceConfig<GreetingService>();
+        serviceConfig.setApplication(new ApplicationConfig("first-dubbo-provider"));
+        serviceConfig.setRegistry(new RegistryConfig("multicast://224.5.6.7:1234"));
+        serviceConfig.setInterface(GreetingService.class);
+        serviceConfig.setRef(new GreetingServiceImpl());
+        serviceConfig.export();
+        System.in.read();
+    }
+}
+```
+
+### Call remote service in consumer
+
+```java
+package org.apache.dubbo.demo.consumer;
+
+import com.alibaba.dubbo.config.ApplicationConfig;
+import com.alibaba.dubbo.config.ReferenceConfig;
+import com.alibaba.dubbo.config.RegistryConfig;
+import org.apache.dubbo.demo.GreetingService;
+
+public class Consumer {
+    public static void main(String[] args) {
+        ReferenceConfig<GreetingService> referenceConfig = new ReferenceConfig<GreetingService>();
+        referenceConfig.setApplication(new ApplicationConfig("first-dubbo-consumer"));
+        referenceConfig.setRegistry(new RegistryConfig("multicast://224.5.6.7:1234"));
+        referenceConfig.setInterface(GreetingService.class);
+        GreetingService greetingService = referenceConfig.get();
+        System.out.println(greetingService.sayHello("world"));
+    }
+}
+```
+
+### Next steps
+
+* [Dubbo user manual](http://dubbo.apache.org/#/docs/user/preface/background.md) - How to use Dubbo and all its features.
+* [Dubbo developer guide](http://dubbo.apache.org/#/docs/dev/build.md) - How to invovle in Dubbo development.
+* [Dubbo admin manual](http://dubbo.apache.org/#/docs/admin/install/provider-demo.md) - How to admin and manage Dubbo services.
+
+## Contact
+
+* Mailing list: [dev@dubbo.incubator.apache.org](mailto:[dev-subscribe@dubbo.incubator.apache.org]) (subscription [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide))
+* Bugs: [Issues](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md)
+* Gitter: [Gitter channel](https://gitter.im/alibaba/dubbo) 
+* Twitter: [@ApacheDubbo](https://twitter.com/ApacheDubbo)
+
+## Contributing
+
+See [CONTRIBUTING](https://github.com/apache/incubator-dubbo/blob/master/CONTRIBUTING.md) for details on submitting patches and the contribution workflow.
+
+### How can I contribute?
+
+* Take a look at issues with tag called [`Good first issue`](https://github.com/apache/incubator-dubbo/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22) or [`Help wanted`](https://github.com/apache/incubator-dubbo/issues?q=is%3Aopen+is%3Aissue+label%3A%22help+wanted%22).
+* Join the discussion on mailing list, subscription [guide](https://github.com/apache/incubator-dubbo/wiki/Mailing-list-subscription-guide).
+* Answer questions on [issues](https://github.com/apache/incubator-dubbo/issues).
+* Fix bugs reported on [issues](https://github.com/apache/incubator-dubbo/issues), and send us pull request.
+* Review the existing [pull request](https://github.com/apache/incubator-dubbo/pulls).
+* Improve the [website](https://github.com/apache/incubator-dubbo-website), typically we need
+  * blog post
+  * translation on documentation
+  * use cases about how Dubbo is being used in enterprise system.
+* Improve the [dubbo-ops/dubbo-monitor](https://github.com/apache/incubator-dubbo-ops).
+* Contribute to the projects listed in [ecosystem](https://github.com/dubbo).
+* Any form of contribution that is not mentioned above.
+* If you would like to contribute, please send an email to dev@dubbo.incubator.apache.org to let us know!
+
+## Reporting bugs
+
+Please follow the [template](https://github.com/apache/incubator-dubbo/issues/new?template=dubbo-issue-report-template.md) for reporting any issues.
+
+## Reporting a security vulnerability
+
+Please report security vulnerability to security@dubbo.incubator.apache.org (private mailing list).
+
+## [Ecosystem](https://github.com/dubbo)
+
+* [Dubbo Website](https://github.com/apache/incubator-dubbo-website) - Apache Dubbo (incubating) official website
+* [Dubbo Samples](https://github.com/dubbo/dubbo-samples) - samples for Apache Dubbo (incubating)
+* [Dubbo Spring Boot](https://github.com/apache/incubator-dubbo-spring-boot-project) - Spring Boot Project for Dubbo
+* [Dubbo OPS](https://github.com/apache/incubator-dubbo-ops) - The reference implementation for dubbo ops (dubbo-admin, dubbo-monitor, dubbo-registry-simple, etc.)
+
+#### Language
+
+* [Node.js](https://github.com/dubbo/dubbo2.js)
+* [Python](https://github.com/dubbo/dubbo-client-py)
+* [Php](https://github.com/dubbo/dubbo-php-framework)
+
+## License
+
+Apache Dubbo is under the Apache 2.0 license. See the [LICENSE](https://github.com/apache/incubator-dubbo/blob/master/LICENSE) file for details.
diff --git a/codestyle/checkstyle-suppressions.xml b/codestyle/checkstyle-suppressions.xml
index 1817cf762c..2deb53abd5 100644
--- a/codestyle/checkstyle-suppressions.xml
+++ b/codestyle/checkstyle-suppressions.xml
@@ -1,8 +1,8 @@
-<?xml version="1.0"?>
-<!DOCTYPE suppressions PUBLIC
-        "-//Puppy Crawl//DTD Suppressions 1.1//EN"
-        "http://www.puppycrawl.com/dtds/suppressions_1_1.dtd">
-<suppressions>
-    <suppress files="[\\/]src[\\/]main[\\/]java[\\/]com[\\/]alibaba[\\/]com[\\/]caucho[\\/]hessian" checks=".*"/>
-    <suppress files="Yylex\.java" checks="AvoidEscapedUnicodeCharacters"/>
+<?xml version="1.0"?>
+<!DOCTYPE suppressions PUBLIC
+        "-//Puppy Crawl//DTD Suppressions 1.1//EN"
+        "http://www.puppycrawl.com/dtds/suppressions_1_1.dtd">
+<suppressions>
+    <suppress files="[\\/]src[\\/]main[\\/]java[\\/]com[\\/]alibaba[\\/]com[\\/]caucho[\\/]hessian" checks=".*"/>
+    <suppress files="Yylex\.java" checks="AvoidEscapedUnicodeCharacters"/>
 </suppressions>
\ No newline at end of file
diff --git a/codestyle/checkstyle.xml b/codestyle/checkstyle.xml
index ffdafd15f4..428e9f15f4 100644
--- a/codestyle/checkstyle.xml
+++ b/codestyle/checkstyle.xml
@@ -1,24 +1,24 @@
-<?xml version="1.0"?>
-<!DOCTYPE module PUBLIC
-        "-//Puppy Crawl//DTD Check Configuration 1.3//EN"
-        "http://checkstyle.sourceforge.net/dtds/configuration_1_3.dtd">
-
-<module name="Checker">
-    <property name="charset" value="UTF-8"/>
-    <property name="fileExtensions" value="java"/>
-
-    <!-- TreeWalker Checks -->
-    <module name="TreeWalker">
-        <module name="SuppressWarningsHolder" />
-
-        <module name="AvoidStarImport"/>
-        <module name="AvoidEscapedUnicodeCharacters">
-            <property name="allowEscapesForControlCharacters" value="true"/>
-            <property name="allowByTailComment" value="true"/>
-            <property name="allowNonPrintableEscapes" value="true"/>
-        </module>
-        <module name="NoLineWrap"/>
-        <module name="OuterTypeFilename"/>
-        <module name="UnusedImports"/>
-    </module>
+<?xml version="1.0"?>
+<!DOCTYPE module PUBLIC
+        "-//Puppy Crawl//DTD Check Configuration 1.3//EN"
+        "http://checkstyle.sourceforge.net/dtds/configuration_1_3.dtd">
+
+<module name="Checker">
+    <property name="charset" value="UTF-8"/>
+    <property name="fileExtensions" value="java"/>
+
+    <!-- TreeWalker Checks -->
+    <module name="TreeWalker">
+        <module name="SuppressWarningsHolder" />
+
+        <module name="AvoidStarImport"/>
+        <module name="AvoidEscapedUnicodeCharacters">
+            <property name="allowEscapesForControlCharacters" value="true"/>
+            <property name="allowByTailComment" value="true"/>
+            <property name="allowNonPrintableEscapes" value="true"/>
+        </module>
+        <module name="NoLineWrap"/>
+        <module name="OuterTypeFilename"/>
+        <module name="UnusedImports"/>
+    </module>
 </module>
\ No newline at end of file
diff --git a/codestyle/dubbo_codestyle_for_idea.xml b/codestyle/dubbo_codestyle_for_idea.xml
index 4c632e4b28..8f1c153081 100644
--- a/codestyle/dubbo_codestyle_for_idea.xml
+++ b/codestyle/dubbo_codestyle_for_idea.xml
@@ -1,18 +1,18 @@
-<code_scheme name="dubbo_codestyle">
-    <option name="CLASS_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99"/>
-    <option name="NAMES_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99"/>
-    <option name="IMPORT_LAYOUT_TABLE">
-        <value>
-            <package name="org.apache.dubbo" withSubpackages="true" static="false"/>
-            <emptyLine/>
-            <package name="com.taobao" withSubpackages="true" static="false"/>
-            <emptyLine/>
-            <package name="" withSubpackages="true" static="false"/>
-            <emptyLine/>
-            <package name="javax" withSubpackages="true" static="false"/>
-            <package name="java" withSubpackages="true" static="false"/>
-            <emptyLine/>
-            <package name="" withSubpackages="true" static="true"/>
-        </value>
-    </option>
+<code_scheme name="dubbo_codestyle">
+    <option name="CLASS_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99"/>
+    <option name="NAMES_COUNT_TO_USE_IMPORT_ON_DEMAND" value="99"/>
+    <option name="IMPORT_LAYOUT_TABLE">
+        <value>
+            <package name="org.apache.dubbo" withSubpackages="true" static="false"/>
+            <emptyLine/>
+            <package name="com.taobao" withSubpackages="true" static="false"/>
+            <emptyLine/>
+            <package name="" withSubpackages="true" static="false"/>
+            <emptyLine/>
+            <package name="javax" withSubpackages="true" static="false"/>
+            <package name="java" withSubpackages="true" static="false"/>
+            <emptyLine/>
+            <package name="" withSubpackages="true" static="true"/>
+        </value>
+    </option>
 </code_scheme>
\ No newline at end of file
diff --git a/dubbo-all/pom.xml b/dubbo-all/pom.xml
index 7a1cdd3682..ba2eff3e32 100644
--- a/dubbo-all/pom.xml
+++ b/dubbo-all/pom.xml
@@ -1,559 +1,559 @@
-<!--
-  Licensed to the Apache Software Foundation (ASF) under one or more
-  contributor license agreements.  See the NOTICE file distributed with
-  this work for additional information regarding copyright ownership.
-  The ASF licenses this file to You under the Apache License, Version 2.0
-  (the "License"); you may not use this file except in compliance with
-  the License.  You may obtain a copy of the License at
-
-      http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing, software
-  distributed under the License is distributed on an "AS IS" BASIS,
-  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  See the License for the specific language governing permissions and
-  limitations under the License.
-  -->
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
-    <modelVersion>4.0.0</modelVersion>
-    <parent>
-        <groupId>org.apache.dubbo</groupId>
-        <artifactId>dubbo-parent</artifactId>
-        <version>2.7.0-SNAPSHOT</version>
-        <relativePath>../pom.xml</relativePath>
-    </parent>
-    <artifactId>dubbo</artifactId>
-    <version>2.7.0-SNAPSHOT</version>
-    <packaging>jar</packaging>
-    <name>dubbo-all</name>
-    <description>The all in one project of dubbo</description>
-    <properties>
-        <skip_maven_deploy>false</skip_maven_deploy>
-    </properties>
-    <dependencies>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-cluster</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-common</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-config-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-config-spring</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-filter-cache</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-filter-validation</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-netty</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-netty4</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-mina</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-grizzly</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-p2p</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-remoting-http</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-dubbo</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-injvm</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-rmi</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-hessian</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-http</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-webservice</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-thrift</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-memcached</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-redis</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-rest</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-default</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-multicast</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-zookeeper</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-redis</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-monitor-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-monitor-default</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-container-spring</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-container-log4j</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-container-logback</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-qos</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-api</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-fastjson</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-fst</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-hessian2</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-jdk</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-serialization-kryo</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-bootstrap</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-compatible</artifactId>
-            <version>${project.version}</version>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>com.alibaba</groupId>
-            <artifactId>hessian-lite</artifactId>
-            <scope>compile</scope>
-            <optional>true</optional>
-        </dependency>
-
-        <!-- Transitive dependencies -->
-        <dependency>
-            <groupId>org.springframework</groupId>
-            <artifactId>spring-context</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>org.javassist</groupId>
-            <artifactId>javassist</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>io.netty</groupId>
-            <artifactId>netty-all</artifactId>
-        </dependency>
-
-        <!-- Temporarily add this part to exclude transitive dependency -->
-        <dependency>
-            <groupId>junit</groupId>
-            <artifactId>junit</artifactId>
-            <version>${junit_version}</version>
-            <scope>test</scope>
-            <optional>true</optional>
-        </dependency>
-        <dependency>
-            <groupId>cglib</groupId>
-            <artifactId>cglib-nodep</artifactId>
-            <version>${cglib_version}</version>
-            <scope>test</scope>
-            <optional>true</optional>
-        </dependency>
-    </dependencies>
-    <build>
-        <plugins>
-            <plugin>
-                <groupId>org.apache.maven.plugins</groupId>
-                <artifactId>maven-shade-plugin</artifactId>
-                <version>1.4</version>
-                <executions>
-                    <execution>
-                        <phase>package</phase>
-                        <goals>
-                            <goal>shade</goal>
-                        </goals>
-                        <configuration>
-                            <createSourcesJar>true</createSourcesJar>
-                            <promoteTransitiveDependencies>false</promoteTransitiveDependencies>
-                            <artifactSet>
-                                <includes>
-                                    <include>com.alibaba:hessian-lite</include>
-                                    <include>org.apache.dubbo:dubbo-compatible</include>
-                                    <include>org.apache.dubbo:dubbo-common</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-api</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-netty</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-netty4</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-mina</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-grizzly</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-p2p</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-http</include>
-                                    <include>org.apache.dubbo:dubbo-remoting-zookeeper</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-api</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-dubbo</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-injvm</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-rmi</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-hessian</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-http</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-webservice</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-thrift</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-memcached</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-redis</include>
-                                    <include>org.apache.dubbo:dubbo-rpc-rest</include>
-                                    <include>org.apache.dubbo:dubbo-filter-validation</include>
-                                    <include>org.apache.dubbo:dubbo-filter-cache</include>
-                                    <include>org.apache.dubbo:dubbo-cluster</include>
-                                    <include>org.apache.dubbo:dubbo-registry-api</include>
-                                    <include>org.apache.dubbo:dubbo-registry-default</include>
-                                    <include>org.apache.dubbo:dubbo-registry-multicast</include>
-                                    <include>org.apache.dubbo:dubbo-registry-zookeeper</include>
-                                    <include>org.apache.dubbo:dubbo-registry-redis</include>
-                                    <include>org.apache.dubbo:dubbo-monitor-api</include>
-                                    <include>org.apache.dubbo:dubbo-monitor-default</include>
-                                    <include>org.apache.dubbo:dubbo-config-api</include>
-                                    <include>org.apache.dubbo:dubbo-config-spring</include>
-                                    <include>org.apache.dubbo:dubbo-container-api</include>
-                                    <include>org.apache.dubbo:dubbo-container-spring</include>
-                                    <include>org.apache.dubbo:dubbo-container-log4j</include>
-                                    <include>org.apache.dubbo:dubbo-container-logback</include>
-                                    <include>org.apache.dubbo:dubbo-qos</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-api</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-fastjson</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-hessian2</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-fst</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-kryo</include>
-                                    <include>org.apache.dubbo:dubbo-serialization-jdk</include>
-                                    <include>org.apache.dubbo:dubbo-bootstrap</include>
-                                </includes>
-                            </artifactSet>
-                            <transformers>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.compiler.Compiler
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>
-                                        META-INF/dubbo/internal/org.apache.dubbo.common.extension.ExtensionFactory
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.serialize.Serialization
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.status.StatusChecker
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.threadpool.ThreadPool
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Dispatcher</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Codec2</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Transporter</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.exchange.Exchanger
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.http.HttpBinder
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.p2p.Networker
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.telnet.TelnetHandler
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>
-                                        META-INF/dubbo/internal/org.apache.dubbo.remoting.zookeeper.ZookeeperTransporter
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.Protocol</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.Filter</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.InvokerListener</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.ExporterListener</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.ProxyFactory</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.Cluster</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.LoadBalance
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.Merger</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.RouterFactory
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>
-                                        META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.ConfiguratorFactory
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.container.Container</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.monitor.MonitorFactory
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.registry.RegistryFactory
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.validation.Validation</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.cache.CacheFactory</resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.store.DataStore
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.logger.LoggerAdapter
-                                    </resource>
-                                </transformer>
-                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
-                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.qos.command.BaseCommand
-                                    </resource>
-                                </transformer>
-                            </transformers>
-                        </configuration>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
+<!--
+  Licensed to the Apache Software Foundation (ASF) under one or more
+  contributor license agreements.  See the NOTICE file distributed with
+  this work for additional information regarding copyright ownership.
+  The ASF licenses this file to You under the Apache License, Version 2.0
+  (the "License"); you may not use this file except in compliance with
+  the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+  -->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+    <parent>
+        <groupId>org.apache.dubbo</groupId>
+        <artifactId>dubbo-parent</artifactId>
+        <version>2.7.0-SNAPSHOT</version>
+        <relativePath>../pom.xml</relativePath>
+    </parent>
+    <artifactId>dubbo</artifactId>
+    <version>2.7.0-SNAPSHOT</version>
+    <packaging>jar</packaging>
+    <name>dubbo-all</name>
+    <description>The all in one project of dubbo</description>
+    <properties>
+        <skip_maven_deploy>false</skip_maven_deploy>
+    </properties>
+    <dependencies>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-cluster</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-common</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-config-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-config-spring</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-filter-cache</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-filter-validation</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-netty</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-netty4</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-mina</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-grizzly</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-p2p</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-remoting-http</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-dubbo</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-injvm</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-rmi</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-hessian</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-http</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-webservice</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-thrift</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-memcached</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-redis</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-rest</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-default</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-multicast</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-zookeeper</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-redis</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-monitor-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-monitor-default</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-container-spring</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-container-log4j</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-container-logback</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-qos</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-api</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-fastjson</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-fst</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-hessian2</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-jdk</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-serialization-kryo</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-bootstrap</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-compatible</artifactId>
+            <version>${project.version}</version>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>com.alibaba</groupId>
+            <artifactId>hessian-lite</artifactId>
+            <scope>compile</scope>
+            <optional>true</optional>
+        </dependency>
+
+        <!-- Transitive dependencies -->
+        <dependency>
+            <groupId>org.springframework</groupId>
+            <artifactId>spring-context</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.javassist</groupId>
+            <artifactId>javassist</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>io.netty</groupId>
+            <artifactId>netty-all</artifactId>
+        </dependency>
+
+        <!-- Temporarily add this part to exclude transitive dependency -->
+        <dependency>
+            <groupId>junit</groupId>
+            <artifactId>junit</artifactId>
+            <version>${junit_version}</version>
+            <scope>test</scope>
+            <optional>true</optional>
+        </dependency>
+        <dependency>
+            <groupId>cglib</groupId>
+            <artifactId>cglib-nodep</artifactId>
+            <version>${cglib_version}</version>
+            <scope>test</scope>
+            <optional>true</optional>
+        </dependency>
+    </dependencies>
+    <build>
+        <plugins>
+            <plugin>
+                <groupId>org.apache.maven.plugins</groupId>
+                <artifactId>maven-shade-plugin</artifactId>
+                <version>1.4</version>
+                <executions>
+                    <execution>
+                        <phase>package</phase>
+                        <goals>
+                            <goal>shade</goal>
+                        </goals>
+                        <configuration>
+                            <createSourcesJar>true</createSourcesJar>
+                            <promoteTransitiveDependencies>false</promoteTransitiveDependencies>
+                            <artifactSet>
+                                <includes>
+                                    <include>com.alibaba:hessian-lite</include>
+                                    <include>org.apache.dubbo:dubbo-compatible</include>
+                                    <include>org.apache.dubbo:dubbo-common</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-api</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-netty</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-netty4</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-mina</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-grizzly</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-p2p</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-http</include>
+                                    <include>org.apache.dubbo:dubbo-remoting-zookeeper</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-api</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-dubbo</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-injvm</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-rmi</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-hessian</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-http</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-webservice</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-thrift</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-memcached</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-redis</include>
+                                    <include>org.apache.dubbo:dubbo-rpc-rest</include>
+                                    <include>org.apache.dubbo:dubbo-filter-validation</include>
+                                    <include>org.apache.dubbo:dubbo-filter-cache</include>
+                                    <include>org.apache.dubbo:dubbo-cluster</include>
+                                    <include>org.apache.dubbo:dubbo-registry-api</include>
+                                    <include>org.apache.dubbo:dubbo-registry-default</include>
+                                    <include>org.apache.dubbo:dubbo-registry-multicast</include>
+                                    <include>org.apache.dubbo:dubbo-registry-zookeeper</include>
+                                    <include>org.apache.dubbo:dubbo-registry-redis</include>
+                                    <include>org.apache.dubbo:dubbo-monitor-api</include>
+                                    <include>org.apache.dubbo:dubbo-monitor-default</include>
+                                    <include>org.apache.dubbo:dubbo-config-api</include>
+                                    <include>org.apache.dubbo:dubbo-config-spring</include>
+                                    <include>org.apache.dubbo:dubbo-container-api</include>
+                                    <include>org.apache.dubbo:dubbo-container-spring</include>
+                                    <include>org.apache.dubbo:dubbo-container-log4j</include>
+                                    <include>org.apache.dubbo:dubbo-container-logback</include>
+                                    <include>org.apache.dubbo:dubbo-qos</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-api</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-fastjson</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-hessian2</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-fst</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-kryo</include>
+                                    <include>org.apache.dubbo:dubbo-serialization-jdk</include>
+                                    <include>org.apache.dubbo:dubbo-bootstrap</include>
+                                </includes>
+                            </artifactSet>
+                            <transformers>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.compiler.Compiler
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>
+                                        META-INF/dubbo/internal/org.apache.dubbo.common.extension.ExtensionFactory
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.serialize.Serialization
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.status.StatusChecker
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.threadpool.ThreadPool
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Dispatcher</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Codec2</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.Transporter</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.exchange.Exchanger
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.http.HttpBinder
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.p2p.Networker
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.remoting.telnet.TelnetHandler
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>
+                                        META-INF/dubbo/internal/org.apache.dubbo.remoting.zookeeper.ZookeeperTransporter
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.Protocol</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.Filter</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.InvokerListener</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.ExporterListener</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.ProxyFactory</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.Cluster</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.LoadBalance
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.Merger</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.RouterFactory
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>
+                                        META-INF/dubbo/internal/org.apache.dubbo.rpc.cluster.ConfiguratorFactory
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.container.Container</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.monitor.MonitorFactory
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.registry.RegistryFactory
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.validation.Validation</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.cache.CacheFactory</resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.store.DataStore
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.common.logger.LoggerAdapter
+                                    </resource>
+                                </transformer>
+                                <transformer implementation="org.apache.maven.plugins.shade.resource.AppendingTransformer">
+                                    <resource>META-INF/dubbo/internal/org.apache.dubbo.qos.command.BaseCommand
+                                    </resource>
+                                </transformer>
+                            </transformers>
+                        </configuration>
+                    </execution>
+                </executions>
+            </plugin>
+        </plugins>
+    </build>
 </project>
\ No newline at end of file
diff --git a/dubbo-bom/pom.xml b/dubbo-bom/pom.xml
index 0bf81218d6..4ee5e7cca4 100644
--- a/dubbo-bom/pom.xml
+++ b/dubbo-bom/pom.xml
@@ -1,316 +1,316 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-
-    <modelVersion>4.0.0</modelVersion>
-
-    <parent>
-        <groupId>org.apache.dubbo</groupId>
-        <artifactId>dubbo-parent</artifactId>
-        <version>2.7.0-SNAPSHOT</version>
-    </parent>
-
-    <groupId>org.apache.dubbo</groupId>
-    <artifactId>dubbo-bom</artifactId>
-    <version>2.7.0-SNAPSHOT</version>
-    <packaging>pom</packaging>
-
-    <name>dubbo-bom</name>
-    <description>Dubbo dependencies BOM</description>
-    <url>https://github.com/apache/incubator-dubbo</url>
-    <inceptionYear>2011</inceptionYear>
-    <licenses>
-        <license>
-            <name>Apache License, Version 2.0</name>
-            <url>http://www.apache.org/licenses/LICENSE-2.0</url>
-            <distribution>repo</distribution>
-        </license>
-    </licenses>
-
-    <scm>
-        <url>https://github.com/apache/incubator-dubbo</url>
-        <connection>scm:git:https://github.com/apache/incubator-dubbo.git</connection>
-        <developerConnection>scm:git:https://github.com/apache/incubator-dubbo.git</developerConnection>
-      <tag>HEAD</tag>
-  </scm>
-    <mailingLists>
-        <mailingList>
-            <name>Development List</name>
-            <subscribe>dev-subscribe@dubbo.apache.org</subscribe>
-            <unsubscribe>dev-unsubscribe@dubbo.apache.org</unsubscribe>
-            <post>dev@dubbo.apache.org</post>
-        </mailingList>
-        <mailingList>
-            <name>Commits List</name>
-            <subscribe>commits-subscribe@dubbo.apache.org</subscribe>
-            <unsubscribe>commits-unsubscribe@dubbo.apache.org</unsubscribe>
-            <post>commits@dubbo.apache.org</post>
-        </mailingList>
-        <mailingList>
-            <name>Issues List</name>
-            <subscribe>issues-subscribe@dubbo.apache.org</subscribe>
-            <unsubscribe>issues-unsubscribe@dubbo.apache.org</unsubscribe>
-            <post>issues@dubbo.apache.org</post>
-        </mailingList>
-    </mailingLists>
-    <developers>
-        <developer>
-            <id>dubbo.io</id>
-            <name>The Dubbo Project Contributors</name>
-            <email>dev-subscribe@dubbo.apache.org</email>
-            <url>http://dubbo.apache.org/</url>
-        </developer>
-    </developers>
-
-    <organization>
-        <name>The Apache Software Foundation</name>
-        <url>http://www.apache.org/</url>
-    </organization>
-
-    <issueManagement>
-        <system>Github Issues</system>
-        <url>https://github.com/apache/incubator-dubbo/issues</url>
-    </issueManagement>
-
-    <dependencyManagement>
-        <dependencies>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-cluster</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-common</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-config-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-config-spring</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-filter-cache</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-filter-validation</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-netty</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-netty4</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-mina</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-grizzly</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-p2p</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-remoting-http</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-dubbo</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-injvm</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-rmi</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-hessian</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-http</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-webservice</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-thrift</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-memcached</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-redis</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-rpc-rest</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-registry-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-registry-default</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-registry-multicast</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-registry-zookeeper</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-registry-redis</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-monitor-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-monitor-default</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-container-spring</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-container-log4j</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-container-logback</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-qos</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-api</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-fastjson</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-fst</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-hessian2</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-jdk</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-serialization-kryo</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-bootstrap</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-            <dependency>
-                <groupId>org.apache.dubbo</groupId>
-                <artifactId>dubbo-compatible</artifactId>
-                <version>${project.version}</version>
-            </dependency>
-        </dependencies>
-    </dependencyManagement>
-
-    <profiles>
-        <profile>
-            <id>release</id>
-            <build>
-                <plugins>
-                    <plugin>
-                        <groupId>org.apache.maven.plugins</groupId>
-                        <artifactId>maven-gpg-plugin</artifactId>
-                        <executions>
-                            <execution>
-                                <phase>verify</phase>
-                                <goals>
-                                    <goal>sign</goal>
-                                </goals>
-                            </execution>
-                        </executions>
-                    </plugin>
-                </plugins>
-            </build>
-        </profile>
-    </profiles>
-
-</project>
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>org.apache.dubbo</groupId>
+        <artifactId>dubbo-parent</artifactId>
+        <version>2.7.0-SNAPSHOT</version>
+    </parent>
+
+    <groupId>org.apache.dubbo</groupId>
+    <artifactId>dubbo-bom</artifactId>
+    <version>2.7.0-SNAPSHOT</version>
+    <packaging>pom</packaging>
+
+    <name>dubbo-bom</name>
+    <description>Dubbo dependencies BOM</description>
+    <url>https://github.com/apache/incubator-dubbo</url>
+    <inceptionYear>2011</inceptionYear>
+    <licenses>
+        <license>
+            <name>Apache License, Version 2.0</name>
+            <url>http://www.apache.org/licenses/LICENSE-2.0</url>
+            <distribution>repo</distribution>
+        </license>
+    </licenses>
+
+    <scm>
+        <url>https://github.com/apache/incubator-dubbo</url>
+        <connection>scm:git:https://github.com/apache/incubator-dubbo.git</connection>
+        <developerConnection>scm:git:https://github.com/apache/incubator-dubbo.git</developerConnection>
+      <tag>HEAD</tag>
+  </scm>
+    <mailingLists>
+        <mailingList>
+            <name>Development List</name>
+            <subscribe>dev-subscribe@dubbo.apache.org</subscribe>
+            <unsubscribe>dev-unsubscribe@dubbo.apache.org</unsubscribe>
+            <post>dev@dubbo.apache.org</post>
+        </mailingList>
+        <mailingList>
+            <name>Commits List</name>
+            <subscribe>commits-subscribe@dubbo.apache.org</subscribe>
+            <unsubscribe>commits-unsubscribe@dubbo.apache.org</unsubscribe>
+            <post>commits@dubbo.apache.org</post>
+        </mailingList>
+        <mailingList>
+            <name>Issues List</name>
+            <subscribe>issues-subscribe@dubbo.apache.org</subscribe>
+            <unsubscribe>issues-unsubscribe@dubbo.apache.org</unsubscribe>
+            <post>issues@dubbo.apache.org</post>
+        </mailingList>
+    </mailingLists>
+    <developers>
+        <developer>
+            <id>dubbo.io</id>
+            <name>The Dubbo Project Contributors</name>
+            <email>dev-subscribe@dubbo.apache.org</email>
+            <url>http://dubbo.apache.org/</url>
+        </developer>
+    </developers>
+
+    <organization>
+        <name>The Apache Software Foundation</name>
+        <url>http://www.apache.org/</url>
+    </organization>
+
+    <issueManagement>
+        <system>Github Issues</system>
+        <url>https://github.com/apache/incubator-dubbo/issues</url>
+    </issueManagement>
+
+    <dependencyManagement>
+        <dependencies>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-cluster</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-common</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-config-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-config-spring</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-filter-cache</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-filter-validation</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-netty</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-netty4</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-mina</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-grizzly</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-p2p</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-remoting-http</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-dubbo</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-injvm</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-rmi</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-hessian</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-http</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-webservice</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-thrift</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-memcached</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-redis</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-rpc-rest</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-registry-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-registry-default</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-registry-multicast</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-registry-zookeeper</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-registry-redis</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-monitor-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-monitor-default</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-container-spring</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-container-log4j</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-container-logback</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-qos</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-api</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-fastjson</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-fst</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-hessian2</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-jdk</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-serialization-kryo</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-bootstrap</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.dubbo</groupId>
+                <artifactId>dubbo-compatible</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+        </dependencies>
+    </dependencyManagement>
+
+    <profiles>
+        <profile>
+            <id>release</id>
+            <build>
+                <plugins>
+                    <plugin>
+                        <groupId>org.apache.maven.plugins</groupId>
+                        <artifactId>maven-gpg-plugin</artifactId>
+                        <executions>
+                            <execution>
+                                <phase>verify</phase>
+                                <goals>
+                                    <goal>sign</goal>
+                                </goals>
+                            </execution>
+                        </executions>
+                    </plugin>
+                </plugins>
+            </build>
+        </profile>
+    </profiles>
+
+</project>
diff --git a/dubbo-bootstrap/pom.xml b/dubbo-bootstrap/pom.xml
index a082550b36..6ebbc43bcf 100644
--- a/dubbo-bootstrap/pom.xml
+++ b/dubbo-bootstrap/pom.xml
@@ -1,47 +1,47 @@
-<!--
-  Licensed to the Apache Software Foundation (ASF) under one or more
-  contributor license agreements.  See the NOTICE file distributed with
-  this work for additional information regarding copyright ownership.
-  The ASF licenses this file to You under the Apache License, Version 2.0
-  (the "License"); you may not use this file except in compliance with
-  the License.  You may obtain a copy of the License at
-
-      http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing, software
-  distributed under the License is distributed on an "AS IS" BASIS,
-  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  See the License for the specific language governing permissions and
-  limitations under the License.
-  -->
-<project xmlns="http://maven.apache.org/POM/4.0.0"
-         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
-         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-    <parent>
-        <artifactId>dubbo-parent</artifactId>
-        <groupId>org.apache.dubbo</groupId>
-        <version>2.7.0-SNAPSHOT</version>
-    </parent>
-    <modelVersion>4.0.0</modelVersion>
-
-    <artifactId>dubbo-bootstrap</artifactId>
-
-
-    <dependencies>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-config-api</artifactId>
-            <version>${project.parent.version}</version>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-common</artifactId>
-            <version>${project.parent.version}</version>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-registry-api</artifactId>
-            <version>${project.parent.version}</version>
-        </dependency>
-    </dependencies>
+<!--
+  Licensed to the Apache Software Foundation (ASF) under one or more
+  contributor license agreements.  See the NOTICE file distributed with
+  this work for additional information regarding copyright ownership.
+  The ASF licenses this file to You under the Apache License, Version 2.0
+  (the "License"); you may not use this file except in compliance with
+  the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+  -->
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <parent>
+        <artifactId>dubbo-parent</artifactId>
+        <groupId>org.apache.dubbo</groupId>
+        <version>2.7.0-SNAPSHOT</version>
+    </parent>
+    <modelVersion>4.0.0</modelVersion>
+
+    <artifactId>dubbo-bootstrap</artifactId>
+
+
+    <dependencies>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-config-api</artifactId>
+            <version>${project.parent.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-common</artifactId>
+            <version>${project.parent.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-registry-api</artifactId>
+            <version>${project.parent.version}</version>
+        </dependency>
+    </dependencies>
 </project>
\ No newline at end of file
diff --git a/dubbo-bootstrap/src/main/java/org/apache/dubbo/bootstrap/DubboBootstrap.java b/dubbo-bootstrap/src/main/java/org/apache/dubbo/bootstrap/DubboBootstrap.java
index b896c0ee84..52e502dc81 100644
--- a/dubbo-bootstrap/src/main/java/org/apache/dubbo/bootstrap/DubboBootstrap.java
+++ b/dubbo-bootstrap/src/main/java/org/apache/dubbo/bootstrap/DubboBootstrap.java
@@ -1,111 +1,111 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.bootstrap;
-
-import org.apache.dubbo.config.DubboShutdownHook;
-import org.apache.dubbo.config.ServiceConfig;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * A bootstrap class to easily start and stop Dubbo via programmatic API.
- * The bootstrap class will be responsible to cleanup the resources during stop.
- */
-public class DubboBootstrap {
-
-    /**
-     * The list of ServiceConfig
-     */
-    private List<ServiceConfig> serviceConfigList;
-
-    /**
-     * Whether register the shutdown hook during start?
-     */
-    private final boolean registerShutdownHookOnStart;
-
-    /**
-     * The shutdown hook used when Dubbo is running under embedded environment
-     */
-    private DubboShutdownHook shutdownHook;
-
-    public DubboBootstrap() {
-        this(true, DubboShutdownHook.getDubboShutdownHook());
-    }
-
-    public DubboBootstrap(boolean registerShutdownHookOnStart) {
-        this(registerShutdownHookOnStart, DubboShutdownHook.getDubboShutdownHook());
-    }
-
-    public DubboBootstrap(boolean registerShutdownHookOnStart, DubboShutdownHook shutdownHook) {
-        this.serviceConfigList = new ArrayList<ServiceConfig>();
-        this.shutdownHook = shutdownHook;
-        this.registerShutdownHookOnStart = registerShutdownHookOnStart;
-    }
-
-    /**
-     * Register service config to bootstrap, which will be called during {@link DubboBootstrap#stop()}
-     * @param serviceConfig the service
-     * @return the bootstrap instance
-     */
-    public DubboBootstrap registerServiceConfig(ServiceConfig serviceConfig) {
-        serviceConfigList.add(serviceConfig);
-        return this;
-    }
-
-    public void start() {
-        if (registerShutdownHookOnStart) {
-            registerShutdownHook();
-        } else {
-            // DubboShutdown hook has been registered in AbstractConfig,
-            // we need to remove it explicitly
-            removeShutdownHook();
-        }
-        for (ServiceConfig serviceConfig: serviceConfigList) {
-            serviceConfig.export();
-        }
-    }
-
-    public void stop() {
-        for (ServiceConfig serviceConfig: serviceConfigList) {
-            serviceConfig.unexport();
-        }
-        shutdownHook.destroyAll();
-        if (registerShutdownHookOnStart) {
-            removeShutdownHook();
-        }
-    }
-
-    /**
-     * Register the shutdown hook
-     */
-    public void registerShutdownHook() {
-        Runtime.getRuntime().addShutdownHook(shutdownHook);
-    }
-
-    /**
-     * Remove this shutdown hook
-     */
-    public void removeShutdownHook() {
-        try {
-            Runtime.getRuntime().removeShutdownHook(shutdownHook);
-        }
-        catch (IllegalStateException ex) {
-            // ignore - VM is already shutting down
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.bootstrap;
+
+import org.apache.dubbo.config.DubboShutdownHook;
+import org.apache.dubbo.config.ServiceConfig;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * A bootstrap class to easily start and stop Dubbo via programmatic API.
+ * The bootstrap class will be responsible to cleanup the resources during stop.
+ */
+public class DubboBootstrap {
+
+    /**
+     * The list of ServiceConfig
+     */
+    private List<ServiceConfig> serviceConfigList;
+
+    /**
+     * Whether register the shutdown hook during start?
+     */
+    private final boolean registerShutdownHookOnStart;
+
+    /**
+     * The shutdown hook used when Dubbo is running under embedded environment
+     */
+    private DubboShutdownHook shutdownHook;
+
+    public DubboBootstrap() {
+        this(true, DubboShutdownHook.getDubboShutdownHook());
+    }
+
+    public DubboBootstrap(boolean registerShutdownHookOnStart) {
+        this(registerShutdownHookOnStart, DubboShutdownHook.getDubboShutdownHook());
+    }
+
+    public DubboBootstrap(boolean registerShutdownHookOnStart, DubboShutdownHook shutdownHook) {
+        this.serviceConfigList = new ArrayList<ServiceConfig>();
+        this.shutdownHook = shutdownHook;
+        this.registerShutdownHookOnStart = registerShutdownHookOnStart;
+    }
+
+    /**
+     * Register service config to bootstrap, which will be called during {@link DubboBootstrap#stop()}
+     * @param serviceConfig the service
+     * @return the bootstrap instance
+     */
+    public DubboBootstrap registerServiceConfig(ServiceConfig serviceConfig) {
+        serviceConfigList.add(serviceConfig);
+        return this;
+    }
+
+    public void start() {
+        if (registerShutdownHookOnStart) {
+            registerShutdownHook();
+        } else {
+            // DubboShutdown hook has been registered in AbstractConfig,
+            // we need to remove it explicitly
+            removeShutdownHook();
+        }
+        for (ServiceConfig serviceConfig: serviceConfigList) {
+            serviceConfig.export();
+        }
+    }
+
+    public void stop() {
+        for (ServiceConfig serviceConfig: serviceConfigList) {
+            serviceConfig.unexport();
+        }
+        shutdownHook.destroyAll();
+        if (registerShutdownHookOnStart) {
+            removeShutdownHook();
+        }
+    }
+
+    /**
+     * Register the shutdown hook
+     */
+    public void registerShutdownHook() {
+        Runtime.getRuntime().addShutdownHook(shutdownHook);
+    }
+
+    /**
+     * Remove this shutdown hook
+     */
+    public void removeShutdownHook() {
+        try {
+            Runtime.getRuntime().removeShutdownHook(shutdownHook);
+        }
+        catch (IllegalStateException ex) {
+            // ignore - VM is already shutting down
+        }
+    }
+}
diff --git a/dubbo-cluster/pom.xml b/dubbo-cluster/pom.xml
index 42941d4db6..e81499e539 100644
--- a/dubbo-cluster/pom.xml
+++ b/dubbo-cluster/pom.xml
@@ -1,38 +1,38 @@
-<!--
-  Licensed to the Apache Software Foundation (ASF) under one or more
-  contributor license agreements.  See the NOTICE file distributed with
-  this work for additional information regarding copyright ownership.
-  The ASF licenses this file to You under the Apache License, Version 2.0
-  (the "License"); you may not use this file except in compliance with
-  the License.  You may obtain a copy of the License at
-
-      http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing, software
-  distributed under the License is distributed on an "AS IS" BASIS,
-  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  See the License for the specific language governing permissions and
-  limitations under the License.
-  -->
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
-    <modelVersion>4.0.0</modelVersion>
-    <parent>
-        <groupId>org.apache.dubbo</groupId>
-        <artifactId>dubbo-parent</artifactId>
-        <version>2.7.0-SNAPSHOT</version>
-    </parent>
-    <artifactId>dubbo-cluster</artifactId>
-    <packaging>jar</packaging>
-    <name>${project.artifactId}</name>
-    <description>The cluster module of dubbo project</description>
-    <properties>
-        <skip_maven_deploy>false</skip_maven_deploy>
-    </properties>
-    <dependencies>
-        <dependency>
-            <groupId>org.apache.dubbo</groupId>
-            <artifactId>dubbo-rpc-api</artifactId>
-            <version>${project.parent.version}</version>
-        </dependency>
-    </dependencies>
+<!--
+  Licensed to the Apache Software Foundation (ASF) under one or more
+  contributor license agreements.  See the NOTICE file distributed with
+  this work for additional information regarding copyright ownership.
+  The ASF licenses this file to You under the Apache License, Version 2.0
+  (the "License"); you may not use this file except in compliance with
+  the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+  -->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+    <parent>
+        <groupId>org.apache.dubbo</groupId>
+        <artifactId>dubbo-parent</artifactId>
+        <version>2.7.0-SNAPSHOT</version>
+    </parent>
+    <artifactId>dubbo-cluster</artifactId>
+    <packaging>jar</packaging>
+    <name>${project.artifactId}</name>
+    <description>The cluster module of dubbo project</description>
+    <properties>
+        <skip_maven_deploy>false</skip_maven_deploy>
+    </properties>
+    <dependencies>
+        <dependency>
+            <groupId>org.apache.dubbo</groupId>
+            <artifactId>dubbo-rpc-api</artifactId>
+            <version>${project.parent.version}</version>
+        </dependency>
+    </dependencies>
 </project>
\ No newline at end of file
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/Merger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/Merger.java
index 64bccf8cbd..a5b1864613 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/Merger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/Merger.java
@@ -1,26 +1,26 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster;
-
-import org.apache.dubbo.common.extension.SPI;
-
-@SPI
-public interface Merger<T> {
-
-    T merge(T... items);
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster;
+
+import org.apache.dubbo.common.extension.SPI;
+
+@SPI
+public interface Merger<T> {
+
+    T merge(T... items);
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/RuleConverter.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/RuleConverter.java
index f2cecdc4d7..d55bf4f441 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/RuleConverter.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/RuleConverter.java
@@ -1,30 +1,30 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster;
-
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.SPI;
-
-import java.util.List;
-
-@SPI
-public interface RuleConverter {
-
-    List<URL> convert(URL subscribeUrl, Object source);
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster;
+
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.SPI;
+
+import java.util.List;
+
+@SPI
+public interface RuleConverter {
+
+    List<URL> convert(URL subscribeUrl, Object source);
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/directory/AbstractDirectory.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/directory/AbstractDirectory.java
index 52f5811277..af1c9351b7 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/directory/AbstractDirectory.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/directory/AbstractDirectory.java
@@ -1,133 +1,133 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.directory;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.RouterFactory;
-import org.apache.dubbo.rpc.cluster.router.MockInvokersSelector;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-
-/**
- * Abstract implementation of Directory: Invoker list returned from this Directory's list method have been filtered by Routers
- *
- */
-public abstract class AbstractDirectory<T> implements Directory<T> {
-
-    // logger
-    private static final Logger logger = LoggerFactory.getLogger(AbstractDirectory.class);
-
-    private final URL url;
-
-    private volatile boolean destroyed = false;
-
-    private volatile URL consumerUrl;
-
-    private volatile List<Router> routers;
-
-    public AbstractDirectory(URL url) {
-        this(url, null);
-    }
-
-    public AbstractDirectory(URL url, List<Router> routers) {
-        this(url, url, routers);
-    }
-
-    public AbstractDirectory(URL url, URL consumerUrl, List<Router> routers) {
-        if (url == null)
-            throw new IllegalArgumentException("url == null");
-        this.url = url;
-        this.consumerUrl = consumerUrl;
-        setRouters(routers);
-    }
-
-    @Override
-    public List<Invoker<T>> list(Invocation invocation) throws RpcException {
-        if (destroyed) {
-            throw new RpcException("Directory already destroyed .url: " + getUrl());
-        }
-        List<Invoker<T>> invokers = doList(invocation);
-        List<Router> localRouters = this.routers; // local reference
-        if (localRouters != null && !localRouters.isEmpty()) {
-            for (Router router : localRouters) {
-                try {
-                    if (router.getUrl() == null || router.getUrl().getParameter(Constants.RUNTIME_KEY, false)) {
-                        invokers = router.route(invokers, getConsumerUrl(), invocation);
-                    }
-                } catch (Throwable t) {
-                    logger.error("Failed to execute router: " + getUrl() + ", cause: " + t.getMessage(), t);
-                }
-            }
-        }
-        return invokers;
-    }
-
-    @Override
-    public URL getUrl() {
-        return url;
-    }
-
-    public List<Router> getRouters() {
-        return routers;
-    }
-
-    protected void setRouters(List<Router> routers) {
-        // copy list
-        routers = routers == null ? new ArrayList<Router>() : new ArrayList<Router>(routers);
-        // append url router
-        String routerKey = url.getParameter(Constants.ROUTER_KEY);
-        if (routerKey != null && routerKey.length() > 0) {
-            RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getExtension(routerKey);
-            routers.add(routerFactory.getRouter(url));
-        }
-        // append mock invoker selector
-        routers.add(new MockInvokersSelector());
-        Collections.sort(routers);
-        this.routers = routers;
-    }
-
-    public URL getConsumerUrl() {
-        return consumerUrl;
-    }
-
-    public void setConsumerUrl(URL consumerUrl) {
-        this.consumerUrl = consumerUrl;
-    }
-
-    public boolean isDestroyed() {
-        return destroyed;
-    }
-
-    @Override
-    public void destroy() {
-        destroyed = true;
-    }
-
-    protected abstract List<Invoker<T>> doList(Invocation invocation) throws RpcException;
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.directory;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.RouterFactory;
+import org.apache.dubbo.rpc.cluster.router.MockInvokersSelector;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Abstract implementation of Directory: Invoker list returned from this Directory's list method have been filtered by Routers
+ *
+ */
+public abstract class AbstractDirectory<T> implements Directory<T> {
+
+    // logger
+    private static final Logger logger = LoggerFactory.getLogger(AbstractDirectory.class);
+
+    private final URL url;
+
+    private volatile boolean destroyed = false;
+
+    private volatile URL consumerUrl;
+
+    private volatile List<Router> routers;
+
+    public AbstractDirectory(URL url) {
+        this(url, null);
+    }
+
+    public AbstractDirectory(URL url, List<Router> routers) {
+        this(url, url, routers);
+    }
+
+    public AbstractDirectory(URL url, URL consumerUrl, List<Router> routers) {
+        if (url == null)
+            throw new IllegalArgumentException("url == null");
+        this.url = url;
+        this.consumerUrl = consumerUrl;
+        setRouters(routers);
+    }
+
+    @Override
+    public List<Invoker<T>> list(Invocation invocation) throws RpcException {
+        if (destroyed) {
+            throw new RpcException("Directory already destroyed .url: " + getUrl());
+        }
+        List<Invoker<T>> invokers = doList(invocation);
+        List<Router> localRouters = this.routers; // local reference
+        if (localRouters != null && !localRouters.isEmpty()) {
+            for (Router router : localRouters) {
+                try {
+                    if (router.getUrl() == null || router.getUrl().getParameter(Constants.RUNTIME_KEY, false)) {
+                        invokers = router.route(invokers, getConsumerUrl(), invocation);
+                    }
+                } catch (Throwable t) {
+                    logger.error("Failed to execute router: " + getUrl() + ", cause: " + t.getMessage(), t);
+                }
+            }
+        }
+        return invokers;
+    }
+
+    @Override
+    public URL getUrl() {
+        return url;
+    }
+
+    public List<Router> getRouters() {
+        return routers;
+    }
+
+    protected void setRouters(List<Router> routers) {
+        // copy list
+        routers = routers == null ? new ArrayList<Router>() : new ArrayList<Router>(routers);
+        // append url router
+        String routerKey = url.getParameter(Constants.ROUTER_KEY);
+        if (routerKey != null && routerKey.length() > 0) {
+            RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getExtension(routerKey);
+            routers.add(routerFactory.getRouter(url));
+        }
+        // append mock invoker selector
+        routers.add(new MockInvokersSelector());
+        Collections.sort(routers);
+        this.routers = routers;
+    }
+
+    public URL getConsumerUrl() {
+        return consumerUrl;
+    }
+
+    public void setConsumerUrl(URL consumerUrl) {
+        this.consumerUrl = consumerUrl;
+    }
+
+    public boolean isDestroyed() {
+        return destroyed;
+    }
+
+    @Override
+    public void destroy() {
+        destroyed = true;
+    }
+
+    protected abstract List<Invoker<T>> doList(Invocation invocation) throws RpcException;
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalance.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalance.java
index b5dea51182..ddd494086e 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalance.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalance.java
@@ -1,64 +1,64 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-
-import java.util.List;
-import java.util.Random;
-
-/**
- * random load balance.
- *
- */
-public class RandomLoadBalance extends AbstractLoadBalance {
-
-    public static final String NAME = "random";
-
-    private final Random random = new Random();
-
-    @Override
-    protected <T> Invoker<T> doSelect(List<Invoker<T>> invokers, URL url, Invocation invocation) {
-        int length = invokers.size(); // Number of invokers
-        int totalWeight = 0; // The sum of weights
-        boolean sameWeight = true; // Every invoker has the same weight?
-        for (int i = 0; i < length; i++) {
-            int weight = getWeight(invokers.get(i), invocation);
-            totalWeight += weight; // Sum
-            if (sameWeight && i > 0
-                    && weight != getWeight(invokers.get(i - 1), invocation)) {
-                sameWeight = false;
-            }
-        }
-        if (totalWeight > 0 && !sameWeight) {
-            // If (not every invoker has the same weight & at least one invoker's weight>0), select randomly based on totalWeight.
-            int offset = random.nextInt(totalWeight);
-            // Return a invoker based on the random value.
-            for (int i = 0; i < length; i++) {
-                offset -= getWeight(invokers.get(i), invocation);
-                if (offset < 0) {
-                    return invokers.get(i);
-                }
-            }
-        }
-        // If all invokers have the same weight value or totalWeight=0, return evenly.
-        return invokers.get(random.nextInt(length));
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+
+import java.util.List;
+import java.util.Random;
+
+/**
+ * random load balance.
+ *
+ */
+public class RandomLoadBalance extends AbstractLoadBalance {
+
+    public static final String NAME = "random";
+
+    private final Random random = new Random();
+
+    @Override
+    protected <T> Invoker<T> doSelect(List<Invoker<T>> invokers, URL url, Invocation invocation) {
+        int length = invokers.size(); // Number of invokers
+        int totalWeight = 0; // The sum of weights
+        boolean sameWeight = true; // Every invoker has the same weight?
+        for (int i = 0; i < length; i++) {
+            int weight = getWeight(invokers.get(i), invocation);
+            totalWeight += weight; // Sum
+            if (sameWeight && i > 0
+                    && weight != getWeight(invokers.get(i - 1), invocation)) {
+                sameWeight = false;
+            }
+        }
+        if (totalWeight > 0 && !sameWeight) {
+            // If (not every invoker has the same weight & at least one invoker's weight>0), select randomly based on totalWeight.
+            int offset = random.nextInt(totalWeight);
+            // Return a invoker based on the random value.
+            for (int i = 0; i < length; i++) {
+                offset -= getWeight(invokers.get(i), invocation);
+                if (offset < 0) {
+                    return invokers.get(i);
+                }
+            }
+        }
+        // If all invokers have the same weight value or totalWeight=0, return evenly.
+        return invokers.get(random.nextInt(length));
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ArrayMerger.java
index d6e58778ba..638e1061d0 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ArrayMerger.java
@@ -1,58 +1,58 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-import java.lang.reflect.Array;
-
-public class ArrayMerger implements Merger<Object[]> {
-
-    public static final ArrayMerger INSTANCE = new ArrayMerger();
-
-    @Override
-    public Object[] merge(Object[]... others) {
-        if (others.length == 0) {
-            return null;
-        }
-        int totalLen = 0;
-        for (int i = 0; i < others.length; i++) {
-            Object item = others[i];
-            if (item != null && item.getClass().isArray()) {
-                totalLen += Array.getLength(item);
-            } else {
-                throw new IllegalArgumentException((i + 1) + "th argument is not an array");
-            }
-        }
-
-        if (totalLen == 0) {
-            return null;
-        }
-
-        Class<?> type = others[0].getClass().getComponentType();
-
-        Object result = Array.newInstance(type, totalLen);
-        int index = 0;
-        for (Object array : others) {
-            for (int i = 0; i < Array.getLength(array); i++) {
-                Array.set(result, index++, Array.get(array, i));
-            }
-        }
-        return (Object[]) result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+import java.lang.reflect.Array;
+
+public class ArrayMerger implements Merger<Object[]> {
+
+    public static final ArrayMerger INSTANCE = new ArrayMerger();
+
+    @Override
+    public Object[] merge(Object[]... others) {
+        if (others.length == 0) {
+            return null;
+        }
+        int totalLen = 0;
+        for (int i = 0; i < others.length; i++) {
+            Object item = others[i];
+            if (item != null && item.getClass().isArray()) {
+                totalLen += Array.getLength(item);
+            } else {
+                throw new IllegalArgumentException((i + 1) + "th argument is not an array");
+            }
+        }
+
+        if (totalLen == 0) {
+            return null;
+        }
+
+        Class<?> type = others[0].getClass().getComponentType();
+
+        Object result = Array.newInstance(type, totalLen);
+        int index = 0;
+        for (Object array : others) {
+            for (int i = 0; i < Array.getLength(array); i++) {
+                Array.set(result, index++, Array.get(array, i));
+            }
+        }
+        return (Object[]) result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/BooleanArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/BooleanArrayMerger.java
index 090f8b13f7..79ef4db341 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/BooleanArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/BooleanArrayMerger.java
@@ -1,40 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class BooleanArrayMerger implements Merger<boolean[]> {
-
-    @Override
-    public boolean[] merge(boolean[]... items) {
-        int totalLen = 0;
-        for (boolean[] array : items) {
-            totalLen += array.length;
-        }
-        boolean[] result = new boolean[totalLen];
-        int index = 0;
-        for (boolean[] array : items) {
-            for (boolean item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class BooleanArrayMerger implements Merger<boolean[]> {
+
+    @Override
+    public boolean[] merge(boolean[]... items) {
+        int totalLen = 0;
+        for (boolean[] array : items) {
+            totalLen += array.length;
+        }
+        boolean[] result = new boolean[totalLen];
+        int index = 0;
+        for (boolean[] array : items) {
+            for (boolean item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ByteArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ByteArrayMerger.java
index c135bb34cc..2c78ce2bd8 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ByteArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ByteArrayMerger.java
@@ -1,40 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class ByteArrayMerger implements Merger<byte[]> {
-
-    @Override
-    public byte[] merge(byte[]... items) {
-        int total = 0;
-        for (byte[] array : items) {
-            total += array.length;
-        }
-        byte[] result = new byte[total];
-        int index = 0;
-        for (byte[] array : items) {
-            for (byte item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class ByteArrayMerger implements Merger<byte[]> {
+
+    @Override
+    public byte[] merge(byte[]... items) {
+        int total = 0;
+        for (byte[] array : items) {
+            total += array.length;
+        }
+        byte[] result = new byte[total];
+        int index = 0;
+        for (byte[] array : items) {
+            for (byte item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/CharArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/CharArrayMerger.java
index e9a3dbcf19..c165d95d43 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/CharArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/CharArrayMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class CharArrayMerger implements Merger<char[]> {
-
-    @Override
-    public char[] merge(char[]... items) {
-        int total = 0;
-        for (char[] array : items) {
-            total += array.length;
-        }
-        char[] result = new char[total];
-        int index = 0;
-        for (char[] array : items) {
-            for (char item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class CharArrayMerger implements Merger<char[]> {
+
+    @Override
+    public char[] merge(char[]... items) {
+        int total = 0;
+        for (char[] array : items) {
+            total += array.length;
+        }
+        char[] result = new char[total];
+        int index = 0;
+        for (char[] array : items) {
+            for (char item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/DoubleArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/DoubleArrayMerger.java
index c42e225276..6c06c1cc11 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/DoubleArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/DoubleArrayMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class DoubleArrayMerger implements Merger<double[]> {
-
-    @Override
-    public double[] merge(double[]... items) {
-        int total = 0;
-        for (double[] array : items) {
-            total += array.length;
-        }
-        double[] result = new double[total];
-        int index = 0;
-        for (double[] array : items) {
-            for (double item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class DoubleArrayMerger implements Merger<double[]> {
+
+    @Override
+    public double[] merge(double[]... items) {
+        int total = 0;
+        for (double[] array : items) {
+            total += array.length;
+        }
+        double[] result = new double[total];
+        int index = 0;
+        for (double[] array : items) {
+            for (double item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/FloatArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/FloatArrayMerger.java
index d6a9e8b464..e96e651aec 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/FloatArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/FloatArrayMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class FloatArrayMerger implements Merger<float[]> {
-
-    @Override
-    public float[] merge(float[]... items) {
-        int total = 0;
-        for (float[] array : items) {
-            total += array.length;
-        }
-        float[] result = new float[total];
-        int index = 0;
-        for (float[] array : items) {
-            for (float item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class FloatArrayMerger implements Merger<float[]> {
+
+    @Override
+    public float[] merge(float[]... items) {
+        int total = 0;
+        for (float[] array : items) {
+            total += array.length;
+        }
+        float[] result = new float[total];
+        int index = 0;
+        for (float[] array : items) {
+            for (float item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/IntArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/IntArrayMerger.java
index 7be893997d..3f3e1511aa 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/IntArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/IntArrayMerger.java
@@ -1,40 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class IntArrayMerger implements Merger<int[]> {
-
-    @Override
-    public int[] merge(int[]... items) {
-        int totalLen = 0;
-        for (int[] item : items) {
-            totalLen += item.length;
-        }
-        int[] result = new int[totalLen];
-        int index = 0;
-        for (int[] item : items) {
-            for (int i : item) {
-                result[index++] = i;
-            }
-        }
-        return result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class IntArrayMerger implements Merger<int[]> {
+
+    @Override
+    public int[] merge(int[]... items) {
+        int totalLen = 0;
+        for (int[] item : items) {
+            totalLen += item.length;
+        }
+        int[] result = new int[totalLen];
+        int index = 0;
+        for (int[] item : items) {
+            for (int i : item) {
+                result[index++] = i;
+            }
+        }
+        return result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ListMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ListMerger.java
index 9ec2fe9251..7f81da7609 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ListMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ListMerger.java
@@ -1,38 +1,38 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-import java.util.ArrayList;
-import java.util.List;
-
-public class ListMerger implements Merger<List<?>> {
-
-    @Override
-    public List<Object> merge(List<?>... items) {
-        List<Object> result = new ArrayList<Object>();
-        for (List<?> item : items) {
-            if (item != null) {
-                result.addAll(item);
-            }
-        }
-        return result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class ListMerger implements Merger<List<?>> {
+
+    @Override
+    public List<Object> merge(List<?>... items) {
+        List<Object> result = new ArrayList<Object>();
+        for (List<?> item : items) {
+            if (item != null) {
+                result.addAll(item);
+            }
+        }
+        return result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/LongArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/LongArrayMerger.java
index 40ab0257fa..a340166bb8 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/LongArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/LongArrayMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class LongArrayMerger implements Merger<long[]> {
-
-    @Override
-    public long[] merge(long[]... items) {
-        int total = 0;
-        for (long[] array : items) {
-            total += array.length;
-        }
-        long[] result = new long[total];
-        int index = 0;
-        for (long[] array : items) {
-            for (long item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class LongArrayMerger implements Merger<long[]> {
+
+    @Override
+    public long[] merge(long[]... items) {
+        int total = 0;
+        for (long[] array : items) {
+            total += array.length;
+        }
+        long[] result = new long[total];
+        int index = 0;
+        for (long[] array : items) {
+            for (long item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MapMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MapMerger.java
index 3e11e8bad4..01c91b884b 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MapMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MapMerger.java
@@ -1,40 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-import java.util.HashMap;
-import java.util.Map;
-
-public class MapMerger implements Merger<Map<?, ?>> {
-
-    @Override
-    public Map<?, ?> merge(Map<?, ?>... items) {
-        if (items.length == 0) {
-            return null;
-        }
-        Map<Object, Object> result = new HashMap<Object, Object>();
-        for (Map<?, ?> item : items) {
-            if (item != null) {
-                result.putAll(item);
-            }
-        }
-        return result;
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class MapMerger implements Merger<Map<?, ?>> {
+
+    @Override
+    public Map<?, ?> merge(Map<?, ?>... items) {
+        if (items.length == 0) {
+            return null;
+        }
+        Map<Object, Object> result = new HashMap<Object, Object>();
+        for (Map<?, ?> item : items) {
+            if (item != null) {
+                result.putAll(item);
+            }
+        }
+        return result;
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MergerFactory.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MergerFactory.java
index 9264fb7c15..a18dec77a8 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MergerFactory.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/MergerFactory.java
@@ -1,64 +1,64 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.common.utils.ReflectUtils;
-import org.apache.dubbo.rpc.cluster.Merger;
-
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
-
-public class MergerFactory {
-
-    private static final ConcurrentMap<Class<?>, Merger<?>> mergerCache =
-            new ConcurrentHashMap<Class<?>, Merger<?>>();
-
-    public static <T> Merger<T> getMerger(Class<T> returnType) {
-        Merger result;
-        if (returnType.isArray()) {
-            Class type = returnType.getComponentType();
-            result = mergerCache.get(type);
-            if (result == null) {
-                loadMergers();
-                result = mergerCache.get(type);
-            }
-            if (result == null && !type.isPrimitive()) {
-                result = ArrayMerger.INSTANCE;
-            }
-        } else {
-            result = mergerCache.get(returnType);
-            if (result == null) {
-                loadMergers();
-                result = mergerCache.get(returnType);
-            }
-        }
-        return result;
-    }
-
-    static void loadMergers() {
-        Set<String> names = ExtensionLoader.getExtensionLoader(Merger.class)
-                .getSupportedExtensions();
-        for (String name : names) {
-            Merger m = ExtensionLoader.getExtensionLoader(Merger.class).getExtension(name);
-            mergerCache.putIfAbsent(ReflectUtils.getGenericClass(m.getClass()), m);
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.common.utils.ReflectUtils;
+import org.apache.dubbo.rpc.cluster.Merger;
+
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentMap;
+
+public class MergerFactory {
+
+    private static final ConcurrentMap<Class<?>, Merger<?>> mergerCache =
+            new ConcurrentHashMap<Class<?>, Merger<?>>();
+
+    public static <T> Merger<T> getMerger(Class<T> returnType) {
+        Merger result;
+        if (returnType.isArray()) {
+            Class type = returnType.getComponentType();
+            result = mergerCache.get(type);
+            if (result == null) {
+                loadMergers();
+                result = mergerCache.get(type);
+            }
+            if (result == null && !type.isPrimitive()) {
+                result = ArrayMerger.INSTANCE;
+            }
+        } else {
+            result = mergerCache.get(returnType);
+            if (result == null) {
+                loadMergers();
+                result = mergerCache.get(returnType);
+            }
+        }
+        return result;
+    }
+
+    static void loadMergers() {
+        Set<String> names = ExtensionLoader.getExtensionLoader(Merger.class)
+                .getSupportedExtensions();
+        for (String name : names) {
+            Merger m = ExtensionLoader.getExtensionLoader(Merger.class).getExtension(name);
+            mergerCache.putIfAbsent(ReflectUtils.getGenericClass(m.getClass()), m);
+        }
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/SetMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/SetMerger.java
index 558d5853cc..db68ddee45 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/SetMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/SetMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-import java.util.HashSet;
-import java.util.Set;
-
-public class SetMerger implements Merger<Set<?>> {
-
-    @Override
-    public Set<Object> merge(Set<?>... items) {
-
-        Set<Object> result = new HashSet<Object>();
-
-        for (Set<?> item : items) {
-            if (item != null) {
-                result.addAll(item);
-            }
-        }
-
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+import java.util.HashSet;
+import java.util.Set;
+
+public class SetMerger implements Merger<Set<?>> {
+
+    @Override
+    public Set<Object> merge(Set<?>... items) {
+
+        Set<Object> result = new HashSet<Object>();
+
+        for (Set<?> item : items) {
+            if (item != null) {
+                result.addAll(item);
+            }
+        }
+
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ShortArrayMerger.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ShortArrayMerger.java
index 3cbce9be51..ff59854e27 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ShortArrayMerger.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/merger/ShortArrayMerger.java
@@ -1,39 +1,39 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.apache.dubbo.rpc.cluster.Merger;
-
-public class ShortArrayMerger implements Merger<short[]> {
-
-    @Override
-    public short[] merge(short[]... items) {
-        int total = 0;
-        for (short[] array : items) {
-            total += array.length;
-        }
-        short[] result = new short[total];
-        int index = 0;
-        for (short[] array : items) {
-            for (short item : array) {
-                result[index++] = item;
-            }
-        }
-        return result;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.apache.dubbo.rpc.cluster.Merger;
+
+public class ShortArrayMerger implements Merger<short[]> {
+
+    @Override
+    public short[] merge(short[]... items) {
+        int total = 0;
+        for (short[] array : items) {
+            total += array.length;
+        }
+        short[] result = new short[total];
+        int index = 0;
+        for (short[] array : items) {
+            for (short item : array) {
+                result[index++] = item;
+            }
+        }
+        return result;
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterFactory.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterFactory.java
index 6b8b324555..acbad75ea0 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterFactory.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterFactory.java
@@ -1,65 +1,65 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.file;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.utils.IOUtils;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.RouterFactory;
-import org.apache.dubbo.rpc.cluster.router.script.ScriptRouterFactory;
-
-import java.io.File;
-import java.io.FileReader;
-import java.io.IOException;
-
-public class FileRouterFactory implements RouterFactory {
-
-    public static final String NAME = "file";
-
-    private RouterFactory routerFactory;
-
-    public void setRouterFactory(RouterFactory routerFactory) {
-        this.routerFactory = routerFactory;
-    }
-
-    @Override
-    public Router getRouter(URL url) {
-        try {
-            // Transform File URL into Script Route URL, and Load
-            // file:///d:/path/to/route.js?router=script ==> script:///d:/path/to/route.js?type=js&rule=<file-content>
-            String protocol = url.getParameter(Constants.ROUTER_KEY, ScriptRouterFactory.NAME); // Replace original protocol (maybe 'file') with 'script'
-            String type = null; // Use file suffix to config script type, e.g., js, groovy ...
-            String path = url.getPath();
-            if (path != null) {
-                int i = path.lastIndexOf('.');
-                if (i > 0) {
-                    type = path.substring(i + 1);
-                }
-            }
-            String rule = IOUtils.read(new FileReader(new File(url.getAbsolutePath())));
-
-            boolean runtime = url.getParameter(Constants.RUNTIME_KEY, false);
-            URL script = url.setProtocol(protocol).addParameter(Constants.TYPE_KEY, type).addParameter(Constants.RUNTIME_KEY, runtime).addParameterAndEncoded(Constants.RULE_KEY, rule);
-
-            return routerFactory.getRouter(script);
-        } catch (IOException e) {
-            throw new IllegalStateException(e.getMessage(), e);
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.file;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.utils.IOUtils;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.RouterFactory;
+import org.apache.dubbo.rpc.cluster.router.script.ScriptRouterFactory;
+
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+
+public class FileRouterFactory implements RouterFactory {
+
+    public static final String NAME = "file";
+
+    private RouterFactory routerFactory;
+
+    public void setRouterFactory(RouterFactory routerFactory) {
+        this.routerFactory = routerFactory;
+    }
+
+    @Override
+    public Router getRouter(URL url) {
+        try {
+            // Transform File URL into Script Route URL, and Load
+            // file:///d:/path/to/route.js?router=script ==> script:///d:/path/to/route.js?type=js&rule=<file-content>
+            String protocol = url.getParameter(Constants.ROUTER_KEY, ScriptRouterFactory.NAME); // Replace original protocol (maybe 'file') with 'script'
+            String type = null; // Use file suffix to config script type, e.g., js, groovy ...
+            String path = url.getPath();
+            if (path != null) {
+                int i = path.lastIndexOf('.');
+                if (i > 0) {
+                    type = path.substring(i + 1);
+                }
+            }
+            String rule = IOUtils.read(new FileReader(new File(url.getAbsolutePath())));
+
+            boolean runtime = url.getParameter(Constants.RUNTIME_KEY, false);
+            URL script = url.setProtocol(protocol).addParameter(Constants.TYPE_KEY, type).addParameter(Constants.RUNTIME_KEY, runtime).addParameterAndEncoded(Constants.RULE_KEY, rule);
+
+            return routerFactory.getRouter(script);
+        } catch (IOException e) {
+            throw new IllegalStateException(e.getMessage(), e);
+        }
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouter.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouter.java
index 38fd6166ef..1ed65ceec5 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouter.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouter.java
@@ -1,109 +1,109 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.tag;
-
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.StringUtils;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcContext;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.cluster.Router;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * TagRouter
- */
-public class TagRouter implements Router, Comparable<Router> {
-
-    private static final Logger logger = LoggerFactory.getLogger(TagRouter.class);
-
-    private final int priority;
-    private final URL url;
-
-    public static final URL ROUTER_URL = new URL("tag", Constants.ANYHOST_VALUE, 0, Constants.ANY_VALUE).addParameters(Constants.RUNTIME_KEY, "true");
-
-    public TagRouter(URL url) {
-        this.url = url;
-        this.priority = url.getParameter(Constants.PRIORITY_KEY, 0);
-    }
-
-    public TagRouter() {
-        this.url = ROUTER_URL;
-        this.priority = url.getParameter(Constants.PRIORITY_KEY, 0);
-    }
-
-    @Override
-    public URL getUrl() {
-        return url;
-    }
-
-    @Override
-    public <T> List<Invoker<T>> route(List<Invoker<T>> invokers, URL url, Invocation invocation) throws RpcException {
-        // filter
-        List<Invoker<T>> result = new ArrayList<>();
-        try {
-            // Dynamic param
-            String tag = RpcContext.getContext().getAttachment(Constants.REQUEST_TAG_KEY);
-            // Tag request
-            if (!StringUtils.isEmpty(tag)) {
-                // Select tag invokers first
-                for (Invoker<T> invoker : invokers) {
-                    if (tag.equals(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
-                        result.add(invoker);
-                    }
-                }
-                // If no invoker be selected, downgrade to normal invokers
-                if (result.isEmpty()) {
-                    for (Invoker<T> invoker : invokers) {
-                        if (StringUtils.isEmpty(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
-                            result.add(invoker);
-                        }
-                    }
-                }
-            // Normal request
-            } else {
-                for (Invoker<T> invoker : invokers) {
-                    // Can't access tag invoker,only normal invoker should be selected
-                    if (StringUtils.isEmpty(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
-                        result.add(invoker);
-                    }
-                }
-            }
-            return result;
-        } catch (Exception e) {
-            logger.error("Route by tag error,return all invokers.", e);
-        }
-        // Downgrade to all invokers
-        return invokers;
-    }
-
-    @Override
-    public int compareTo(Router o) {
-        if (o == null || o.getClass() != TagRouter.class) {
-            return 1;
-        }
-        TagRouter c = (TagRouter) o;
-        return this.priority == c.priority ? url.toFullString().compareTo(c.url.toFullString()) : (this.priority > c.priority ? 1 : -1);
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.tag;
+
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.common.utils.StringUtils;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcContext;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.cluster.Router;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * TagRouter
+ */
+public class TagRouter implements Router, Comparable<Router> {
+
+    private static final Logger logger = LoggerFactory.getLogger(TagRouter.class);
+
+    private final int priority;
+    private final URL url;
+
+    public static final URL ROUTER_URL = new URL("tag", Constants.ANYHOST_VALUE, 0, Constants.ANY_VALUE).addParameters(Constants.RUNTIME_KEY, "true");
+
+    public TagRouter(URL url) {
+        this.url = url;
+        this.priority = url.getParameter(Constants.PRIORITY_KEY, 0);
+    }
+
+    public TagRouter() {
+        this.url = ROUTER_URL;
+        this.priority = url.getParameter(Constants.PRIORITY_KEY, 0);
+    }
+
+    @Override
+    public URL getUrl() {
+        return url;
+    }
+
+    @Override
+    public <T> List<Invoker<T>> route(List<Invoker<T>> invokers, URL url, Invocation invocation) throws RpcException {
+        // filter
+        List<Invoker<T>> result = new ArrayList<>();
+        try {
+            // Dynamic param
+            String tag = RpcContext.getContext().getAttachment(Constants.REQUEST_TAG_KEY);
+            // Tag request
+            if (!StringUtils.isEmpty(tag)) {
+                // Select tag invokers first
+                for (Invoker<T> invoker : invokers) {
+                    if (tag.equals(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
+                        result.add(invoker);
+                    }
+                }
+                // If no invoker be selected, downgrade to normal invokers
+                if (result.isEmpty()) {
+                    for (Invoker<T> invoker : invokers) {
+                        if (StringUtils.isEmpty(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
+                            result.add(invoker);
+                        }
+                    }
+                }
+            // Normal request
+            } else {
+                for (Invoker<T> invoker : invokers) {
+                    // Can't access tag invoker,only normal invoker should be selected
+                    if (StringUtils.isEmpty(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
+                        result.add(invoker);
+                    }
+                }
+            }
+            return result;
+        } catch (Exception e) {
+            logger.error("Route by tag error,return all invokers.", e);
+        }
+        // Downgrade to all invokers
+        return invokers;
+    }
+
+    @Override
+    public int compareTo(Router o) {
+        if (o == null || o.getClass() != TagRouter.class) {
+            return 1;
+        }
+        TagRouter c = (TagRouter) o;
+        return this.priority == c.priority ? url.toFullString().compareTo(c.url.toFullString()) : (this.priority > c.priority ? 1 : -1);
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterFactory.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterFactory.java
index 05ad427ce6..f31e355173 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterFactory.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterFactory.java
@@ -1,32 +1,32 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.tag;
-
-
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.RouterFactory;
-
-public class TagRouterFactory implements RouterFactory {
-
-    public static final String NAME = "tag";
-
-    @Override
-    public Router getRouter(URL url) {
-        return new TagRouter(url);
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.tag;
+
+
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.RouterFactory;
+
+public class TagRouterFactory implements RouterFactory {
+
+    public static final String NAME = "tag";
+
+    @Override
+    public Router getRouter(URL url) {
+        return new TagRouter(url);
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/AvailableClusterInvoker.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/AvailableClusterInvoker.java
index c75052c02e..9845924da2 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/AvailableClusterInvoker.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/AvailableClusterInvoker.java
@@ -1,48 +1,48 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.LoadBalance;
-
-import java.util.List;
-
-/**
- * AvailableCluster
- *
- */
-public class AvailableClusterInvoker<T> extends AbstractClusterInvoker<T> {
-
-    public AvailableClusterInvoker(Directory<T> directory) {
-        super(directory);
-    }
-
-    @Override
-    public Result doInvoke(Invocation invocation, List<Invoker<T>> invokers, LoadBalance loadbalance) throws RpcException {
-        for (Invoker<T> invoker : invokers) {
-            if (invoker.isAvailable()) {
-                return invoker.invoke(invocation);
-            }
-        }
-        throw new RpcException("No provider available in " + invokers);
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.LoadBalance;
+
+import java.util.List;
+
+/**
+ * AvailableCluster
+ *
+ */
+public class AvailableClusterInvoker<T> extends AbstractClusterInvoker<T> {
+
+    public AvailableClusterInvoker(Directory<T> directory) {
+        super(directory);
+    }
+
+    @Override
+    public Result doInvoke(Invocation invocation, List<Invoker<T>> invokers, LoadBalance loadbalance) throws RpcException {
+        for (Invoker<T> invoker : invokers) {
+            if (invoker.isAvailable()) {
+                return invoker.invoke(invocation);
+            }
+        }
+        throw new RpcException("No provider available in " + invokers);
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/ForkingClusterInvoker.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/ForkingClusterInvoker.java
index 28b4471612..75da23b9ed 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/ForkingClusterInvoker.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/ForkingClusterInvoker.java
@@ -1,110 +1,110 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.threadlocal.NamedInternalThreadFactory;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcContext;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.LoadBalance;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.concurrent.BlockingQueue;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.LinkedBlockingQueue;
-import java.util.concurrent.TimeUnit;
-import java.util.concurrent.atomic.AtomicInteger;
-
-/**
- * Invoke a specific number of invokers concurrently, usually used for demanding real-time operations, but need to waste more service resources.
- *
- * <a href="http://en.wikipedia.org/wiki/Fork_(topology)">Fork</a>
- */
-public class ForkingClusterInvoker<T> extends AbstractClusterInvoker<T> {
-
-    /**
-     * Use {@link NamedInternalThreadFactory} to produce {@link org.apache.dubbo.common.threadlocal.InternalThread}
-     * which with the use of {@link org.apache.dubbo.common.threadlocal.InternalThreadLocal} in {@link RpcContext}.
-     */
-    private final ExecutorService executor = Executors.newCachedThreadPool(
-            new NamedInternalThreadFactory("forking-cluster-timer", true));
-
-    public ForkingClusterInvoker(Directory<T> directory) {
-        super(directory);
-    }
-
-    @Override
-    @SuppressWarnings({"unchecked", "rawtypes"})
-    public Result doInvoke(final Invocation invocation, List<Invoker<T>> invokers, LoadBalance loadbalance) throws RpcException {
-        try {
-            checkInvokers(invokers, invocation);
-            final List<Invoker<T>> selected;
-            final int forks = getUrl().getParameter(Constants.FORKS_KEY, Constants.DEFAULT_FORKS);
-            final int timeout = getUrl().getParameter(Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT);
-            if (forks <= 0 || forks >= invokers.size()) {
-                selected = invokers;
-            } else {
-                selected = new ArrayList<Invoker<T>>();
-                for (int i = 0; i < forks; i++) {
-                    // TODO. Add some comment here, refer chinese version for more details.
-                    Invoker<T> invoker = select(loadbalance, invocation, invokers, selected);
-                    if (!selected.contains(invoker)) {//Avoid add the same invoker several times.
-                        selected.add(invoker);
-                    }
-                }
-            }
-            RpcContext.getContext().setInvokers((List) selected);
-            final AtomicInteger count = new AtomicInteger();
-            final BlockingQueue<Object> ref = new LinkedBlockingQueue<Object>();
-            for (final Invoker<T> invoker : selected) {
-                executor.execute(new Runnable() {
-                    @Override
-                    public void run() {
-                        try {
-                            Result result = invoker.invoke(invocation);
-                            ref.offer(result);
-                        } catch (Throwable e) {
-                            int value = count.incrementAndGet();
-                            if (value >= selected.size()) {
-                                ref.offer(e);
-                            }
-                        }
-                    }
-                });
-            }
-            try {
-                Object ret = ref.poll(timeout, TimeUnit.MILLISECONDS);
-                if (ret instanceof Throwable) {
-                    Throwable e = (Throwable) ret;
-                    throw new RpcException(e instanceof RpcException ? ((RpcException) e).getCode() : 0, "Failed to forking invoke provider " + selected + ", but no luck to perform the invocation. Last error is: " + e.getMessage(), e.getCause() != null ? e.getCause() : e);
-                }
-                return (Result) ret;
-            } catch (InterruptedException e) {
-                throw new RpcException("Failed to forking invoke provider " + selected + ", but no luck to perform the invocation. Last error is: " + e.getMessage(), e);
-            }
-        } finally {
-            // clear attachments which is binding to current thread.
-            RpcContext.getContext().clearAttachments();
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.threadlocal.NamedInternalThreadFactory;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcContext;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.LoadBalance;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.BlockingQueue;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.LinkedBlockingQueue;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicInteger;
+
+/**
+ * Invoke a specific number of invokers concurrently, usually used for demanding real-time operations, but need to waste more service resources.
+ *
+ * <a href="http://en.wikipedia.org/wiki/Fork_(topology)">Fork</a>
+ */
+public class ForkingClusterInvoker<T> extends AbstractClusterInvoker<T> {
+
+    /**
+     * Use {@link NamedInternalThreadFactory} to produce {@link org.apache.dubbo.common.threadlocal.InternalThread}
+     * which with the use of {@link org.apache.dubbo.common.threadlocal.InternalThreadLocal} in {@link RpcContext}.
+     */
+    private final ExecutorService executor = Executors.newCachedThreadPool(
+            new NamedInternalThreadFactory("forking-cluster-timer", true));
+
+    public ForkingClusterInvoker(Directory<T> directory) {
+        super(directory);
+    }
+
+    @Override
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    public Result doInvoke(final Invocation invocation, List<Invoker<T>> invokers, LoadBalance loadbalance) throws RpcException {
+        try {
+            checkInvokers(invokers, invocation);
+            final List<Invoker<T>> selected;
+            final int forks = getUrl().getParameter(Constants.FORKS_KEY, Constants.DEFAULT_FORKS);
+            final int timeout = getUrl().getParameter(Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT);
+            if (forks <= 0 || forks >= invokers.size()) {
+                selected = invokers;
+            } else {
+                selected = new ArrayList<Invoker<T>>();
+                for (int i = 0; i < forks; i++) {
+                    // TODO. Add some comment here, refer chinese version for more details.
+                    Invoker<T> invoker = select(loadbalance, invocation, invokers, selected);
+                    if (!selected.contains(invoker)) {//Avoid add the same invoker several times.
+                        selected.add(invoker);
+                    }
+                }
+            }
+            RpcContext.getContext().setInvokers((List) selected);
+            final AtomicInteger count = new AtomicInteger();
+            final BlockingQueue<Object> ref = new LinkedBlockingQueue<Object>();
+            for (final Invoker<T> invoker : selected) {
+                executor.execute(new Runnable() {
+                    @Override
+                    public void run() {
+                        try {
+                            Result result = invoker.invoke(invocation);
+                            ref.offer(result);
+                        } catch (Throwable e) {
+                            int value = count.incrementAndGet();
+                            if (value >= selected.size()) {
+                                ref.offer(e);
+                            }
+                        }
+                    }
+                });
+            }
+            try {
+                Object ret = ref.poll(timeout, TimeUnit.MILLISECONDS);
+                if (ret instanceof Throwable) {
+                    Throwable e = (Throwable) ret;
+                    throw new RpcException(e instanceof RpcException ? ((RpcException) e).getCode() : 0, "Failed to forking invoke provider " + selected + ", but no luck to perform the invocation. Last error is: " + e.getMessage(), e.getCause() != null ? e.getCause() : e);
+                }
+                return (Result) ret;
+            } catch (InterruptedException e) {
+                throw new RpcException("Failed to forking invoke provider " + selected + ", but no luck to perform the invocation. Last error is: " + e.getMessage(), e);
+            }
+        } finally {
+            // clear attachments which is binding to current thread.
+            RpcContext.getContext().clearAttachments();
+        }
+    }
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableCluster.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableCluster.java
index 1e0f43d5be..a30877d2f7 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableCluster.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableCluster.java
@@ -1,33 +1,33 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.cluster.Cluster;
-import org.apache.dubbo.rpc.cluster.Directory;
-
-public class MergeableCluster implements Cluster {
-
-    public static final String NAME = "mergeable";
-
-    @Override
-    public <T> Invoker<T> join(Directory<T> directory) throws RpcException {
-        return new MergeableClusterInvoker<T>(directory);
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.cluster.Cluster;
+import org.apache.dubbo.rpc.cluster.Directory;
+
+public class MergeableCluster implements Cluster {
+
+    public static final String NAME = "mergeable";
+
+    @Override
+    public <T> Invoker<T> join(Directory<T> directory) throws RpcException {
+        return new MergeableClusterInvoker<T>(directory);
+    }
+
+}
diff --git a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvoker.java b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvoker.java
index 0c68eab84e..34e994723a 100644
--- a/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvoker.java
+++ b/dubbo-cluster/src/main/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvoker.java
@@ -1,200 +1,200 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.ConfigUtils;
-import org.apache.dubbo.common.utils.NamedThreadFactory;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.RpcResult;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.Merger;
-import org.apache.dubbo.rpc.cluster.merger.MergerFactory;
-
-import java.lang.reflect.Array;
-import java.lang.reflect.Method;
-import java.lang.reflect.Modifier;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.Callable;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.Future;
-import java.util.concurrent.TimeUnit;
-
-@SuppressWarnings("unchecked")
-public class MergeableClusterInvoker<T> implements Invoker<T> {
-
-    private static final Logger log = LoggerFactory.getLogger(MergeableClusterInvoker.class);
-    private final Directory<T> directory;
-    private ExecutorService executor = Executors.newCachedThreadPool(new NamedThreadFactory("mergeable-cluster-executor", true));
-
-    public MergeableClusterInvoker(Directory<T> directory) {
-        this.directory = directory;
-    }
-
-    @Override
-    @SuppressWarnings("rawtypes")
-    public Result invoke(final Invocation invocation) throws RpcException {
-        List<Invoker<T>> invokers = directory.list(invocation);
-
-        String merger = getUrl().getMethodParameter(invocation.getMethodName(), Constants.MERGER_KEY);
-        if (ConfigUtils.isEmpty(merger)) { // If a method doesn't have a merger, only invoke one Group
-            for (final Invoker<T> invoker : invokers) {
-                if (invoker.isAvailable()) {
-                    return invoker.invoke(invocation);
-                }
-            }
-            return invokers.iterator().next().invoke(invocation);
-        }
-
-        Class<?> returnType;
-        try {
-            returnType = getInterface().getMethod(
-                    invocation.getMethodName(), invocation.getParameterTypes()).getReturnType();
-        } catch (NoSuchMethodException e) {
-            returnType = null;
-        }
-
-        Map<String, Future<Result>> results = new HashMap<String, Future<Result>>();
-        for (final Invoker<T> invoker : invokers) {
-            Future<Result> future = executor.submit(new Callable<Result>() {
-                @Override
-                public Result call() throws Exception {
-                    return invoker.invoke(new RpcInvocation(invocation, invoker));
-                }
-            });
-            results.put(invoker.getUrl().getServiceKey(), future);
-        }
-
-        Object result = null;
-
-        List<Result> resultList = new ArrayList<Result>(results.size());
-
-        int timeout = getUrl().getMethodParameter(invocation.getMethodName(), Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT);
-        for (Map.Entry<String, Future<Result>> entry : results.entrySet()) {
-            Future<Result> future = entry.getValue();
-            try {
-                Result r = future.get(timeout, TimeUnit.MILLISECONDS);
-                if (r.hasException()) {
-                    log.error("Invoke " + getGroupDescFromServiceKey(entry.getKey()) + 
-                                    " failed: " + r.getException().getMessage(), 
-                            r.getException());
-                } else {
-                    resultList.add(r);
-                }
-            } catch (Exception e) {
-                throw new RpcException("Failed to invoke service " + entry.getKey() + ": " + e.getMessage(), e);
-            }
-        }
-
-        if (resultList.isEmpty()) {
-            return new RpcResult((Object) null);
-        } else if (resultList.size() == 1) {
-            return resultList.iterator().next();
-        }
-
-        if (returnType == void.class) {
-            return new RpcResult((Object) null);
-        }
-
-        if (merger.startsWith(".")) {
-            merger = merger.substring(1);
-            Method method;
-            try {
-                method = returnType.getMethod(merger, returnType);
-            } catch (NoSuchMethodException e) {
-                throw new RpcException("Can not merge result because missing method [ " + merger + " ] in class [ " + 
-                        returnType.getClass().getName() + " ]");
-            }
-            if (!Modifier.isPublic(method.getModifiers())) {
-                method.setAccessible(true);
-            }
-            result = resultList.remove(0).getValue();
-            try {
-                if (method.getReturnType() != void.class
-                        && method.getReturnType().isAssignableFrom(result.getClass())) {
-                    for (Result r : resultList) {
-                        result = method.invoke(result, r.getValue());
-                    }
-                } else {
-                    for (Result r : resultList) {
-                        method.invoke(result, r.getValue());
-                    }
-                }
-            } catch (Exception e) {
-                throw new RpcException("Can not merge result: " + e.getMessage(), e);
-            }
-        } else {
-            Merger resultMerger;
-            if (ConfigUtils.isDefault(merger)) {
-                resultMerger = MergerFactory.getMerger(returnType);
-            } else {
-                resultMerger = ExtensionLoader.getExtensionLoader(Merger.class).getExtension(merger);
-            }
-            if (resultMerger != null) {
-                List<Object> rets = new ArrayList<Object>(resultList.size());
-                for (Result r : resultList) {
-                    rets.add(r.getValue());
-                }
-                result = resultMerger.merge(
-                        rets.toArray((Object[]) Array.newInstance(returnType, 0)));
-            } else {
-                throw new RpcException("There is no merger to merge result.");
-            }
-        }
-        return new RpcResult(result);
-    }
-
-    @Override
-    public Class<T> getInterface() {
-        return directory.getInterface();
-    }
-
-    @Override
-    public URL getUrl() {
-        return directory.getUrl();
-    }
-
-    @Override
-    public boolean isAvailable() {
-        return directory.isAvailable();
-    }
-
-    @Override
-    public void destroy() {
-        directory.destroy();
-    }
-
-    private String getGroupDescFromServiceKey(String key) {
-        int index = key.indexOf("/");
-        if (index > 0) {
-            return "group [ " + key.substring(0, index) + " ]";
-        }
-        return key;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.common.utils.ConfigUtils;
+import org.apache.dubbo.common.utils.NamedThreadFactory;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.RpcResult;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.Merger;
+import org.apache.dubbo.rpc.cluster.merger.MergerFactory;
+
+import java.lang.reflect.Array;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
+import java.util.concurrent.TimeUnit;
+
+@SuppressWarnings("unchecked")
+public class MergeableClusterInvoker<T> implements Invoker<T> {
+
+    private static final Logger log = LoggerFactory.getLogger(MergeableClusterInvoker.class);
+    private final Directory<T> directory;
+    private ExecutorService executor = Executors.newCachedThreadPool(new NamedThreadFactory("mergeable-cluster-executor", true));
+
+    public MergeableClusterInvoker(Directory<T> directory) {
+        this.directory = directory;
+    }
+
+    @Override
+    @SuppressWarnings("rawtypes")
+    public Result invoke(final Invocation invocation) throws RpcException {
+        List<Invoker<T>> invokers = directory.list(invocation);
+
+        String merger = getUrl().getMethodParameter(invocation.getMethodName(), Constants.MERGER_KEY);
+        if (ConfigUtils.isEmpty(merger)) { // If a method doesn't have a merger, only invoke one Group
+            for (final Invoker<T> invoker : invokers) {
+                if (invoker.isAvailable()) {
+                    return invoker.invoke(invocation);
+                }
+            }
+            return invokers.iterator().next().invoke(invocation);
+        }
+
+        Class<?> returnType;
+        try {
+            returnType = getInterface().getMethod(
+                    invocation.getMethodName(), invocation.getParameterTypes()).getReturnType();
+        } catch (NoSuchMethodException e) {
+            returnType = null;
+        }
+
+        Map<String, Future<Result>> results = new HashMap<String, Future<Result>>();
+        for (final Invoker<T> invoker : invokers) {
+            Future<Result> future = executor.submit(new Callable<Result>() {
+                @Override
+                public Result call() throws Exception {
+                    return invoker.invoke(new RpcInvocation(invocation, invoker));
+                }
+            });
+            results.put(invoker.getUrl().getServiceKey(), future);
+        }
+
+        Object result = null;
+
+        List<Result> resultList = new ArrayList<Result>(results.size());
+
+        int timeout = getUrl().getMethodParameter(invocation.getMethodName(), Constants.TIMEOUT_KEY, Constants.DEFAULT_TIMEOUT);
+        for (Map.Entry<String, Future<Result>> entry : results.entrySet()) {
+            Future<Result> future = entry.getValue();
+            try {
+                Result r = future.get(timeout, TimeUnit.MILLISECONDS);
+                if (r.hasException()) {
+                    log.error("Invoke " + getGroupDescFromServiceKey(entry.getKey()) + 
+                                    " failed: " + r.getException().getMessage(), 
+                            r.getException());
+                } else {
+                    resultList.add(r);
+                }
+            } catch (Exception e) {
+                throw new RpcException("Failed to invoke service " + entry.getKey() + ": " + e.getMessage(), e);
+            }
+        }
+
+        if (resultList.isEmpty()) {
+            return new RpcResult((Object) null);
+        } else if (resultList.size() == 1) {
+            return resultList.iterator().next();
+        }
+
+        if (returnType == void.class) {
+            return new RpcResult((Object) null);
+        }
+
+        if (merger.startsWith(".")) {
+            merger = merger.substring(1);
+            Method method;
+            try {
+                method = returnType.getMethod(merger, returnType);
+            } catch (NoSuchMethodException e) {
+                throw new RpcException("Can not merge result because missing method [ " + merger + " ] in class [ " + 
+                        returnType.getClass().getName() + " ]");
+            }
+            if (!Modifier.isPublic(method.getModifiers())) {
+                method.setAccessible(true);
+            }
+            result = resultList.remove(0).getValue();
+            try {
+                if (method.getReturnType() != void.class
+                        && method.getReturnType().isAssignableFrom(result.getClass())) {
+                    for (Result r : resultList) {
+                        result = method.invoke(result, r.getValue());
+                    }
+                } else {
+                    for (Result r : resultList) {
+                        method.invoke(result, r.getValue());
+                    }
+                }
+            } catch (Exception e) {
+                throw new RpcException("Can not merge result: " + e.getMessage(), e);
+            }
+        } else {
+            Merger resultMerger;
+            if (ConfigUtils.isDefault(merger)) {
+                resultMerger = MergerFactory.getMerger(returnType);
+            } else {
+                resultMerger = ExtensionLoader.getExtensionLoader(Merger.class).getExtension(merger);
+            }
+            if (resultMerger != null) {
+                List<Object> rets = new ArrayList<Object>(resultList.size());
+                for (Result r : resultList) {
+                    rets.add(r.getValue());
+                }
+                result = resultMerger.merge(
+                        rets.toArray((Object[]) Array.newInstance(returnType, 0)));
+            } else {
+                throw new RpcException("There is no merger to merge result.");
+            }
+        }
+        return new RpcResult(result);
+    }
+
+    @Override
+    public Class<T> getInterface() {
+        return directory.getInterface();
+    }
+
+    @Override
+    public URL getUrl() {
+        return directory.getUrl();
+    }
+
+    @Override
+    public boolean isAvailable() {
+        return directory.isAvailable();
+    }
+
+    @Override
+    public void destroy() {
+        directory.destroy();
+    }
+
+    private String getGroupDescFromServiceKey(String key) {
+        int index = key.indexOf("/");
+        if (index > 0) {
+            return "group [ " + key.substring(0, index) + " ]";
+        }
+        return key;
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/StickyTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/StickyTest.java
index ded3ad6af6..8c073cb512 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/StickyTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/StickyTest.java
@@ -1,161 +1,161 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster;
-
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.RpcResult;
-import org.apache.dubbo.rpc.cluster.support.AbstractClusterInvoker;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-@SuppressWarnings("unchecked")
-public class StickyTest {
-
-    private List<Invoker<StickyTest>> invokers = new ArrayList<Invoker<StickyTest>>();
-
-
-    private Invoker<StickyTest> invoker1 = mock(Invoker.class);
-    private  Invoker<StickyTest> invoker2 = mock(Invoker.class);
-    private RpcInvocation invocation;
-    private Directory<StickyTest> dic;
-    private Result result = new RpcResult();
-    private StickyClusterInvoker<StickyTest> clusterinvoker = null;
-    private URL url = URL.valueOf("test://test:11/test?"
-                    + "&loadbalance=roundrobin"
-                    + "&" + Constants.CLUSTER_STICKY_KEY + "=true"
-    );
-    private int runs = 1;
-
-    @Before
-    public void setUp() throws Exception {
-        dic = mock(Directory.class);
-        invocation = new RpcInvocation();
-
-        given(dic.getUrl()).willReturn(url);
-        given(dic.list(invocation)).willReturn(invokers);
-        given(dic.getInterface()).willReturn(StickyTest.class);
-
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-
-        clusterinvoker = new StickyClusterInvoker<StickyTest>(dic);
-    }
-
-    @Test
-    public void testStickyNoCheck() {
-        int count = testSticky(null, false);
-        System.out.println(count);
-        Assert.assertTrue(count > 0 && count <= runs);
-    }
-
-    @Test
-    public void testStickyForceCheck() {
-        int count = testSticky(null, true);
-        Assert.assertTrue(count == 0 || count == runs);
-    }
-
-    @Test
-    public void testMethodStickyNoCheck() {
-        int count = testSticky("method1", false);
-        System.out.println(count);
-        Assert.assertTrue(count > 0 && count <= runs);
-    }
-
-    @Test
-    public void testMethodStickyForceCheck() {
-        int count = testSticky("method1", true);
-        Assert.assertTrue(count == 0 || count == runs);
-    }
-
-    @Test
-    public void testMethodsSticky() {
-        for (int i = 0; i < 100; i++) {//Two different methods should always use the same invoker every time.
-            int count1 = testSticky("method1", true);
-            int count2 = testSticky("method2", true);
-            Assert.assertTrue(count1 == count2);
-        }
-    }
-
-    public int testSticky(String methodName, boolean check) {
-        if (methodName == null) {
-            url = url.addParameter(Constants.CLUSTER_STICKY_KEY, String.valueOf(check));
-        } else {
-            url = url.addParameter(methodName + "." + Constants.CLUSTER_STICKY_KEY, String.valueOf(check));
-        }
-
-        given(invoker1.invoke(invocation)).willReturn(result);
-        given(invoker1.isAvailable()).willReturn(true);
-        given(invoker1.getUrl()).willReturn(url);
-        given(invoker1.getInterface()).willReturn(StickyTest.class);
-
-        given(invoker2.invoke(invocation)).willReturn(result);
-        given(invoker2.isAvailable()).willReturn(true);
-        given(invoker2.getUrl()).willReturn(url);
-        given(invoker2.getInterface()).willReturn(StickyTest.class);
-
-        invocation.setMethodName(methodName);
-
-        int count = 0;
-        for (int i = 0; i < runs; i++) {
-            Assert.assertEquals(null, clusterinvoker.invoke(invocation));
-            if (invoker1 == clusterinvoker.getSelectedInvoker()) {
-                count++;
-            }
-        }
-        return count;
-    }
-
-
-    static class StickyClusterInvoker<T> extends AbstractClusterInvoker<T> {
-        private Invoker<T> selectedInvoker;
-
-        public StickyClusterInvoker(Directory<T> directory) {
-            super(directory);
-        }
-
-        public StickyClusterInvoker(Directory<T> directory, URL url) {
-            super(directory, url);
-        }
-
-        @Override
-        protected Result doInvoke(Invocation invocation, List<Invoker<T>> invokers,
-                                  LoadBalance loadbalance) throws RpcException {
-            Invoker<T> invoker = select(loadbalance, invocation, invokers, null);
-            selectedInvoker = invoker;
-            return null;
-        }
-
-        public Invoker<T> getSelectedInvoker() {
-            return selectedInvoker;
-        }
-    }
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster;
+
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.RpcResult;
+import org.apache.dubbo.rpc.cluster.support.AbstractClusterInvoker;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+@SuppressWarnings("unchecked")
+public class StickyTest {
+
+    private List<Invoker<StickyTest>> invokers = new ArrayList<Invoker<StickyTest>>();
+
+
+    private Invoker<StickyTest> invoker1 = mock(Invoker.class);
+    private  Invoker<StickyTest> invoker2 = mock(Invoker.class);
+    private RpcInvocation invocation;
+    private Directory<StickyTest> dic;
+    private Result result = new RpcResult();
+    private StickyClusterInvoker<StickyTest> clusterinvoker = null;
+    private URL url = URL.valueOf("test://test:11/test?"
+                    + "&loadbalance=roundrobin"
+                    + "&" + Constants.CLUSTER_STICKY_KEY + "=true"
+    );
+    private int runs = 1;
+
+    @Before
+    public void setUp() throws Exception {
+        dic = mock(Directory.class);
+        invocation = new RpcInvocation();
+
+        given(dic.getUrl()).willReturn(url);
+        given(dic.list(invocation)).willReturn(invokers);
+        given(dic.getInterface()).willReturn(StickyTest.class);
+
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+
+        clusterinvoker = new StickyClusterInvoker<StickyTest>(dic);
+    }
+
+    @Test
+    public void testStickyNoCheck() {
+        int count = testSticky(null, false);
+        System.out.println(count);
+        Assert.assertTrue(count > 0 && count <= runs);
+    }
+
+    @Test
+    public void testStickyForceCheck() {
+        int count = testSticky(null, true);
+        Assert.assertTrue(count == 0 || count == runs);
+    }
+
+    @Test
+    public void testMethodStickyNoCheck() {
+        int count = testSticky("method1", false);
+        System.out.println(count);
+        Assert.assertTrue(count > 0 && count <= runs);
+    }
+
+    @Test
+    public void testMethodStickyForceCheck() {
+        int count = testSticky("method1", true);
+        Assert.assertTrue(count == 0 || count == runs);
+    }
+
+    @Test
+    public void testMethodsSticky() {
+        for (int i = 0; i < 100; i++) {//Two different methods should always use the same invoker every time.
+            int count1 = testSticky("method1", true);
+            int count2 = testSticky("method2", true);
+            Assert.assertTrue(count1 == count2);
+        }
+    }
+
+    public int testSticky(String methodName, boolean check) {
+        if (methodName == null) {
+            url = url.addParameter(Constants.CLUSTER_STICKY_KEY, String.valueOf(check));
+        } else {
+            url = url.addParameter(methodName + "." + Constants.CLUSTER_STICKY_KEY, String.valueOf(check));
+        }
+
+        given(invoker1.invoke(invocation)).willReturn(result);
+        given(invoker1.isAvailable()).willReturn(true);
+        given(invoker1.getUrl()).willReturn(url);
+        given(invoker1.getInterface()).willReturn(StickyTest.class);
+
+        given(invoker2.invoke(invocation)).willReturn(result);
+        given(invoker2.isAvailable()).willReturn(true);
+        given(invoker2.getUrl()).willReturn(url);
+        given(invoker2.getInterface()).willReturn(StickyTest.class);
+
+        invocation.setMethodName(methodName);
+
+        int count = 0;
+        for (int i = 0; i < runs; i++) {
+            Assert.assertEquals(null, clusterinvoker.invoke(invocation));
+            if (invoker1 == clusterinvoker.getSelectedInvoker()) {
+                count++;
+            }
+        }
+        return count;
+    }
+
+
+    static class StickyClusterInvoker<T> extends AbstractClusterInvoker<T> {
+        private Invoker<T> selectedInvoker;
+
+        public StickyClusterInvoker(Directory<T> directory) {
+            super(directory);
+        }
+
+        public StickyClusterInvoker(Directory<T> directory, URL url) {
+            super(directory, url);
+        }
+
+        @Override
+        protected Result doInvoke(Invocation invocation, List<Invoker<T>> invokers,
+                                  LoadBalance loadbalance) throws RpcException {
+            Invoker<T> invoker = select(loadbalance, invocation, invokers, null);
+            selectedInvoker = invoker;
+            return null;
+        }
+
+        public Invoker<T> getSelectedInvoker() {
+            return selectedInvoker;
+        }
+    }
 }
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/configurator/consts/UrlConstant.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/configurator/consts/UrlConstant.java
index 193f7ac364..1bf9a37b47 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/configurator/consts/UrlConstant.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/configurator/consts/UrlConstant.java
@@ -1,31 +1,31 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.configurator.consts;
-
-/**
- * test case url constant
- */
-public class UrlConstant {
-    public static final String URL_CONSUMER = "dubbo://10.20.153.10:20880/com.foo.BarService?application=foo&side=consumer";
-    public static final String URL_ONE = "dubbo://10.20.153.10:20880/com.foo.BarService?application=foo&timeout=1000&side=consumer";
-    public static final String APPLICATION_BAR_SIDE_CONSUMER_11 = "dubbo://10.20.153.11:20880/com.foo.BarService?application=bar&side=consumer";
-    public static final String TIMEOUT_1000_SIDE_CONSUMER_11 = "dubbo://10.20.153.11:20880/com.foo.BarService?application=bar&timeout=1000&side=consumer";
-    public static final String SERVICE_TIMEOUT_200 = "override://10.20.153.10/com.foo.BarService?timeout=200";
-    public static final String APPLICATION_BAR_SIDE_CONSUMER_10 = "dubbo://10.20.153.10:20880/com.foo.BarService?application=bar&side=consumer";
-    public static final String TIMEOUT_1000_SIDE_CONSUMER_10 = "dubbo://10.20.153.10:20880/com.foo.BarService?application=bar&timeout=1000&side=consumer";
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.configurator.consts;
+
+/**
+ * test case url constant
+ */
+public class UrlConstant {
+    public static final String URL_CONSUMER = "dubbo://10.20.153.10:20880/com.foo.BarService?application=foo&side=consumer";
+    public static final String URL_ONE = "dubbo://10.20.153.10:20880/com.foo.BarService?application=foo&timeout=1000&side=consumer";
+    public static final String APPLICATION_BAR_SIDE_CONSUMER_11 = "dubbo://10.20.153.11:20880/com.foo.BarService?application=bar&side=consumer";
+    public static final String TIMEOUT_1000_SIDE_CONSUMER_11 = "dubbo://10.20.153.11:20880/com.foo.BarService?application=bar&timeout=1000&side=consumer";
+    public static final String SERVICE_TIMEOUT_200 = "override://10.20.153.10/com.foo.BarService?timeout=200";
+    public static final String APPLICATION_BAR_SIDE_CONSUMER_10 = "dubbo://10.20.153.10:20880/com.foo.BarService?application=bar&side=consumer";
+    public static final String TIMEOUT_1000_SIDE_CONSUMER_10 = "dubbo://10.20.153.10:20880/com.foo.BarService?application=bar&timeout=1000&side=consumer";
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/MockDirInvocation.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/MockDirInvocation.java
index 279160e716..e6052e8080 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/MockDirInvocation.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/MockDirInvocation.java
@@ -1,66 +1,66 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.directory;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * MockInvocation.java
- */
-public class MockDirInvocation implements Invocation {
-
-    public String getMethodName() {
-        return "echo";
-    }
-
-    public Class<?>[] getParameterTypes() {
-        return new Class[]{String.class};
-    }
-
-    public Object[] getArguments() {
-        return new Object[]{"aa"};
-    }
-
-    public Map<String, String> getAttachments() {
-        Map<String, String> attachments = new HashMap<String, String>();
-        attachments.put(Constants.PATH_KEY, "dubbo");
-        attachments.put(Constants.GROUP_KEY, "dubbo");
-        attachments.put(Constants.VERSION_KEY, "1.0.0");
-        attachments.put(Constants.DUBBO_VERSION_KEY, "1.0.0");
-        attachments.put(Constants.TOKEN_KEY, "sfag");
-        attachments.put(Constants.TIMEOUT_KEY, "1000");
-        return attachments;
-    }
-
-    public Invoker<?> getInvoker() {
-        return null;
-    }
-
-    public String getAttachment(String key) {
-        return getAttachments().get(key);
-    }
-
-    public String getAttachment(String key, String defaultValue) {
-        return getAttachments().get(key);
-    }
-
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.directory;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * MockInvocation.java
+ */
+public class MockDirInvocation implements Invocation {
+
+    public String getMethodName() {
+        return "echo";
+    }
+
+    public Class<?>[] getParameterTypes() {
+        return new Class[]{String.class};
+    }
+
+    public Object[] getArguments() {
+        return new Object[]{"aa"};
+    }
+
+    public Map<String, String> getAttachments() {
+        Map<String, String> attachments = new HashMap<String, String>();
+        attachments.put(Constants.PATH_KEY, "dubbo");
+        attachments.put(Constants.GROUP_KEY, "dubbo");
+        attachments.put(Constants.VERSION_KEY, "1.0.0");
+        attachments.put(Constants.DUBBO_VERSION_KEY, "1.0.0");
+        attachments.put(Constants.TOKEN_KEY, "sfag");
+        attachments.put(Constants.TIMEOUT_KEY, "1000");
+        return attachments;
+    }
+
+    public Invoker<?> getInvoker() {
+        return null;
+    }
+
+    public String getAttachment(String key) {
+        return getAttachments().get(key);
+    }
+
+    public String getAttachment(String key, String defaultValue) {
+        return getAttachments().get(key);
+    }
+
 }
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/StaticDirectoryTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/StaticDirectoryTest.java
index 0bf0562fd7..553bb551b9 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/StaticDirectoryTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/directory/StaticDirectoryTest.java
@@ -1,65 +1,65 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.directory;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.utils.NetUtils;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.router.MockInvoker;
-import org.apache.dubbo.rpc.cluster.router.condition.ConditionRouterFactory;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * StaticDirectory Test
- */
-public class StaticDirectoryTest {
-    private URL SCRIPT_URL = URL.valueOf("condition://0.0.0.0/com.foo.BarService");
-
-    private URL getRouteUrl(String rule) {
-        return SCRIPT_URL.addParameterAndEncoded(Constants.RULE_KEY, rule);
-    }
-
-    @Test
-    public void testStaticDirectory() {
-        Router router = new ConditionRouterFactory().getRouter(getRouteUrl(" => " + " host = " + NetUtils.getLocalHost()));
-        List<Router> routers = new ArrayList<Router>();
-        routers.add(router);
-        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
-        Invoker<String> invoker1 = new MockInvoker<String>(URL.valueOf("dubbo://10.20.3.3:20880/com.foo.BarService"));
-        Invoker<String> invoker2 = new MockInvoker<String>(URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/com.foo.BarService"));
-        Invoker<String> invoker3 = new MockInvoker<String>(URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/com.foo.BarService"));
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-        invokers.add(invoker3);
-        List<Invoker<String>> filteredInvokers = router.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
-        StaticDirectory staticDirectory = new StaticDirectory(filteredInvokers);
-        Boolean isAvailable = staticDirectory.isAvailable();
-        Assert.assertTrue(!isAvailable);
-        List<Invoker> newInvokers = staticDirectory.list(new MockDirInvocation());
-        Assert.assertTrue(newInvokers.size() > 0);
-        staticDirectory.destroy();
-        Assert.assertTrue(newInvokers.size() == 0);
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.directory;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.utils.NetUtils;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.router.MockInvoker;
+import org.apache.dubbo.rpc.cluster.router.condition.ConditionRouterFactory;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * StaticDirectory Test
+ */
+public class StaticDirectoryTest {
+    private URL SCRIPT_URL = URL.valueOf("condition://0.0.0.0/com.foo.BarService");
+
+    private URL getRouteUrl(String rule) {
+        return SCRIPT_URL.addParameterAndEncoded(Constants.RULE_KEY, rule);
+    }
+
+    @Test
+    public void testStaticDirectory() {
+        Router router = new ConditionRouterFactory().getRouter(getRouteUrl(" => " + " host = " + NetUtils.getLocalHost()));
+        List<Router> routers = new ArrayList<Router>();
+        routers.add(router);
+        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
+        Invoker<String> invoker1 = new MockInvoker<String>(URL.valueOf("dubbo://10.20.3.3:20880/com.foo.BarService"));
+        Invoker<String> invoker2 = new MockInvoker<String>(URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/com.foo.BarService"));
+        Invoker<String> invoker3 = new MockInvoker<String>(URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/com.foo.BarService"));
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+        invokers.add(invoker3);
+        List<Invoker<String>> filteredInvokers = router.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
+        StaticDirectory staticDirectory = new StaticDirectory(filteredInvokers);
+        Boolean isAvailable = staticDirectory.isAvailable();
+        Assert.assertTrue(!isAvailable);
+        List<Invoker> newInvokers = staticDirectory.list(new MockDirInvocation());
+        Assert.assertTrue(newInvokers.size() > 0);
+        staticDirectory.destroy();
+        Assert.assertTrue(newInvokers.size() == 0);
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/ConsistentHashLoadBalanceTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/ConsistentHashLoadBalanceTest.java
index 7281fdbdeb..7c73822087 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/ConsistentHashLoadBalanceTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/ConsistentHashLoadBalanceTest.java
@@ -1,40 +1,40 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.rpc.Invoker;
-
-import org.junit.Assert;
-import org.junit.Ignore;
-import org.junit.Test;
-
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicLong;
-
-public class ConsistentHashLoadBalanceTest extends LoadBalanceBaseTest {
-    @Ignore
-    @Test
-    public void testConsistentHashLoadBalance() {
-        int runs = 10000;
-        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, ConsistentHashLoadBalance.NAME);
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-            Assert.assertTrue("abs diff should < avg", Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.rpc.Invoker;
+
+import org.junit.Assert;
+import org.junit.Ignore;
+import org.junit.Test;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicLong;
+
+public class ConsistentHashLoadBalanceTest extends LoadBalanceBaseTest {
+    @Ignore
+    @Test
+    public void testConsistentHashLoadBalance() {
+        int runs = 10000;
+        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, ConsistentHashLoadBalance.NAME);
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+            Assert.assertTrue("abs diff should < avg", Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
+        }
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LeastActiveBalanceTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LeastActiveBalanceTest.java
index fd151bcdb2..151e8de112 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LeastActiveBalanceTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LeastActiveBalanceTest.java
@@ -1,42 +1,42 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License")); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.rpc.Invoker;
-
-import org.junit.Assert;
-import org.junit.Ignore;
-import org.junit.Test;
-
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicLong;
-
-public class LeastActiveBalanceTest extends LoadBalanceBaseTest {
-    @Ignore
-    @Test
-    public void testLeastActiveLoadBalance_select() {
-        int runs = 10000;
-        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, LeastActiveLoadBalance.NAME);
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-            //            System.out.println(count);
-            Assert.assertTrue("abs diff shoud < avg",
-                    Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License")); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.rpc.Invoker;
+
+import org.junit.Assert;
+import org.junit.Ignore;
+import org.junit.Test;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicLong;
+
+public class LeastActiveBalanceTest extends LoadBalanceBaseTest {
+    @Ignore
+    @Test
+    public void testLeastActiveLoadBalance_select() {
+        int runs = 10000;
+        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, LeastActiveLoadBalance.NAME);
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+            //            System.out.println(count);
+            Assert.assertTrue("abs diff shoud < avg",
+                    Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
+        }
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LoadBalanceBaseTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LoadBalanceBaseTest.java
index 877631f56e..8dfd5c58ad 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LoadBalanceBaseTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/LoadBalanceBaseTest.java
@@ -1,148 +1,148 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License")); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.cluster.LoadBalance;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.atomic.AtomicLong;
-
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-/**
- * RoundRobinLoadBalanceTest
- */
-@SuppressWarnings({"unchecked", "rawtypes"})
-public class LoadBalanceBaseTest {
-    Invocation invocation;
-    List<Invoker<LoadBalanceBaseTest>> invokers = new ArrayList<Invoker<LoadBalanceBaseTest>>();
-    Invoker<LoadBalanceBaseTest> invoker1;
-    Invoker<LoadBalanceBaseTest> invoker2;
-    Invoker<LoadBalanceBaseTest> invoker3;
-    Invoker<LoadBalanceBaseTest> invoker4;
-    Invoker<LoadBalanceBaseTest> invoker5;
-
-    /**
-     * @throws java.lang.Exception
-     */
-    @BeforeClass
-    public static void setUpBeforeClass() throws Exception {
-    }
-
-    /**
-     * @throws java.lang.Exception
-     */
-    @Before
-    public void setUp() throws Exception {
-
-        invocation = mock(Invocation.class);
-        given(invocation.getMethodName()).willReturn("method1");
-
-        invoker1 = mock(Invoker.class);
-        invoker2 = mock(Invoker.class);
-        invoker3 = mock(Invoker.class);
-        invoker4 = mock(Invoker.class);
-        invoker5 = mock(Invoker.class);
-
-        URL url1 = URL.valueOf("test://127.0.0.1:1/DemoService");
-        URL url2 = URL.valueOf("test://127.0.0.1:2/DemoService");
-        URL url3 = URL.valueOf("test://127.0.0.1:3/DemoService");
-        URL url4 = URL.valueOf("test://127.0.0.1:4/DemoService");
-        URL url5 = URL.valueOf("test://127.0.0.1:5/DemoService");
-
-        given(invoker1.isAvailable()).willReturn(true);
-        given(invoker1.getInterface()).willReturn(LoadBalanceBaseTest.class);
-        given(invoker1.getUrl()).willReturn(url1);
-
-        given(invoker2.isAvailable()).willReturn(true);
-        given(invoker2.getInterface()).willReturn(LoadBalanceBaseTest.class);
-        given(invoker2.getUrl()).willReturn(url2);
-
-        given(invoker3.isAvailable()).willReturn(true);
-        given(invoker3.getInterface()).willReturn(LoadBalanceBaseTest.class);
-        given(invoker3.getUrl()).willReturn(url3);
-
-        given(invoker4.isAvailable()).willReturn(true);
-        given(invoker4.getInterface()).willReturn(LoadBalanceBaseTest.class);
-        given(invoker4.getUrl()).willReturn(url4);
-
-        given(invoker5.isAvailable()).willReturn(true);
-        given(invoker5.getInterface()).willReturn(LoadBalanceBaseTest.class);
-        given(invoker5.getUrl()).willReturn(url5);
-
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-        invokers.add(invoker3);
-        invokers.add(invoker4);
-        invokers.add(invoker5);
-    }
-
-    public Map<Invoker, AtomicLong> getInvokeCounter(int runs, String loadbalanceName) {
-        Map<Invoker, AtomicLong> counter = new ConcurrentHashMap<Invoker, AtomicLong>();
-        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(loadbalanceName);
-        for (Invoker invoker : invokers) {
-            counter.put(invoker, new AtomicLong(0));
-        }
-        for (int i = 0; i < runs; i++) {
-            Invoker sinvoker = lb.select(invokers, invokers.get(0).getUrl(), invocation);
-            counter.get(sinvoker).incrementAndGet();
-        }
-        return counter;
-    }
-
-    @Test
-    public void testLoadBalanceWarmup() {
-        Assert.assertEquals(1, calculateDefaultWarmupWeight(0));
-        Assert.assertEquals(1, calculateDefaultWarmupWeight(13));
-        Assert.assertEquals(1, calculateDefaultWarmupWeight(6 * 1000));
-        Assert.assertEquals(2, calculateDefaultWarmupWeight(12 * 1000));
-        Assert.assertEquals(10, calculateDefaultWarmupWeight(60 * 1000));
-        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000));
-        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000 + 23));
-        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000 + 5999));
-        Assert.assertEquals(51, calculateDefaultWarmupWeight(5 * 60 * 1000 + 6000));
-        Assert.assertEquals(90, calculateDefaultWarmupWeight(9 * 60 * 1000));
-        Assert.assertEquals(98, calculateDefaultWarmupWeight(10 * 60 * 1000 - 12 * 1000));
-        Assert.assertEquals(99, calculateDefaultWarmupWeight(10 * 60 * 1000 - 6 * 1000));
-        Assert.assertEquals(100, calculateDefaultWarmupWeight(10 * 60 * 1000));
-        Assert.assertEquals(100, calculateDefaultWarmupWeight(20 * 60 * 1000));
-    }
-
-    /**
-     * handle default data
-     *
-     * @return
-     */
-    private static int calculateDefaultWarmupWeight(int uptime) {
-        return AbstractLoadBalance.calculateWarmupWeight(uptime, Constants.DEFAULT_WARMUP, Constants.DEFAULT_WEIGHT);
-    }
-
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License")); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.cluster.LoadBalance;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.atomic.AtomicLong;
+
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+/**
+ * RoundRobinLoadBalanceTest
+ */
+@SuppressWarnings({"unchecked", "rawtypes"})
+public class LoadBalanceBaseTest {
+    Invocation invocation;
+    List<Invoker<LoadBalanceBaseTest>> invokers = new ArrayList<Invoker<LoadBalanceBaseTest>>();
+    Invoker<LoadBalanceBaseTest> invoker1;
+    Invoker<LoadBalanceBaseTest> invoker2;
+    Invoker<LoadBalanceBaseTest> invoker3;
+    Invoker<LoadBalanceBaseTest> invoker4;
+    Invoker<LoadBalanceBaseTest> invoker5;
+
+    /**
+     * @throws java.lang.Exception
+     */
+    @BeforeClass
+    public static void setUpBeforeClass() throws Exception {
+    }
+
+    /**
+     * @throws java.lang.Exception
+     */
+    @Before
+    public void setUp() throws Exception {
+
+        invocation = mock(Invocation.class);
+        given(invocation.getMethodName()).willReturn("method1");
+
+        invoker1 = mock(Invoker.class);
+        invoker2 = mock(Invoker.class);
+        invoker3 = mock(Invoker.class);
+        invoker4 = mock(Invoker.class);
+        invoker5 = mock(Invoker.class);
+
+        URL url1 = URL.valueOf("test://127.0.0.1:1/DemoService");
+        URL url2 = URL.valueOf("test://127.0.0.1:2/DemoService");
+        URL url3 = URL.valueOf("test://127.0.0.1:3/DemoService");
+        URL url4 = URL.valueOf("test://127.0.0.1:4/DemoService");
+        URL url5 = URL.valueOf("test://127.0.0.1:5/DemoService");
+
+        given(invoker1.isAvailable()).willReturn(true);
+        given(invoker1.getInterface()).willReturn(LoadBalanceBaseTest.class);
+        given(invoker1.getUrl()).willReturn(url1);
+
+        given(invoker2.isAvailable()).willReturn(true);
+        given(invoker2.getInterface()).willReturn(LoadBalanceBaseTest.class);
+        given(invoker2.getUrl()).willReturn(url2);
+
+        given(invoker3.isAvailable()).willReturn(true);
+        given(invoker3.getInterface()).willReturn(LoadBalanceBaseTest.class);
+        given(invoker3.getUrl()).willReturn(url3);
+
+        given(invoker4.isAvailable()).willReturn(true);
+        given(invoker4.getInterface()).willReturn(LoadBalanceBaseTest.class);
+        given(invoker4.getUrl()).willReturn(url4);
+
+        given(invoker5.isAvailable()).willReturn(true);
+        given(invoker5.getInterface()).willReturn(LoadBalanceBaseTest.class);
+        given(invoker5.getUrl()).willReturn(url5);
+
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+        invokers.add(invoker3);
+        invokers.add(invoker4);
+        invokers.add(invoker5);
+    }
+
+    public Map<Invoker, AtomicLong> getInvokeCounter(int runs, String loadbalanceName) {
+        Map<Invoker, AtomicLong> counter = new ConcurrentHashMap<Invoker, AtomicLong>();
+        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(loadbalanceName);
+        for (Invoker invoker : invokers) {
+            counter.put(invoker, new AtomicLong(0));
+        }
+        for (int i = 0; i < runs; i++) {
+            Invoker sinvoker = lb.select(invokers, invokers.get(0).getUrl(), invocation);
+            counter.get(sinvoker).incrementAndGet();
+        }
+        return counter;
+    }
+
+    @Test
+    public void testLoadBalanceWarmup() {
+        Assert.assertEquals(1, calculateDefaultWarmupWeight(0));
+        Assert.assertEquals(1, calculateDefaultWarmupWeight(13));
+        Assert.assertEquals(1, calculateDefaultWarmupWeight(6 * 1000));
+        Assert.assertEquals(2, calculateDefaultWarmupWeight(12 * 1000));
+        Assert.assertEquals(10, calculateDefaultWarmupWeight(60 * 1000));
+        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000));
+        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000 + 23));
+        Assert.assertEquals(50, calculateDefaultWarmupWeight(5 * 60 * 1000 + 5999));
+        Assert.assertEquals(51, calculateDefaultWarmupWeight(5 * 60 * 1000 + 6000));
+        Assert.assertEquals(90, calculateDefaultWarmupWeight(9 * 60 * 1000));
+        Assert.assertEquals(98, calculateDefaultWarmupWeight(10 * 60 * 1000 - 12 * 1000));
+        Assert.assertEquals(99, calculateDefaultWarmupWeight(10 * 60 * 1000 - 6 * 1000));
+        Assert.assertEquals(100, calculateDefaultWarmupWeight(10 * 60 * 1000));
+        Assert.assertEquals(100, calculateDefaultWarmupWeight(20 * 60 * 1000));
+    }
+
+    /**
+     * handle default data
+     *
+     * @return
+     */
+    private static int calculateDefaultWarmupWeight(int uptime) {
+        return AbstractLoadBalance.calculateWarmupWeight(uptime, Constants.DEFAULT_WARMUP, Constants.DEFAULT_WEIGHT);
+    }
+
 }
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalanceTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalanceTest.java
index 3f20291d3d..d3d2f71e99 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalanceTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RandomLoadBalanceTest.java
@@ -1,57 +1,57 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License")); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcStatus;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicLong;
-
-/**
- * RandomLoadBalance Test
- */
-public class RandomLoadBalanceTest extends LoadBalanceBaseTest {
-    @Test
-    public void testRandomLoadBalanceSelect() {
-        int runs = 1000;
-        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, RandomLoadBalance.NAME);
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-            Assert.assertTrue("abs diff should < avg", Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
-        }
-
-        for (int i = 0; i < 5; i++) {
-            for (int j = 0; j <= i; j++) {
-                RpcStatus.beginCount(invokers.get(i).getUrl(), invocation.getMethodName());
-            }
-        }
-        counter = getInvokeCounter(runs, LeastActiveLoadBalance.NAME);
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-        }
-        Assert.assertEquals(runs, counter.get(invoker1).intValue());
-        Assert.assertEquals(0, counter.get(invoker2).intValue());
-        Assert.assertEquals(0, counter.get(invoker3).intValue());
-        Assert.assertEquals(0, counter.get(invoker4).intValue());
-        Assert.assertEquals(0, counter.get(invoker5).intValue());
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License")); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcStatus;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicLong;
+
+/**
+ * RandomLoadBalance Test
+ */
+public class RandomLoadBalanceTest extends LoadBalanceBaseTest {
+    @Test
+    public void testRandomLoadBalanceSelect() {
+        int runs = 1000;
+        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, RandomLoadBalance.NAME);
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+            Assert.assertTrue("abs diff should < avg", Math.abs(count - runs / (0f + invokers.size())) < runs / (0f + invokers.size()));
+        }
+
+        for (int i = 0; i < 5; i++) {
+            for (int j = 0; j <= i; j++) {
+                RpcStatus.beginCount(invokers.get(i).getUrl(), invocation.getMethodName());
+            }
+        }
+        counter = getInvokeCounter(runs, LeastActiveLoadBalance.NAME);
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+        }
+        Assert.assertEquals(runs, counter.get(invoker1).intValue());
+        Assert.assertEquals(0, counter.get(invoker2).intValue());
+        Assert.assertEquals(0, counter.get(invoker3).intValue());
+        Assert.assertEquals(0, counter.get(invoker4).intValue());
+        Assert.assertEquals(0, counter.get(invoker5).intValue());
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RoundRobinLoadBalanceTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RoundRobinLoadBalanceTest.java
index f3ae351874..1dac01dea1 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RoundRobinLoadBalanceTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/loadbalance/RoundRobinLoadBalanceTest.java
@@ -1,37 +1,37 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.loadbalance;
-
-import org.apache.dubbo.rpc.Invoker;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicLong;
-
-public class RoundRobinLoadBalanceTest extends LoadBalanceBaseTest {
-    @Test
-    public void testRoundRobinLoadBalanceSelect() {
-        int runs = 10000;
-        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, RoundRobinLoadBalance.NAME);
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-            Assert.assertTrue("abs diff should < 1", Math.abs(count - runs / (0f + invokers.size())) < 1f);
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.loadbalance;
+
+import org.apache.dubbo.rpc.Invoker;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicLong;
+
+public class RoundRobinLoadBalanceTest extends LoadBalanceBaseTest {
+    @Test
+    public void testRoundRobinLoadBalanceSelect() {
+        int runs = 10000;
+        Map<Invoker, AtomicLong> counter = getInvokeCounter(runs, RoundRobinLoadBalance.NAME);
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+            Assert.assertTrue("abs diff should < 1", Math.abs(count - runs / (0f + invokers.size())) < 1f);
+        }
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/merger/ResultMergerTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/merger/ResultMergerTest.java
index f5044f305e..87e42240ee 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/merger/ResultMergerTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/merger/ResultMergerTest.java
@@ -1,281 +1,281 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.merger;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-import java.lang.reflect.Array;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-public class ResultMergerTest {
-    /**
-     * ArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testArrayMerger() throws Exception {
-        String[] stringArray1 = {"1", "2", "3"};
-        String[] stringArray2 = {"4", "5", "6"};
-        String[] stringArray3 = {};
-
-        Object result = ArrayMerger.INSTANCE.merge(stringArray1, stringArray2, stringArray3);
-        Assert.assertTrue(result.getClass().isArray());
-        Assert.assertEquals(6, Array.getLength(result));
-        Assert.assertTrue(String.class.isInstance(Array.get(result, 0)));
-        for (int i = 0; i < 6; i++) {
-            Assert.assertEquals(String.valueOf(i + 1), Array.get(result, i));
-        }
-
-        int[] intArray1 = {1, 2, 3};
-        int[] intArray2 = {4, 5, 6};
-        int[] intArray3 = {7};
-        result = MergerFactory.getMerger(int[].class).merge(intArray1, intArray2, intArray3);
-        Assert.assertTrue(result.getClass().isArray());
-        Assert.assertEquals(7, Array.getLength(result));
-        Assert.assertTrue(int.class == result.getClass().getComponentType());
-        for (int i = 0; i < 7; i++) {
-            Assert.assertEquals(i + 1, Array.get(result, i));
-        }
-
-    }
-
-    /**
-     * BooleanArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testBooleanArrayMerger() throws Exception {
-        boolean[] arrayOne = {true, false};
-        boolean[] arrayTwo = {false};
-        boolean[] result = MergerFactory.getMerger(boolean[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(3, result.length);
-        boolean[] mergedResult = {true, false, false};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertEquals(mergedResult[i], result[i]);
-        }
-    }
-
-    /**
-     * ByteArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testByteArrayMerger() throws Exception {
-        byte[] arrayOne = {1, 2};
-        byte[] arrayTwo = {1, 32};
-        byte[] result = MergerFactory.getMerger(byte[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        byte[] mergedResult = {1, 2, 1, 32};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertEquals(mergedResult[i], result[i]);
-        }
-    }
-
-    /**
-     * CharArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testCharArrayMerger() throws Exception {
-        char[] arrayOne = "hello".toCharArray();
-        char[] arrayTwo = "world".toCharArray();
-        char[] result = MergerFactory.getMerger(char[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(10, result.length);
-        char[] mergedResult = "helloworld".toCharArray();
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertEquals(mergedResult[i], result[i]);
-        }
-    }
-
-    /**
-     * DoubleArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testDoubleArrayMerger() throws Exception {
-        double[] arrayOne = {1.2d, 3.5d};
-        double[] arrayTwo = {2d, 34d};
-        double[] result = MergerFactory.getMerger(double[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        double[] mergedResult = {1.2d, 3.5d, 2d, 34d};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertTrue(mergedResult[i] == result[i]);
-        }
-    }
-
-    /**
-     * FloatArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testFloatArrayMerger() throws Exception {
-        float[] arrayOne = {1.2f, 3.5f};
-        float[] arrayTwo = {2f, 34f};
-        float[] result = MergerFactory.getMerger(float[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        double[] mergedResult = {1.2f, 3.5f, 2f, 34f};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertTrue(mergedResult[i] == result[i]);
-        }
-    }
-
-    /**
-     * IntArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testIntArrayMerger() throws Exception {
-        int[] arrayOne = {1, 2};
-        int[] arrayTwo = {2, 34};
-        int[] result = MergerFactory.getMerger(int[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        double[] mergedResult = {1, 2, 2, 34};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertTrue(mergedResult[i] == result[i]);
-        }
-    }
-
-    /**
-     * ListMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testListMerger() throws Exception {
-        List<Object> list1 = new ArrayList<Object>(){{
-            add(null);
-            add("1");
-            add("2"); 
-        }};
-        List<Object> list2 = new ArrayList<Object>(){{
-            add("3");
-            add("4");
-        }};
-
-        List result = MergerFactory.getMerger(List.class).merge(list1, list2);
-        Assert.assertEquals(5, result.size());
-        ArrayList<String> expected = new ArrayList<String>() {{
-            add(null);
-            add("1");
-            add("2");
-            add("3");
-            add("4");
-        }};
-        Assert.assertEquals(expected, result);
-    }
-
-    /**
-     * LongArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testMapArrayMerger() throws Exception {
-        Map<Object, Object> mapOne = new HashMap() {{
-            put("11", 222);
-            put("223", 11);
-        }};
-        Map<Object, Object> mapTwo = new HashMap() {{
-            put("3333", 3232);
-            put("444", 2323);
-        }};
-        Map<Object, Object> result = MergerFactory.getMerger(Map.class).merge(mapOne, mapTwo);
-        Assert.assertEquals(4, result.size());
-        Map<Object, Object> mergedResult = new HashMap() {{
-            put("11", 222);
-            put("223", 11);
-            put("3333", 3232);
-            put("444", 2323);
-        }};
-        Assert.assertEquals(mergedResult, result);
-    }
-
-    /**
-     * LongArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testLongArrayMerger() throws Exception {
-        long[] arrayOne = {1l, 2l};
-        long[] arrayTwo = {2l, 34l};
-        long[] result = MergerFactory.getMerger(long[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        double[] mergedResult = {1l, 2l, 2l, 34l};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertTrue(mergedResult[i] == result[i]);
-        }
-    }
-
-    /**
-     * SetMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testSetMerger() throws Exception {
-        Set<Object> set1 = new HashSet<Object>();
-        set1.add(null);
-        set1.add("1");
-        set1.add("2");
-        Set<Object> set2 = new HashSet<Object>();
-        set2.add("2");
-        set2.add("3");
-
-        Set result = MergerFactory.getMerger(Set.class).merge(set1, set2);
-
-        Assert.assertEquals(4, result.size());
-        Assert.assertEquals(new HashSet<String>() {
-            {
-                add(null);
-                add("1");
-                add("2");
-                add("3");
-            }
-        }, result);
-    }
-
-    /**
-     * ShortArrayMerger test
-     *
-     * @throws Exception
-     */
-    @Test
-    public void testShortArrayMerger() throws Exception {
-        short[] arrayOne = {1, 2};
-        short[] arrayTwo = {2, 34};
-        short[] result = MergerFactory.getMerger(short[].class).merge(arrayOne, arrayTwo);
-        Assert.assertEquals(4, result.length);
-        double[] mergedResult = {1, 2, 2, 34};
-        for (int i = 0; i < mergedResult.length; i++) {
-            Assert.assertTrue(mergedResult[i] == result[i]);
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.merger;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.lang.reflect.Array;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+public class ResultMergerTest {
+    /**
+     * ArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testArrayMerger() throws Exception {
+        String[] stringArray1 = {"1", "2", "3"};
+        String[] stringArray2 = {"4", "5", "6"};
+        String[] stringArray3 = {};
+
+        Object result = ArrayMerger.INSTANCE.merge(stringArray1, stringArray2, stringArray3);
+        Assert.assertTrue(result.getClass().isArray());
+        Assert.assertEquals(6, Array.getLength(result));
+        Assert.assertTrue(String.class.isInstance(Array.get(result, 0)));
+        for (int i = 0; i < 6; i++) {
+            Assert.assertEquals(String.valueOf(i + 1), Array.get(result, i));
+        }
+
+        int[] intArray1 = {1, 2, 3};
+        int[] intArray2 = {4, 5, 6};
+        int[] intArray3 = {7};
+        result = MergerFactory.getMerger(int[].class).merge(intArray1, intArray2, intArray3);
+        Assert.assertTrue(result.getClass().isArray());
+        Assert.assertEquals(7, Array.getLength(result));
+        Assert.assertTrue(int.class == result.getClass().getComponentType());
+        for (int i = 0; i < 7; i++) {
+            Assert.assertEquals(i + 1, Array.get(result, i));
+        }
+
+    }
+
+    /**
+     * BooleanArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testBooleanArrayMerger() throws Exception {
+        boolean[] arrayOne = {true, false};
+        boolean[] arrayTwo = {false};
+        boolean[] result = MergerFactory.getMerger(boolean[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(3, result.length);
+        boolean[] mergedResult = {true, false, false};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertEquals(mergedResult[i], result[i]);
+        }
+    }
+
+    /**
+     * ByteArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testByteArrayMerger() throws Exception {
+        byte[] arrayOne = {1, 2};
+        byte[] arrayTwo = {1, 32};
+        byte[] result = MergerFactory.getMerger(byte[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        byte[] mergedResult = {1, 2, 1, 32};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertEquals(mergedResult[i], result[i]);
+        }
+    }
+
+    /**
+     * CharArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testCharArrayMerger() throws Exception {
+        char[] arrayOne = "hello".toCharArray();
+        char[] arrayTwo = "world".toCharArray();
+        char[] result = MergerFactory.getMerger(char[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(10, result.length);
+        char[] mergedResult = "helloworld".toCharArray();
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertEquals(mergedResult[i], result[i]);
+        }
+    }
+
+    /**
+     * DoubleArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testDoubleArrayMerger() throws Exception {
+        double[] arrayOne = {1.2d, 3.5d};
+        double[] arrayTwo = {2d, 34d};
+        double[] result = MergerFactory.getMerger(double[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        double[] mergedResult = {1.2d, 3.5d, 2d, 34d};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertTrue(mergedResult[i] == result[i]);
+        }
+    }
+
+    /**
+     * FloatArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testFloatArrayMerger() throws Exception {
+        float[] arrayOne = {1.2f, 3.5f};
+        float[] arrayTwo = {2f, 34f};
+        float[] result = MergerFactory.getMerger(float[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        double[] mergedResult = {1.2f, 3.5f, 2f, 34f};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertTrue(mergedResult[i] == result[i]);
+        }
+    }
+
+    /**
+     * IntArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testIntArrayMerger() throws Exception {
+        int[] arrayOne = {1, 2};
+        int[] arrayTwo = {2, 34};
+        int[] result = MergerFactory.getMerger(int[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        double[] mergedResult = {1, 2, 2, 34};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertTrue(mergedResult[i] == result[i]);
+        }
+    }
+
+    /**
+     * ListMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testListMerger() throws Exception {
+        List<Object> list1 = new ArrayList<Object>(){{
+            add(null);
+            add("1");
+            add("2"); 
+        }};
+        List<Object> list2 = new ArrayList<Object>(){{
+            add("3");
+            add("4");
+        }};
+
+        List result = MergerFactory.getMerger(List.class).merge(list1, list2);
+        Assert.assertEquals(5, result.size());
+        ArrayList<String> expected = new ArrayList<String>() {{
+            add(null);
+            add("1");
+            add("2");
+            add("3");
+            add("4");
+        }};
+        Assert.assertEquals(expected, result);
+    }
+
+    /**
+     * LongArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testMapArrayMerger() throws Exception {
+        Map<Object, Object> mapOne = new HashMap() {{
+            put("11", 222);
+            put("223", 11);
+        }};
+        Map<Object, Object> mapTwo = new HashMap() {{
+            put("3333", 3232);
+            put("444", 2323);
+        }};
+        Map<Object, Object> result = MergerFactory.getMerger(Map.class).merge(mapOne, mapTwo);
+        Assert.assertEquals(4, result.size());
+        Map<Object, Object> mergedResult = new HashMap() {{
+            put("11", 222);
+            put("223", 11);
+            put("3333", 3232);
+            put("444", 2323);
+        }};
+        Assert.assertEquals(mergedResult, result);
+    }
+
+    /**
+     * LongArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testLongArrayMerger() throws Exception {
+        long[] arrayOne = {1l, 2l};
+        long[] arrayTwo = {2l, 34l};
+        long[] result = MergerFactory.getMerger(long[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        double[] mergedResult = {1l, 2l, 2l, 34l};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertTrue(mergedResult[i] == result[i]);
+        }
+    }
+
+    /**
+     * SetMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testSetMerger() throws Exception {
+        Set<Object> set1 = new HashSet<Object>();
+        set1.add(null);
+        set1.add("1");
+        set1.add("2");
+        Set<Object> set2 = new HashSet<Object>();
+        set2.add("2");
+        set2.add("3");
+
+        Set result = MergerFactory.getMerger(Set.class).merge(set1, set2);
+
+        Assert.assertEquals(4, result.size());
+        Assert.assertEquals(new HashSet<String>() {
+            {
+                add(null);
+                add("1");
+                add("2");
+                add("3");
+            }
+        }, result);
+    }
+
+    /**
+     * ShortArrayMerger test
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testShortArrayMerger() throws Exception {
+        short[] arrayOne = {1, 2};
+        short[] arrayTwo = {2, 34};
+        short[] result = MergerFactory.getMerger(short[].class).merge(arrayOne, arrayTwo);
+        Assert.assertEquals(4, result.length);
+        double[] mergedResult = {1, 2, 2, 34};
+        for (int i = 0; i < mergedResult.length; i++) {
+            Assert.assertTrue(mergedResult[i] == result[i]);
+        }
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/MockInvoker.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/MockInvoker.java
index c7db31fce0..00946a79ea 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/MockInvoker.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/MockInvoker.java
@@ -1,62 +1,62 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router;
-
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcException;
-
-public class MockInvoker<T> implements Invoker<T> {
-    private boolean available = false;
-    private URL url;
-
-    public MockInvoker() {
-    }
-
-    public MockInvoker(URL url) {
-        super();
-        this.url = url;
-    }
-
-    public MockInvoker(boolean available) {
-        this.available = available;
-    }
-
-    @Override
-    public Class<T> getInterface() {
-        return null;
-    }
-
-    public URL getUrl() {
-        return url;
-    }
-
-    @Override
-    public boolean isAvailable() {
-        return available;
-    }
-
-    public Result invoke(Invocation invocation) throws RpcException {
-        return null;
-    }
-
-    @Override
-    public void destroy() {
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router;
+
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcException;
+
+public class MockInvoker<T> implements Invoker<T> {
+    private boolean available = false;
+    private URL url;
+
+    public MockInvoker() {
+    }
+
+    public MockInvoker(URL url) {
+        super();
+        this.url = url;
+    }
+
+    public MockInvoker(boolean available) {
+        this.available = available;
+    }
+
+    @Override
+    public Class<T> getInterface() {
+        return null;
+    }
+
+    public URL getUrl() {
+        return url;
+    }
+
+    @Override
+    public boolean isAvailable() {
+        return available;
+    }
+
+    public Result invoke(Invocation invocation) throws RpcException {
+        return null;
+    }
+
+    @Override
+    public void destroy() {
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterEngineTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterEngineTest.java
index 941e80cdd1..47b8661da0 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterEngineTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/file/FileRouterEngineTest.java
@@ -1,188 +1,188 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.file;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.RpcResult;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.LoadBalance;
-import org.apache.dubbo.rpc.cluster.RouterFactory;
-import org.apache.dubbo.rpc.cluster.directory.StaticDirectory;
-import org.apache.dubbo.rpc.cluster.support.AbstractClusterInvoker;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import javax.script.ScriptEngineManager;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-@SuppressWarnings("unchecked")
-public class FileRouterEngineTest {
-    private static boolean isScriptUnsupported = new ScriptEngineManager().getEngineByName("javascript") == null;
-    List<Invoker<FileRouterEngineTest>> invokers = new ArrayList<Invoker<FileRouterEngineTest>>();
-    Invoker<FileRouterEngineTest> invoker1 = mock(Invoker.class);
-    Invoker<FileRouterEngineTest> invoker2 = mock(Invoker.class);
-    Invocation invocation;
-    Directory<FileRouterEngineTest> dic;
-    Result result = new RpcResult();
-    private RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getAdaptiveExtension();
-
-    @BeforeClass
-    public static void setUpBeforeClass() throws Exception {
-    }
-
-    @Before
-    public void setUp() throws Exception {
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-    }
-
-    @Test
-    public void testRouteNotAvailable() {
-        if (isScriptUnsupported) return;
-        URL url = initUrl("notAvailablerule.javascript");
-        initInvocation("method1");
-        initDic(url);
-        initInvokers(url, true, false);
-
-        MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
-                dic, url);
-        for (int i = 0; i < 100; i++) {
-            sinvoker.invoke(invocation);
-            Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
-            Assert.assertEquals(invoker2, invoker);
-        }
-    }
-
-    @Test
-    public void testRouteAvailable() {
-        if (isScriptUnsupported) return;
-        URL url = initUrl("availablerule.javascript");
-        initInvocation("method1");
-        initDic(url);
-        initInvokers(url);
-
-        MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
-                dic, url);
-        for (int i = 0; i < 100; i++) {
-            sinvoker.invoke(invocation);
-            Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
-            Assert.assertEquals(invoker1, invoker);
-        }
-    }
-
-    @Test
-    public void testRouteByMethodName() {
-        if (isScriptUnsupported) return;
-        URL url = initUrl("methodrule.javascript");
-        {
-            initInvocation("method1");
-            initDic(url);
-            initInvokers(url, true, true);
-
-            MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
-                    dic, url);
-            for (int i = 0; i < 100; i++) {
-                sinvoker.invoke(invocation);
-                Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
-                Assert.assertEquals(invoker1, invoker);
-            }
-        }
-        {
-            initInvocation("method2");
-            initDic(url);
-            initInvokers(url, true, true);
-            MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
-                    dic, url);
-            for (int i = 0; i < 100; i++) {
-                sinvoker.invoke(invocation);
-                Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
-                Assert.assertEquals(invoker2, invoker);
-            }
-        }
-    }
-
-    private URL initUrl(String filename) {
-        filename = getClass().getClassLoader().getResource(getClass().getPackage().getName().replace('.', '/') + "/" + filename).toString();
-        URL url = URL.valueOf(filename);
-        url = url.addParameter(Constants.RUNTIME_KEY, true);
-        return url;
-    }
-
-    private void initInvocation(String methodName) {
-        invocation = new RpcInvocation();
-        ((RpcInvocation) invocation).setMethodName(methodName);
-    }
-
-    private void initInvokers(URL url) {
-        initInvokers(url, true, false);
-    }
-
-    private void initInvokers(URL url, boolean invoker1Status, boolean invoker2Status) {
-        given(invoker1.invoke(invocation)).willReturn(result);
-        given(invoker1.isAvailable()).willReturn(invoker1Status);
-        given(invoker1.getUrl()).willReturn(url);
-        given(invoker1.getInterface()).willReturn(FileRouterEngineTest.class);
-
-        given(invoker2.invoke(invocation)).willReturn(result);
-        given(invoker2.isAvailable()).willReturn(invoker2Status);
-        given(invoker2.getUrl()).willReturn(url);
-        given(invoker2.getInterface()).willReturn(FileRouterEngineTest.class);
-    }
-
-    private void initDic(URL url) {
-        dic = new StaticDirectory<FileRouterEngineTest>(url, invokers, Arrays.asList(routerFactory.getRouter(url)));
-    }
-
-    static class MockClusterInvoker<T> extends AbstractClusterInvoker<T> {
-        private Invoker<T> selectedInvoker;
-
-        public MockClusterInvoker(Directory<T> directory) {
-            super(directory);
-        }
-
-        public MockClusterInvoker(Directory<T> directory, URL url) {
-            super(directory, url);
-        }
-
-        @Override
-        protected Result doInvoke(Invocation invocation, List<Invoker<T>> invokers,
-                                  LoadBalance loadbalance) throws RpcException {
-            Invoker<T> invoker = select(loadbalance, invocation, invokers, null);
-            selectedInvoker = invoker;
-            return null;
-        }
-
-        public Invoker<T> getSelectedInvoker() {
-            return selectedInvoker;
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.file;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.RpcResult;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.LoadBalance;
+import org.apache.dubbo.rpc.cluster.RouterFactory;
+import org.apache.dubbo.rpc.cluster.directory.StaticDirectory;
+import org.apache.dubbo.rpc.cluster.support.AbstractClusterInvoker;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import javax.script.ScriptEngineManager;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+@SuppressWarnings("unchecked")
+public class FileRouterEngineTest {
+    private static boolean isScriptUnsupported = new ScriptEngineManager().getEngineByName("javascript") == null;
+    List<Invoker<FileRouterEngineTest>> invokers = new ArrayList<Invoker<FileRouterEngineTest>>();
+    Invoker<FileRouterEngineTest> invoker1 = mock(Invoker.class);
+    Invoker<FileRouterEngineTest> invoker2 = mock(Invoker.class);
+    Invocation invocation;
+    Directory<FileRouterEngineTest> dic;
+    Result result = new RpcResult();
+    private RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getAdaptiveExtension();
+
+    @BeforeClass
+    public static void setUpBeforeClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() throws Exception {
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+    }
+
+    @Test
+    public void testRouteNotAvailable() {
+        if (isScriptUnsupported) return;
+        URL url = initUrl("notAvailablerule.javascript");
+        initInvocation("method1");
+        initDic(url);
+        initInvokers(url, true, false);
+
+        MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
+                dic, url);
+        for (int i = 0; i < 100; i++) {
+            sinvoker.invoke(invocation);
+            Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
+            Assert.assertEquals(invoker2, invoker);
+        }
+    }
+
+    @Test
+    public void testRouteAvailable() {
+        if (isScriptUnsupported) return;
+        URL url = initUrl("availablerule.javascript");
+        initInvocation("method1");
+        initDic(url);
+        initInvokers(url);
+
+        MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
+                dic, url);
+        for (int i = 0; i < 100; i++) {
+            sinvoker.invoke(invocation);
+            Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
+            Assert.assertEquals(invoker1, invoker);
+        }
+    }
+
+    @Test
+    public void testRouteByMethodName() {
+        if (isScriptUnsupported) return;
+        URL url = initUrl("methodrule.javascript");
+        {
+            initInvocation("method1");
+            initDic(url);
+            initInvokers(url, true, true);
+
+            MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
+                    dic, url);
+            for (int i = 0; i < 100; i++) {
+                sinvoker.invoke(invocation);
+                Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
+                Assert.assertEquals(invoker1, invoker);
+            }
+        }
+        {
+            initInvocation("method2");
+            initDic(url);
+            initInvokers(url, true, true);
+            MockClusterInvoker<FileRouterEngineTest> sinvoker = new MockClusterInvoker<FileRouterEngineTest>(
+                    dic, url);
+            for (int i = 0; i < 100; i++) {
+                sinvoker.invoke(invocation);
+                Invoker<FileRouterEngineTest> invoker = sinvoker.getSelectedInvoker();
+                Assert.assertEquals(invoker2, invoker);
+            }
+        }
+    }
+
+    private URL initUrl(String filename) {
+        filename = getClass().getClassLoader().getResource(getClass().getPackage().getName().replace('.', '/') + "/" + filename).toString();
+        URL url = URL.valueOf(filename);
+        url = url.addParameter(Constants.RUNTIME_KEY, true);
+        return url;
+    }
+
+    private void initInvocation(String methodName) {
+        invocation = new RpcInvocation();
+        ((RpcInvocation) invocation).setMethodName(methodName);
+    }
+
+    private void initInvokers(URL url) {
+        initInvokers(url, true, false);
+    }
+
+    private void initInvokers(URL url, boolean invoker1Status, boolean invoker2Status) {
+        given(invoker1.invoke(invocation)).willReturn(result);
+        given(invoker1.isAvailable()).willReturn(invoker1Status);
+        given(invoker1.getUrl()).willReturn(url);
+        given(invoker1.getInterface()).willReturn(FileRouterEngineTest.class);
+
+        given(invoker2.invoke(invocation)).willReturn(result);
+        given(invoker2.isAvailable()).willReturn(invoker2Status);
+        given(invoker2.getUrl()).willReturn(url);
+        given(invoker2.getInterface()).willReturn(FileRouterEngineTest.class);
+    }
+
+    private void initDic(URL url) {
+        dic = new StaticDirectory<FileRouterEngineTest>(url, invokers, Arrays.asList(routerFactory.getRouter(url)));
+    }
+
+    static class MockClusterInvoker<T> extends AbstractClusterInvoker<T> {
+        private Invoker<T> selectedInvoker;
+
+        public MockClusterInvoker(Directory<T> directory) {
+            super(directory);
+        }
+
+        public MockClusterInvoker(Directory<T> directory, URL url) {
+            super(directory, url);
+        }
+
+        @Override
+        protected Result doInvoke(Invocation invocation, List<Invoker<T>> invokers,
+                                  LoadBalance loadbalance) throws RpcException {
+            Invoker<T> invoker = select(loadbalance, invocation, invokers, null);
+            selectedInvoker = invoker;
+            return null;
+        }
+
+        public Invoker<T> getSelectedInvoker() {
+            return selectedInvoker;
+        }
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/script/ScriptRouterTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/script/ScriptRouterTest.java
index 8a01a99ec5..89e6416051 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/script/ScriptRouterTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/script/ScriptRouterTest.java
@@ -1,89 +1,89 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.script;
-
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.router.MockInvoker;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import javax.script.ScriptException;
-import java.util.ArrayList;
-import java.util.List;
-
-public class ScriptRouterTest {
-
-    private URL SCRIPT_URL = URL.valueOf("script://javascript?type=javascript");
-
-    @BeforeClass
-    public static void setUpBeforeClass() throws Exception {
-    }
-
-    @Before
-    public void setUp() throws Exception {
-    }
-
-    private URL getRouteUrl(String rule) {
-        return SCRIPT_URL.addParameterAndEncoded(Constants.RULE_KEY, rule);
-    }
-
-    @Test
-    public void testRouteReturnAll() {
-        Router router = new ScriptRouterFactory().getRouter(getRouteUrl("function route(op1,op2){return op1} route(invokers)"));
-        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
-        invokers.add(new MockInvoker<String>());
-        invokers.add(new MockInvoker<String>());
-        invokers.add(new MockInvoker<String>());
-        List<Invoker<String>> filteredInvokers = router.route(invokers, invokers.get(0).getUrl(), new RpcInvocation());
-        Assert.assertEquals(invokers, filteredInvokers);
-    }
-
-    @Test
-    public void testRoutePickInvokers() {
-        String rule = "var result = new java.util.ArrayList(invokers.size());" +
-                "for (i=0;i<invokers.size(); i++){ " +
-                "if (invokers.get(i).isAvailable()) {" +
-                "result.add(invokers.get(i)) ;" +
-                "}" +
-                "} ; " +
-                "return result;";
-        String script = "function route(invokers,invocation,context){" + rule + "} route(invokers,invocation,context)";
-        Router router = new ScriptRouterFactory().getRouter(getRouteUrl(script));
-
-        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
-        Invoker<String> invoker1 = new MockInvoker<String>(false);
-        Invoker<String> invoker2 = new MockInvoker<String>(true);
-        Invoker<String> invoker3 = new MockInvoker<String>(true);
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-        invokers.add(invoker3);
-        List<Invoker<String>> filteredInvokers = router.route(invokers, invokers.get(0).getUrl(), new RpcInvocation());
-        Assert.assertEquals(2, filteredInvokers.size());
-        Assert.assertEquals(invoker2, filteredInvokers.get(0));
-        Assert.assertEquals(invoker3, filteredInvokers.get(1));
-    }
-
-    //TODO Add tests for abnormal scene
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.script;
+
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.router.MockInvoker;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import javax.script.ScriptException;
+import java.util.ArrayList;
+import java.util.List;
+
+public class ScriptRouterTest {
+
+    private URL SCRIPT_URL = URL.valueOf("script://javascript?type=javascript");
+
+    @BeforeClass
+    public static void setUpBeforeClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() throws Exception {
+    }
+
+    private URL getRouteUrl(String rule) {
+        return SCRIPT_URL.addParameterAndEncoded(Constants.RULE_KEY, rule);
+    }
+
+    @Test
+    public void testRouteReturnAll() {
+        Router router = new ScriptRouterFactory().getRouter(getRouteUrl("function route(op1,op2){return op1} route(invokers)"));
+        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
+        invokers.add(new MockInvoker<String>());
+        invokers.add(new MockInvoker<String>());
+        invokers.add(new MockInvoker<String>());
+        List<Invoker<String>> filteredInvokers = router.route(invokers, invokers.get(0).getUrl(), new RpcInvocation());
+        Assert.assertEquals(invokers, filteredInvokers);
+    }
+
+    @Test
+    public void testRoutePickInvokers() {
+        String rule = "var result = new java.util.ArrayList(invokers.size());" +
+                "for (i=0;i<invokers.size(); i++){ " +
+                "if (invokers.get(i).isAvailable()) {" +
+                "result.add(invokers.get(i)) ;" +
+                "}" +
+                "} ; " +
+                "return result;";
+        String script = "function route(invokers,invocation,context){" + rule + "} route(invokers,invocation,context)";
+        Router router = new ScriptRouterFactory().getRouter(getRouteUrl(script));
+
+        List<Invoker<String>> invokers = new ArrayList<Invoker<String>>();
+        Invoker<String> invoker1 = new MockInvoker<String>(false);
+        Invoker<String> invoker2 = new MockInvoker<String>(true);
+        Invoker<String> invoker3 = new MockInvoker<String>(true);
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+        invokers.add(invoker3);
+        List<Invoker<String>> filteredInvokers = router.route(invokers, invokers.get(0).getUrl(), new RpcInvocation());
+        Assert.assertEquals(2, filteredInvokers.size());
+        Assert.assertEquals(invoker2, filteredInvokers.get(0));
+        Assert.assertEquals(invoker3, filteredInvokers.get(1));
+    }
+
+    //TODO Add tests for abnormal scene
 }
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterTest.java
index 839af44efe..424244dcca 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/router/tag/TagRouterTest.java
@@ -1,169 +1,169 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.router.tag;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.common.utils.NetUtils;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.RpcContext;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.cluster.Router;
-import org.apache.dubbo.rpc.cluster.RouterFactory;
-import org.apache.dubbo.rpc.cluster.router.MockInvoker;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-
-public class TagRouterTest {
-
-    private URL tagUrl = new URL("tag"
-            , Constants.ANYHOST_VALUE, 0
-            , Constants.ANY_VALUE)
-            .addParameters(
-                    Constants.RUNTIME_KEY, "true"
-            );
-
-    @BeforeClass
-    public static void setUpBeforeClass() throws Exception {
-    }
-
-    @Before
-    public void setUp() throws Exception {
-    }
-
-    @Test
-    public void testRoute_matchTag() {
-
-        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "red");
-
-        List<Invoker<String>> invokers = new ArrayList<>();
-        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
-        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
-        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
-        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.4:20880/com.foo.BarService"));
-
-        invokers.add(redInvoker);
-        invokers.add(yellowInvoker);
-        invokers.add(blueInvoker);
-        invokers.add(defaultInvoker);
-
-        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
-        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
-        Assert.assertTrue(filteredInvokers.contains(redInvoker));
-        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
-        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
-        Assert.assertFalse(filteredInvokers.contains(defaultInvoker));
-    }
-
-    @Test
-    public void testRoute_matchDefault() {
-
-        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "");
-
-        List<Invoker<String>> invokers = new ArrayList<>();
-        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
-        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
-        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
-        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.4:20880/com.foo.BarService"));
-
-        invokers.add(redInvoker);
-        invokers.add(yellowInvoker);
-        invokers.add(blueInvoker);
-        invokers.add(defaultInvoker);
-
-        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
-        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
-        Assert.assertTrue(filteredInvokers.contains(defaultInvoker));
-        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
-        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
-        Assert.assertFalse(filteredInvokers.contains(redInvoker));
-    }
-
-    @Test
-    public void testRoute_requestWithTag_shouldDowngrade() {
-
-        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "black");
-
-        List<Invoker<String>> invokers = new ArrayList<>();
-        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
-        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
-        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
-        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.4:20880/com.foo.BarService"));
-
-        invokers.add(redInvoker);
-        invokers.add(yellowInvoker);
-        invokers.add(blueInvoker);
-        invokers.add(defaultInvoker);
-
-        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
-        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
-        Assert.assertTrue(filteredInvokers.contains(defaultInvoker));
-        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
-        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
-        Assert.assertFalse(filteredInvokers.contains(redInvoker));
-    }
-
-    @Test
-    public void testRoute_requestWithoutTag_shouldNotDowngrade() {
-
-        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "");
-
-        List<Invoker<String>> invokers = new ArrayList<>();
-        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
-        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
-        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
-                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
-
-        invokers.add(redInvoker);
-        invokers.add(yellowInvoker);
-        invokers.add(blueInvoker);
-
-        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
-        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
-        Assert.assertEquals(0, filteredInvokers.size());
-    }
-
-    @Test
-    public void testRoute_createBySpi() {
-        URL zkProvider = URL.valueOf("zookeeper://10.20.3.1:20880/com.foo.BarService?router=tag");
-        String parameter = zkProvider.getParameter(Constants.ROUTER_KEY);
-        RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getExtension(parameter);
-        Router tagRouter = routerFactory.getRouter(zkProvider);
-        Assert.assertTrue(tagRouter instanceof TagRouter);
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.router.tag;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.common.utils.NetUtils;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.RpcContext;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.cluster.Router;
+import org.apache.dubbo.rpc.cluster.RouterFactory;
+import org.apache.dubbo.rpc.cluster.router.MockInvoker;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class TagRouterTest {
+
+    private URL tagUrl = new URL("tag"
+            , Constants.ANYHOST_VALUE, 0
+            , Constants.ANY_VALUE)
+            .addParameters(
+                    Constants.RUNTIME_KEY, "true"
+            );
+
+    @BeforeClass
+    public static void setUpBeforeClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() throws Exception {
+    }
+
+    @Test
+    public void testRoute_matchTag() {
+
+        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "red");
+
+        List<Invoker<String>> invokers = new ArrayList<>();
+        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
+        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
+        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
+        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.4:20880/com.foo.BarService"));
+
+        invokers.add(redInvoker);
+        invokers.add(yellowInvoker);
+        invokers.add(blueInvoker);
+        invokers.add(defaultInvoker);
+
+        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
+        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
+        Assert.assertTrue(filteredInvokers.contains(redInvoker));
+        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
+        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
+        Assert.assertFalse(filteredInvokers.contains(defaultInvoker));
+    }
+
+    @Test
+    public void testRoute_matchDefault() {
+
+        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "");
+
+        List<Invoker<String>> invokers = new ArrayList<>();
+        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
+        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
+        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
+        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.4:20880/com.foo.BarService"));
+
+        invokers.add(redInvoker);
+        invokers.add(yellowInvoker);
+        invokers.add(blueInvoker);
+        invokers.add(defaultInvoker);
+
+        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
+        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
+        Assert.assertTrue(filteredInvokers.contains(defaultInvoker));
+        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
+        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
+        Assert.assertFalse(filteredInvokers.contains(redInvoker));
+    }
+
+    @Test
+    public void testRoute_requestWithTag_shouldDowngrade() {
+
+        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "black");
+
+        List<Invoker<String>> invokers = new ArrayList<>();
+        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
+        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
+        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
+        Invoker<String> defaultInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.4:20880/com.foo.BarService"));
+
+        invokers.add(redInvoker);
+        invokers.add(yellowInvoker);
+        invokers.add(blueInvoker);
+        invokers.add(defaultInvoker);
+
+        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
+        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
+        Assert.assertTrue(filteredInvokers.contains(defaultInvoker));
+        Assert.assertFalse(filteredInvokers.contains(yellowInvoker));
+        Assert.assertFalse(filteredInvokers.contains(blueInvoker));
+        Assert.assertFalse(filteredInvokers.contains(redInvoker));
+    }
+
+    @Test
+    public void testRoute_requestWithoutTag_shouldNotDowngrade() {
+
+        RpcContext.getContext().setAttachment(Constants.REQUEST_TAG_KEY, "");
+
+        List<Invoker<String>> invokers = new ArrayList<>();
+        Invoker<String> redInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.1:20880/com.foo.BarService?tag=red"));
+        Invoker<String> yellowInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.2:20880/com.foo.BarService?tag=yellow"));
+        Invoker<String> blueInvoker = new MockInvoker<>(URL.valueOf(
+                "dubbo://10.20.3.3:20880/com.foo.BarService?tag=blue"));
+
+        invokers.add(redInvoker);
+        invokers.add(yellowInvoker);
+        invokers.add(blueInvoker);
+
+        Router tagRouter = new TagRouterFactory().getRouter(tagUrl);
+        List<Invoker<String>> filteredInvokers = tagRouter.route(invokers, URL.valueOf("consumer://" + NetUtils.getLocalHost() + "/com.foo.BarService"), new RpcInvocation());
+        Assert.assertEquals(0, filteredInvokers.size());
+    }
+
+    @Test
+    public void testRoute_createBySpi() {
+        URL zkProvider = URL.valueOf("zookeeper://10.20.3.1:20880/com.foo.BarService?router=tag");
+        String parameter = zkProvider.getParameter(Constants.ROUTER_KEY);
+        RouterFactory routerFactory = ExtensionLoader.getExtensionLoader(RouterFactory.class).getExtension(parameter);
+        Router tagRouter = routerFactory.getRouter(zkProvider);
+        Assert.assertTrue(tagRouter instanceof TagRouter);
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/AbstractClusterInvokerTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/AbstractClusterInvokerTest.java
index 247a719ad8..f8d45c8343 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/AbstractClusterInvokerTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/AbstractClusterInvokerTest.java
@@ -1,522 +1,522 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.common.extension.ExtensionLoader;
-import org.apache.dubbo.common.utils.NetUtils;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcContext;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.cluster.Directory;
-import org.apache.dubbo.rpc.cluster.LoadBalance;
-import org.apache.dubbo.rpc.cluster.directory.StaticDirectory;
-import org.apache.dubbo.rpc.cluster.filter.DemoService;
-import org.apache.dubbo.rpc.cluster.loadbalance.LeastActiveLoadBalance;
-import org.apache.dubbo.rpc.cluster.loadbalance.RandomLoadBalance;
-import org.apache.dubbo.rpc.cluster.loadbalance.RoundRobinLoadBalance;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-import org.mockito.Mockito;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.atomic.AtomicLong;
-
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-/**
- * AbstractClusterInvokerTest
- */
-@SuppressWarnings("rawtypes")
-public class AbstractClusterInvokerTest {
-    List<Invoker<IHelloService>> invokers = new ArrayList<Invoker<IHelloService>>();
-    List<Invoker<IHelloService>> selectedInvokers = new ArrayList<Invoker<IHelloService>>();
-    AbstractClusterInvoker<IHelloService> cluster;
-    AbstractClusterInvoker<IHelloService> cluster_nocheck;
-    Directory<IHelloService> dic;
-    RpcInvocation invocation = new RpcInvocation();
-    URL url = URL.valueOf("registry://localhost:9090");
-
-    Invoker<IHelloService> invoker1;
-    Invoker<IHelloService> invoker2;
-    Invoker<IHelloService> invoker3;
-    Invoker<IHelloService> invoker4;
-    Invoker<IHelloService> invoker5;
-    Invoker<IHelloService> mockedInvoker1;
-
-
-    @BeforeClass
-    public static void setUpBeforeClass() throws Exception {
-    }
-
-    @SuppressWarnings({"unchecked"})
-    @Before
-    public void setUp() throws Exception {
-        invocation.setMethodName("sayHello");
-
-        invoker1 = mock(Invoker.class);
-        invoker2 = mock(Invoker.class);
-        invoker3 = mock(Invoker.class);
-        invoker4 = mock(Invoker.class);
-        invoker5 = mock(Invoker.class);
-        mockedInvoker1 = mock(Invoker.class);
-
-        URL turl = URL.valueOf("test://test:11/test");
-
-        given(invoker1.isAvailable()).willReturn(false);
-        given(invoker1.getInterface()).willReturn(IHelloService.class);
-        given(invoker1.getUrl()).willReturn(turl.addParameter("name", "invoker1"));
-
-        given(invoker2.isAvailable()).willReturn(true);
-        given(invoker2.getInterface()).willReturn(IHelloService.class);
-        given(invoker2.getUrl()).willReturn(turl.addParameter("name", "invoker2"));
-
-        given(invoker3.isAvailable()).willReturn(false);
-        given(invoker3.getInterface()).willReturn(IHelloService.class);
-        given(invoker3.getUrl()).willReturn(turl.addParameter("name", "invoker3"));
-
-        given(invoker4.isAvailable()).willReturn(true);
-        given(invoker4.getInterface()).willReturn(IHelloService.class);
-        given(invoker4.getUrl()).willReturn(turl.addParameter("name", "invoker4"));
-
-        given(invoker5.isAvailable()).willReturn(false);
-        given(invoker5.getInterface()).willReturn(IHelloService.class);
-        given(invoker5.getUrl()).willReturn(turl.addParameter("name", "invoker5"));
-
-        given(mockedInvoker1.isAvailable()).willReturn(false);
-        given(mockedInvoker1.getInterface()).willReturn(IHelloService.class);
-        given(mockedInvoker1.getUrl()).willReturn(turl.setProtocol("mock"));
-
-        invokers.add(invoker1);
-        dic = new StaticDirectory<IHelloService>(url, invokers, null);
-        cluster = new AbstractClusterInvoker(dic) {
-            @Override
-            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
-                    throws RpcException {
-                return null;
-            }
-        };
-
-        cluster_nocheck = new AbstractClusterInvoker(dic, url.addParameterIfAbsent(Constants.CLUSTER_AVAILABLE_CHECK_KEY, Boolean.FALSE.toString())) {
-            @Override
-            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
-                    throws RpcException {
-                return null;
-            }
-        };
-
-    }
-
-
-    @Test
-    public void testBindingAttachment() {
-        final String attachKey = "attach";
-        final String attachValue = "value";
-
-        // setup attachment
-        RpcContext.getContext().setAttachment(attachKey, attachValue);
-        Map<String, String> attachments = RpcContext.getContext().getAttachments();
-        Assert.assertTrue("set attachment failed!", attachments != null && attachments.size() == 1);
-
-        cluster = new AbstractClusterInvoker(dic) {
-            @Override
-            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
-                    throws RpcException {
-                // attachment will be bind to invocation
-                String value = invocation.getAttachment(attachKey);
-                Assert.assertTrue("binding attachment failed!", value != null && value.equals(attachValue));
-                return null;
-            }
-        };
-
-        // invoke
-        cluster.invoke(invocation);
-    }
-
-    @Test
-    public void testSelect_Invokersize0() throws Exception {
-        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
-        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
-        {
-            Invoker invoker = cluster.select(l, null, null, null);
-            Assert.assertEquals(null, invoker);
-        }
-        {
-            invokers.clear();
-            selectedInvokers.clear();
-            Invoker invoker = cluster.select(l, null, invokers, null);
-            Assert.assertEquals(null, invoker);
-        }
-    }
-
-    @Test
-    public void testSelect_Invokersize1() throws Exception {
-        invokers.clear();
-        invokers.add(invoker1);
-        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
-        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
-        Invoker invoker = cluster.select(l, null, invokers, null);
-        Assert.assertEquals(invoker1, invoker);
-    }
-
-    @Test
-    public void testSelect_Invokersize2AndselectNotNull() throws Exception {
-        invokers.clear();
-        invokers.add(invoker2);
-        invokers.add(invoker4);
-        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
-        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
-        {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker4);
-            Invoker invoker = cluster.select(l, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(invoker2, invoker);
-        }
-        {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker2);
-            Invoker invoker = cluster.select(l, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(invoker4, invoker);
-        }
-    }
-
-    @Test
-    public void testSelect_multiInvokers() throws Exception {
-        testSelect_multiInvokers(RoundRobinLoadBalance.NAME);
-        testSelect_multiInvokers(LeastActiveLoadBalance.NAME);
-        testSelect_multiInvokers(RandomLoadBalance.NAME);
-    }
-
-    @Test
-    public void testCloseAvailablecheck() {
-        LoadBalance lb = mock(LoadBalance.class);
-        given(lb.select(invokers, url, invocation)).willReturn(invoker1);
-
-        initlistsize5();
-
-        Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-        Assert.assertEquals(false, sinvoker.isAvailable());
-        Assert.assertEquals(invoker1, sinvoker);
-
-    }
-
-    @Test
-    public void testDonotSelectAgainAndNoCheckAvailable() {
-
-        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
-        initlistsize5();
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker4);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertSame(invoker1, sinvoker);
-        }
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker4);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertSame(invoker2, sinvoker);
-        }
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker4);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertSame(invoker3, sinvoker);
-        }
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker4);
-            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertSame(invoker5, sinvoker);
-        }
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker4);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertTrue(invokers.contains(sinvoker));
-        }
-
-    }
-
-    @Test
-    public void testSelectAgainAndCheckAvailable() {
-
-        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
-        initlistsize5();
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertTrue(sinvoker == invoker4);
-        }
-        {
-            //Boundary condition test .
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker4);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
-        }
-        {
-            //Boundary condition test .
-            for (int i = 0; i < 100; i++) {
-                selectedInvokers.clear();
-                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
-            }
-        }
-        {
-            //Boundary condition test .
-            for (int i = 0; i < 100; i++) {
-                selectedInvokers.clear();
-                selectedInvokers.add(invoker1);
-                selectedInvokers.add(invoker3);
-                selectedInvokers.add(invoker5);
-                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
-            }
-        }
-        {
-            //Boundary condition test .
-            for (int i = 0; i < 100; i++) {
-                selectedInvokers.clear();
-                selectedInvokers.add(invoker1);
-                selectedInvokers.add(invoker3);
-                selectedInvokers.add(invoker2);
-                selectedInvokers.add(invoker4);
-                selectedInvokers.add(invoker5);
-                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
-            }
-        }
-    }
-
-
-    public void testSelect_multiInvokers(String lbname) throws Exception {
-
-        int min = 1000, max = 5000;
-        Double d = (Math.random() * (max - min + 1) + min);
-        int runs = d.intValue();
-        Assert.assertTrue(runs > min);
-        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(lbname);
-        initlistsize5();
-        for (int i = 0; i < runs; i++) {
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-        for (int i = 0; i < runs; i++) {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-        for (int i = 0; i < runs; i++) {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker2);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-        for (int i = 0; i < runs; i++) {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker4);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-        for (int i = 0; i < runs; i++) {
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker3);
-            selectedInvokers.add(invoker5);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-        for (int i = 0; i < runs; i++) {
-
-            selectedInvokers.clear();
-            selectedInvokers.add(invoker1);
-            selectedInvokers.add(invoker2);
-            selectedInvokers.add(invoker3);
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            Assert.assertEquals(true, sinvoker.isAvailable());
-
-            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
-        }
-    }
-
-    /**
-     * Test balance.
-     */
-    @Test
-    public void testSelectBalance() {
-
-        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
-        initlistsize5();
-
-        Map<Invoker, AtomicLong> counter = new ConcurrentHashMap<Invoker, AtomicLong>();
-        for (Invoker invoker : invokers) {
-            counter.put(invoker, new AtomicLong(0));
-        }
-        int runs = 1000;
-        for (int i = 0; i < runs; i++) {
-            selectedInvokers.clear();
-            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
-            counter.get(sinvoker).incrementAndGet();
-        }
-
-        for (Invoker minvoker : counter.keySet()) {
-            Long count = counter.get(minvoker).get();
-//            System.out.println(count);
-            if (minvoker.isAvailable())
-                Assert.assertTrue("count should > avg", count > runs / invokers.size());
-        }
-
-        Assert.assertEquals(runs, counter.get(invoker2).get() + counter.get(invoker4).get());
-        ;
-
-    }
-
-    private void initlistsize5() {
-        invokers.clear();
-        selectedInvokers.clear();//Clear first, previous test case will make sure that the right invoker2 will be used.
-        invokers.add(invoker1);
-        invokers.add(invoker2);
-        invokers.add(invoker3);
-        invokers.add(invoker4);
-        invokers.add(invoker5);
-    }
-
-    @Test()
-    public void testTimeoutExceptionCode() {
-        List<Invoker<DemoService>> invokers = new ArrayList<Invoker<DemoService>>();
-        invokers.add(new Invoker<DemoService>() {
-
-            @Override
-            public Class<DemoService> getInterface() {
-                return DemoService.class;
-            }
-
-            public URL getUrl() {
-                return URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/" + DemoService.class.getName());
-            }
-
-            @Override
-            public boolean isAvailable() {
-                return false;
-            }
-
-            public Result invoke(Invocation invocation) throws RpcException {
-                throw new RpcException(RpcException.TIMEOUT_EXCEPTION, "test timeout");
-            }
-
-            @Override
-            public void destroy() {
-            }
-        });
-        Directory<DemoService> directory = new StaticDirectory<DemoService>(invokers);
-        FailoverClusterInvoker<DemoService> failoverClusterInvoker = new FailoverClusterInvoker<DemoService>(directory);
-        try {
-            failoverClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
-            Assert.fail();
-        } catch (RpcException e) {
-            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
-        }
-        ForkingClusterInvoker<DemoService> forkingClusterInvoker = new ForkingClusterInvoker<DemoService>(directory);
-        try {
-            forkingClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
-            Assert.fail();
-        } catch (RpcException e) {
-            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
-        }
-        FailfastClusterInvoker<DemoService> failfastClusterInvoker = new FailfastClusterInvoker<DemoService>(directory);
-        try {
-            failfastClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
-            Assert.fail();
-        } catch (RpcException e) {
-            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
-        }
-    }
-
-    /**
-     * Test mock invoker selector works as expected
-     */
-    @Test
-    public void testMockedInvokerSelect() {
-        initlistsize5();
-        invokers.add(mockedInvoker1);
-
-        RpcInvocation mockedInvocation = new RpcInvocation();
-        mockedInvocation.setMethodName("sayHello");
-        mockedInvocation.setAttachment(Constants.INVOCATION_NEED_MOCK, "true");
-        List<Invoker<IHelloService>> mockedInvokers = dic.list(mockedInvocation);
-        Assert.assertEquals(1, mockedInvokers.size());
-
-        List<Invoker<IHelloService>> invokers = dic.list(invocation);
-        Assert.assertEquals(5, invokers.size());
-    }
-
-    public static interface IHelloService {
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.common.extension.ExtensionLoader;
+import org.apache.dubbo.common.utils.NetUtils;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcContext;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.cluster.Directory;
+import org.apache.dubbo.rpc.cluster.LoadBalance;
+import org.apache.dubbo.rpc.cluster.directory.StaticDirectory;
+import org.apache.dubbo.rpc.cluster.filter.DemoService;
+import org.apache.dubbo.rpc.cluster.loadbalance.LeastActiveLoadBalance;
+import org.apache.dubbo.rpc.cluster.loadbalance.RandomLoadBalance;
+import org.apache.dubbo.rpc.cluster.loadbalance.RoundRobinLoadBalance;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.mockito.Mockito;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.atomic.AtomicLong;
+
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+/**
+ * AbstractClusterInvokerTest
+ */
+@SuppressWarnings("rawtypes")
+public class AbstractClusterInvokerTest {
+    List<Invoker<IHelloService>> invokers = new ArrayList<Invoker<IHelloService>>();
+    List<Invoker<IHelloService>> selectedInvokers = new ArrayList<Invoker<IHelloService>>();
+    AbstractClusterInvoker<IHelloService> cluster;
+    AbstractClusterInvoker<IHelloService> cluster_nocheck;
+    Directory<IHelloService> dic;
+    RpcInvocation invocation = new RpcInvocation();
+    URL url = URL.valueOf("registry://localhost:9090");
+
+    Invoker<IHelloService> invoker1;
+    Invoker<IHelloService> invoker2;
+    Invoker<IHelloService> invoker3;
+    Invoker<IHelloService> invoker4;
+    Invoker<IHelloService> invoker5;
+    Invoker<IHelloService> mockedInvoker1;
+
+
+    @BeforeClass
+    public static void setUpBeforeClass() throws Exception {
+    }
+
+    @SuppressWarnings({"unchecked"})
+    @Before
+    public void setUp() throws Exception {
+        invocation.setMethodName("sayHello");
+
+        invoker1 = mock(Invoker.class);
+        invoker2 = mock(Invoker.class);
+        invoker3 = mock(Invoker.class);
+        invoker4 = mock(Invoker.class);
+        invoker5 = mock(Invoker.class);
+        mockedInvoker1 = mock(Invoker.class);
+
+        URL turl = URL.valueOf("test://test:11/test");
+
+        given(invoker1.isAvailable()).willReturn(false);
+        given(invoker1.getInterface()).willReturn(IHelloService.class);
+        given(invoker1.getUrl()).willReturn(turl.addParameter("name", "invoker1"));
+
+        given(invoker2.isAvailable()).willReturn(true);
+        given(invoker2.getInterface()).willReturn(IHelloService.class);
+        given(invoker2.getUrl()).willReturn(turl.addParameter("name", "invoker2"));
+
+        given(invoker3.isAvailable()).willReturn(false);
+        given(invoker3.getInterface()).willReturn(IHelloService.class);
+        given(invoker3.getUrl()).willReturn(turl.addParameter("name", "invoker3"));
+
+        given(invoker4.isAvailable()).willReturn(true);
+        given(invoker4.getInterface()).willReturn(IHelloService.class);
+        given(invoker4.getUrl()).willReturn(turl.addParameter("name", "invoker4"));
+
+        given(invoker5.isAvailable()).willReturn(false);
+        given(invoker5.getInterface()).willReturn(IHelloService.class);
+        given(invoker5.getUrl()).willReturn(turl.addParameter("name", "invoker5"));
+
+        given(mockedInvoker1.isAvailable()).willReturn(false);
+        given(mockedInvoker1.getInterface()).willReturn(IHelloService.class);
+        given(mockedInvoker1.getUrl()).willReturn(turl.setProtocol("mock"));
+
+        invokers.add(invoker1);
+        dic = new StaticDirectory<IHelloService>(url, invokers, null);
+        cluster = new AbstractClusterInvoker(dic) {
+            @Override
+            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
+                    throws RpcException {
+                return null;
+            }
+        };
+
+        cluster_nocheck = new AbstractClusterInvoker(dic, url.addParameterIfAbsent(Constants.CLUSTER_AVAILABLE_CHECK_KEY, Boolean.FALSE.toString())) {
+            @Override
+            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
+                    throws RpcException {
+                return null;
+            }
+        };
+
+    }
+
+
+    @Test
+    public void testBindingAttachment() {
+        final String attachKey = "attach";
+        final String attachValue = "value";
+
+        // setup attachment
+        RpcContext.getContext().setAttachment(attachKey, attachValue);
+        Map<String, String> attachments = RpcContext.getContext().getAttachments();
+        Assert.assertTrue("set attachment failed!", attachments != null && attachments.size() == 1);
+
+        cluster = new AbstractClusterInvoker(dic) {
+            @Override
+            protected Result doInvoke(Invocation invocation, List invokers, LoadBalance loadbalance)
+                    throws RpcException {
+                // attachment will be bind to invocation
+                String value = invocation.getAttachment(attachKey);
+                Assert.assertTrue("binding attachment failed!", value != null && value.equals(attachValue));
+                return null;
+            }
+        };
+
+        // invoke
+        cluster.invoke(invocation);
+    }
+
+    @Test
+    public void testSelect_Invokersize0() throws Exception {
+        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
+        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
+        {
+            Invoker invoker = cluster.select(l, null, null, null);
+            Assert.assertEquals(null, invoker);
+        }
+        {
+            invokers.clear();
+            selectedInvokers.clear();
+            Invoker invoker = cluster.select(l, null, invokers, null);
+            Assert.assertEquals(null, invoker);
+        }
+    }
+
+    @Test
+    public void testSelect_Invokersize1() throws Exception {
+        invokers.clear();
+        invokers.add(invoker1);
+        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
+        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
+        Invoker invoker = cluster.select(l, null, invokers, null);
+        Assert.assertEquals(invoker1, invoker);
+    }
+
+    @Test
+    public void testSelect_Invokersize2AndselectNotNull() throws Exception {
+        invokers.clear();
+        invokers.add(invoker2);
+        invokers.add(invoker4);
+        LoadBalance l = cluster.initLoadBalance(invokers, invocation);
+        Assert.assertNotNull("cluster.initLoadBalance returns null!", l);
+        {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker4);
+            Invoker invoker = cluster.select(l, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(invoker2, invoker);
+        }
+        {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker2);
+            Invoker invoker = cluster.select(l, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(invoker4, invoker);
+        }
+    }
+
+    @Test
+    public void testSelect_multiInvokers() throws Exception {
+        testSelect_multiInvokers(RoundRobinLoadBalance.NAME);
+        testSelect_multiInvokers(LeastActiveLoadBalance.NAME);
+        testSelect_multiInvokers(RandomLoadBalance.NAME);
+    }
+
+    @Test
+    public void testCloseAvailablecheck() {
+        LoadBalance lb = mock(LoadBalance.class);
+        given(lb.select(invokers, url, invocation)).willReturn(invoker1);
+
+        initlistsize5();
+
+        Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+        Assert.assertEquals(false, sinvoker.isAvailable());
+        Assert.assertEquals(invoker1, sinvoker);
+
+    }
+
+    @Test
+    public void testDonotSelectAgainAndNoCheckAvailable() {
+
+        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
+        initlistsize5();
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker4);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertSame(invoker1, sinvoker);
+        }
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker4);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertSame(invoker2, sinvoker);
+        }
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker4);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertSame(invoker3, sinvoker);
+        }
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker4);
+            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertSame(invoker5, sinvoker);
+        }
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker4);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster_nocheck.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertTrue(invokers.contains(sinvoker));
+        }
+
+    }
+
+    @Test
+    public void testSelectAgainAndCheckAvailable() {
+
+        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
+        initlistsize5();
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertTrue(sinvoker == invoker4);
+        }
+        {
+            //Boundary condition test .
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker4);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
+        }
+        {
+            //Boundary condition test .
+            for (int i = 0; i < 100; i++) {
+                selectedInvokers.clear();
+                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
+            }
+        }
+        {
+            //Boundary condition test .
+            for (int i = 0; i < 100; i++) {
+                selectedInvokers.clear();
+                selectedInvokers.add(invoker1);
+                selectedInvokers.add(invoker3);
+                selectedInvokers.add(invoker5);
+                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
+            }
+        }
+        {
+            //Boundary condition test .
+            for (int i = 0; i < 100; i++) {
+                selectedInvokers.clear();
+                selectedInvokers.add(invoker1);
+                selectedInvokers.add(invoker3);
+                selectedInvokers.add(invoker2);
+                selectedInvokers.add(invoker4);
+                selectedInvokers.add(invoker5);
+                Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+                Assert.assertTrue(sinvoker == invoker2 || sinvoker == invoker4);
+            }
+        }
+    }
+
+
+    public void testSelect_multiInvokers(String lbname) throws Exception {
+
+        int min = 1000, max = 5000;
+        Double d = (Math.random() * (max - min + 1) + min);
+        int runs = d.intValue();
+        Assert.assertTrue(runs > min);
+        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(lbname);
+        initlistsize5();
+        for (int i = 0; i < runs; i++) {
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+        for (int i = 0; i < runs; i++) {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+        for (int i = 0; i < runs; i++) {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker2);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+        for (int i = 0; i < runs; i++) {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker4);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+        for (int i = 0; i < runs; i++) {
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker3);
+            selectedInvokers.add(invoker5);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+        for (int i = 0; i < runs; i++) {
+
+            selectedInvokers.clear();
+            selectedInvokers.add(invoker1);
+            selectedInvokers.add(invoker2);
+            selectedInvokers.add(invoker3);
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            Assert.assertEquals(true, sinvoker.isAvailable());
+
+            Mockito.clearInvocations(invoker1, invoker2, invoker3, invoker4, invoker5);
+        }
+    }
+
+    /**
+     * Test balance.
+     */
+    @Test
+    public void testSelectBalance() {
+
+        LoadBalance lb = ExtensionLoader.getExtensionLoader(LoadBalance.class).getExtension(RoundRobinLoadBalance.NAME);
+        initlistsize5();
+
+        Map<Invoker, AtomicLong> counter = new ConcurrentHashMap<Invoker, AtomicLong>();
+        for (Invoker invoker : invokers) {
+            counter.put(invoker, new AtomicLong(0));
+        }
+        int runs = 1000;
+        for (int i = 0; i < runs; i++) {
+            selectedInvokers.clear();
+            Invoker sinvoker = cluster.select(lb, invocation, invokers, selectedInvokers);
+            counter.get(sinvoker).incrementAndGet();
+        }
+
+        for (Invoker minvoker : counter.keySet()) {
+            Long count = counter.get(minvoker).get();
+//            System.out.println(count);
+            if (minvoker.isAvailable())
+                Assert.assertTrue("count should > avg", count > runs / invokers.size());
+        }
+
+        Assert.assertEquals(runs, counter.get(invoker2).get() + counter.get(invoker4).get());
+        ;
+
+    }
+
+    private void initlistsize5() {
+        invokers.clear();
+        selectedInvokers.clear();//Clear first, previous test case will make sure that the right invoker2 will be used.
+        invokers.add(invoker1);
+        invokers.add(invoker2);
+        invokers.add(invoker3);
+        invokers.add(invoker4);
+        invokers.add(invoker5);
+    }
+
+    @Test()
+    public void testTimeoutExceptionCode() {
+        List<Invoker<DemoService>> invokers = new ArrayList<Invoker<DemoService>>();
+        invokers.add(new Invoker<DemoService>() {
+
+            @Override
+            public Class<DemoService> getInterface() {
+                return DemoService.class;
+            }
+
+            public URL getUrl() {
+                return URL.valueOf("dubbo://" + NetUtils.getLocalHost() + ":20880/" + DemoService.class.getName());
+            }
+
+            @Override
+            public boolean isAvailable() {
+                return false;
+            }
+
+            public Result invoke(Invocation invocation) throws RpcException {
+                throw new RpcException(RpcException.TIMEOUT_EXCEPTION, "test timeout");
+            }
+
+            @Override
+            public void destroy() {
+            }
+        });
+        Directory<DemoService> directory = new StaticDirectory<DemoService>(invokers);
+        FailoverClusterInvoker<DemoService> failoverClusterInvoker = new FailoverClusterInvoker<DemoService>(directory);
+        try {
+            failoverClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
+            Assert.fail();
+        } catch (RpcException e) {
+            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
+        }
+        ForkingClusterInvoker<DemoService> forkingClusterInvoker = new ForkingClusterInvoker<DemoService>(directory);
+        try {
+            forkingClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
+            Assert.fail();
+        } catch (RpcException e) {
+            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
+        }
+        FailfastClusterInvoker<DemoService> failfastClusterInvoker = new FailfastClusterInvoker<DemoService>(directory);
+        try {
+            failfastClusterInvoker.invoke(new RpcInvocation("sayHello", new Class<?>[0], new Object[0]));
+            Assert.fail();
+        } catch (RpcException e) {
+            Assert.assertEquals(RpcException.TIMEOUT_EXCEPTION, e.getCode());
+        }
+    }
+
+    /**
+     * Test mock invoker selector works as expected
+     */
+    @Test
+    public void testMockedInvokerSelect() {
+        initlistsize5();
+        invokers.add(mockedInvoker1);
+
+        RpcInvocation mockedInvocation = new RpcInvocation();
+        mockedInvocation.setMethodName("sayHello");
+        mockedInvocation.setAttachment(Constants.INVOCATION_NEED_MOCK, "true");
+        List<Invoker<IHelloService>> mockedInvokers = dic.list(mockedInvocation);
+        Assert.assertEquals(1, mockedInvokers.size());
+
+        List<Invoker<IHelloService>> invokers = dic.list(invocation);
+        Assert.assertEquals(5, invokers.size());
+    }
+
+    public static interface IHelloService {
+    }
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/ClusterUtilsTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/ClusterUtilsTest.java
index 65cc1b2ce5..170bce0403 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/ClusterUtilsTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/ClusterUtilsTest.java
@@ -1,80 +1,80 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-
-import org.junit.Assert;
-import org.junit.Test;
-
-public class ClusterUtilsTest {
-
-    @Test
-    public void testMergeUrl() throws Exception {
-        URL providerURL = URL.valueOf("dubbo://localhost:55555");
-        providerURL = providerURL.setPath("path")
-                .setUsername("username")
-                .setPassword("password");
-
-        providerURL = providerURL.addParameter(Constants.GROUP_KEY, "dubbo")
-                .addParameter(Constants.VERSION_KEY, "1.2.3")
-                .addParameter(Constants.DUBBO_VERSION_KEY, "2.3.7")
-                .addParameter(Constants.THREADPOOL_KEY, "fixed")
-                .addParameter(Constants.THREADS_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.THREAD_NAME_KEY, "test")
-                .addParameter(Constants.CORE_THREADS_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.QUEUES_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.ALIVE_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADS_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADPOOL_KEY, "fixed")
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.CORE_THREADS_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.QUEUES_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.ALIVE_KEY, Integer.MAX_VALUE)
-                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREAD_NAME_KEY, "test");
-
-        URL consumerURL = URL.valueOf("dubbo://localhost:55555");
-        consumerURL = consumerURL.addParameter(Constants.PID_KEY, "1234");
-        consumerURL = consumerURL.addParameter(Constants.THREADPOOL_KEY, "foo");
-
-        URL url = ClusterUtils.mergeUrl(providerURL, consumerURL.getParameters());
-
-        Assert.assertFalse(url.hasParameter(Constants.THREADS_KEY));
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADS_KEY));
-
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADPOOL_KEY));
-
-        Assert.assertFalse(url.hasParameter(Constants.CORE_THREADS_KEY));
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.CORE_THREADS_KEY));
-
-        Assert.assertFalse(url.hasParameter(Constants.QUEUES_KEY));
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.QUEUES_KEY));
-
-        Assert.assertFalse(url.hasParameter(Constants.ALIVE_KEY));
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.ALIVE_KEY));
-
-        Assert.assertFalse(url.hasParameter(Constants.THREAD_NAME_KEY));
-        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREAD_NAME_KEY));
-
-        Assert.assertEquals(url.getPath(), "path");
-        Assert.assertEquals(url.getUsername(), "username");
-        Assert.assertEquals(url.getPassword(), "password");
-        Assert.assertEquals(url.getParameter(Constants.PID_KEY), "1234");
-        Assert.assertEquals(url.getParameter(Constants.THREADPOOL_KEY), "foo");
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+public class ClusterUtilsTest {
+
+    @Test
+    public void testMergeUrl() throws Exception {
+        URL providerURL = URL.valueOf("dubbo://localhost:55555");
+        providerURL = providerURL.setPath("path")
+                .setUsername("username")
+                .setPassword("password");
+
+        providerURL = providerURL.addParameter(Constants.GROUP_KEY, "dubbo")
+                .addParameter(Constants.VERSION_KEY, "1.2.3")
+                .addParameter(Constants.DUBBO_VERSION_KEY, "2.3.7")
+                .addParameter(Constants.THREADPOOL_KEY, "fixed")
+                .addParameter(Constants.THREADS_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.THREAD_NAME_KEY, "test")
+                .addParameter(Constants.CORE_THREADS_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.QUEUES_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.ALIVE_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADS_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADPOOL_KEY, "fixed")
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.CORE_THREADS_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.QUEUES_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.ALIVE_KEY, Integer.MAX_VALUE)
+                .addParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREAD_NAME_KEY, "test");
+
+        URL consumerURL = URL.valueOf("dubbo://localhost:55555");
+        consumerURL = consumerURL.addParameter(Constants.PID_KEY, "1234");
+        consumerURL = consumerURL.addParameter(Constants.THREADPOOL_KEY, "foo");
+
+        URL url = ClusterUtils.mergeUrl(providerURL, consumerURL.getParameters());
+
+        Assert.assertFalse(url.hasParameter(Constants.THREADS_KEY));
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADS_KEY));
+
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREADPOOL_KEY));
+
+        Assert.assertFalse(url.hasParameter(Constants.CORE_THREADS_KEY));
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.CORE_THREADS_KEY));
+
+        Assert.assertFalse(url.hasParameter(Constants.QUEUES_KEY));
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.QUEUES_KEY));
+
+        Assert.assertFalse(url.hasParameter(Constants.ALIVE_KEY));
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.ALIVE_KEY));
+
+        Assert.assertFalse(url.hasParameter(Constants.THREAD_NAME_KEY));
+        Assert.assertFalse(url.hasParameter(Constants.DEFAULT_KEY_PREFIX + Constants.THREAD_NAME_KEY));
+
+        Assert.assertEquals(url.getPath(), "path");
+        Assert.assertEquals(url.getUsername(), "username");
+        Assert.assertEquals(url.getPassword(), "password");
+        Assert.assertEquals(url.getParameter(Constants.PID_KEY), "1234");
+        Assert.assertEquals(url.getParameter(Constants.THREADPOOL_KEY), "foo");
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/FailfastClusterInvokerTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/FailfastClusterInvokerTest.java
index 41dc79ca2e..2f5ffd7c6d 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/FailfastClusterInvokerTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/FailfastClusterInvokerTest.java
@@ -1,125 +1,125 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcContext;
-import org.apache.dubbo.rpc.RpcException;
-import org.apache.dubbo.rpc.RpcInvocation;
-import org.apache.dubbo.rpc.RpcResult;
-import org.apache.dubbo.rpc.cluster.Directory;
-
-import org.junit.Assert;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.fail;
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-/**
- * FailfastClusterInvokerTest
- *
- */
-@SuppressWarnings("unchecked")
-public class FailfastClusterInvokerTest {
-    List<Invoker<FailfastClusterInvokerTest>> invokers = new ArrayList<Invoker<FailfastClusterInvokerTest>>();
-    URL url = URL.valueOf("test://test:11/test");
-    Invoker<FailfastClusterInvokerTest> invoker1 = mock(Invoker.class);
-    RpcInvocation invocation = new RpcInvocation();
-    Directory<FailfastClusterInvokerTest> dic;
-    Result result = new RpcResult();
-
-    /**
-     * @throws java.lang.Exception
-     */
-
-    @Before
-    public void setUp() throws Exception {
-
-        dic = mock(Directory.class);
-
-        given(dic.getUrl()).willReturn(url);
-        given(dic.list(invocation)).willReturn(invokers);
-        given(dic.getInterface()).willReturn(FailfastClusterInvokerTest.class);
-
-        invocation.setMethodName("method1");
-
-        invokers.add(invoker1);
-    }
-
-    private void resetInvoker1ToException() {
-        given(invoker1.invoke(invocation)).willThrow(new RuntimeException());
-        given(invoker1.getUrl()).willReturn(url);
-        given(invoker1.getInterface()).willReturn(FailfastClusterInvokerTest.class);
-    }
-
-    private void resetInvoker1ToNoException() {
-        given(invoker1.invoke(invocation)).willReturn(result);
-        given(invoker1.getUrl()).willReturn(url);
-        given(invoker1.getInterface()).willReturn(FailfastClusterInvokerTest.class);
-    }
-
-    @Test(expected = RpcException.class)
-    public void testInvokeExceptoin() {
-        resetInvoker1ToException();
-        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
-        invoker.invoke(invocation);
-        Assert.assertSame(invoker1, RpcContext.getContext().getInvoker());
-    }
-
-    @Test()
-    public void testInvokeNoExceptoin() {
-
-        resetInvoker1ToNoException();
-
-        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
-        Result ret = invoker.invoke(invocation);
-        Assert.assertSame(result, ret);
-    }
-
-    @Test()
-    public void testNoInvoke() {
-        dic = mock(Directory.class);
-
-        given(dic.getUrl()).willReturn(url);
-        given(dic.list(invocation)).willReturn(null);
-        given(dic.getInterface()).willReturn(FailfastClusterInvokerTest.class);
-
-        invocation.setMethodName("method1");
-
-        invokers.add(invoker1);
-
-        resetInvoker1ToNoException();
-
-        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
-        try {
-            invoker.invoke(invocation);
-            fail();
-        } catch (RpcException expected) {
-            assertFalse(expected.getCause() instanceof RpcException);
-        }
-    }
-
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcContext;
+import org.apache.dubbo.rpc.RpcException;
+import org.apache.dubbo.rpc.RpcInvocation;
+import org.apache.dubbo.rpc.RpcResult;
+import org.apache.dubbo.rpc.cluster.Directory;
+
+import org.junit.Assert;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.fail;
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+/**
+ * FailfastClusterInvokerTest
+ *
+ */
+@SuppressWarnings("unchecked")
+public class FailfastClusterInvokerTest {
+    List<Invoker<FailfastClusterInvokerTest>> invokers = new ArrayList<Invoker<FailfastClusterInvokerTest>>();
+    URL url = URL.valueOf("test://test:11/test");
+    Invoker<FailfastClusterInvokerTest> invoker1 = mock(Invoker.class);
+    RpcInvocation invocation = new RpcInvocation();
+    Directory<FailfastClusterInvokerTest> dic;
+    Result result = new RpcResult();
+
+    /**
+     * @throws java.lang.Exception
+     */
+
+    @Before
+    public void setUp() throws Exception {
+
+        dic = mock(Directory.class);
+
+        given(dic.getUrl()).willReturn(url);
+        given(dic.list(invocation)).willReturn(invokers);
+        given(dic.getInterface()).willReturn(FailfastClusterInvokerTest.class);
+
+        invocation.setMethodName("method1");
+
+        invokers.add(invoker1);
+    }
+
+    private void resetInvoker1ToException() {
+        given(invoker1.invoke(invocation)).willThrow(new RuntimeException());
+        given(invoker1.getUrl()).willReturn(url);
+        given(invoker1.getInterface()).willReturn(FailfastClusterInvokerTest.class);
+    }
+
+    private void resetInvoker1ToNoException() {
+        given(invoker1.invoke(invocation)).willReturn(result);
+        given(invoker1.getUrl()).willReturn(url);
+        given(invoker1.getInterface()).willReturn(FailfastClusterInvokerTest.class);
+    }
+
+    @Test(expected = RpcException.class)
+    public void testInvokeExceptoin() {
+        resetInvoker1ToException();
+        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
+        invoker.invoke(invocation);
+        Assert.assertSame(invoker1, RpcContext.getContext().getInvoker());
+    }
+
+    @Test()
+    public void testInvokeNoExceptoin() {
+
+        resetInvoker1ToNoException();
+
+        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
+        Result ret = invoker.invoke(invocation);
+        Assert.assertSame(result, ret);
+    }
+
+    @Test()
+    public void testNoInvoke() {
+        dic = mock(Directory.class);
+
+        given(dic.getUrl()).willReturn(url);
+        given(dic.list(invocation)).willReturn(null);
+        given(dic.getInterface()).willReturn(FailfastClusterInvokerTest.class);
+
+        invocation.setMethodName("method1");
+
+        invokers.add(invoker1);
+
+        resetInvoker1ToNoException();
+
+        FailfastClusterInvoker<FailfastClusterInvokerTest> invoker = new FailfastClusterInvoker<FailfastClusterInvokerTest>(dic);
+        try {
+            invoker.invoke(invocation);
+            fail();
+        } catch (RpcException expected) {
+            assertFalse(expected.getCause() instanceof RpcException);
+        }
+    }
+
 }
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/Menu.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/Menu.java
index b3564d27ae..8dc5393fd3 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/Menu.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/Menu.java
@@ -1,66 +1,66 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-public class Menu {
-
-    private Map<String, List<String>> menus = new HashMap<String, List<String>>();
-
-    public Menu() {
-    }
-
-    public Menu(Map<String, List<String>> menus) {
-        for (String key : menus.keySet()) {
-            this.menus.put(key, new ArrayList<String>(menus.get(key)));
-        }
-    }
-
-    public void putMenuItem(String menu, String item) {
-        List<String> items = menus.get(menu);
-        if (item == null) {
-            items = new ArrayList<String>();
-            menus.put(menu, items);
-        }
-        items.add(item);
-    }
-
-    public void addMenu(String menu, List<String> items) {
-        List<String> menuItems = menus.get(menu);
-        if (menuItems == null) {
-            menus.put(menu, new ArrayList<String>(items));
-        } else {
-            menuItems.addAll(new ArrayList<String>(items));
-        }
-    }
-
-    public Map<String, List<String>> getMenus() {
-        return Collections.unmodifiableMap(menus);
-    }
-
-    public void merge(Menu menu) {
-        for (Map.Entry<String, List<String>> entry : menu.menus.entrySet()) {
-            addMenu(entry.getKey(), entry.getValue());
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class Menu {
+
+    private Map<String, List<String>> menus = new HashMap<String, List<String>>();
+
+    public Menu() {
+    }
+
+    public Menu(Map<String, List<String>> menus) {
+        for (String key : menus.keySet()) {
+            this.menus.put(key, new ArrayList<String>(menus.get(key)));
+        }
+    }
+
+    public void putMenuItem(String menu, String item) {
+        List<String> items = menus.get(menu);
+        if (item == null) {
+            items = new ArrayList<String>();
+            menus.put(menu, items);
+        }
+        items.add(item);
+    }
+
+    public void addMenu(String menu, List<String> items) {
+        List<String> menuItems = menus.get(menu);
+        if (menuItems == null) {
+            menus.put(menu, new ArrayList<String>(items));
+        } else {
+            menuItems.addAll(new ArrayList<String>(items));
+        }
+    }
+
+    public Map<String, List<String>> getMenus() {
+        return Collections.unmodifiableMap(menus);
+    }
+
+    public void merge(Menu menu) {
+        for (Map.Entry<String, List<String>> entry : menu.menus.entrySet()) {
+            addMenu(entry.getKey(), entry.getValue());
+        }
+    }
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MenuService.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MenuService.java
index caf27df57b..444cfe9820 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MenuService.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MenuService.java
@@ -1,27 +1,27 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import java.util.List;
-
-public interface MenuService {
-
-    public Menu getMenu();
-
-    public void addMenu(String menu, List<String> items);
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import java.util.List;
+
+public interface MenuService {
+
+    public Menu getMenu();
+
+    public void addMenu(String menu, List<String> items);
+
+}
diff --git a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvokerTest.java b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvokerTest.java
index 12d6ba41e3..b6821257ba 100644
--- a/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvokerTest.java
+++ b/dubbo-cluster/src/test/java/org/apache/dubbo/rpc/cluster/support/MergeableClusterInvokerTest.java
@@ -1,226 +1,226 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.rpc.cluster.support;
-
-import org.apache.dubbo.common.Constants;
-import org.apache.dubbo.common.URL;
-import org.apache.dubbo.rpc.Invocation;
-import org.apache.dubbo.rpc.Invoker;
-import org.apache.dubbo.rpc.Result;
-import org.apache.dubbo.rpc.RpcResult;
-import org.apache.dubbo.rpc.cluster.Directory;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.lang.reflect.InvocationHandler;
-import java.lang.reflect.Method;
-import java.lang.reflect.Proxy;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.mockito.BDDMockito.given;
-import static org.mockito.Mockito.mock;
-
-public class MergeableClusterInvokerTest {
-
-    private Directory directory = mock(Directory.class);
-    private Invoker firstInvoker = mock(Invoker.class);
-    private Invoker secondInvoker = mock(Invoker.class);
-    private Invocation invocation = mock(Invocation.class);
-
-    private MergeableClusterInvoker<MenuService> mergeableClusterInvoker;
-
-    private String[] list1 = {"10", "11", "12"};
-    private String[] list2 = {"20", "21", "22"};
-    private String[] list3 = {"23", "24", "25"};
-    private String[] list4 = {"30", "31", "32"};
-
-    private Map<String, List<String>> firstMenuMap = new HashMap<String, List<String>>() {
-        {
-            put("1", Arrays.asList(list1));
-            put("2", Arrays.asList(list2));
-        }
-    };
-
-    private Map<String, List<String>> secondMenuMap = new HashMap<String, List<String>>() {
-        {
-            put("2", Arrays.asList(list3));
-            put("3", Arrays.asList(list4));
-        }
-    };
-
-    private Menu firstMenu = new Menu(firstMenuMap);
-    private Menu secondMenu = new Menu(secondMenuMap);
-
-    private URL url = URL.valueOf("test://test/" + MenuService.class.getName());
-
-    static void merge(Map<String, List<String>> first, Map<String, List<String>> second) {
-        for (Map.Entry<String, List<String>> entry : second.entrySet()) {
-            List<String> value = first.get(entry.getKey());
-            if (value != null) {
-                value.addAll(entry.getValue());
-            } else {
-                first.put(entry.getKey(), new ArrayList<String>(entry.getValue()));
-            }
-        }
-    }
-
-    @Before
-    public void setUp() throws Exception {
-
-        directory = mock(Directory.class);
-        firstInvoker = mock(Invoker.class);
-        secondInvoker = mock(Invoker.class);
-        invocation = mock(Invocation.class);
-
-    }
-
-    @Test
-    public void testGetMenuSuccessfully() throws Exception {
-
-        // setup
-        url = url.addParameter(Constants.MERGER_KEY, ".merge");
-
-        given(invocation.getMethodName()).willReturn("getMenu");
-        given(invocation.getParameterTypes()).willReturn(new Class<?>[]{});
-        given(invocation.getArguments()).willReturn(new Object[]{});
-        given(invocation.getAttachments()).willReturn(new HashMap<String, String>())
-                ;
-        given(invocation.getInvoker()).willReturn(firstInvoker);
-
-        firstInvoker = (Invoker) Proxy.newProxyInstance(getClass().getClassLoader(), new Class<?>[]{Invoker.class}, new InvocationHandler() {
-
-            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
-                if ("getUrl".equals(method.getName())) {
-                    return url.addParameter(Constants.GROUP_KEY, "first");
-                }
-                if ("getInterface".equals(method.getName())) {
-                    return MenuService.class;
-                }
-                if ("invoke".equals(method.getName())) {
-                    return new RpcResult(firstMenu);
-                }
-                return null;
-            }
-        });
-
-        secondInvoker = (Invoker) Proxy.newProxyInstance(getClass().getClassLoader(), new Class<?>[]{Invoker.class}, new InvocationHandler() {
-
-            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
-                if ("getUrl".equals(method.getName())) {
-                    return url.addParameter(Constants.GROUP_KEY, "second");
-                }
-                if ("getInterface".equals(method.getName())) {
-                    return MenuService.class;
-                }
-                if ("invoke".equals(method.getName())) {
-                    return new RpcResult(secondMenu);
-                }
-                return null;
-            }
-        });
-
-        given(directory.list(invocation)).willReturn(new ArrayList() {
-
-            {
-                add(firstInvoker);
-                add(secondInvoker);
-            }
-        });
-        given(directory.getUrl()).willReturn(url);
-        given(directory.getInterface()).willReturn(MenuService.class);
-
-        mergeableClusterInvoker = new MergeableClusterInvoker<MenuService>(directory);
-
-        // invoke
-        Result result = mergeableClusterInvoker.invoke(invocation);
-        Assert.assertTrue(result.getValue() instanceof Menu);
-        Menu menu = (Menu) result.getValue();
-        Map<String, List<String>> expected = new HashMap<String, List<String>>();
-        merge(expected, firstMenuMap);
-        merge(expected, secondMenuMap);
-        assertEquals(expected.keySet(), menu.getMenus().keySet());
-        for (String key : expected.keySet()) {
-            // FIXME: cannot guarantee the sequence of the merge result, check implementation in
-            // MergeableClusterInvoker#invoke
-            List<String> values1 = new ArrayList<String>(expected.get(key));
-            List<String> values2 = new ArrayList<String>(menu.getMenus().get(key));
-            Collections.sort(values1);
-            Collections.sort(values2);
-            assertEquals(values1, values2);
-        }
-    }
-
-    @Test
-    public void testAddMenu() throws Exception {
-
-        String menu = "first";
-        List<String> menuItems = new ArrayList<String>() {
-            {
-                add("1");
-                add("2");
-            }
-        };
-
-        given(invocation.getMethodName()).willReturn("addMenu");
-        given(invocation.getParameterTypes()).willReturn(
-                new Class<?>[]{String.class, List.class});
-        given(invocation.getArguments()).willReturn(new Object[]{menu, menuItems})
-                ;
-        given(invocation.getAttachments()).willReturn(new HashMap<String, String>())
-                ;
-        given(invocation.getInvoker()).willReturn(firstInvoker);
-
-        given(firstInvoker.getUrl()).willReturn(
-                url.addParameter(Constants.GROUP_KEY, "first"));
-        given(firstInvoker.getInterface()).willReturn(MenuService.class);
-        given(firstInvoker.invoke(invocation)).willReturn(new RpcResult())
-                ;
-        given(firstInvoker.isAvailable()).willReturn(true);
-
-        given(secondInvoker.getUrl()).willReturn(
-                url.addParameter(Constants.GROUP_KEY, "second"));
-        given(secondInvoker.getInterface()).willReturn(MenuService.class);
-        given(secondInvoker.invoke(invocation)).willReturn(new RpcResult())
-                ;
-        given(secondInvoker.isAvailable()).willReturn(true);
-
-        given(directory.list(invocation)).willReturn(new ArrayList() {
-
-            {
-                add(firstInvoker);
-                add(secondInvoker);
-            }
-        });
-        given(directory.getUrl()).willReturn(url);
-        given(directory.getInterface()).willReturn(MenuService.class);
-
-        mergeableClusterInvoker = new MergeableClusterInvoker<MenuService>(directory);
-
-        Result result = mergeableClusterInvoker.invoke(invocation);
-        Assert.assertNull(result.getValue());
-
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.rpc.cluster.support;
+
+import org.apache.dubbo.common.Constants;
+import org.apache.dubbo.common.URL;
+import org.apache.dubbo.rpc.Invocation;
+import org.apache.dubbo.rpc.Invoker;
+import org.apache.dubbo.rpc.Result;
+import org.apache.dubbo.rpc.RpcResult;
+import org.apache.dubbo.rpc.cluster.Directory;
+
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.BDDMockito.given;
+import static org.mockito.Mockito.mock;
+
+public class MergeableClusterInvokerTest {
+
+    private Directory directory = mock(Directory.class);
+    private Invoker firstInvoker = mock(Invoker.class);
+    private Invoker secondInvoker = mock(Invoker.class);
+    private Invocation invocation = mock(Invocation.class);
+
+    private MergeableClusterInvoker<MenuService> mergeableClusterInvoker;
+
+    private String[] list1 = {"10", "11", "12"};
+    private String[] list2 = {"20", "21", "22"};
+    private String[] list3 = {"23", "24", "25"};
+    private String[] list4 = {"30", "31", "32"};
+
+    private Map<String, List<String>> firstMenuMap = new HashMap<String, List<String>>() {
+        {
+            put("1", Arrays.asList(list1));
+            put("2", Arrays.asList(list2));
+        }
+    };
+
+    private Map<String, List<String>> secondMenuMap = new HashMap<String, List<String>>() {
+        {
+            put("2", Arrays.asList(list3));
+            put("3", Arrays.asList(list4));
+        }
+    };
+
+    private Menu firstMenu = new Menu(firstMenuMap);
+    private Menu secondMenu = new Menu(secondMenuMap);
+
+    private URL url = URL.valueOf("test://test/" + MenuService.class.getName());
+
+    static void merge(Map<String, List<String>> first, Map<String, List<String>> second) {
+        for (Map.Entry<String, List<String>> entry : second.entrySet()) {
+            List<String> value = first.get(entry.getKey());
+            if (value != null) {
+                value.addAll(entry.getValue());
+            } else {
+                first.put(entry.getKey(), new ArrayList<String>(entry.getValue()));
+            }
+        }
+    }
+
+    @Before
+    public void setUp() throws Exception {
+
+        directory = mock(Directory.class);
+        firstInvoker = mock(Invoker.class);
+        secondInvoker = mock(Invoker.class);
+        invocation = mock(Invocation.class);
+
+    }
+
+    @Test
+    public void testGetMenuSuccessfully() throws Exception {
+
+        // setup
+        url = url.addParameter(Constants.MERGER_KEY, ".merge");
+
+        given(invocation.getMethodName()).willReturn("getMenu");
+        given(invocation.getParameterTypes()).willReturn(new Class<?>[]{});
+        given(invocation.getArguments()).willReturn(new Object[]{});
+        given(invocation.getAttachments()).willReturn(new HashMap<String, String>())
+                ;
+        given(invocation.getInvoker()).willReturn(firstInvoker);
+
+        firstInvoker = (Invoker) Proxy.newProxyInstance(getClass().getClassLoader(), new Class<?>[]{Invoker.class}, new InvocationHandler() {
+
+            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
+                if ("getUrl".equals(method.getName())) {
+                    return url.addParameter(Constants.GROUP_KEY, "first");
+                }
+                if ("getInterface".equals(method.getName())) {
+                    return MenuService.class;
+                }
+                if ("invoke".equals(method.getName())) {
+                    return new RpcResult(firstMenu);
+                }
+                return null;
+            }
+        });
+
+        secondInvoker = (Invoker) Proxy.newProxyInstance(getClass().getClassLoader(), new Class<?>[]{Invoker.class}, new InvocationHandler() {
+
+            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
+                if ("getUrl".equals(method.getName())) {
+                    return url.addParameter(Constants.GROUP_KEY, "second");
+                }
+                if ("getInterface".equals(method.getName())) {
+                    return MenuService.class;
+                }
+                if ("invoke".equals(method.getName())) {
+                    return new RpcResult(secondMenu);
+                }
+                return null;
+            }
+        });
+
+        given(directory.list(invocation)).willReturn(new ArrayList() {
+
+            {
+                add(firstInvoker);
+                add(secondInvoker);
+            }
+        });
+        given(directory.getUrl()).willReturn(url);
+        given(directory.getInterface()).willReturn(MenuService.class);
+
+        mergeableClusterInvoker = new MergeableClusterInvoker<MenuService>(directory);
+
+        // invoke
+        Result result = mergeableClusterInvoker.invoke(invocation);
+        Assert.assertTrue(result.getValue() instanceof Menu);
+        Menu menu = (Menu) result.getValue();
+        Map<String, List<String>> expected = new HashMap<String, List<String>>();
+        merge(expected, firstMenuMap);
+        merge(expected, secondMenuMap);
+        assertEquals(expected.keySet(), menu.getMenus().keySet());
+        for (String key : expected.keySet()) {
+            // FIXME: cannot guarantee the sequence of the merge result, check implementation in
+            // MergeableClusterInvoker#invoke
+            List<String> values1 = new ArrayList<String>(expected.get(key));
+            List<String> values2 = new ArrayList<String>(menu.getMenus().get(key));
+            Collections.sort(values1);
+            Collections.sort(values2);
+            assertEquals(values1, values2);
+        }
+    }
+
+    @Test
+    public void testAddMenu() throws Exception {
+
+        String menu = "first";
+        List<String> menuItems = new ArrayList<String>() {
+            {
+                add("1");
+                add("2");
+            }
+        };
+
+        given(invocation.getMethodName()).willReturn("addMenu");
+        given(invocation.getParameterTypes()).willReturn(
+                new Class<?>[]{String.class, List.class});
+        given(invocation.getArguments()).willReturn(new Object[]{menu, menuItems})
+                ;
+        given(invocation.getAttachments()).willReturn(new HashMap<String, String>())
+                ;
+        given(invocation.getInvoker()).willReturn(firstInvoker);
+
+        given(firstInvoker.getUrl()).willReturn(
+                url.addParameter(Constants.GROUP_KEY, "first"));
+        given(firstInvoker.getInterface()).willReturn(MenuService.class);
+        given(firstInvoker.invoke(invocation)).willReturn(new RpcResult())
+                ;
+        given(firstInvoker.isAvailable()).willReturn(true);
+
+        given(secondInvoker.getUrl()).willReturn(
+                url.addParameter(Constants.GROUP_KEY, "second"));
+        given(secondInvoker.getInterface()).willReturn(MenuService.class);
+        given(secondInvoker.invoke(invocation)).willReturn(new RpcResult())
+                ;
+        given(secondInvoker.isAvailable()).willReturn(true);
+
+        given(directory.list(invocation)).willReturn(new ArrayList() {
+
+            {
+                add(firstInvoker);
+                add(secondInvoker);
+            }
+        });
+        given(directory.getUrl()).willReturn(url);
+        given(directory.getInterface()).willReturn(MenuService.class);
+
+        mergeableClusterInvoker = new MergeableClusterInvoker<MenuService>(directory);
+
+        Result result = mergeableClusterInvoker.invoke(invocation);
+        Assert.assertNull(result.getValue());
+
+    }
+
+}
diff --git a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/availablerule.javascript b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/availablerule.javascript
index c76de32ee4..8c051a047f 100644
--- a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/availablerule.javascript
+++ b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/availablerule.javascript
@@ -1,11 +1,11 @@
-function route(invokers,invocation,context){ 
-	var result = new java.util.ArrayList(invokers.size());
-	
-	for (i=0;i<invokers.size(); i++){ 
-	    if (invokers.get(i).isAvailable()) {
-	        result.add(invokers.get(i)) ;
-	    }
-	} ; 
-	return result;
-};
+function route(invokers,invocation,context){ 
+	var result = new java.util.ArrayList(invokers.size());
+	
+	for (i=0;i<invokers.size(); i++){ 
+	    if (invokers.get(i).isAvailable()) {
+	        result.add(invokers.get(i)) ;
+	    }
+	} ; 
+	return result;
+};
 route(invokers,invocation,context);
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/methodrule.javascript b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/methodrule.javascript
index 77ff4561b3..96f4746863 100644
--- a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/methodrule.javascript
+++ b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/methodrule.javascript
@@ -1,10 +1,10 @@
-function route(invokers,invocation,context){ 
-	var result = new java.util.ArrayList();
-	if (invokers.size()>1 && invocation.getMethodName() .equals("method1")) {
-	   	result.add(invokers.get(0)) ;
-	} else {
-		result.add(invokers.get(1)) ;
-	}
-	return result;
-};
+function route(invokers,invocation,context){ 
+	var result = new java.util.ArrayList();
+	if (invokers.size()>1 && invocation.getMethodName() .equals("method1")) {
+	   	result.add(invokers.get(0)) ;
+	} else {
+		result.add(invokers.get(1)) ;
+	}
+	return result;
+};
 route(invokers,invocation,context);
\ No newline at end of file
diff --git a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/notAvailablerule.javascript b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/notAvailablerule.javascript
index 1fcdcaeb0d..acee8d0ebc 100644
--- a/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/notAvailablerule.javascript
+++ b/dubbo-cluster/src/test/resources/org/apache/dubbo/rpc/cluster/router/file/notAvailablerule.javascript
@@ -1,11 +1,11 @@
-function route(invokers,invocation,context){ 
-	var result = new java.util.ArrayList(invokers.size());
-	
-	for (i=0;i<invokers.size(); i++){ 
-	    if (!invokers.get(i).isAvailable()) {
-	        result.add(invokers.get(i)) ;
-	    }
-	} ; 
-	return result;
-};
+function route(invokers,invocation,context){ 
+	var result = new java.util.ArrayList(invokers.size());
+	
+	for (i=0;i<invokers.size(); i++){ 
+	    if (!invokers.get(i).isAvailable()) {
+	        result.add(invokers.get(i)) ;
+	    }
+	} ; 
+	return result;
+};
 route(invokers,invocation,context);
\ No newline at end of file
diff --git a/dubbo-common/pom.xml b/dubbo-common/pom.xml
index 22a13222fe..b1bd947518 100644
--- a/dubbo-common/pom.xml
+++ b/dubbo-common/pom.xml
@@ -1,81 +1,81 @@
-<!--
-  Licensed to the Apache Software Foundation (ASF) under one or more
-  contributor license agreements.  See the NOTICE file distributed with
-  this work for additional information regarding copyright ownership.
-  The ASF licenses this file to You under the Apache License, Version 2.0
-  (the "License"); you may not use this file except in compliance with
-  the License.  You may obtain a copy of the License at
-
-      http://www.apache.org/licenses/LICENSE-2.0
-
-  Unless required by applicable law or agreed to in writing, software
-  distributed under the License is distributed on an "AS IS" BASIS,
-  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  See the License for the specific language governing permissions and
-  limitations under the License.
-  -->
-
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
-    <modelVersion>4.0.0</modelVersion>
-    <parent>
-        <groupId>org.apache.dubbo</groupId>
-        <artifactId>dubbo-parent</artifactId>
-        <version>2.7.0-SNAPSHOT</version>
-    </parent>
-    <artifactId>dubbo-common</artifactId>
-    <packaging>jar</packaging>
-    <name>${project.artifactId}</name>
-    <description>The common module of dubbo project</description>
-    <properties>
-        <skip_maven_deploy>false</skip_maven_deploy>
-    </properties>
-    <dependencies>
-        <dependency>
-            <groupId>org.slf4j</groupId>
-            <artifactId>slf4j-api</artifactId>
-            <scope>provided</scope>
-        </dependency>
-        <dependency>
-            <groupId>commons-logging</groupId>
-            <artifactId>commons-logging</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>log4j</groupId>
-            <artifactId>log4j</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.logging.log4j</groupId>
-            <artifactId>log4j-api</artifactId>
-            <scope>provided</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.apache.logging.log4j</groupId>
-            <artifactId>log4j-core</artifactId>
-            <scope>provided</scope>
-        </dependency>
-        <dependency>
-            <groupId>org.javassist</groupId>
-            <artifactId>javassist</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>com.alibaba</groupId>
-            <artifactId>hessian-lite</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>com.alibaba</groupId>
-            <artifactId>fastjson</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>com.esotericsoftware</groupId>
-            <artifactId>kryo</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>de.javakaffee</groupId>
-            <artifactId>kryo-serializers</artifactId>
-        </dependency>
-        <dependency>
-            <groupId>de.ruedigermoeller</groupId>
-            <artifactId>fst</artifactId>
-        </dependency>
-    </dependencies>
+<!--
+  Licensed to the Apache Software Foundation (ASF) under one or more
+  contributor license agreements.  See the NOTICE file distributed with
+  this work for additional information regarding copyright ownership.
+  The ASF licenses this file to You under the Apache License, Version 2.0
+  (the "License"); you may not use this file except in compliance with
+  the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+  -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+    <parent>
+        <groupId>org.apache.dubbo</groupId>
+        <artifactId>dubbo-parent</artifactId>
+        <version>2.7.0-SNAPSHOT</version>
+    </parent>
+    <artifactId>dubbo-common</artifactId>
+    <packaging>jar</packaging>
+    <name>${project.artifactId}</name>
+    <description>The common module of dubbo project</description>
+    <properties>
+        <skip_maven_deploy>false</skip_maven_deploy>
+    </properties>
+    <dependencies>
+        <dependency>
+            <groupId>org.slf4j</groupId>
+            <artifactId>slf4j-api</artifactId>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>commons-logging</groupId>
+            <artifactId>commons-logging</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>log4j</groupId>
+            <artifactId>log4j</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.logging.log4j</groupId>
+            <artifactId>log4j-api</artifactId>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.logging.log4j</groupId>
+            <artifactId>log4j-core</artifactId>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.javassist</groupId>
+            <artifactId>javassist</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>com.alibaba</groupId>
+            <artifactId>hessian-lite</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>com.alibaba</groupId>
+            <artifactId>fastjson</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>com.esotericsoftware</groupId>
+            <artifactId>kryo</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>de.javakaffee</groupId>
+            <artifactId>kryo-serializers</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>de.ruedigermoeller</groupId>
+            <artifactId>fst</artifactId>
+        </dependency>
+    </dependencies>
 </project>
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/com/alibaba/dubbo/common/extension/Activate.java b/dubbo-common/src/main/java/com/alibaba/dubbo/common/extension/Activate.java
index 9aecbce000..b767cde5d1 100644
--- a/dubbo-common/src/main/java/com/alibaba/dubbo/common/extension/Activate.java
+++ b/dubbo-common/src/main/java/com/alibaba/dubbo/common/extension/Activate.java
@@ -1,45 +1,45 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.alibaba.dubbo.common.extension;
-
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * See @org.apache.dubbo.common.extension.Activate
- */
-@Documented
-@Retention(RetentionPolicy.RUNTIME)
-@Target({ElementType.TYPE, ElementType.METHOD})
-@Deprecated
-public @interface Activate {
-
-    String[] group() default {};
-
-    String[] value() default {};
-
-    @Deprecated
-    String[] before() default {};
-
-    @Deprecated
-    String[] after() default {};
-
-    int order() default 0;
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.alibaba.dubbo.common.extension;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * See @org.apache.dubbo.common.extension.Activate
+ */
+@Documented
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.TYPE, ElementType.METHOD})
+@Deprecated
+public @interface Activate {
+
+    String[] group() default {};
+
+    String[] value() default {};
+
+    @Deprecated
+    String[] before() default {};
+
+    @Deprecated
+    String[] after() default {};
+
+    int order() default 0;
 }
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/Constants.java b/dubbo-common/src/main/java/org/apache/dubbo/common/Constants.java
index 9506930690..5583d9a275 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/Constants.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/Constants.java
@@ -1,652 +1,652 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.common;
-
-import java.util.concurrent.ExecutorService;
-import java.util.regex.Pattern;
-/**
- * Constants
- */
-public class Constants {
-
-    public static final String PROVIDER = "provider";
-
-    public static final String CONSUMER = "consumer";
-
-    public static final String REGISTER = "register";
-
-    public static final String UNREGISTER = "unregister";
-
-    public static final String SUBSCRIBE = "subscribe";
-
-    public static final String UNSUBSCRIBE = "unsubscribe";
-
-    public static final String CATEGORY_KEY = "category";
-
-    public static final String PROVIDERS_CATEGORY = "providers";
-
-    public static final String CONSUMERS_CATEGORY = "consumers";
-
-    public static final String ROUTERS_CATEGORY = "routers";
-
-    public static final String CONFIGURATORS_CATEGORY = "configurators";
-
-    public static final String DEFAULT_CATEGORY = PROVIDERS_CATEGORY;
-
-    public static final String ENABLED_KEY = "enabled";
-
-    public static final String DISABLED_KEY = "disabled";
-
-    public static final String VALIDATION_KEY = "validation";
-
-    public static final String CACHE_KEY = "cache";
-
-    public static final String DYNAMIC_KEY = "dynamic";
-
-    public static final String DUBBO_PROPERTIES_KEY = "dubbo.properties.file";
-
-    public static final String DEFAULT_DUBBO_PROPERTIES = "dubbo.properties";
-
-    public static final String SENT_KEY = "sent";
-
-    public static final boolean DEFAULT_SENT = false;
-
-    public static final String REGISTRY_PROTOCOL = "registry";
-
-    public static final String $INVOKE = "$invoke";
-
-    public static final String $ECHO = "$echo";
-
-    public static final int DEFAULT_IO_THREADS = Math.min(Runtime.getRuntime().availableProcessors() + 1, 32);
-
-    public static final String DEFAULT_PROXY = "javassist";
-
-    public static final int DEFAULT_PAYLOAD = 8 * 1024 * 1024;                      // 8M
-
-    public static final String DEFAULT_CLUSTER = "failover";
-
-    public static final String DEFAULT_DIRECTORY = "dubbo";
-
-    public static final String DEFAULT_LOADBALANCE = "random";
-
-    public static final String DEFAULT_PROTOCOL = "dubbo";
-
-    public static final String DEFAULT_EXCHANGER = "header";
-
-    public static final String DEFAULT_TRANSPORTER = "netty";
-
-    public static final String DEFAULT_REMOTING_SERVER = "netty";
-
-    public static final String DEFAULT_REMOTING_CLIENT = "netty";
-
-    public static final String DEFAULT_REMOTING_CODEC = "dubbo";
-
-    public static final String DEFAULT_REMOTING_SERIALIZATION = "hessian2";
-
-    public static final String DEFAULT_HTTP_SERVER = "servlet";
-
-    public static final String DEFAULT_HTTP_CLIENT = "jdk";
-
-    public static final String DEFAULT_HTTP_SERIALIZATION = "json";
-
-    public static final String DEFAULT_CHARSET = "UTF-8";
-
-    public static final int DEFAULT_WEIGHT = 100;
-
-    public static final int DEFAULT_FORKS = 2;
-
-    public static final String DEFAULT_THREAD_NAME = "Dubbo";
-
-    public static final int DEFAULT_CORE_THREADS = 0;
-
-    public static final int DEFAULT_THREADS = 200;
-
-    public static final boolean DEFAULT_KEEP_ALIVE = true;
-
-    public static final int DEFAULT_QUEUES = 0;
-
-    public static final int DEFAULT_ALIVE = 60 * 1000;
-
-    public static final int DEFAULT_CONNECTIONS = 0;
-
-    public static final int DEFAULT_ACCEPTS = 0;
-
-    public static final int DEFAULT_IDLE_TIMEOUT = 600 * 1000;
-
-    public static final int DEFAULT_HEARTBEAT = 60 * 1000;
-
-    public static final int DEFAULT_TIMEOUT = 1000;
-
-    public static final int DEFAULT_CONNECT_TIMEOUT = 3000;
-
-//    public static final int DEFAULT_REGISTRY_CONNECT_TIMEOUT = 5000;
-
-    public static final int DEFAULT_RETRIES = 2;
-
-    // default buffer size is 8k.
-    public static final int DEFAULT_BUFFER_SIZE = 8 * 1024;
-
-    public static final int MAX_BUFFER_SIZE = 16 * 1024;
-
-    public static final int MIN_BUFFER_SIZE = 1 * 1024;
-
-    public static final String REMOVE_VALUE_PREFIX = "-";
-
-    public static final String HIDE_KEY_PREFIX = ".";
-
-    public static final String DEFAULT_KEY_PREFIX = "default.";
-
-    public static final String DEFAULT_KEY = "default";
-
-    public static final String LOADBALANCE_KEY = "loadbalance";
-
-    // key for router type, for e.g., "script"/"file",  corresponding to ScriptRouterFactory.NAME, FileRouterFactory.NAME
-    public static final String ROUTER_KEY = "router";
-
-    public static final String CLUSTER_KEY = "cluster";
-
-    public static final String REGISTRY_KEY = "registry";
-
-    public static final String MONITOR_KEY = "monitor";
-
-    public static final String SIDE_KEY = "side";
-
-    public static final String PROVIDER_SIDE = "provider";
-
-    public static final String CONSUMER_SIDE = "consumer";
-
-    public static final String DEFAULT_REGISTRY = "dubbo";
-
-    public static final String BACKUP_KEY = "backup";
-
-    public static final String DIRECTORY_KEY = "directory";
-
-    public static final String DEPRECATED_KEY = "deprecated";
-
-    public static final String ANYHOST_KEY = "anyhost";
-
-    public static final String ANYHOST_VALUE = "0.0.0.0";
-
-    public static final String LOCALHOST_KEY = "localhost";
-
-    public static final String LOCALHOST_VALUE = "127.0.0.1";
-
-    public static final String APPLICATION_KEY = "application";
-
-    public static final String LOCAL_KEY = "local";
-
-    public static final String STUB_KEY = "stub";
-
-    public static final String MOCK_KEY = "mock";
-
-    public static final String PROTOCOL_KEY = "protocol";
-
-    public static final String PROXY_KEY = "proxy";
-
-    public static final String WEIGHT_KEY = "weight";
-
-    public static final String FORKS_KEY = "forks";
-
-    public static final String DEFAULT_THREADPOOL = "limited";
-
-    public static final String DEFAULT_CLIENT_THREADPOOL = "cached";
-
-    public static final String THREADPOOL_KEY = "threadpool";
-
-    public static final String THREAD_NAME_KEY = "threadname";
-
-    public static final String IO_THREADS_KEY = "iothreads";
-
-    public static final String CORE_THREADS_KEY = "corethreads";
-
-    public static final String THREADS_KEY = "threads";
-
-    public static final String QUEUES_KEY = "queues";
-
-    public static final String ALIVE_KEY = "alive";
-
-    public static final String EXECUTES_KEY = "executes";
-
-    public static final String BUFFER_KEY = "buffer";
-
-    public static final String PAYLOAD_KEY = "payload";
-
-    public static final String REFERENCE_FILTER_KEY = "reference.filter";
-
-    public static final String INVOKER_LISTENER_KEY = "invoker.listener";
-
-    public static final String SERVICE_FILTER_KEY = "service.filter";
-
-    public static final String EXPORTER_LISTENER_KEY = "exporter.listener";
-
-    public static final String ACCESS_LOG_KEY = "accesslog";
-
-    public static final String ACTIVES_KEY = "actives";
-
-    public static final String CONNECTIONS_KEY = "connections";
-
-    public static final String ACCEPTS_KEY = "accepts";
-
-    public static final String IDLE_TIMEOUT_KEY = "idle.timeout";
-
-    public static final String HEARTBEAT_KEY = "heartbeat";
-
-    public static final String HEARTBEAT_TIMEOUT_KEY = "heartbeat.timeout";
-
-    public static final String CONNECT_TIMEOUT_KEY = "connect.timeout";
-
-    public static final String TIMEOUT_KEY = "timeout";
-
-    public static final String RETRIES_KEY = "retries";
-
-    public static final String PROMPT_KEY = "prompt";
-
-    public static final String DEFAULT_PROMPT = "dubbo>";
-
-    public static final String CODEC_KEY = "codec";
-
-    public static final String SERIALIZATION_KEY = "serialization";
-
-    public static final String EXTENSION_KEY = "extension";
-
-    public static final String KEEP_ALIVE_KEY = "keepalive";
-
-    public static final String OPTIMIZER_KEY = "optimizer";
-
-    public static final String EXCHANGER_KEY = "exchanger";
-
-    public static final String TRANSPORTER_KEY = "transporter";
-
-    public static final String SERVER_KEY = "server";
-
-    public static final String CLIENT_KEY = "client";
-
-    public static final String ID_KEY = "id";
-
-    public static final String ASYNC_KEY = "async";
-
-    public static final String FUTURE_GENERATED_KEY = "future_generated";
-    public static final String FUTURE_RETURNTYPE_KEY = "future_returntype";
-
-    public static final String ASYNC_SUFFIX = "Async";
-
-    public static final String RETURN_KEY = "return";
-
-    public static final String TOKEN_KEY = "token";
-
-    public static final String METHOD_KEY = "method";
-
-    public static final String METHODS_KEY = "methods";
-
-    public static final String CHARSET_KEY = "charset";
-
-    public static final String RECONNECT_KEY = "reconnect";
-
-    public static final String SEND_RECONNECT_KEY = "send.reconnect";
-
-    public static final int DEFAULT_RECONNECT_PERIOD = 2000;
-
-    public static final String SHUTDOWN_TIMEOUT_KEY = "shutdown.timeout";
-
-    public static final int DEFAULT_SHUTDOWN_TIMEOUT = 1000 * 60 * 15;
-
-    public static final String PID_KEY = "pid";
-
-    public static final String TIMESTAMP_KEY = "timestamp";
-
-    public static final String REMOTE_TIMESTAMP_KEY = "remote.timestamp";
-
-    public static final String WARMUP_KEY = "warmup";
-
-    public static final int DEFAULT_WARMUP = 10 * 60 * 1000;
-
-    public static final String CHECK_KEY = "check";
-
-    public static final String REGISTER_KEY = "register";
-
-    public static final String SUBSCRIBE_KEY = "subscribe";
-
-    public static final String GROUP_KEY = "group";
-
-    public static final String PATH_KEY = "path";
-
-    public static final String INTERFACE_KEY = "interface";
-
-    public static final String INTERFACES = "interfaces";
-
-    public static final String GENERIC_KEY = "generic";
-
-    public static final String FILE_KEY = "file";
-
-    public static final String DUMP_DIRECTORY = "dump.directory";
-
-    public static final String WAIT_KEY = "wait";
-
-    public static final String CLASSIFIER_KEY = "classifier";
-
-    public static final String VERSION_KEY = "version";
-
-    public static final String REVISION_KEY = "revision";
-
-    public static final String DUBBO_VERSION_KEY = "dubbo";
-
-    public static final String HESSIAN_VERSION_KEY = "hessian.version";
-
-    public static final String DISPATCHER_KEY = "dispatcher";
-
-    public static final String CHANNEL_HANDLER_KEY = "channel.handler";
-
-    public static final String DEFAULT_CHANNEL_HANDLER = "default";
-
-    public static final String ANY_VALUE = "*";
-
-    public static final String COMMA_SEPARATOR = ",";
-
-    public static final Pattern COMMA_SPLIT_PATTERN = Pattern
-            .compile("\\s*[,]+\\s*");
-
-    public final static String PATH_SEPARATOR = "/";
-
-    public static final String REGISTRY_SEPARATOR = "|";
-
-    public static final Pattern REGISTRY_SPLIT_PATTERN = Pattern
-            .compile("\\s*[|;]+\\s*");
-
-    public static final String SEMICOLON_SEPARATOR = ";";
-
-    public static final Pattern SEMICOLON_SPLIT_PATTERN = Pattern
-            .compile("\\s*[;]+\\s*");
-
-    public static final String CONNECT_QUEUE_CAPACITY = "connect.queue.capacity";
-
-    public static final String CONNECT_QUEUE_WARNING_SIZE = "connect.queue.warning.size";
-
-    public static final int DEFAULT_CONNECT_QUEUE_WARNING_SIZE = 1000;
-
-    public static final String CHANNEL_ATTRIBUTE_READONLY_KEY = "channel.readonly";
-
-    public static final String CHANNEL_READONLYEVENT_SENT_KEY = "channel.readonly.sent";
-
-    public static final String CHANNEL_SEND_READONLYEVENT_KEY = "channel.readonly.send";
-
-    public static final String COUNT_PROTOCOL = "count";
-
-    public static final String TRACE_PROTOCOL = "trace";
-
-    public static final String EMPTY_PROTOCOL = "empty";
-
-    public static final String ADMIN_PROTOCOL = "admin";
-
-    public static final String PROVIDER_PROTOCOL = "provider";
-
-    public static final String CONSUMER_PROTOCOL = "consumer";
-
-    public static final String ROUTE_PROTOCOL = "route";
-
-    public static final String SCRIPT_PROTOCOL = "script";
-
-    public static final String CONDITION_PROTOCOL = "condition";
-
-    public static final String MOCK_PROTOCOL = "mock";
-
-    public static final String RETURN_PREFIX = "return ";
-
-    public static final String THROW_PREFIX = "throw";
-
-    public static final String FAIL_PREFIX = "fail:";
-
-    public static final String FORCE_PREFIX = "force:";
-
-    public static final String FORCE_KEY = "force";
-
-    public static final String MERGER_KEY = "merger";
-
-    /**
-     * To decide whether to exclude unavailable invoker from the cluster
-     */
-    public static final String CLUSTER_AVAILABLE_CHECK_KEY = "cluster.availablecheck";
-
-    /**
-     * The default value of cluster.availablecheck
-     *
-     * @see #CLUSTER_AVAILABLE_CHECK_KEY
-     */
-    public static final boolean DEFAULT_CLUSTER_AVAILABLE_CHECK = true;
-
-    /**
-     * To decide whether to enable sticky strategy for cluster
-     */
-    public static final String CLUSTER_STICKY_KEY = "sticky";
-
-    /**
-     * The default value of sticky
-     *
-     * @see #CLUSTER_STICKY_KEY
-     */
-    public static final boolean DEFAULT_CLUSTER_STICKY = false;
-
-    /**
-     * To decide whether to make connection when the client is created
-     */
-    public static final String LAZY_CONNECT_KEY = "lazy";
-
-    /**
-     * The initial state for lazy connection
-     */
-    public static final String LAZY_CONNECT_INITIAL_STATE_KEY = "connect.lazy.initial.state";
-
-    /**
-     * The default value of lazy connection's initial state: true
-     *
-     * @see #LAZY_CONNECT_INITIAL_STATE_KEY
-     */
-    public static final boolean DEFAULT_LAZY_CONNECT_INITIAL_STATE = true;
-
-    /**
-     * To decide whether register center saves file synchronously, the default value is asynchronously
-     */
-    public static final String REGISTRY_FILESAVE_SYNC_KEY = "save.file";
-
-    /**
-     * Period of registry center's retry interval
-     */
-    public static final String REGISTRY_RETRY_PERIOD_KEY = "retry.period";
-
-    /**
-     * Default value for the period of retry interval in milliseconds: 5000
-     */
-    public static final int DEFAULT_REGISTRY_RETRY_PERIOD = 5 * 1000;
-
-    /**
-     * Reconnection period in milliseconds for register center
-     */
-    public static final String REGISTRY_RECONNECT_PERIOD_KEY = "reconnect.period";
-
-    public static final int DEFAULT_REGISTRY_RECONNECT_PERIOD = 3 * 1000;
-
-    public static final String SESSION_TIMEOUT_KEY = "session";
-
-    public static final int DEFAULT_SESSION_TIMEOUT = 60 * 1000;
-
-    /**
-     * The key name for export URL in register center
-     */
-    public static final String EXPORT_KEY = "export";
-
-    /**
-     * The key name for reference URL in register center
-     */
-    public static final String REFER_KEY = "refer";
-
-    /**
-     * callback inst id
-     */
-    public static final String CALLBACK_SERVICE_KEY = "callback.service.instid";
-
-    /**
-     * The limit of callback service instances for one interface on every client
-     */
-    public static final String CALLBACK_INSTANCES_LIMIT_KEY = "callbacks";
-
-    /**
-     * The default limit number for callback service instances
-     *
-     * @see #CALLBACK_INSTANCES_LIMIT_KEY
-     */
-    public static final int DEFAULT_CALLBACK_INSTANCES = 1;
-
-    public static final String CALLBACK_SERVICE_PROXY_KEY = "callback.service.proxy";
-
-    public static final String IS_CALLBACK_SERVICE = "is_callback_service";
-
-    /**
-     * Invokers in channel's callback
-     */
-    public static final String CHANNEL_CALLBACK_KEY = "channel.callback.invokers.key";
-
-    @Deprecated
-    public static final String SHUTDOWN_WAIT_SECONDS_KEY = "dubbo.service.shutdown.wait.seconds";
-
-    public static final String SHUTDOWN_WAIT_KEY = "dubbo.service.shutdown.wait";
-
-    public static final String IS_SERVER_KEY = "isserver";
-
-    /**
-     * Default timeout value in milliseconds for server shutdown
-     */
-    public static final int DEFAULT_SERVER_SHUTDOWN_TIMEOUT = 10000;
-
-    public static final String ON_CONNECT_KEY = "onconnect";
-
-    public static final String ON_DISCONNECT_KEY = "ondisconnect";
-
-    public static final String ON_INVOKE_METHOD_KEY = "oninvoke.method";
-
-    public static final String ON_RETURN_METHOD_KEY = "onreturn.method";
-
-    public static final String ON_THROW_METHOD_KEY = "onthrow.method";
-
-    public static final String ON_INVOKE_INSTANCE_KEY = "oninvoke.instance";
-
-    public static final String ON_RETURN_INSTANCE_KEY = "onreturn.instance";
-
-    public static final String ON_THROW_INSTANCE_KEY = "onthrow.instance";
-
-    public static final String OVERRIDE_PROTOCOL = "override";
-
-    public static final String PRIORITY_KEY = "priority";
-
-    public static final String RULE_KEY = "rule";
-
-    public static final String TYPE_KEY = "type";
-
-    public static final String RUNTIME_KEY = "runtime";
-
-    /**
-     * when ROUTER_KEY's value is set to ROUTER_TYPE_CLEAR, RegistryDirectory will clean all current routers
-     */
-    public static final String ROUTER_TYPE_CLEAR = "clean";
-
-    public static final String DEFAULT_SCRIPT_TYPE_KEY = "javascript";
-
-    public static final String STUB_EVENT_KEY = "dubbo.stub.event";
-
-    public static final boolean DEFAULT_STUB_EVENT = false;
-
-    public static final String STUB_EVENT_METHODS_KEY = "dubbo.stub.event.methods";
-
-    /**
-     * When this attribute appears in invocation's attachment, mock invoker will be used
-     */
-    public static final String INVOCATION_NEED_MOCK = "invocation.need.mock";
-
-    public static final String LOCAL_PROTOCOL = "injvm";
-
-    public static final String AUTO_ATTACH_INVOCATIONID_KEY = "invocationid.autoattach";
-
-    public static final String SCOPE_KEY = "scope";
-
-    public static final String SCOPE_LOCAL = "local";
-
-    public static final String SCOPE_REMOTE = "remote";
-
-    public static final String SCOPE_NONE = "none";
-
-    public static final String RELIABLE_PROTOCOL = "napoli";
-
-    public static final String TPS_LIMIT_RATE_KEY = "tps";
-
-    public static final String TPS_LIMIT_INTERVAL_KEY = "tps.interval";
-
-    public static final long DEFAULT_TPS_LIMIT_INTERVAL = 60 * 1000;
-
-    public static final String DECODE_IN_IO_THREAD_KEY = "decode.in.io";
-
-    public static final boolean DEFAULT_DECODE_IN_IO_THREAD = true;
-
-    public static final String INPUT_KEY = "input";
-
-    public static final String OUTPUT_KEY = "output";
-
-    public static final String EXECUTOR_SERVICE_COMPONENT_KEY = ExecutorService.class.getName();
-
-    public static final String GENERIC_SERIALIZATION_NATIVE_JAVA = "nativejava";
-
-    public static final String GENERIC_SERIALIZATION_DEFAULT = "true";
-
-    public static final String GENERIC_SERIALIZATION_BEAN = "bean";
-
-    public static final String DUBBO_IP_TO_REGISTRY = "DUBBO_IP_TO_REGISTRY";
-
-    public static final String DUBBO_PORT_TO_REGISTRY = "DUBBO_PORT_TO_REGISTRY";
-
-    public static final String DUBBO_IP_TO_BIND = "DUBBO_IP_TO_BIND";
-
-    public static final String DUBBO_PORT_TO_BIND = "DUBBO_PORT_TO_BIND";
-
-    public static final String BIND_IP_KEY = "bind.ip";
-
-    public static final String BIND_PORT_KEY = "bind.port";
-
-    public static final String REGISTER_IP_KEY = "register.ip";
-
-    public static final String QOS_ENABLE = "qos.enable";
-
-    public static final String QOS_PORT = "qos.port";
-
-    public static final String ACCEPT_FOREIGN_IP = "qos.accept.foreign.ip";
-
-    public static final String HESSIAN2_REQUEST_KEY = "hessian2.request";
-
-    public static final boolean DEFAULT_HESSIAN2_REQUEST = false;
-
-    public static final String HESSIAN_OVERLOAD_METHOD_KEY = "hessian.overload.method";
-
-    public static final boolean DEFAULT_HESSIAN_OVERLOAD_METHOD = false;
-
-    public static final String MULTICAST = "multicast";
-
-    public static final String TAG_KEY = "tag";
-
-    public static final String REQUEST_TAG_KEY = "request.tag";
-
-    /*
-     * private Constants(){ }
-     */
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.common;
+
+import java.util.concurrent.ExecutorService;
+import java.util.regex.Pattern;
+/**
+ * Constants
+ */
+public class Constants {
+
+    public static final String PROVIDER = "provider";
+
+    public static final String CONSUMER = "consumer";
+
+    public static final String REGISTER = "register";
+
+    public static final String UNREGISTER = "unregister";
+
+    public static final String SUBSCRIBE = "subscribe";
+
+    public static final String UNSUBSCRIBE = "unsubscribe";
+
+    public static final String CATEGORY_KEY = "category";
+
+    public static final String PROVIDERS_CATEGORY = "providers";
+
+    public static final String CONSUMERS_CATEGORY = "consumers";
+
+    public static final String ROUTERS_CATEGORY = "routers";
+
+    public static final String CONFIGURATORS_CATEGORY = "configurators";
+
+    public static final String DEFAULT_CATEGORY = PROVIDERS_CATEGORY;
+
+    public static final String ENABLED_KEY = "enabled";
+
+    public static final String DISABLED_KEY = "disabled";
+
+    public static final String VALIDATION_KEY = "validation";
+
+    public static final String CACHE_KEY = "cache";
+
+    public static final String DYNAMIC_KEY = "dynamic";
+
+    public static final String DUBBO_PROPERTIES_KEY = "dubbo.properties.file";
+
+    public static final String DEFAULT_DUBBO_PROPERTIES = "dubbo.properties";
+
+    public static final String SENT_KEY = "sent";
+
+    public static final boolean DEFAULT_SENT = false;
+
+    public static final String REGISTRY_PROTOCOL = "registry";
+
+    public static final String $INVOKE = "$invoke";
+
+    public static final String $ECHO = "$echo";
+
+    public static final int DEFAULT_IO_THREADS = Math.min(Runtime.getRuntime().availableProcessors() + 1, 32);
+
+    public static final String DEFAULT_PROXY = "javassist";
+
+    public static final int DEFAULT_PAYLOAD = 8 * 1024 * 1024;                      // 8M
+
+    public static final String DEFAULT_CLUSTER = "failover";
+
+    public static final String DEFAULT_DIRECTORY = "dubbo";
+
+    public static final String DEFAULT_LOADBALANCE = "random";
+
+    public static final String DEFAULT_PROTOCOL = "dubbo";
+
+    public static final String DEFAULT_EXCHANGER = "header";
+
+    public static final String DEFAULT_TRANSPORTER = "netty";
+
+    public static final String DEFAULT_REMOTING_SERVER = "netty";
+
+    public static final String DEFAULT_REMOTING_CLIENT = "netty";
+
+    public static final String DEFAULT_REMOTING_CODEC = "dubbo";
+
+    public static final String DEFAULT_REMOTING_SERIALIZATION = "hessian2";
+
+    public static final String DEFAULT_HTTP_SERVER = "servlet";
+
+    public static final String DEFAULT_HTTP_CLIENT = "jdk";
+
+    public static final String DEFAULT_HTTP_SERIALIZATION = "json";
+
+    public static final String DEFAULT_CHARSET = "UTF-8";
+
+    public static final int DEFAULT_WEIGHT = 100;
+
+    public static final int DEFAULT_FORKS = 2;
+
+    public static final String DEFAULT_THREAD_NAME = "Dubbo";
+
+    public static final int DEFAULT_CORE_THREADS = 0;
+
+    public static final int DEFAULT_THREADS = 200;
+
+    public static final boolean DEFAULT_KEEP_ALIVE = true;
+
+    public static final int DEFAULT_QUEUES = 0;
+
+    public static final int DEFAULT_ALIVE = 60 * 1000;
+
+    public static final int DEFAULT_CONNECTIONS = 0;
+
+    public static final int DEFAULT_ACCEPTS = 0;
+
+    public static final int DEFAULT_IDLE_TIMEOUT = 600 * 1000;
+
+    public static final int DEFAULT_HEARTBEAT = 60 * 1000;
+
+    public static final int DEFAULT_TIMEOUT = 1000;
+
+    public static final int DEFAULT_CONNECT_TIMEOUT = 3000;
+
+//    public static final int DEFAULT_REGISTRY_CONNECT_TIMEOUT = 5000;
+
+    public static final int DEFAULT_RETRIES = 2;
+
+    // default buffer size is 8k.
+    public static final int DEFAULT_BUFFER_SIZE = 8 * 1024;
+
+    public static final int MAX_BUFFER_SIZE = 16 * 1024;
+
+    public static final int MIN_BUFFER_SIZE = 1 * 1024;
+
+    public static final String REMOVE_VALUE_PREFIX = "-";
+
+    public static final String HIDE_KEY_PREFIX = ".";
+
+    public static final String DEFAULT_KEY_PREFIX = "default.";
+
+    public static final String DEFAULT_KEY = "default";
+
+    public static final String LOADBALANCE_KEY = "loadbalance";
+
+    // key for router type, for e.g., "script"/"file",  corresponding to ScriptRouterFactory.NAME, FileRouterFactory.NAME
+    public static final String ROUTER_KEY = "router";
+
+    public static final String CLUSTER_KEY = "cluster";
+
+    public static final String REGISTRY_KEY = "registry";
+
+    public static final String MONITOR_KEY = "monitor";
+
+    public static final String SIDE_KEY = "side";
+
+    public static final String PROVIDER_SIDE = "provider";
+
+    public static final String CONSUMER_SIDE = "consumer";
+
+    public static final String DEFAULT_REGISTRY = "dubbo";
+
+    public static final String BACKUP_KEY = "backup";
+
+    public static final String DIRECTORY_KEY = "directory";
+
+    public static final String DEPRECATED_KEY = "deprecated";
+
+    public static final String ANYHOST_KEY = "anyhost";
+
+    public static final String ANYHOST_VALUE = "0.0.0.0";
+
+    public static final String LOCALHOST_KEY = "localhost";
+
+    public static final String LOCALHOST_VALUE = "127.0.0.1";
+
+    public static final String APPLICATION_KEY = "application";
+
+    public static final String LOCAL_KEY = "local";
+
+    public static final String STUB_KEY = "stub";
+
+    public static final String MOCK_KEY = "mock";
+
+    public static final String PROTOCOL_KEY = "protocol";
+
+    public static final String PROXY_KEY = "proxy";
+
+    public static final String WEIGHT_KEY = "weight";
+
+    public static final String FORKS_KEY = "forks";
+
+    public static final String DEFAULT_THREADPOOL = "limited";
+
+    public static final String DEFAULT_CLIENT_THREADPOOL = "cached";
+
+    public static final String THREADPOOL_KEY = "threadpool";
+
+    public static final String THREAD_NAME_KEY = "threadname";
+
+    public static final String IO_THREADS_KEY = "iothreads";
+
+    public static final String CORE_THREADS_KEY = "corethreads";
+
+    public static final String THREADS_KEY = "threads";
+
+    public static final String QUEUES_KEY = "queues";
+
+    public static final String ALIVE_KEY = "alive";
+
+    public static final String EXECUTES_KEY = "executes";
+
+    public static final String BUFFER_KEY = "buffer";
+
+    public static final String PAYLOAD_KEY = "payload";
+
+    public static final String REFERENCE_FILTER_KEY = "reference.filter";
+
+    public static final String INVOKER_LISTENER_KEY = "invoker.listener";
+
+    public static final String SERVICE_FILTER_KEY = "service.filter";
+
+    public static final String EXPORTER_LISTENER_KEY = "exporter.listener";
+
+    public static final String ACCESS_LOG_KEY = "accesslog";
+
+    public static final String ACTIVES_KEY = "actives";
+
+    public static final String CONNECTIONS_KEY = "connections";
+
+    public static final String ACCEPTS_KEY = "accepts";
+
+    public static final String IDLE_TIMEOUT_KEY = "idle.timeout";
+
+    public static final String HEARTBEAT_KEY = "heartbeat";
+
+    public static final String HEARTBEAT_TIMEOUT_KEY = "heartbeat.timeout";
+
+    public static final String CONNECT_TIMEOUT_KEY = "connect.timeout";
+
+    public static final String TIMEOUT_KEY = "timeout";
+
+    public static final String RETRIES_KEY = "retries";
+
+    public static final String PROMPT_KEY = "prompt";
+
+    public static final String DEFAULT_PROMPT = "dubbo>";
+
+    public static final String CODEC_KEY = "codec";
+
+    public static final String SERIALIZATION_KEY = "serialization";
+
+    public static final String EXTENSION_KEY = "extension";
+
+    public static final String KEEP_ALIVE_KEY = "keepalive";
+
+    public static final String OPTIMIZER_KEY = "optimizer";
+
+    public static final String EXCHANGER_KEY = "exchanger";
+
+    public static final String TRANSPORTER_KEY = "transporter";
+
+    public static final String SERVER_KEY = "server";
+
+    public static final String CLIENT_KEY = "client";
+
+    public static final String ID_KEY = "id";
+
+    public static final String ASYNC_KEY = "async";
+
+    public static final String FUTURE_GENERATED_KEY = "future_generated";
+    public static final String FUTURE_RETURNTYPE_KEY = "future_returntype";
+
+    public static final String ASYNC_SUFFIX = "Async";
+
+    public static final String RETURN_KEY = "return";
+
+    public static final String TOKEN_KEY = "token";
+
+    public static final String METHOD_KEY = "method";
+
+    public static final String METHODS_KEY = "methods";
+
+    public static final String CHARSET_KEY = "charset";
+
+    public static final String RECONNECT_KEY = "reconnect";
+
+    public static final String SEND_RECONNECT_KEY = "send.reconnect";
+
+    public static final int DEFAULT_RECONNECT_PERIOD = 2000;
+
+    public static final String SHUTDOWN_TIMEOUT_KEY = "shutdown.timeout";
+
+    public static final int DEFAULT_SHUTDOWN_TIMEOUT = 1000 * 60 * 15;
+
+    public static final String PID_KEY = "pid";
+
+    public static final String TIMESTAMP_KEY = "timestamp";
+
+    public static final String REMOTE_TIMESTAMP_KEY = "remote.timestamp";
+
+    public static final String WARMUP_KEY = "warmup";
+
+    public static final int DEFAULT_WARMUP = 10 * 60 * 1000;
+
+    public static final String CHECK_KEY = "check";
+
+    public static final String REGISTER_KEY = "register";
+
+    public static final String SUBSCRIBE_KEY = "subscribe";
+
+    public static final String GROUP_KEY = "group";
+
+    public static final String PATH_KEY = "path";
+
+    public static final String INTERFACE_KEY = "interface";
+
+    public static final String INTERFACES = "interfaces";
+
+    public static final String GENERIC_KEY = "generic";
+
+    public static final String FILE_KEY = "file";
+
+    public static final String DUMP_DIRECTORY = "dump.directory";
+
+    public static final String WAIT_KEY = "wait";
+
+    public static final String CLASSIFIER_KEY = "classifier";
+
+    public static final String VERSION_KEY = "version";
+
+    public static final String REVISION_KEY = "revision";
+
+    public static final String DUBBO_VERSION_KEY = "dubbo";
+
+    public static final String HESSIAN_VERSION_KEY = "hessian.version";
+
+    public static final String DISPATCHER_KEY = "dispatcher";
+
+    public static final String CHANNEL_HANDLER_KEY = "channel.handler";
+
+    public static final String DEFAULT_CHANNEL_HANDLER = "default";
+
+    public static final String ANY_VALUE = "*";
+
+    public static final String COMMA_SEPARATOR = ",";
+
+    public static final Pattern COMMA_SPLIT_PATTERN = Pattern
+            .compile("\\s*[,]+\\s*");
+
+    public final static String PATH_SEPARATOR = "/";
+
+    public static final String REGISTRY_SEPARATOR = "|";
+
+    public static final Pattern REGISTRY_SPLIT_PATTERN = Pattern
+            .compile("\\s*[|;]+\\s*");
+
+    public static final String SEMICOLON_SEPARATOR = ";";
+
+    public static final Pattern SEMICOLON_SPLIT_PATTERN = Pattern
+            .compile("\\s*[;]+\\s*");
+
+    public static final String CONNECT_QUEUE_CAPACITY = "connect.queue.capacity";
+
+    public static final String CONNECT_QUEUE_WARNING_SIZE = "connect.queue.warning.size";
+
+    public static final int DEFAULT_CONNECT_QUEUE_WARNING_SIZE = 1000;
+
+    public static final String CHANNEL_ATTRIBUTE_READONLY_KEY = "channel.readonly";
+
+    public static final String CHANNEL_READONLYEVENT_SENT_KEY = "channel.readonly.sent";
+
+    public static final String CHANNEL_SEND_READONLYEVENT_KEY = "channel.readonly.send";
+
+    public static final String COUNT_PROTOCOL = "count";
+
+    public static final String TRACE_PROTOCOL = "trace";
+
+    public static final String EMPTY_PROTOCOL = "empty";
+
+    public static final String ADMIN_PROTOCOL = "admin";
+
+    public static final String PROVIDER_PROTOCOL = "provider";
+
+    public static final String CONSUMER_PROTOCOL = "consumer";
+
+    public static final String ROUTE_PROTOCOL = "route";
+
+    public static final String SCRIPT_PROTOCOL = "script";
+
+    public static final String CONDITION_PROTOCOL = "condition";
+
+    public static final String MOCK_PROTOCOL = "mock";
+
+    public static final String RETURN_PREFIX = "return ";
+
+    public static final String THROW_PREFIX = "throw";
+
+    public static final String FAIL_PREFIX = "fail:";
+
+    public static final String FORCE_PREFIX = "force:";
+
+    public static final String FORCE_KEY = "force";
+
+    public static final String MERGER_KEY = "merger";
+
+    /**
+     * To decide whether to exclude unavailable invoker from the cluster
+     */
+    public static final String CLUSTER_AVAILABLE_CHECK_KEY = "cluster.availablecheck";
+
+    /**
+     * The default value of cluster.availablecheck
+     *
+     * @see #CLUSTER_AVAILABLE_CHECK_KEY
+     */
+    public static final boolean DEFAULT_CLUSTER_AVAILABLE_CHECK = true;
+
+    /**
+     * To decide whether to enable sticky strategy for cluster
+     */
+    public static final String CLUSTER_STICKY_KEY = "sticky";
+
+    /**
+     * The default value of sticky
+     *
+     * @see #CLUSTER_STICKY_KEY
+     */
+    public static final boolean DEFAULT_CLUSTER_STICKY = false;
+
+    /**
+     * To decide whether to make connection when the client is created
+     */
+    public static final String LAZY_CONNECT_KEY = "lazy";
+
+    /**
+     * The initial state for lazy connection
+     */
+    public static final String LAZY_CONNECT_INITIAL_STATE_KEY = "connect.lazy.initial.state";
+
+    /**
+     * The default value of lazy connection's initial state: true
+     *
+     * @see #LAZY_CONNECT_INITIAL_STATE_KEY
+     */
+    public static final boolean DEFAULT_LAZY_CONNECT_INITIAL_STATE = true;
+
+    /**
+     * To decide whether register center saves file synchronously, the default value is asynchronously
+     */
+    public static final String REGISTRY_FILESAVE_SYNC_KEY = "save.file";
+
+    /**
+     * Period of registry center's retry interval
+     */
+    public static final String REGISTRY_RETRY_PERIOD_KEY = "retry.period";
+
+    /**
+     * Default value for the period of retry interval in milliseconds: 5000
+     */
+    public static final int DEFAULT_REGISTRY_RETRY_PERIOD = 5 * 1000;
+
+    /**
+     * Reconnection period in milliseconds for register center
+     */
+    public static final String REGISTRY_RECONNECT_PERIOD_KEY = "reconnect.period";
+
+    public static final int DEFAULT_REGISTRY_RECONNECT_PERIOD = 3 * 1000;
+
+    public static final String SESSION_TIMEOUT_KEY = "session";
+
+    public static final int DEFAULT_SESSION_TIMEOUT = 60 * 1000;
+
+    /**
+     * The key name for export URL in register center
+     */
+    public static final String EXPORT_KEY = "export";
+
+    /**
+     * The key name for reference URL in register center
+     */
+    public static final String REFER_KEY = "refer";
+
+    /**
+     * callback inst id
+     */
+    public static final String CALLBACK_SERVICE_KEY = "callback.service.instid";
+
+    /**
+     * The limit of callback service instances for one interface on every client
+     */
+    public static final String CALLBACK_INSTANCES_LIMIT_KEY = "callbacks";
+
+    /**
+     * The default limit number for callback service instances
+     *
+     * @see #CALLBACK_INSTANCES_LIMIT_KEY
+     */
+    public static final int DEFAULT_CALLBACK_INSTANCES = 1;
+
+    public static final String CALLBACK_SERVICE_PROXY_KEY = "callback.service.proxy";
+
+    public static final String IS_CALLBACK_SERVICE = "is_callback_service";
+
+    /**
+     * Invokers in channel's callback
+     */
+    public static final String CHANNEL_CALLBACK_KEY = "channel.callback.invokers.key";
+
+    @Deprecated
+    public static final String SHUTDOWN_WAIT_SECONDS_KEY = "dubbo.service.shutdown.wait.seconds";
+
+    public static final String SHUTDOWN_WAIT_KEY = "dubbo.service.shutdown.wait";
+
+    public static final String IS_SERVER_KEY = "isserver";
+
+    /**
+     * Default timeout value in milliseconds for server shutdown
+     */
+    public static final int DEFAULT_SERVER_SHUTDOWN_TIMEOUT = 10000;
+
+    public static final String ON_CONNECT_KEY = "onconnect";
+
+    public static final String ON_DISCONNECT_KEY = "ondisconnect";
+
+    public static final String ON_INVOKE_METHOD_KEY = "oninvoke.method";
+
+    public static final String ON_RETURN_METHOD_KEY = "onreturn.method";
+
+    public static final String ON_THROW_METHOD_KEY = "onthrow.method";
+
+    public static final String ON_INVOKE_INSTANCE_KEY = "oninvoke.instance";
+
+    public static final String ON_RETURN_INSTANCE_KEY = "onreturn.instance";
+
+    public static final String ON_THROW_INSTANCE_KEY = "onthrow.instance";
+
+    public static final String OVERRIDE_PROTOCOL = "override";
+
+    public static final String PRIORITY_KEY = "priority";
+
+    public static final String RULE_KEY = "rule";
+
+    public static final String TYPE_KEY = "type";
+
+    public static final String RUNTIME_KEY = "runtime";
+
+    /**
+     * when ROUTER_KEY's value is set to ROUTER_TYPE_CLEAR, RegistryDirectory will clean all current routers
+     */
+    public static final String ROUTER_TYPE_CLEAR = "clean";
+
+    public static final String DEFAULT_SCRIPT_TYPE_KEY = "javascript";
+
+    public static final String STUB_EVENT_KEY = "dubbo.stub.event";
+
+    public static final boolean DEFAULT_STUB_EVENT = false;
+
+    public static final String STUB_EVENT_METHODS_KEY = "dubbo.stub.event.methods";
+
+    /**
+     * When this attribute appears in invocation's attachment, mock invoker will be used
+     */
+    public static final String INVOCATION_NEED_MOCK = "invocation.need.mock";
+
+    public static final String LOCAL_PROTOCOL = "injvm";
+
+    public static final String AUTO_ATTACH_INVOCATIONID_KEY = "invocationid.autoattach";
+
+    public static final String SCOPE_KEY = "scope";
+
+    public static final String SCOPE_LOCAL = "local";
+
+    public static final String SCOPE_REMOTE = "remote";
+
+    public static final String SCOPE_NONE = "none";
+
+    public static final String RELIABLE_PROTOCOL = "napoli";
+
+    public static final String TPS_LIMIT_RATE_KEY = "tps";
+
+    public static final String TPS_LIMIT_INTERVAL_KEY = "tps.interval";
+
+    public static final long DEFAULT_TPS_LIMIT_INTERVAL = 60 * 1000;
+
+    public static final String DECODE_IN_IO_THREAD_KEY = "decode.in.io";
+
+    public static final boolean DEFAULT_DECODE_IN_IO_THREAD = true;
+
+    public static final String INPUT_KEY = "input";
+
+    public static final String OUTPUT_KEY = "output";
+
+    public static final String EXECUTOR_SERVICE_COMPONENT_KEY = ExecutorService.class.getName();
+
+    public static final String GENERIC_SERIALIZATION_NATIVE_JAVA = "nativejava";
+
+    public static final String GENERIC_SERIALIZATION_DEFAULT = "true";
+
+    public static final String GENERIC_SERIALIZATION_BEAN = "bean";
+
+    public static final String DUBBO_IP_TO_REGISTRY = "DUBBO_IP_TO_REGISTRY";
+
+    public static final String DUBBO_PORT_TO_REGISTRY = "DUBBO_PORT_TO_REGISTRY";
+
+    public static final String DUBBO_IP_TO_BIND = "DUBBO_IP_TO_BIND";
+
+    public static final String DUBBO_PORT_TO_BIND = "DUBBO_PORT_TO_BIND";
+
+    public static final String BIND_IP_KEY = "bind.ip";
+
+    public static final String BIND_PORT_KEY = "bind.port";
+
+    public static final String REGISTER_IP_KEY = "register.ip";
+
+    public static final String QOS_ENABLE = "qos.enable";
+
+    public static final String QOS_PORT = "qos.port";
+
+    public static final String ACCEPT_FOREIGN_IP = "qos.accept.foreign.ip";
+
+    public static final String HESSIAN2_REQUEST_KEY = "hessian2.request";
+
+    public static final boolean DEFAULT_HESSIAN2_REQUEST = false;
+
+    public static final String HESSIAN_OVERLOAD_METHOD_KEY = "hessian.overload.method";
+
+    public static final boolean DEFAULT_HESSIAN_OVERLOAD_METHOD = false;
+
+    public static final String MULTICAST = "multicast";
+
+    public static final String TAG_KEY = "tag";
+
+    public static final String REQUEST_TAG_KEY = "request.tag";
+
+    /*
+     * private Constants(){ }
+     */
+
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/Version.java b/dubbo-common/src/main/java/org/apache/dubbo/common/Version.java
index 983cbb98e1..0a46d672c2 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/Version.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/Version.java
@@ -1,205 +1,205 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common;
-
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.ClassHelper;
-
-import java.net.URL;
-import java.security.CodeSource;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Version
- */
-public final class Version {
-    private static final Logger logger = LoggerFactory.getLogger(Version.class);
-
-    // Dubbo RPC protocol version, for compatibility, it must not be between 2.0.10 ~ 2.6.2
-    public static final String DEFAULT_DUBBO_PROTOCOL_VERSION = "2.0.2";
-    // Dubbo implementation version, usually is jar version.
-    private static final String VERSION = getVersion(Version.class, "");
-
-    /**
-     * For protocol compatibility purpose.
-     * Because {@link #isSupportResponseAttatchment} is checked for every call, int compare expect to has higher performance than string.
-     */
-    private static final int LOWEST_VERSION_FOR_RESPONSE_ATTATCHMENT = 20002; // 2.0.2
-    private static final Map<String, Integer> VERSION2INT = new HashMap<String, Integer>();
-
-    static {
-        // check if there's duplicated jar
-        Version.checkDuplicate(Version.class);
-    }
-
-    private Version() {
-    }
-
-    public static String getProtocolVersion() {
-        return DEFAULT_DUBBO_PROTOCOL_VERSION;
-    }
-
-    public static String getVersion() {
-        return VERSION;
-    }
-
-    public static boolean isSupportResponseAttatchment(String version) {
-        if (version == null || version.length() == 0) {
-            return false;
-        }
-        // for previous dubbo version(2.0.10/020010~2.6.2/020602), this version is the jar's version, so they need to be ignore
-        int iVersion = getIntVersion(version);
-        if (iVersion >= 20010 && iVersion <= 20602) {
-            return false;
-        }
-
-        return iVersion >= LOWEST_VERSION_FOR_RESPONSE_ATTATCHMENT;
-    }
-
-    public static int getIntVersion(String version) {
-        Integer v = VERSION2INT.get(version);
-        if (v == null) {
-            v = parseInt(version);
-            VERSION2INT.put(version, v);
-        }
-        return v;
-    }
-
-    private static int parseInt(String version) {
-        int v = 0;
-        String[] vArr = version.split("\\.");
-        int len = vArr.length;
-        for (int i = 0; i < len; i++) {
-            v += Integer.parseInt(getDigital(vArr[i])) * Math.pow(10, (len - i - 1) * 2);
-        }
-        return v;
-    }
-
-    private static String getDigital(String v) {
-        int index = 0;
-        for (int i = 0; i < v.length(); i++) {
-            char c = v.charAt(i);
-            if (Character.isDigit(c)) {
-                if (i == v.length() - 1) {
-                    index = i + 1;
-                } else {
-                    index = i;
-                }
-                continue;
-            } else {
-                index = i;
-                break;
-            }
-        }
-        return v.substring(0, index);
-    }
-
-    private static boolean hasResource(String path) {
-        try {
-            return Version.class.getClassLoader().getResource(path) != null;
-        } catch (Throwable t) {
-            return false;
-        }
-    }
-
-    public static String getVersion(Class<?> cls, String defaultVersion) {
-        try {
-            // find version info from MANIFEST.MF first
-            String version = cls.getPackage().getImplementationVersion();
-            if (version == null || version.length() == 0) {
-                version = cls.getPackage().getSpecificationVersion();
-            }
-            if (version == null || version.length() == 0) {
-                // guess version fro jar file name if nothing's found from MANIFEST.MF
-                CodeSource codeSource = cls.getProtectionDomain().getCodeSource();
-                if (codeSource == null) {
-                    logger.info("No codeSource for class " + cls.getName() + " when getVersion, use default version " + defaultVersion);
-                } else {
-                    String file = codeSource.getLocation().getFile();
-                    if (file != null && file.length() > 0 && file.endsWith(".jar")) {
-                        file = file.substring(0, file.length() - 4);
-                        int i = file.lastIndexOf('/');
-                        if (i >= 0) {
-                            file = file.substring(i + 1);
-                        }
-                        i = file.indexOf("-");
-                        if (i >= 0) {
-                            file = file.substring(i + 1);
-                        }
-                        while (file.length() > 0 && !Character.isDigit(file.charAt(0))) {
-                            i = file.indexOf("-");
-                            if (i >= 0) {
-                                file = file.substring(i + 1);
-                            } else {
-                                break;
-                            }
-                        }
-                        version = file;
-                    }
-                }
-            }
-            // return default version if no version info is found
-            return version == null || version.length() == 0 ? defaultVersion : version;
-        } catch (Throwable e) {
-            // return default version when any exception is thrown
-            logger.error("return default version, ignore exception " + e.getMessage(), e);
-            return defaultVersion;
-        }
-    }
-
-    public static void checkDuplicate(Class<?> cls, boolean failOnError) {
-        checkDuplicate(cls.getName().replace('.', '/') + ".class", failOnError);
-    }
-
-    public static void checkDuplicate(Class<?> cls) {
-        checkDuplicate(cls, false);
-    }
-
-    public static void checkDuplicate(String path, boolean failOnError) {
-        try {
-            // search in caller's classloader
-            Enumeration<URL> urls = ClassHelper.getCallerClassLoader(Version.class).getResources(path);
-            Set<String> files = new HashSet<String>();
-            while (urls.hasMoreElements()) {
-                URL url = urls.nextElement();
-                if (url != null) {
-                    String file = url.getFile();
-                    if (file != null && file.length() > 0) {
-                        files.add(file);
-                    }
-                }
-            }
-            // duplicated jar is found
-            if (files.size() > 1) {
-                String error = "Duplicate class " + path + " in " + files.size() + " jar " + files;
-                if (failOnError) {
-                    throw new IllegalStateException(error);
-                } else {
-                    logger.error(error);
-                }
-            }
-        } catch (Throwable e) {
-            logger.error(e.getMessage(), e);
-        }
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common;
+
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.common.utils.ClassHelper;
+
+import java.net.URL;
+import java.security.CodeSource;
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Version
+ */
+public final class Version {
+    private static final Logger logger = LoggerFactory.getLogger(Version.class);
+
+    // Dubbo RPC protocol version, for compatibility, it must not be between 2.0.10 ~ 2.6.2
+    public static final String DEFAULT_DUBBO_PROTOCOL_VERSION = "2.0.2";
+    // Dubbo implementation version, usually is jar version.
+    private static final String VERSION = getVersion(Version.class, "");
+
+    /**
+     * For protocol compatibility purpose.
+     * Because {@link #isSupportResponseAttatchment} is checked for every call, int compare expect to has higher performance than string.
+     */
+    private static final int LOWEST_VERSION_FOR_RESPONSE_ATTATCHMENT = 20002; // 2.0.2
+    private static final Map<String, Integer> VERSION2INT = new HashMap<String, Integer>();
+
+    static {
+        // check if there's duplicated jar
+        Version.checkDuplicate(Version.class);
+    }
+
+    private Version() {
+    }
+
+    public static String getProtocolVersion() {
+        return DEFAULT_DUBBO_PROTOCOL_VERSION;
+    }
+
+    public static String getVersion() {
+        return VERSION;
+    }
+
+    public static boolean isSupportResponseAttatchment(String version) {
+        if (version == null || version.length() == 0) {
+            return false;
+        }
+        // for previous dubbo version(2.0.10/020010~2.6.2/020602), this version is the jar's version, so they need to be ignore
+        int iVersion = getIntVersion(version);
+        if (iVersion >= 20010 && iVersion <= 20602) {
+            return false;
+        }
+
+        return iVersion >= LOWEST_VERSION_FOR_RESPONSE_ATTATCHMENT;
+    }
+
+    public static int getIntVersion(String version) {
+        Integer v = VERSION2INT.get(version);
+        if (v == null) {
+            v = parseInt(version);
+            VERSION2INT.put(version, v);
+        }
+        return v;
+    }
+
+    private static int parseInt(String version) {
+        int v = 0;
+        String[] vArr = version.split("\\.");
+        int len = vArr.length;
+        for (int i = 0; i < len; i++) {
+            v += Integer.parseInt(getDigital(vArr[i])) * Math.pow(10, (len - i - 1) * 2);
+        }
+        return v;
+    }
+
+    private static String getDigital(String v) {
+        int index = 0;
+        for (int i = 0; i < v.length(); i++) {
+            char c = v.charAt(i);
+            if (Character.isDigit(c)) {
+                if (i == v.length() - 1) {
+                    index = i + 1;
+                } else {
+                    index = i;
+                }
+                continue;
+            } else {
+                index = i;
+                break;
+            }
+        }
+        return v.substring(0, index);
+    }
+
+    private static boolean hasResource(String path) {
+        try {
+            return Version.class.getClassLoader().getResource(path) != null;
+        } catch (Throwable t) {
+            return false;
+        }
+    }
+
+    public static String getVersion(Class<?> cls, String defaultVersion) {
+        try {
+            // find version info from MANIFEST.MF first
+            String version = cls.getPackage().getImplementationVersion();
+            if (version == null || version.length() == 0) {
+                version = cls.getPackage().getSpecificationVersion();
+            }
+            if (version == null || version.length() == 0) {
+                // guess version fro jar file name if nothing's found from MANIFEST.MF
+                CodeSource codeSource = cls.getProtectionDomain().getCodeSource();
+                if (codeSource == null) {
+                    logger.info("No codeSource for class " + cls.getName() + " when getVersion, use default version " + defaultVersion);
+                } else {
+                    String file = codeSource.getLocation().getFile();
+                    if (file != null && file.length() > 0 && file.endsWith(".jar")) {
+                        file = file.substring(0, file.length() - 4);
+                        int i = file.lastIndexOf('/');
+                        if (i >= 0) {
+                            file = file.substring(i + 1);
+                        }
+                        i = file.indexOf("-");
+                        if (i >= 0) {
+                            file = file.substring(i + 1);
+                        }
+                        while (file.length() > 0 && !Character.isDigit(file.charAt(0))) {
+                            i = file.indexOf("-");
+                            if (i >= 0) {
+                                file = file.substring(i + 1);
+                            } else {
+                                break;
+                            }
+                        }
+                        version = file;
+                    }
+                }
+            }
+            // return default version if no version info is found
+            return version == null || version.length() == 0 ? defaultVersion : version;
+        } catch (Throwable e) {
+            // return default version when any exception is thrown
+            logger.error("return default version, ignore exception " + e.getMessage(), e);
+            return defaultVersion;
+        }
+    }
+
+    public static void checkDuplicate(Class<?> cls, boolean failOnError) {
+        checkDuplicate(cls.getName().replace('.', '/') + ".class", failOnError);
+    }
+
+    public static void checkDuplicate(Class<?> cls) {
+        checkDuplicate(cls, false);
+    }
+
+    public static void checkDuplicate(String path, boolean failOnError) {
+        try {
+            // search in caller's classloader
+            Enumeration<URL> urls = ClassHelper.getCallerClassLoader(Version.class).getResources(path);
+            Set<String> files = new HashSet<String>();
+            while (urls.hasMoreElements()) {
+                URL url = urls.nextElement();
+                if (url != null) {
+                    String file = url.getFile();
+                    if (file != null && file.length() > 0) {
+                        files.add(file);
+                    }
+                }
+            }
+            // duplicated jar is found
+            if (files.size() > 1) {
+                String error = "Duplicate class " + path + " in " + files.size() + " jar " + files;
+                if (failOnError) {
+                    throw new IllegalStateException(error);
+                } else {
+                    logger.error(error);
+                }
+            }
+        } catch (Throwable e) {
+            logger.error(e.getMessage(), e);
+        }
+    }
+
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanAccessor.java b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanAccessor.java
index 7160de265f..6da6696944 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanAccessor.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanAccessor.java
@@ -1,42 +1,42 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.beanutil;
-
-public enum JavaBeanAccessor {
-
-    /**
-     * Field accessor.
-     */
-    FIELD,
-    /**
-     * Method accessor.
-     */
-    METHOD,
-    /**
-     * Method prefer to field.
-     */
-    ALL;
-
-    public static boolean isAccessByMethod(JavaBeanAccessor accessor) {
-        return METHOD.equals(accessor) || ALL.equals(accessor);
-    }
-
-    public static boolean isAccessByField(JavaBeanAccessor accessor) {
-        return FIELD.equals(accessor) || ALL.equals(accessor);
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.beanutil;
+
+public enum JavaBeanAccessor {
+
+    /**
+     * Field accessor.
+     */
+    FIELD,
+    /**
+     * Method accessor.
+     */
+    METHOD,
+    /**
+     * Method prefer to field.
+     */
+    ALL;
+
+    public static boolean isAccessByMethod(JavaBeanAccessor accessor) {
+        return METHOD.equals(accessor) || ALL.equals(accessor);
+    }
+
+    public static boolean isAccessByField(JavaBeanAccessor accessor) {
+        return FIELD.equals(accessor) || ALL.equals(accessor);
+    }
+
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanDescriptor.java b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanDescriptor.java
index bd328c1c0d..e3285546e8 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanDescriptor.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanDescriptor.java
@@ -1,213 +1,213 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.dubbo.common.beanutil;
-
-import java.io.Serializable;
-import java.util.Iterator;
-import java.util.LinkedHashMap;
-import java.util.Map;
-
-public final class JavaBeanDescriptor implements Serializable, Iterable<Map.Entry<Object, Object>> {
-
-    public static final int TYPE_CLASS = 1;
-    public static final int TYPE_ENUM = 2;
-    public static final int TYPE_COLLECTION = 3;
-    public static final int TYPE_MAP = 4;
-    public static final int TYPE_ARRAY = 5;
-    /**
-     * @see org.apache.dubbo.common.utils.ReflectUtils#isPrimitive(Class)
-     */
-    public static final int TYPE_PRIMITIVE = 6;
-    public static final int TYPE_BEAN = 7;
-    private static final long serialVersionUID = -8505586483570518029L;
-    private static final String ENUM_PROPERTY_NAME = "name";
-
-    private static final String CLASS_PROPERTY_NAME = "name";
-
-    private static final String PRIMITIVE_PROPERTY_VALUE = "value";
-
-    /**
-     * Used to define a type is valid.
-     *
-     * @see #isValidType(int)
-     */
-    private static final int TYPE_MAX = TYPE_BEAN;
-
-    /**
-     * Used to define a type is valid.
-     *
-     * @see #isValidType(int)
-     */
-    private static final int TYPE_MIN = TYPE_CLASS;
-
-    private String className;
-
-    private int type;
-
-    private Map<Object, Object> properties = new LinkedHashMap<Object, Object>();
-
-    public JavaBeanDescriptor() {
-    }
-
-    public JavaBeanDescriptor(String className, int type) {
-        notEmpty(className, "class name is empty");
-        if (!isValidType(type)) {
-            throw new IllegalArgumentException("type [ " + type + " ] is unsupported");
-        }
-
-        this.className = className;
-        this.type = type;
-    }
-
-    public boolean isClassType() {
-        return TYPE_CLASS == type;
-    }
-
-    public boolean isEnumType() {
-        return TYPE_ENUM == type;
-    }
-
-    public boolean isCollectionType() {
-        return TYPE_COLLECTION == type;
-    }
-
-    public boolean isMapType() {
-        return TYPE_MAP == type;
-    }
-
-    public boolean isArrayType() {
-        return TYPE_ARRAY == type;
-    }
-
-    public boolean isPrimitiveType() {
-        return TYPE_PRIMITIVE == type;
-    }
-
-    public boolean isBeanType() {
-        return TYPE_BEAN == type;
-    }
-
-    public int getType() {
-        return type;
-    }
-
-    public void setType(int type) {
-        this.type = type;
-    }
-
-    public String getClassName() {
-        return className;
-    }
-
-    public void setClassName(String className) {
-        this.className = className;
-    }
-
-    public Object setProperty(Object propertyName, Object propertyValue) {
-        notNull(propertyName, "Property name is null");
-
-        Object oldValue = properties.put(propertyName, propertyValue);
-        return oldValue;
-    }
-
-    public String setEnumNameProperty(String name) {
-        if (isEnumType()) {
-            Object result = setProperty(ENUM_PROPERTY_NAME, name);
-            return result == null ? null : result.toString();
-        }
-        throw new IllegalStateException("The instance is not a enum wrapper");
-    }
-
-    public String getEnumPropertyName() {
-        if (isEnumType()) {
-            Object result = getProperty(ENUM_PROPERTY_NAME);
-            return result == null ? null : result.toString();
-        }
-        throw new IllegalStateException("The instance is not a enum wrapper");
-    }
-
-    public String setClassNameProperty(String name) {
-        if (isClassType()) {
-            Object result = setProperty(CLASS_PROPERTY_NAME, name);
-            return result == null ? null : result.toString();
-        }
-        throw new IllegalStateException("The instance is not a class wrapper");
-    }
-
-    public String getClassNameProperty() {
-        if (isClassType()) {
-            Object result = getProperty(CLASS_PROPERTY_NAME);
-            return result == null ? null : result.toString();
-        }
-        throw new IllegalStateException("The instance is not a class wrapper");
-    }
-
-    public Object setPrimitiveProperty(Object primitiveValue) {
-        if (isPrimitiveType()) {
-            return setProperty(PRIMITIVE_PROPERTY_VALUE, primitiveValue);
-        }
-        throw new IllegalStateException("The instance is not a primitive type wrapper");
-    }
-
-    public Object getPrimitiveProperty() {
-        if (isPrimitiveType()) {
-            return getProperty(PRIMITIVE_PROPERTY_VALUE);
-        }
-        throw new IllegalStateException("The instance is not a primitive type wrapper");
-    }
-
-    public Object getProperty(Object propertyName) {
-        notNull(propertyName, "Property name is null");
-        Object propertyValue = properties.get(propertyName);
-        return propertyValue;
-    }
-
-    public boolean containsProperty(Object propertyName) {
-        notNull(propertyName, "Property name is null");
-        return properties.containsKey(propertyName);
-    }
-
-    @Override
-    public Iterator<Map.Entry<Object, Object>> iterator() {
-        return properties.entrySet().iterator();
-    }
-
-    public int propertySize() {
-        return properties.size();
-    }
-
-    private boolean isValidType(int type) {
-        return TYPE_MIN <= type && type <= TYPE_MAX;
-    }
-
-    private void notNull(Object obj, String message) {
-        if (obj == null) {
-            throw new IllegalArgumentException(message);
-        }
-    }
-
-    private void notEmpty(String string, String message) {
-        if (isEmpty(string)) {
-            throw new IllegalArgumentException(message);
-        }
-    }
-
-    private boolean isEmpty(String string) {
-        return string == null || "".equals(string.trim());
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.dubbo.common.beanutil;
+
+import java.io.Serializable;
+import java.util.Iterator;
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+public final class JavaBeanDescriptor implements Serializable, Iterable<Map.Entry<Object, Object>> {
+
+    public static final int TYPE_CLASS = 1;
+    public static final int TYPE_ENUM = 2;
+    public static final int TYPE_COLLECTION = 3;
+    public static final int TYPE_MAP = 4;
+    public static final int TYPE_ARRAY = 5;
+    /**
+     * @see org.apache.dubbo.common.utils.ReflectUtils#isPrimitive(Class)
+     */
+    public static final int TYPE_PRIMITIVE = 6;
+    public static final int TYPE_BEAN = 7;
+    private static final long serialVersionUID = -8505586483570518029L;
+    private static final String ENUM_PROPERTY_NAME = "name";
+
+    private static final String CLASS_PROPERTY_NAME = "name";
+
+    private static final String PRIMITIVE_PROPERTY_VALUE = "value";
+
+    /**
+     * Used to define a type is valid.
+     *
+     * @see #isValidType(int)
+     */
+    private static final int TYPE_MAX = TYPE_BEAN;
+
+    /**
+     * Used to define a type is valid.
+     *
+     * @see #isValidType(int)
+     */
+    private static final int TYPE_MIN = TYPE_CLASS;
+
+    private String className;
+
+    private int type;
+
+    private Map<Object, Object> properties = new LinkedHashMap<Object, Object>();
+
+    public JavaBeanDescriptor() {
+    }
+
+    public JavaBeanDescriptor(String className, int type) {
+        notEmpty(className, "class name is empty");
+        if (!isValidType(type)) {
+            throw new IllegalArgumentException("type [ " + type + " ] is unsupported");
+        }
+
+        this.className = className;
+        this.type = type;
+    }
+
+    public boolean isClassType() {
+        return TYPE_CLASS == type;
+    }
+
+    public boolean isEnumType() {
+        return TYPE_ENUM == type;
+    }
+
+    public boolean isCollectionType() {
+        return TYPE_COLLECTION == type;
+    }
+
+    public boolean isMapType() {
+        return TYPE_MAP == type;
+    }
+
+    public boolean isArrayType() {
+        return TYPE_ARRAY == type;
+    }
+
+    public boolean isPrimitiveType() {
+        return TYPE_PRIMITIVE == type;
+    }
+
+    public boolean isBeanType() {
+        return TYPE_BEAN == type;
+    }
+
+    public int getType() {
+        return type;
+    }
+
+    public void setType(int type) {
+        this.type = type;
+    }
+
+    public String getClassName() {
+        return className;
+    }
+
+    public void setClassName(String className) {
+        this.className = className;
+    }
+
+    public Object setProperty(Object propertyName, Object propertyValue) {
+        notNull(propertyName, "Property name is null");
+
+        Object oldValue = properties.put(propertyName, propertyValue);
+        return oldValue;
+    }
+
+    public String setEnumNameProperty(String name) {
+        if (isEnumType()) {
+            Object result = setProperty(ENUM_PROPERTY_NAME, name);
+            return result == null ? null : result.toString();
+        }
+        throw new IllegalStateException("The instance is not a enum wrapper");
+    }
+
+    public String getEnumPropertyName() {
+        if (isEnumType()) {
+            Object result = getProperty(ENUM_PROPERTY_NAME);
+            return result == null ? null : result.toString();
+        }
+        throw new IllegalStateException("The instance is not a enum wrapper");
+    }
+
+    public String setClassNameProperty(String name) {
+        if (isClassType()) {
+            Object result = setProperty(CLASS_PROPERTY_NAME, name);
+            return result == null ? null : result.toString();
+        }
+        throw new IllegalStateException("The instance is not a class wrapper");
+    }
+
+    public String getClassNameProperty() {
+        if (isClassType()) {
+            Object result = getProperty(CLASS_PROPERTY_NAME);
+            return result == null ? null : result.toString();
+        }
+        throw new IllegalStateException("The instance is not a class wrapper");
+    }
+
+    public Object setPrimitiveProperty(Object primitiveValue) {
+        if (isPrimitiveType()) {
+            return setProperty(PRIMITIVE_PROPERTY_VALUE, primitiveValue);
+        }
+        throw new IllegalStateException("The instance is not a primitive type wrapper");
+    }
+
+    public Object getPrimitiveProperty() {
+        if (isPrimitiveType()) {
+            return getProperty(PRIMITIVE_PROPERTY_VALUE);
+        }
+        throw new IllegalStateException("The instance is not a primitive type wrapper");
+    }
+
+    public Object getProperty(Object propertyName) {
+        notNull(propertyName, "Property name is null");
+        Object propertyValue = properties.get(propertyName);
+        return propertyValue;
+    }
+
+    public boolean containsProperty(Object propertyName) {
+        notNull(propertyName, "Property name is null");
+        return properties.containsKey(propertyName);
+    }
+
+    @Override
+    public Iterator<Map.Entry<Object, Object>> iterator() {
+        return properties.entrySet().iterator();
+    }
+
+    public int propertySize() {
+        return properties.size();
+    }
+
+    private boolean isValidType(int type) {
+        return TYPE_MIN <= type && type <= TYPE_MAX;
+    }
+
+    private void notNull(Object obj, String message) {
+        if (obj == null) {
+            throw new IllegalArgumentException(message);
+        }
+    }
+
+    private void notEmpty(String string, String message) {
+        if (isEmpty(string)) {
+            throw new IllegalArgumentException(message);
+        }
+    }
+
+    private boolean isEmpty(String string) {
+        return string == null || "".equals(string.trim());
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanSerializeUtil.java b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanSerializeUtil.java
index ea9f582648..ce8c51a021 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanSerializeUtil.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/beanutil/JavaBeanSerializeUtil.java
@@ -1,459 +1,459 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.beanutil;
-
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.LogHelper;
-import org.apache.dubbo.common.utils.ReflectUtils;
-
-import java.lang.reflect.Array;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.Field;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.IdentityHashMap;
-import java.util.Map;
-
-public final class JavaBeanSerializeUtil {
-
-    private static final Logger logger = LoggerFactory.getLogger(JavaBeanSerializeUtil.class);
-    private static final Map<String, Class<?>> TYPES = new HashMap<String, Class<?>>();
-    private static final String ARRAY_PREFIX = "[";
-    private static final String REFERENCE_TYPE_PREFIX = "L";
-    private static final String REFERENCE_TYPE_SUFFIX = ";";
-
-    static {
-        TYPES.put(boolean.class.getName(), boolean.class);
-        TYPES.put(byte.class.getName(), byte.class);
-        TYPES.put(short.class.getName(), short.class);
-        TYPES.put(int.class.getName(), int.class);
-        TYPES.put(long.class.getName(), long.class);
-        TYPES.put(float.class.getName(), float.class);
-        TYPES.put(double.class.getName(), double.class);
-        TYPES.put(void.class.getName(), void.class);
-        TYPES.put("Z", boolean.class);
-        TYPES.put("B", byte.class);
-        TYPES.put("C", char.class);
-        TYPES.put("D", double.class);
-        TYPES.put("F", float.class);
-        TYPES.put("I", int.class);
-        TYPES.put("J", long.class);
-        TYPES.put("S", short.class);
-    }
-
-    private JavaBeanSerializeUtil() {
-    }
-
-    public static JavaBeanDescriptor serialize(Object obj) {
-        JavaBeanDescriptor result = serialize(obj, JavaBeanAccessor.FIELD);
-        return result;
-    }
-
-    public static JavaBeanDescriptor serialize(Object obj, JavaBeanAccessor accessor) {
-        if (obj == null) {
-            return null;
-        }
-        if (obj instanceof JavaBeanDescriptor) {
-            return (JavaBeanDescriptor) obj;
-        }
-        IdentityHashMap<Object, JavaBeanDescriptor> cache = new IdentityHashMap<Object, JavaBeanDescriptor>();
-        JavaBeanDescriptor result = createDescriptorIfAbsent(obj, accessor, cache);
-        return result;
-    }
-
-    private static JavaBeanDescriptor createDescriptorForSerialize(Class<?> cl) {
-        if (cl.isEnum()) {
-            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_ENUM);
-        } else if (cl.isArray()) {
-            return new JavaBeanDescriptor(cl.getComponentType().getName(), JavaBeanDescriptor.TYPE_ARRAY);
-        } else if (ReflectUtils.isPrimitive(cl)) {
-            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_PRIMITIVE);
-        } else if (Class.class.equals(cl)) {
-            return new JavaBeanDescriptor(Class.class.getName(), JavaBeanDescriptor.TYPE_CLASS);
-        } else if (Collection.class.isAssignableFrom(cl)) {
-            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_COLLECTION);
-        } else if (Map.class.isAssignableFrom(cl)) {
-            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_MAP);
-        } else {
-            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_BEAN);
-        }
-    }
-
-    private static JavaBeanDescriptor createDescriptorIfAbsent(Object obj, JavaBeanAccessor accessor, IdentityHashMap<Object, JavaBeanDescriptor> cache) {
-        if (cache.containsKey(obj)) {
-            return cache.get(obj);
-        } else if (obj instanceof JavaBeanDescriptor) {
-            return (JavaBeanDescriptor) obj;
-        } else {
-            JavaBeanDescriptor result = createDescriptorForSerialize(obj.getClass());
-            cache.put(obj, result);
-            serializeInternal(result, obj, accessor, cache);
-            return result;
-        }
-    }
-
-    private static void serializeInternal(JavaBeanDescriptor descriptor, Object obj, JavaBeanAccessor accessor, IdentityHashMap<Object, JavaBeanDescriptor> cache) {
-        if (obj == null || descriptor == null) {
-            return;
-        }
-
-        if (obj.getClass().isEnum()) {
-            descriptor.setEnumNameProperty(((Enum<?>) obj).name());
-        } else if (ReflectUtils.isPrimitive(obj.getClass())) {
-            descriptor.setPrimitiveProperty(obj);
-        } else if (Class.class.equals(obj.getClass())) {
-            descriptor.setClassNameProperty(((Class<?>) obj).getName());
-        } else if (obj.getClass().isArray()) {
-            int len = Array.getLength(obj);
-            for (int i = 0; i < len; i++) {
-                Object item = Array.get(obj, i);
-                if (item == null) {
-                    descriptor.setProperty(i, null);
-                } else {
-                    JavaBeanDescriptor itemDescriptor = createDescriptorIfAbsent(item, accessor, cache);
-                    descriptor.setProperty(i, itemDescriptor);
-                }
-            }
-        } else if (obj instanceof Collection) {
-            Collection collection = (Collection) obj;
-            int index = 0;
-            for (Object item : collection) {
-                if (item == null) {
-                    descriptor.setProperty(index++, null);
-                } else {
-                    JavaBeanDescriptor itemDescriptor = createDescriptorIfAbsent(item, accessor, cache);
-                    descriptor.setProperty(index++, itemDescriptor);
-                }
-            }
-        } else if (obj instanceof Map) {
-            Map map = (Map) obj;
-            for (Object key : map.keySet()) {
-                Object value = map.get(key);
-                Object keyDescriptor = key == null ? null : createDescriptorIfAbsent(key, accessor, cache);
-                Object valueDescriptor = value == null ? null : createDescriptorIfAbsent(value, accessor, cache);
-                descriptor.setProperty(keyDescriptor, valueDescriptor);
-            } // ~ end of loop map
-        } else {
-            if (JavaBeanAccessor.isAccessByMethod(accessor)) {
-                Map<String, Method> methods = ReflectUtils.getBeanPropertyReadMethods(obj.getClass());
-                for (Map.Entry<String, Method> entry : methods.entrySet()) {
-                    try {
-                        Object value = entry.getValue().invoke(obj);
-                        if (value == null) {
-                            continue;
-                        }
-                        JavaBeanDescriptor valueDescriptor = createDescriptorIfAbsent(value, accessor, cache);
-                        descriptor.setProperty(entry.getKey(), valueDescriptor);
-                    } catch (Exception e) {
-                        throw new RuntimeException(e.getMessage(), e);
-                    }
-                } // ~ end of loop method map
-            } // ~ end of if (JavaBeanAccessor.isAccessByMethod(accessor))
-
-            if (JavaBeanAccessor.isAccessByField(accessor)) {
-                Map<String, Field> fields = ReflectUtils.getBeanPropertyFields(obj.getClass());
-                for (Map.Entry<String, Field> entry : fields.entrySet()) {
-                    if (!descriptor.containsProperty(entry.getKey())) {
-                        try {
-                            Object value = entry.getValue().get(obj);
-                            if (value == null) {
-                                continue;
-                            }
-                            JavaBeanDescriptor valueDescriptor = createDescriptorIfAbsent(value, accessor, cache);
-                            descriptor.setProperty(entry.getKey(), valueDescriptor);
-                        } catch (Exception e) {
-                            throw new RuntimeException(e.getMessage(), e);
-                        }
-                    }
-                } // ~ end of loop field map
-            } // ~ end of if (JavaBeanAccessor.isAccessByField(accessor))
-
-        } // ~ end of else
-
-    } // ~ end of method serializeInternal
-
-    public static Object deserialize(JavaBeanDescriptor beanDescriptor) {
-        Object result = deserialize(
-                beanDescriptor,
-                Thread.currentThread().getContextClassLoader());
-        return result;
-    }
-
-    public static Object deserialize(JavaBeanDescriptor beanDescriptor, ClassLoader loader) {
-        if (beanDescriptor == null) {
-            return null;
-        }
-        IdentityHashMap<JavaBeanDescriptor, Object> cache = new IdentityHashMap<JavaBeanDescriptor, Object>();
-        Object result = instantiateForDeserialize(beanDescriptor, loader, cache);
-        deserializeInternal(result, beanDescriptor, loader, cache);
-        return result;
-    }
-
-    private static void deserializeInternal(Object result, JavaBeanDescriptor beanDescriptor, ClassLoader loader, IdentityHashMap<JavaBeanDescriptor, Object> cache) {
-        if (beanDescriptor.isEnumType() || beanDescriptor.isClassType() || beanDescriptor.isPrimitiveType()) {
-            return;
-        }
-
-        if (beanDescriptor.isArrayType()) {
-            int index = 0;
-            for (Map.Entry<Object, Object> entry : beanDescriptor) {
-                Object item = entry.getValue();
-                if (item instanceof JavaBeanDescriptor) {
-                    JavaBeanDescriptor itemDescriptor = (JavaBeanDescriptor) entry.getValue();
-                    item = instantiateForDeserialize(itemDescriptor, loader, cache);
-                    deserializeInternal(item, itemDescriptor, loader, cache);
-                }
-                Array.set(result, index++, item);
-            }
-        } else if (beanDescriptor.isCollectionType()) {
-            Collection collection = (Collection) result;
-            for (Map.Entry<Object, Object> entry : beanDescriptor) {
-                Object item = entry.getValue();
-                if (item instanceof JavaBeanDescriptor) {
-                    JavaBeanDescriptor itemDescriptor = (JavaBeanDescriptor) entry.getValue();
-                    item = instantiateForDeserialize(itemDescriptor, loader, cache);
-                    deserializeInternal(item, itemDescriptor, loader, cache);
-                }
-                collection.add(item);
-            }
-        } else if (beanDescriptor.isMapType()) {
-            Map map = (Map) result;
-            for (Map.Entry<Object, Object> entry : beanDescriptor) {
-                Object key = entry.getKey();
-                Object value = entry.getValue();
-                if (key != null && key instanceof JavaBeanDescriptor) {
-                    JavaBeanDescriptor keyDescriptor = (JavaBeanDescriptor) entry.getKey();
-                    key = instantiateForDeserialize(keyDescriptor, loader, cache);
-                    deserializeInternal(key, keyDescriptor, loader, cache);
-                }
-                if (value != null && value instanceof JavaBeanDescriptor) {
-                    JavaBeanDescriptor valueDescriptor = (JavaBeanDescriptor) entry.getValue();
-                    value = instantiateForDeserialize(valueDescriptor, loader, cache);
-                    deserializeInternal(value, valueDescriptor, loader, cache);
-                }
-                map.put(key, value);
-            }
-        } else if (beanDescriptor.isBeanType()) {
-            for (Map.Entry<Object, Object> entry : beanDescriptor) {
-                String property = entry.getKey().toString();
-                Object value = entry.getValue();
-                if (value == null) {
-                    continue;
-                }
-
-                if (value instanceof JavaBeanDescriptor) {
-                    JavaBeanDescriptor valueDescriptor = (JavaBeanDescriptor) entry.getValue();
-                    value = instantiateForDeserialize(valueDescriptor, loader, cache);
-                    deserializeInternal(value, valueDescriptor, loader, cache);
-                }
-
-                Method method = getSetterMethod(result.getClass(), property, value.getClass());
-                boolean setByMethod = false;
-                try {
-                    if (method != null) {
-                        method.invoke(result, value);
-                        setByMethod = true;
-                    }
-                } catch (Exception e) {
-                    LogHelper.warn(logger, "Failed to set property through method " + method, e);
-                }
-
-                if (!setByMethod) {
-                    try {
-                        Field field = result.getClass().getField(property);
-                        if (field != null) {
-                            field.set(result, value);
-                        }
-                    } catch (NoSuchFieldException e1) {
-                        LogHelper.warn(logger, "Failed to set field value", e1);
-                    } catch (IllegalAccessException e1) {
-                        LogHelper.warn(logger, "Failed to set field value", e1);
-                    }
-                }
-            }
-        } else {
-            throw new IllegalArgumentException("Unsupported type " + beanDescriptor.getClassName() + ":" + beanDescriptor.getType());
-        }
-    }
-
-    private static Method getSetterMethod(Class<?> cls, String property, Class<?> valueCls) {
-        String name = "set" + property.substring(0, 1).toUpperCase() + property.substring(1);
-        Method method = null;
-        try {
-            method = cls.getMethod(name, valueCls);
-        } catch (NoSuchMethodException e) {
-            for (Method m : cls.getMethods()) {
-                if (ReflectUtils.isBeanPropertyWriteMethod(m)
-                        && m.getName().equals(name)) {
-                    method = m;
-                }
-            }
-        }
-        if (method != null) {
-            method.setAccessible(true);
-        }
-        return method;
-    }
-
-    private static Object instantiate(Class<?> cl) throws Exception {
-        Constructor<?>[] constructors = cl.getDeclaredConstructors();
-        Constructor<?> constructor = null;
-        int argc = Integer.MAX_VALUE;
-        for (Constructor<?> c : constructors) {
-            if (c.getParameterTypes().length < argc) {
-                argc = c.getParameterTypes().length;
-                constructor = c;
-            }
-        }
-
-        if (constructor != null) {
-            Class<?>[] paramTypes = constructor.getParameterTypes();
-            Object[] constructorArgs = new Object[paramTypes.length];
-            for (int i = 0; i < constructorArgs.length; i++) {
-                constructorArgs[i] = getConstructorArg(paramTypes[i]);
-            }
-            try {
-                constructor.setAccessible(true);
-                return constructor.newInstance(constructorArgs);
-            } catch (InstantiationException e) {
-                LogHelper.warn(logger, e.getMessage(), e);
-            } catch (IllegalAccessException e) {
-                LogHelper.warn(logger, e.getMessage(), e);
-            } catch (InvocationTargetException e) {
-                LogHelper.warn(logger, e.getMessage(), e);
-            }
-        }
-
-        return cl.newInstance();
-    }
-
-    public static Object getConstructorArg(Class<?> cl) {
-        if (boolean.class.equals(cl) || Boolean.class.equals(cl)) {
-            return Boolean.FALSE;
-        } else if (byte.class.equals(cl) || Byte.class.equals(cl)) {
-            return Byte.valueOf((byte) 0);
-        } else if (short.class.equals(cl) || Short.class.equals(cl)) {
-            return Short.valueOf((short) 0);
-        } else if (int.class.equals(cl) || Integer.class.equals(cl)) {
-            return Integer.valueOf(0);
-        } else if (long.class.equals(cl) || Long.class.equals(cl)) {
-            return Long.valueOf(0L);
-        } else if (float.class.equals(cl) || Float.class.equals(cl)) {
-            return Float.valueOf((float) 0);
-        } else if (double.class.equals(cl) || Double.class.equals(cl)) {
-            return Double.valueOf((double) 0);
-        } else if (char.class.equals(cl) || Character.class.equals(cl)) {
-            return new Character((char) 0);
-        } else {
-            return null;
-        }
-    }
-
-    private static Object instantiateForDeserialize(JavaBeanDescriptor beanDescriptor, ClassLoader loader, IdentityHashMap<JavaBeanDescriptor, Object> cache) {
-        if (cache.containsKey(beanDescriptor)) {
-            return cache.get(beanDescriptor);
-        }
-        Object result = null;
-        if (beanDescriptor.isClassType()) {
-            try {
-                result = name2Class(loader, beanDescriptor.getClassNameProperty());
-                return result;
-            } catch (ClassNotFoundException e) {
-                throw new RuntimeException(e.getMessage(), e);
-            }
-        } else if (beanDescriptor.isEnumType()) {
-            try {
-                Class<?> enumType = name2Class(loader, beanDescriptor.getClassName());
-                Method method = getEnumValueOfMethod(enumType);
-                result = method.invoke(null, enumType, beanDescriptor.getEnumPropertyName());
-                return result;
-            } catch (Exception e) {
-                throw new RuntimeException(e.getMessage(), e);
-            }
-        } else if (beanDescriptor.isPrimitiveType()) {
-            result = beanDescriptor.getPrimitiveProperty();
-            return result;
-        } else if (beanDescriptor.isArrayType()) {
-            Class<?> componentType;
-            try {
-                componentType = name2Class(loader, beanDescriptor.getClassName());
-            } catch (ClassNotFoundException e) {
-                throw new RuntimeException(e.getMessage(), e);
-            }
-            result = Array.newInstance(componentType, beanDescriptor.propertySize());
-            cache.put(beanDescriptor, result);
-        } else try {
-            Class<?> cl = name2Class(loader, beanDescriptor.getClassName());
-            result = instantiate(cl);
-            cache.put(beanDescriptor, result);
-        } catch (ClassNotFoundException e) {
-            throw new RuntimeException(e.getMessage(), e);
-        } catch (Exception e) {
-            throw new RuntimeException(e.getMessage(), e);
-        }
-
-        return result;
-    }
-
-    /**
-     * Transform the Class.forName String to Class Object.
-     *
-     * @param name Class.getName()
-     * @return Class
-     * @throws ClassNotFoundException Class.forName
-     */
-    public static Class<?> name2Class(ClassLoader loader, String name) throws ClassNotFoundException {
-        if (TYPES.containsKey(name)) {
-            return TYPES.get(name);
-        }
-        if (isArray(name)) {
-            int dimension = 0;
-            while (isArray(name)) {
-                ++dimension;
-                name = name.substring(1);
-            }
-            Class type = name2Class(loader, name);
-            int[] dimensions = new int[dimension];
-            for (int i = 0; i < dimension; i++) {
-                dimensions[i] = 0;
-            }
-            return Array.newInstance(type, dimensions).getClass();
-        }
-        if (isReferenceType(name)) {
-            name = name.substring(1, name.length() - 1);
-        }
-        return Class.forName(name, false, loader);
-    }
-
-    private static boolean isArray(String type) {
-        return type != null && type.startsWith(ARRAY_PREFIX);
-    }
-
-    private static boolean isReferenceType(String type) {
-        return type != null
-                && type.startsWith(REFERENCE_TYPE_PREFIX)
-                && type.endsWith(REFERENCE_TYPE_SUFFIX);
-    }
-
-    private static Method getEnumValueOfMethod(Class cl) throws NoSuchMethodException {
-        return cl.getMethod("valueOf", Class.class, String.class);
-    }
-
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.beanutil;
+
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.common.utils.LogHelper;
+import org.apache.dubbo.common.utils.ReflectUtils;
+
+import java.lang.reflect.Array;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.IdentityHashMap;
+import java.util.Map;
+
+public final class JavaBeanSerializeUtil {
+
+    private static final Logger logger = LoggerFactory.getLogger(JavaBeanSerializeUtil.class);
+    private static final Map<String, Class<?>> TYPES = new HashMap<String, Class<?>>();
+    private static final String ARRAY_PREFIX = "[";
+    private static final String REFERENCE_TYPE_PREFIX = "L";
+    private static final String REFERENCE_TYPE_SUFFIX = ";";
+
+    static {
+        TYPES.put(boolean.class.getName(), boolean.class);
+        TYPES.put(byte.class.getName(), byte.class);
+        TYPES.put(short.class.getName(), short.class);
+        TYPES.put(int.class.getName(), int.class);
+        TYPES.put(long.class.getName(), long.class);
+        TYPES.put(float.class.getName(), float.class);
+        TYPES.put(double.class.getName(), double.class);
+        TYPES.put(void.class.getName(), void.class);
+        TYPES.put("Z", boolean.class);
+        TYPES.put("B", byte.class);
+        TYPES.put("C", char.class);
+        TYPES.put("D", double.class);
+        TYPES.put("F", float.class);
+        TYPES.put("I", int.class);
+        TYPES.put("J", long.class);
+        TYPES.put("S", short.class);
+    }
+
+    private JavaBeanSerializeUtil() {
+    }
+
+    public static JavaBeanDescriptor serialize(Object obj) {
+        JavaBeanDescriptor result = serialize(obj, JavaBeanAccessor.FIELD);
+        return result;
+    }
+
+    public static JavaBeanDescriptor serialize(Object obj, JavaBeanAccessor accessor) {
+        if (obj == null) {
+            return null;
+        }
+        if (obj instanceof JavaBeanDescriptor) {
+            return (JavaBeanDescriptor) obj;
+        }
+        IdentityHashMap<Object, JavaBeanDescriptor> cache = new IdentityHashMap<Object, JavaBeanDescriptor>();
+        JavaBeanDescriptor result = createDescriptorIfAbsent(obj, accessor, cache);
+        return result;
+    }
+
+    private static JavaBeanDescriptor createDescriptorForSerialize(Class<?> cl) {
+        if (cl.isEnum()) {
+            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_ENUM);
+        } else if (cl.isArray()) {
+            return new JavaBeanDescriptor(cl.getComponentType().getName(), JavaBeanDescriptor.TYPE_ARRAY);
+        } else if (ReflectUtils.isPrimitive(cl)) {
+            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_PRIMITIVE);
+        } else if (Class.class.equals(cl)) {
+            return new JavaBeanDescriptor(Class.class.getName(), JavaBeanDescriptor.TYPE_CLASS);
+        } else if (Collection.class.isAssignableFrom(cl)) {
+            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_COLLECTION);
+        } else if (Map.class.isAssignableFrom(cl)) {
+            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_MAP);
+        } else {
+            return new JavaBeanDescriptor(cl.getName(), JavaBeanDescriptor.TYPE_BEAN);
+        }
+    }
+
+    private static JavaBeanDescriptor createDescriptorIfAbsent(Object obj, JavaBeanAccessor accessor, IdentityHashMap<Object, JavaBeanDescriptor> cache) {
+        if (cache.containsKey(obj)) {
+            return cache.get(obj);
+        } else if (obj instanceof JavaBeanDescriptor) {
+            return (JavaBeanDescriptor) obj;
+        } else {
+            JavaBeanDescriptor result = createDescriptorForSerialize(obj.getClass());
+            cache.put(obj, result);
+            serializeInternal(result, obj, accessor, cache);
+            return result;
+        }
+    }
+
+    private static void serializeInternal(JavaBeanDescriptor descriptor, Object obj, JavaBeanAccessor accessor, IdentityHashMap<Object, JavaBeanDescriptor> cache) {
+        if (obj == null || descriptor == null) {
+            return;
+        }
+
+        if (obj.getClass().isEnum()) {
+            descriptor.setEnumNameProperty(((Enum<?>) obj).name());
+        } else if (ReflectUtils.isPrimitive(obj.getClass())) {
+            descriptor.setPrimitiveProperty(obj);
+        } else if (Class.class.equals(obj.getClass())) {
+            descriptor.setClassNameProperty(((Class<?>) obj).getName());
+        } else if (obj.getClass().isArray()) {
+            int len = Array.getLength(obj);
+            for (int i = 0; i < len; i++) {
+                Object item = Array.get(obj, i);
+                if (item == null) {
+                    descriptor.setProperty(i, null);
+                } else {
+                    JavaBeanDescriptor itemDescriptor = createDescriptorIfAbsent(item, accessor, cache);
+                    descriptor.setProperty(i, itemDescriptor);
+                }
+            }
+        } else if (obj instanceof Collection) {
+            Collection collection = (Collection) obj;
+            int index = 0;
+            for (Object item : collection) {
+                if (item == null) {
+                    descriptor.setProperty(index++, null);
+                } else {
+                    JavaBeanDescriptor itemDescriptor = createDescriptorIfAbsent(item, accessor, cache);
+                    descriptor.setProperty(index++, itemDescriptor);
+                }
+            }
+        } else if (obj instanceof Map) {
+            Map map = (Map) obj;
+            for (Object key : map.keySet()) {
+                Object value = map.get(key);
+                Object keyDescriptor = key == null ? null : createDescriptorIfAbsent(key, accessor, cache);
+                Object valueDescriptor = value == null ? null : createDescriptorIfAbsent(value, accessor, cache);
+                descriptor.setProperty(keyDescriptor, valueDescriptor);
+            } // ~ end of loop map
+        } else {
+            if (JavaBeanAccessor.isAccessByMethod(accessor)) {
+                Map<String, Method> methods = ReflectUtils.getBeanPropertyReadMethods(obj.getClass());
+                for (Map.Entry<String, Method> entry : methods.entrySet()) {
+                    try {
+                        Object value = entry.getValue().invoke(obj);
+                        if (value == null) {
+                            continue;
+                        }
+                        JavaBeanDescriptor valueDescriptor = createDescriptorIfAbsent(value, accessor, cache);
+                        descriptor.setProperty(entry.getKey(), valueDescriptor);
+                    } catch (Exception e) {
+                        throw new RuntimeException(e.getMessage(), e);
+                    }
+                } // ~ end of loop method map
+            } // ~ end of if (JavaBeanAccessor.isAccessByMethod(accessor))
+
+            if (JavaBeanAccessor.isAccessByField(accessor)) {
+                Map<String, Field> fields = ReflectUtils.getBeanPropertyFields(obj.getClass());
+                for (Map.Entry<String, Field> entry : fields.entrySet()) {
+                    if (!descriptor.containsProperty(entry.getKey())) {
+                        try {
+                            Object value = entry.getValue().get(obj);
+                            if (value == null) {
+                                continue;
+                            }
+                            JavaBeanDescriptor valueDescriptor = createDescriptorIfAbsent(value, accessor, cache);
+                            descriptor.setProperty(entry.getKey(), valueDescriptor);
+                        } catch (Exception e) {
+                            throw new RuntimeException(e.getMessage(), e);
+                        }
+                    }
+                } // ~ end of loop field map
+            } // ~ end of if (JavaBeanAccessor.isAccessByField(accessor))
+
+        } // ~ end of else
+
+    } // ~ end of method serializeInternal
+
+    public static Object deserialize(JavaBeanDescriptor beanDescriptor) {
+        Object result = deserialize(
+                beanDescriptor,
+                Thread.currentThread().getContextClassLoader());
+        return result;
+    }
+
+    public static Object deserialize(JavaBeanDescriptor beanDescriptor, ClassLoader loader) {
+        if (beanDescriptor == null) {
+            return null;
+        }
+        IdentityHashMap<JavaBeanDescriptor, Object> cache = new IdentityHashMap<JavaBeanDescriptor, Object>();
+        Object result = instantiateForDeserialize(beanDescriptor, loader, cache);
+        deserializeInternal(result, beanDescriptor, loader, cache);
+        return result;
+    }
+
+    private static void deserializeInternal(Object result, JavaBeanDescriptor beanDescriptor, ClassLoader loader, IdentityHashMap<JavaBeanDescriptor, Object> cache) {
+        if (beanDescriptor.isEnumType() || beanDescriptor.isClassType() || beanDescriptor.isPrimitiveType()) {
+            return;
+        }
+
+        if (beanDescriptor.isArrayType()) {
+            int index = 0;
+            for (Map.Entry<Object, Object> entry : beanDescriptor) {
+                Object item = entry.getValue();
+                if (item instanceof JavaBeanDescriptor) {
+                    JavaBeanDescriptor itemDescriptor = (JavaBeanDescriptor) entry.getValue();
+                    item = instantiateForDeserialize(itemDescriptor, loader, cache);
+                    deserializeInternal(item, itemDescriptor, loader, cache);
+                }
+                Array.set(result, index++, item);
+            }
+        } else if (beanDescriptor.isCollectionType()) {
+            Collection collection = (Collection) result;
+            for (Map.Entry<Object, Object> entry : beanDescriptor) {
+                Object item = entry.getValue();
+                if (item instanceof JavaBeanDescriptor) {
+                    JavaBeanDescriptor itemDescriptor = (JavaBeanDescriptor) entry.getValue();
+                    item = instantiateForDeserialize(itemDescriptor, loader, cache);
+                    deserializeInternal(item, itemDescriptor, loader, cache);
+                }
+                collection.add(item);
+            }
+        } else if (beanDescriptor.isMapType()) {
+            Map map = (Map) result;
+            for (Map.Entry<Object, Object> entry : beanDescriptor) {
+                Object key = entry.getKey();
+                Object value = entry.getValue();
+                if (key != null && key instanceof JavaBeanDescriptor) {
+                    JavaBeanDescriptor keyDescriptor = (JavaBeanDescriptor) entry.getKey();
+                    key = instantiateForDeserialize(keyDescriptor, loader, cache);
+                    deserializeInternal(key, keyDescriptor, loader, cache);
+                }
+                if (value != null && value instanceof JavaBeanDescriptor) {
+                    JavaBeanDescriptor valueDescriptor = (JavaBeanDescriptor) entry.getValue();
+                    value = instantiateForDeserialize(valueDescriptor, loader, cache);
+                    deserializeInternal(value, valueDescriptor, loader, cache);
+                }
+                map.put(key, value);
+            }
+        } else if (beanDescriptor.isBeanType()) {
+            for (Map.Entry<Object, Object> entry : beanDescriptor) {
+                String property = entry.getKey().toString();
+                Object value = entry.getValue();
+                if (value == null) {
+                    continue;
+                }
+
+                if (value instanceof JavaBeanDescriptor) {
+                    JavaBeanDescriptor valueDescriptor = (JavaBeanDescriptor) entry.getValue();
+                    value = instantiateForDeserialize(valueDescriptor, loader, cache);
+                    deserializeInternal(value, valueDescriptor, loader, cache);
+                }
+
+                Method method = getSetterMethod(result.getClass(), property, value.getClass());
+                boolean setByMethod = false;
+                try {
+                    if (method != null) {
+                        method.invoke(result, value);
+                        setByMethod = true;
+                    }
+                } catch (Exception e) {
+                    LogHelper.warn(logger, "Failed to set property through method " + method, e);
+                }
+
+                if (!setByMethod) {
+                    try {
+                        Field field = result.getClass().getField(property);
+                        if (field != null) {
+                            field.set(result, value);
+                        }
+                    } catch (NoSuchFieldException e1) {
+                        LogHelper.warn(logger, "Failed to set field value", e1);
+                    } catch (IllegalAccessException e1) {
+                        LogHelper.warn(logger, "Failed to set field value", e1);
+                    }
+                }
+            }
+        } else {
+            throw new IllegalArgumentException("Unsupported type " + beanDescriptor.getClassName() + ":" + beanDescriptor.getType());
+        }
+    }
+
+    private static Method getSetterMethod(Class<?> cls, String property, Class<?> valueCls) {
+        String name = "set" + property.substring(0, 1).toUpperCase() + property.substring(1);
+        Method method = null;
+        try {
+            method = cls.getMethod(name, valueCls);
+        } catch (NoSuchMethodException e) {
+            for (Method m : cls.getMethods()) {
+                if (ReflectUtils.isBeanPropertyWriteMethod(m)
+                        && m.getName().equals(name)) {
+                    method = m;
+                }
+            }
+        }
+        if (method != null) {
+            method.setAccessible(true);
+        }
+        return method;
+    }
+
+    private static Object instantiate(Class<?> cl) throws Exception {
+        Constructor<?>[] constructors = cl.getDeclaredConstructors();
+        Constructor<?> constructor = null;
+        int argc = Integer.MAX_VALUE;
+        for (Constructor<?> c : constructors) {
+            if (c.getParameterTypes().length < argc) {
+                argc = c.getParameterTypes().length;
+                constructor = c;
+            }
+        }
+
+        if (constructor != null) {
+            Class<?>[] paramTypes = constructor.getParameterTypes();
+            Object[] constructorArgs = new Object[paramTypes.length];
+            for (int i = 0; i < constructorArgs.length; i++) {
+                constructorArgs[i] = getConstructorArg(paramTypes[i]);
+            }
+            try {
+                constructor.setAccessible(true);
+                return constructor.newInstance(constructorArgs);
+            } catch (InstantiationException e) {
+                LogHelper.warn(logger, e.getMessage(), e);
+            } catch (IllegalAccessException e) {
+                LogHelper.warn(logger, e.getMessage(), e);
+            } catch (InvocationTargetException e) {
+                LogHelper.warn(logger, e.getMessage(), e);
+            }
+        }
+
+        return cl.newInstance();
+    }
+
+    public static Object getConstructorArg(Class<?> cl) {
+        if (boolean.class.equals(cl) || Boolean.class.equals(cl)) {
+            return Boolean.FALSE;
+        } else if (byte.class.equals(cl) || Byte.class.equals(cl)) {
+            return Byte.valueOf((byte) 0);
+        } else if (short.class.equals(cl) || Short.class.equals(cl)) {
+            return Short.valueOf((short) 0);
+        } else if (int.class.equals(cl) || Integer.class.equals(cl)) {
+            return Integer.valueOf(0);
+        } else if (long.class.equals(cl) || Long.class.equals(cl)) {
+            return Long.valueOf(0L);
+        } else if (float.class.equals(cl) || Float.class.equals(cl)) {
+            return Float.valueOf((float) 0);
+        } else if (double.class.equals(cl) || Double.class.equals(cl)) {
+            return Double.valueOf((double) 0);
+        } else if (char.class.equals(cl) || Character.class.equals(cl)) {
+            return new Character((char) 0);
+        } else {
+            return null;
+        }
+    }
+
+    private static Object instantiateForDeserialize(JavaBeanDescriptor beanDescriptor, ClassLoader loader, IdentityHashMap<JavaBeanDescriptor, Object> cache) {
+        if (cache.containsKey(beanDescriptor)) {
+            return cache.get(beanDescriptor);
+        }
+        Object result = null;
+        if (beanDescriptor.isClassType()) {
+            try {
+                result = name2Class(loader, beanDescriptor.getClassNameProperty());
+                return result;
+            } catch (ClassNotFoundException e) {
+                throw new RuntimeException(e.getMessage(), e);
+            }
+        } else if (beanDescriptor.isEnumType()) {
+            try {
+                Class<?> enumType = name2Class(loader, beanDescriptor.getClassName());
+                Method method = getEnumValueOfMethod(enumType);
+                result = method.invoke(null, enumType, beanDescriptor.getEnumPropertyName());
+                return result;
+            } catch (Exception e) {
+                throw new RuntimeException(e.getMessage(), e);
+            }
+        } else if (beanDescriptor.isPrimitiveType()) {
+            result = beanDescriptor.getPrimitiveProperty();
+            return result;
+        } else if (beanDescriptor.isArrayType()) {
+            Class<?> componentType;
+            try {
+                componentType = name2Class(loader, beanDescriptor.getClassName());
+            } catch (ClassNotFoundException e) {
+                throw new RuntimeException(e.getMessage(), e);
+            }
+            result = Array.newInstance(componentType, beanDescriptor.propertySize());
+            cache.put(beanDescriptor, result);
+        } else try {
+            Class<?> cl = name2Class(loader, beanDescriptor.getClassName());
+            result = instantiate(cl);
+            cache.put(beanDescriptor, result);
+        } catch (ClassNotFoundException e) {
+            throw new RuntimeException(e.getMessage(), e);
+        } catch (Exception e) {
+            throw new RuntimeException(e.getMessage(), e);
+        }
+
+        return result;
+    }
+
+    /**
+     * Transform the Class.forName String to Class Object.
+     *
+     * @param name Class.getName()
+     * @return Class
+     * @throws ClassNotFoundException Class.forName
+     */
+    public static Class<?> name2Class(ClassLoader loader, String name) throws ClassNotFoundException {
+        if (TYPES.containsKey(name)) {
+            return TYPES.get(name);
+        }
+        if (isArray(name)) {
+            int dimension = 0;
+            while (isArray(name)) {
+                ++dimension;
+                name = name.substring(1);
+            }
+            Class type = name2Class(loader, name);
+            int[] dimensions = new int[dimension];
+            for (int i = 0; i < dimension; i++) {
+                dimensions[i] = 0;
+            }
+            return Array.newInstance(type, dimensions).getClass();
+        }
+        if (isReferenceType(name)) {
+            name = name.substring(1, name.length() - 1);
+        }
+        return Class.forName(name, false, loader);
+    }
+
+    private static boolean isArray(String type) {
+        return type != null && type.startsWith(ARRAY_PREFIX);
+    }
+
+    private static boolean isReferenceType(String type) {
+        return type != null
+                && type.startsWith(REFERENCE_TYPE_PREFIX)
+                && type.endsWith(REFERENCE_TYPE_SUFFIX);
+    }
+
+    private static Method getEnumValueOfMethod(Class cl) throws NoSuchMethodException {
+        return cl.getMethod("valueOf", Class.class, String.class);
+    }
+
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/concurrent/ExecutionList.java b/dubbo-common/src/main/java/org/apache/dubbo/common/concurrent/ExecutionList.java
index c88626cbe6..b093fc1e19 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/concurrent/ExecutionList.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/concurrent/ExecutionList.java
@@ -1,180 +1,180 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.concurrent;
-
-import org.apache.dubbo.common.logger.Logger;
-import org.apache.dubbo.common.logger.LoggerFactory;
-import org.apache.dubbo.common.utils.NamedThreadFactory;
-
-import java.util.concurrent.Executor;
-import java.util.concurrent.SynchronousQueue;
-import java.util.concurrent.ThreadPoolExecutor;
-import java.util.concurrent.TimeUnit;
-
-/**
- * <p>A list of listeners, each with an associated {@code Executor}, that
- * guarantees that every {@code Runnable} that is {@linkplain #add added} will
- * be executed after {@link #execute()} is called. Any {@code Runnable} added
- * after the call to {@code execute} is still guaranteed to execute. There is no
- * guarantee, however, that listeners will be executed in the order that they
- * are added.
- * <p>
- * <p>Exceptions thrown by a listener will be propagated up to the executor.
- * Any exception thrown during {@code Executor.execute} (e.g., a {@code
- * RejectedExecutionException} or an exception thrown by {@linkplain
- * MoreExecutors#sameThreadExecutor inline execution}) will be caught and
- * logged.
- */
-public final class ExecutionList {
-    // Logger to log exceptions caught when running runnables.
-    static final Logger logger = LoggerFactory.getLogger(ExecutionList.class.getName());
-
-    /**
-     * The runnable, executor pairs to execute.  This acts as a stack threaded through the
-     * {@link RunnableExecutorPair#next} field.
-     */
-    private RunnableExecutorPair runnables;
-
-    private boolean executed;
-
-    private static final Executor DEFAULT_EXECUTOR = new ThreadPoolExecutor(1, 10, 60000L, TimeUnit.MILLISECONDS, new SynchronousQueue<Runnable>(), new NamedThreadFactory("DubboFutureCallbackDefault", true));
-
-    /**
-     * Creates a new, empty {@link ExecutionList}.
-     */
-    public ExecutionList() {
-    }
-
-    /**
-     * Adds the {@code Runnable} and accompanying {@code Executor} to the list of
-     * listeners to execute. If execution has already begun, the listener is
-     * executed immediately.
-     * <p>
-     * <p>Note: For fast, lightweight listeners that would be safe to execute in
-     * any thread, consider {@link MoreExecutors#sameThreadExecutor}. For heavier
-     * listeners, {@code sameThreadExecutor()} carries some caveats: First, the
-     * thread that the listener runs in depends on whether the {@code
-     * ExecutionList} has been executed at the time it is added. In particular,
-     * listeners may run in the thread that calls {@code add}. Second, the thread
-     * that calls {@link #execute} may be an internal implementation thread, such
-     * as an RPC network thread, and {@code sameThreadExecutor()} listeners may
-     * run in this thread. Finally, during the execution of a {@code
-     * sameThreadExecutor} listener, all other registered but unexecuted
-     * listeners are prevented from running, even if those listeners are to run
-     * in other executors.
-     */
-    public void add(Runnable runnable, Executor executor) {
-        // Fail fast on a null.  We throw NPE here because the contract of
-        // Executor states that it throws NPE on null listener, so we propagate
-        // that contract up into the add method as well.
-        if (runnable == null) {
-            throw new NullPointerException("Runnable can not be null!");
-        }
-        if (executor == null) {
-            logger.info("Executor for listenablefuture is null, will use default executor!");
-            executor = DEFAULT_EXECUTOR;
-        }
-        // Lock while we check state.  We must maintain the lock while adding the
-        // new pair so that another thread can't run the list out from under us.
-        // We only add to the list if we have not yet started execution.
-        synchronized (this) {
-            if (!executed) {
-                runnables = new RunnableExecutorPair(runnable, executor, runnables);
-                return;
-            }
-        }
-        // Execute the runnable immediately. Because of scheduling this may end up
-        // getting called before some of the previously added runnables, but we're
-        // OK with that.  If we want to change the contract to guarantee ordering
-        // among runnables we'd have to modify the logic here to allow it.
-        executeListener(runnable, executor);
-    }
-
-    /**
-     * Runs this execution list, executing all existing pairs in the order they
-     * were added. However, note that listeners added after this point may be
-     * executed before those previously added, and note that the execution order
-     * of all listeners is ultimately chosen by the implementations of the
-     * supplied executors.
-     * <p>
-     * <p>This method is idempotent. Calling it several times in parallel is
-     * semantically equivalent to calling it exactly once.
-     *
-     * @since 10.0 (present in 1.0 as {@code run})
-     */
-    public void execute() {
-        // Lock while we update our state so the add method above will finish adding
-        // any listeners before we start to run them.
-        RunnableExecutorPair list;
-        synchronized (this) {
-            if (executed) {
-                return;
-            }
-            executed = true;
-            list = runnables;
-            runnables = null;  // allow GC to free listeners even if this stays around for a while.
-        }
-        // If we succeeded then list holds all the runnables we to execute.  The pairs in the stack are
-        // in the opposite order from how they were added so we need to reverse the list to fulfill our
-        // contract.
-        // This is somewhat annoying, but turns out to be very fast in practice.  Alternatively, we
-        // could drop the contract on the method that enforces this queue like behavior since depending
-        // on it is likely to be a bug anyway.
-
-        // N.B. All writes to the list and the next pointers must have happened before the above
-        // synchronized block, so we can iterate the list without the lock held here.
-        RunnableExecutorPair reversedList = null;
-        while (list != null) {
-            RunnableExecutorPair tmp = list;
-            list = list.next;
-            tmp.next = reversedList;
-            reversedList = tmp;
-        }
-        while (reversedList != null) {
-            executeListener(reversedList.runnable, reversedList.executor);
-            reversedList = reversedList.next;
-        }
-    }
-
-    /**
-     * Submits the given runnable to the given {@link Executor} catching and logging all
-     * {@linkplain RuntimeException runtime exceptions} thrown by the executor.
-     */
-    private static void executeListener(Runnable runnable, Executor executor) {
-        try {
-            executor.execute(runnable);
-        } catch (RuntimeException e) {
-            // Log it and keep going, bad runnable and/or executor.  Don't
-            // punish the other runnables if we're given a bad one.  We only
-            // catch RuntimeException because we want Errors to propagate up.
-            logger.error("RuntimeException while executing runnable "
-                    + runnable + " with executor " + executor, e);
-        }
-    }
-
-    private static final class RunnableExecutorPair {
-        final Runnable runnable;
-        final Executor executor;
-        RunnableExecutorPair next;
-
-        RunnableExecutorPair(Runnable runnable, Executor executor, RunnableExecutorPair next) {
-            this.runnable = runnable;
-            this.executor = executor;
-            this.next = next;
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.concurrent;
+
+import org.apache.dubbo.common.logger.Logger;
+import org.apache.dubbo.common.logger.LoggerFactory;
+import org.apache.dubbo.common.utils.NamedThreadFactory;
+
+import java.util.concurrent.Executor;
+import java.util.concurrent.SynchronousQueue;
+import java.util.concurrent.ThreadPoolExecutor;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * <p>A list of listeners, each with an associated {@code Executor}, that
+ * guarantees that every {@code Runnable} that is {@linkplain #add added} will
+ * be executed after {@link #execute()} is called. Any {@code Runnable} added
+ * after the call to {@code execute} is still guaranteed to execute. There is no
+ * guarantee, however, that listeners will be executed in the order that they
+ * are added.
+ * <p>
+ * <p>Exceptions thrown by a listener will be propagated up to the executor.
+ * Any exception thrown during {@code Executor.execute} (e.g., a {@code
+ * RejectedExecutionException} or an exception thrown by {@linkplain
+ * MoreExecutors#sameThreadExecutor inline execution}) will be caught and
+ * logged.
+ */
+public final class ExecutionList {
+    // Logger to log exceptions caught when running runnables.
+    static final Logger logger = LoggerFactory.getLogger(ExecutionList.class.getName());
+
+    /**
+     * The runnable, executor pairs to execute.  This acts as a stack threaded through the
+     * {@link RunnableExecutorPair#next} field.
+     */
+    private RunnableExecutorPair runnables;
+
+    private boolean executed;
+
+    private static final Executor DEFAULT_EXECUTOR = new ThreadPoolExecutor(1, 10, 60000L, TimeUnit.MILLISECONDS, new SynchronousQueue<Runnable>(), new NamedThreadFactory("DubboFutureCallbackDefault", true));
+
+    /**
+     * Creates a new, empty {@link ExecutionList}.
+     */
+    public ExecutionList() {
+    }
+
+    /**
+     * Adds the {@code Runnable} and accompanying {@code Executor} to the list of
+     * listeners to execute. If execution has already begun, the listener is
+     * executed immediately.
+     * <p>
+     * <p>Note: For fast, lightweight listeners that would be safe to execute in
+     * any thread, consider {@link MoreExecutors#sameThreadExecutor}. For heavier
+     * listeners, {@code sameThreadExecutor()} carries some caveats: First, the
+     * thread that the listener runs in depends on whether the {@code
+     * ExecutionList} has been executed at the time it is added. In particular,
+     * listeners may run in the thread that calls {@code add}. Second, the thread
+     * that calls {@link #execute} may be an internal implementation thread, such
+     * as an RPC network thread, and {@code sameThreadExecutor()} listeners may
+     * run in this thread. Finally, during the execution of a {@code
+     * sameThreadExecutor} listener, all other registered but unexecuted
+     * listeners are prevented from running, even if those listeners are to run
+     * in other executors.
+     */
+    public void add(Runnable runnable, Executor executor) {
+        // Fail fast on a null.  We throw NPE here because the contract of
+        // Executor states that it throws NPE on null listener, so we propagate
+        // that contract up into the add method as well.
+        if (runnable == null) {
+            throw new NullPointerException("Runnable can not be null!");
+        }
+        if (executor == null) {
+            logger.info("Executor for listenablefuture is null, will use default executor!");
+            executor = DEFAULT_EXECUTOR;
+        }
+        // Lock while we check state.  We must maintain the lock while adding the
+        // new pair so that another thread can't run the list out from under us.
+        // We only add to the list if we have not yet started execution.
+        synchronized (this) {
+            if (!executed) {
+                runnables = new RunnableExecutorPair(runnable, executor, runnables);
+                return;
+            }
+        }
+        // Execute the runnable immediately. Because of scheduling this may end up
+        // getting called before some of the previously added runnables, but we're
+        // OK with that.  If we want to change the contract to guarantee ordering
+        // among runnables we'd have to modify the logic here to allow it.
+        executeListener(runnable, executor);
+    }
+
+    /**
+     * Runs this execution list, executing all existing pairs in the order they
+     * were added. However, note that listeners added after this point may be
+     * executed before those previously added, and note that the execution order
+     * of all listeners is ultimately chosen by the implementations of the
+     * supplied executors.
+     * <p>
+     * <p>This method is idempotent. Calling it several times in parallel is
+     * semantically equivalent to calling it exactly once.
+     *
+     * @since 10.0 (present in 1.0 as {@code run})
+     */
+    public void execute() {
+        // Lock while we update our state so the add method above will finish adding
+        // any listeners before we start to run them.
+        RunnableExecutorPair list;
+        synchronized (this) {
+            if (executed) {
+                return;
+            }
+            executed = true;
+            list = runnables;
+            runnables = null;  // allow GC to free listeners even if this stays around for a while.
+        }
+        // If we succeeded then list holds all the runnables we to execute.  The pairs in the stack are
+        // in the opposite order from how they were added so we need to reverse the list to fulfill our
+        // contract.
+        // This is somewhat annoying, but turns out to be very fast in practice.  Alternatively, we
+        // could drop the contract on the method that enforces this queue like behavior since depending
+        // on it is likely to be a bug anyway.
+
+        // N.B. All writes to the list and the next pointers must have happened before the above
+        // synchronized block, so we can iterate the list without the lock held here.
+        RunnableExecutorPair reversedList = null;
+        while (list != null) {
+            RunnableExecutorPair tmp = list;
+            list = list.next;
+            tmp.next = reversedList;
+            reversedList = tmp;
+        }
+        while (reversedList != null) {
+            executeListener(reversedList.runnable, reversedList.executor);
+            reversedList = reversedList.next;
+        }
+    }
+
+    /**
+     * Submits the given runnable to the given {@link Executor} catching and logging all
+     * {@linkplain RuntimeException runtime exceptions} thrown by the executor.
+     */
+    private static void executeListener(Runnable runnable, Executor executor) {
+        try {
+            executor.execute(runnable);
+        } catch (RuntimeException e) {
+            // Log it and keep going, bad runnable and/or executor.  Don't
+            // punish the other runnables if we're given a bad one.  We only
+            // catch RuntimeException because we want Errors to propagate up.
+            logger.error("RuntimeException while executing runnable "
+                    + runnable + " with executor " + executor, e);
+        }
+    }
+
+    private static final class RunnableExecutorPair {
+        final Runnable runnable;
+        final Executor executor;
+        RunnableExecutorPair next;
+
+        RunnableExecutorPair(Runnable runnable, Executor executor, RunnableExecutorPair next) {
+            this.runnable = runnable;
+            this.executor = executor;
+            this.next = next;
+        }
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/config/AsyncFor.java b/dubbo-common/src/main/java/org/apache/dubbo/common/config/AsyncFor.java
index dee04fcbc0..24120e4906 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/config/AsyncFor.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/config/AsyncFor.java
@@ -1,42 +1,42 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.config;
-
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * TODO This definition should better be placed in module 'dubbo-config-api', but only can be done when "rpc" dependencies are removed from "dubbo-config-api"
- * If an interface is annotated with AsyncFor, it will be treated as an async counterpart for the sync one.
- */
-@Documented
-@Retention(RetentionPolicy.RUNTIME)
-@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
-public @interface AsyncFor {
-
-    /**
-     * The original sync-style interface
-     *
-     * @return
-     */
-    Class<?> value();
-
-}
-
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.config;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * TODO This definition should better be placed in module 'dubbo-config-api', but only can be done when "rpc" dependencies are removed from "dubbo-config-api"
+ * If an interface is annotated with AsyncFor, it will be treated as an async counterpart for the sync one.
+ */
+@Documented
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
+public @interface AsyncFor {
+
+    /**
+     * The original sync-style interface
+     *
+     * @return
+     */
+    Class<?> value();
+
+}
+
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/extension/Adaptive.java b/dubbo-common/src/main/java/org/apache/dubbo/common/extension/Adaptive.java
index 686438e76d..d819374373 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/extension/Adaptive.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/extension/Adaptive.java
@@ -1,60 +1,60 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.extension;
-
-import org.apache.dubbo.common.URL;
-
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * Provide helpful information for {@link ExtensionLoader} to inject dependency extension instance.
- *
- * @see ExtensionLoader
- * @see URL
- */
-@Documented
-@Retention(RetentionPolicy.RUNTIME)
-@Target({ElementType.TYPE, ElementType.METHOD})
-public @interface Adaptive {
-    /**
-     * Decide which target extension to be injected. The name of the target extension is decided by the parameter passed
-     * in the URL, and the parameter names are given by this method.
-     * <p>
-     * If the specified parameters are not found from {@link URL}, then the default extension will be used for
-     * dependency injection (specified in its interface's {@link SPI}).
-     * <p>
-     * For examples, given <code>String[] {"key1", "key2"}</code>:
-     * <ol>
-     * <li>find parameter 'key1' in URL, use its value as the extension's name</li>
-     * <li>try 'key2' for extension's name if 'key1' is not found (or its value is empty) in URL</li>
-     * <li>use default extension if 'key2' doesn't appear either</li>
-     * <li>otherwise, throw {@link IllegalStateException}</li>
-     * </ol>
-     * If default extension's name is not give on interface's {@link SPI}, then a name is generated from interface's
-     * class name with the rule: divide classname from capital char into several parts, and separate the parts with
-     * dot '.', for example: for {@code org.apache.dubbo.xxx.YyyInvokerWrapper}, its default name is
-     * <code>String[] {"yyy.invoker.wrapper"}</code>. This name will be used to search for parameter from URL.
-     *
-     * @return parameter key names in URL
-     */
-    String[] value() default {};
-
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.extension;
+
+import org.apache.dubbo.common.URL;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * Provide helpful information for {@link ExtensionLoader} to inject dependency extension instance.
+ *
+ * @see ExtensionLoader
+ * @see URL
+ */
+@Documented
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.TYPE, ElementType.METHOD})
+public @interface Adaptive {
+    /**
+     * Decide which target extension to be injected. The name of the target extension is decided by the parameter passed
+     * in the URL, and the parameter names are given by this method.
+     * <p>
+     * If the specified parameters are not found from {@link URL}, then the default extension will be used for
+     * dependency injection (specified in its interface's {@link SPI}).
+     * <p>
+     * For examples, given <code>String[] {"key1", "key2"}</code>:
+     * <ol>
+     * <li>find parameter 'key1' in URL, use its value as the extension's name</li>
+     * <li>try 'key2' for extension's name if 'key1' is not found (or its value is empty) in URL</li>
+     * <li>use default extension if 'key2' doesn't appear either</li>
+     * <li>otherwise, throw {@link IllegalStateException}</li>
+     * </ol>
+     * If default extension's name is not give on interface's {@link SPI}, then a name is generated from interface's
+     * class name with the rule: divide classname from capital char into several parts, and separate the parts with
+     * dot '.', for example: for {@code org.apache.dubbo.xxx.YyyInvokerWrapper}, its default name is
+     * <code>String[] {"yyy.invoker.wrapper"}</code>. This name will be used to search for parameter from URL.
+     *
+     * @return parameter key names in URL
+     */
+    String[] value() default {};
+
 }
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/Bytes.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/Bytes.java
index a2cc9835c5..e2adb0af80 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/Bytes.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/Bytes.java
@@ -1,883 +1,883 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import org.apache.dubbo.common.utils.IOUtils;
-
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.zip.DeflaterOutputStream;
-import java.util.zip.InflaterInputStream;
-
-/**
- * CodecUtils.
- */
-
-public class Bytes {
-    private static final String C64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/="; //default base64.
-
-    private static final char[] BASE16 = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}, BASE64 = C64.toCharArray();
-
-    private static final int MASK4 = 0x0f, MASK6 = 0x3f, MASK8 = 0xff;
-
-    private static final Map<Integer, byte[]> DECODE_TABLE_MAP = new ConcurrentHashMap<Integer, byte[]>();
-
-    private static ThreadLocal<MessageDigest> MD = new ThreadLocal<MessageDigest>();
-
-    private Bytes() {
-    }
-
-    /**
-     * byte array copy.
-     *
-     * @param src    src.
-     * @param length new length.
-     * @return new byte array.
-     */
-    public static byte[] copyOf(byte[] src, int length) {
-        byte[] dest = new byte[length];
-        System.arraycopy(src, 0, dest, 0, Math.min(src.length, length));
-        return dest;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @return byte[].
-     */
-    public static byte[] short2bytes(short v) {
-        byte[] ret = {0, 0};
-        short2bytes(v, ret);
-        return ret;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void short2bytes(short v, byte[] b) {
-        short2bytes(v, b, 0);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void short2bytes(short v, byte[] b, int off) {
-        b[off + 1] = (byte) v;
-        b[off + 0] = (byte) (v >>> 8);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @return byte[].
-     */
-    public static byte[] int2bytes(int v) {
-        byte[] ret = {0, 0, 0, 0};
-        int2bytes(v, ret);
-        return ret;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void int2bytes(int v, byte[] b) {
-        int2bytes(v, b, 0);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v   value.
-     * @param b   byte array.
-     * @param off array offset.
-     */
-    public static void int2bytes(int v, byte[] b, int off) {
-        b[off + 3] = (byte) v;
-        b[off + 2] = (byte) (v >>> 8);
-        b[off + 1] = (byte) (v >>> 16);
-        b[off + 0] = (byte) (v >>> 24);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @return byte[].
-     */
-    public static byte[] float2bytes(float v) {
-        byte[] ret = {0, 0, 0, 0};
-        float2bytes(v, ret);
-        return ret;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void float2bytes(float v, byte[] b) {
-        float2bytes(v, b, 0);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v   value.
-     * @param b   byte array.
-     * @param off array offset.
-     */
-    public static void float2bytes(float v, byte[] b, int off) {
-        int i = Float.floatToIntBits(v);
-        b[off + 3] = (byte) i;
-        b[off + 2] = (byte) (i >>> 8);
-        b[off + 1] = (byte) (i >>> 16);
-        b[off + 0] = (byte) (i >>> 24);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @return byte[].
-     */
-    public static byte[] long2bytes(long v) {
-        byte[] ret = {0, 0, 0, 0, 0, 0, 0, 0};
-        long2bytes(v, ret);
-        return ret;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void long2bytes(long v, byte[] b) {
-        long2bytes(v, b, 0);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v   value.
-     * @param b   byte array.
-     * @param off array offset.
-     */
-    public static void long2bytes(long v, byte[] b, int off) {
-        b[off + 7] = (byte) v;
-        b[off + 6] = (byte) (v >>> 8);
-        b[off + 5] = (byte) (v >>> 16);
-        b[off + 4] = (byte) (v >>> 24);
-        b[off + 3] = (byte) (v >>> 32);
-        b[off + 2] = (byte) (v >>> 40);
-        b[off + 1] = (byte) (v >>> 48);
-        b[off + 0] = (byte) (v >>> 56);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @return byte[].
-     */
-    public static byte[] double2bytes(double v) {
-        byte[] ret = {0, 0, 0, 0, 0, 0, 0, 0};
-        double2bytes(v, ret);
-        return ret;
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v value.
-     * @param b byte array.
-     */
-    public static void double2bytes(double v, byte[] b) {
-        double2bytes(v, b, 0);
-    }
-
-    /**
-     * to byte array.
-     *
-     * @param v   value.
-     * @param b   byte array.
-     * @param off array offset.
-     */
-    public static void double2bytes(double v, byte[] b, int off) {
-        long j = Double.doubleToLongBits(v);
-        b[off + 7] = (byte) j;
-        b[off + 6] = (byte) (j >>> 8);
-        b[off + 5] = (byte) (j >>> 16);
-        b[off + 4] = (byte) (j >>> 24);
-        b[off + 3] = (byte) (j >>> 32);
-        b[off + 2] = (byte) (j >>> 40);
-        b[off + 1] = (byte) (j >>> 48);
-        b[off + 0] = (byte) (j >>> 56);
-    }
-
-    /**
-     * to short.
-     *
-     * @param b byte array.
-     * @return short.
-     */
-    public static short bytes2short(byte[] b) {
-        return bytes2short(b, 0);
-    }
-
-    /**
-     * to short.
-     *
-     * @param b   byte array.
-     * @param off offset.
-     * @return short.
-     */
-    public static short bytes2short(byte[] b, int off) {
-        return (short) (((b[off + 1] & 0xFF) << 0) +
-                ((b[off + 0]) << 8));
-    }
-
-    /**
-     * to int.
-     *
-     * @param b byte array.
-     * @return int.
-     */
-    public static int bytes2int(byte[] b) {
-        return bytes2int(b, 0);
-    }
-
-    /**
-     * to int.
-     *
-     * @param b   byte array.
-     * @param off offset.
-     * @return int.
-     */
-    public static int bytes2int(byte[] b, int off) {
-        return ((b[off + 3] & 0xFF) << 0) +
-                ((b[off + 2] & 0xFF) << 8) +
-                ((b[off + 1] & 0xFF) << 16) +
-                ((b[off + 0]) << 24);
-    }
-
-    /**
-     * to int.
-     *
-     * @param b byte array.
-     * @return int.
-     */
-    public static float bytes2float(byte[] b) {
-        return bytes2float(b, 0);
-    }
-
-    /**
-     * to int.
-     *
-     * @param b   byte array.
-     * @param off offset.
-     * @return int.
-     */
-    public static float bytes2float(byte[] b, int off) {
-        int i = ((b[off + 3] & 0xFF) << 0) +
-                ((b[off + 2] & 0xFF) << 8) +
-                ((b[off + 1] & 0xFF) << 16) +
-                ((b[off + 0]) << 24);
-        return Float.intBitsToFloat(i);
-    }
-
-    /**
-     * to long.
-     *
-     * @param b byte array.
-     * @return long.
-     */
-    public static long bytes2long(byte[] b) {
-        return bytes2long(b, 0);
-    }
-
-    /**
-     * to long.
-     *
-     * @param b   byte array.
-     * @param off offset.
-     * @return long.
-     */
-    public static long bytes2long(byte[] b, int off) {
-        return ((b[off + 7] & 0xFFL) << 0) +
-                ((b[off + 6] & 0xFFL) << 8) +
-                ((b[off + 5] & 0xFFL) << 16) +
-                ((b[off + 4] & 0xFFL) << 24) +
-                ((b[off + 3] & 0xFFL) << 32) +
-                ((b[off + 2] & 0xFFL) << 40) +
-                ((b[off + 1] & 0xFFL) << 48) +
-                (((long) b[off + 0]) << 56);
-    }
-
-    /**
-     * to long.
-     *
-     * @param b byte array.
-     * @return double.
-     */
-    public static double bytes2double(byte[] b) {
-        return bytes2double(b, 0);
-    }
-
-    /**
-     * to long.
-     *
-     * @param b   byte array.
-     * @param off offset.
-     * @return double.
-     */
-    public static double bytes2double(byte[] b, int off) {
-        long j = ((b[off + 7] & 0xFFL) << 0) +
-                ((b[off + 6] & 0xFFL) << 8) +
-                ((b[off + 5] & 0xFFL) << 16) +
-                ((b[off + 4] & 0xFFL) << 24) +
-                ((b[off + 3] & 0xFFL) << 32) +
-                ((b[off + 2] & 0xFFL) << 40) +
-                ((b[off + 1] & 0xFFL) << 48) +
-                (((long) b[off + 0]) << 56);
-        return Double.longBitsToDouble(j);
-    }
-
-    /**
-     * to hex string.
-     *
-     * @param bs byte array.
-     * @return hex string.
-     */
-    public static String bytes2hex(byte[] bs) {
-        return bytes2hex(bs, 0, bs.length);
-    }
-
-    /**
-     * to hex string.
-     *
-     * @param bs  byte array.
-     * @param off offset.
-     * @param len length.
-     * @return hex string.
-     */
-    public static String bytes2hex(byte[] bs, int off, int len) {
-        if (off < 0)
-            throw new IndexOutOfBoundsException("bytes2hex: offset < 0, offset is " + off);
-        if (len < 0)
-            throw new IndexOutOfBoundsException("bytes2hex: length < 0, length is " + len);
-        if (off + len > bs.length)
-            throw new IndexOutOfBoundsException("bytes2hex: offset + length > array length.");
-
-        byte b;
-        int r = off, w = 0;
-        char[] cs = new char[len * 2];
-        for (int i = 0; i < len; i++) {
-            b = bs[r++];
-            cs[w++] = BASE16[b >> 4 & MASK4];
-            cs[w++] = BASE16[b & MASK4];
-        }
-        return new String(cs);
-    }
-
-    /**
-     * from hex string.
-     *
-     * @param str hex string.
-     * @return byte array.
-     */
-    public static byte[] hex2bytes(String str) {
-        return hex2bytes(str, 0, str.length());
-    }
-
-    /**
-     * from hex string.
-     *
-     * @param str hex string.
-     * @param off offset.
-     * @param len length.
-     * @return byte array.
-     */
-    public static byte[] hex2bytes(final String str, final int off, int len) {
-        if ((len & 1) == 1)
-            throw new IllegalArgumentException("hex2bytes: ( len & 1 ) == 1.");
-
-        if (off < 0)
-            throw new IndexOutOfBoundsException("hex2bytes: offset < 0, offset is " + off);
-        if (len < 0)
-            throw new IndexOutOfBoundsException("hex2bytes: length < 0, length is " + len);
-        if (off + len > str.length())
-            throw new IndexOutOfBoundsException("hex2bytes: offset + length > array length.");
-
-        int num = len / 2, r = off, w = 0;
-        byte[] b = new byte[num];
-        for (int i = 0; i < num; i++)
-            b[w++] = (byte) (hex(str.charAt(r++)) << 4 | hex(str.charAt(r++)));
-        return b;
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param b byte array.
-     * @return base64 string.
-     */
-    public static String bytes2base64(byte[] b) {
-        return bytes2base64(b, 0, b.length, BASE64);
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param b byte array.
-     * @return base64 string.
-     */
-    public static String bytes2base64(byte[] b, int offset, int length) {
-        return bytes2base64(b, offset, length, BASE64);
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param b    byte array.
-     * @param code base64 code string(0-63 is base64 char,64 is pad char).
-     * @return base64 string.
-     */
-    public static String bytes2base64(byte[] b, String code) {
-        return bytes2base64(b, 0, b.length, code);
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param b    byte array.
-     * @param code base64 code string(0-63 is base64 char,64 is pad char).
-     * @return base64 string.
-     */
-    public static String bytes2base64(byte[] b, int offset, int length, String code) {
-        if (code.length() < 64)
-            throw new IllegalArgumentException("Base64 code length < 64.");
-
-        return bytes2base64(b, offset, length, code.toCharArray());
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param b    byte array.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return base64 string.
-     */
-    public static String bytes2base64(byte[] b, char[] code) {
-        return bytes2base64(b, 0, b.length, code);
-    }
-
-    /**
-     * to base64 string.
-     *
-     * @param bs   byte array.
-     * @param off  offset.
-     * @param len  length.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return base64 string.
-     */
-    public static String bytes2base64(final byte[] bs, final int off, final int len, final char[] code) {
-        if (off < 0)
-            throw new IndexOutOfBoundsException("bytes2base64: offset < 0, offset is " + off);
-        if (len < 0)
-            throw new IndexOutOfBoundsException("bytes2base64: length < 0, length is " + len);
-        if (off + len > bs.length)
-            throw new IndexOutOfBoundsException("bytes2base64: offset + length > array length.");
-
-        if (code.length < 64)
-            throw new IllegalArgumentException("Base64 code length < 64.");
-
-        boolean pad = code.length > 64; // has pad char.
-        int num = len / 3, rem = len % 3, r = off, w = 0;
-        char[] cs = new char[num * 4 + (rem == 0 ? 0 : pad ? 4 : rem + 1)];
-
-        for (int i = 0; i < num; i++) {
-            int b1 = bs[r++] & MASK8, b2 = bs[r++] & MASK8, b3 = bs[r++] & MASK8;
-
-            cs[w++] = code[b1 >> 2];
-            cs[w++] = code[(b1 << 4) & MASK6 | (b2 >> 4)];
-            cs[w++] = code[(b2 << 2) & MASK6 | (b3 >> 6)];
-            cs[w++] = code[b3 & MASK6];
-        }
-
-        if (rem == 1) {
-            int b1 = bs[r++] & MASK8;
-            cs[w++] = code[b1 >> 2];
-            cs[w++] = code[(b1 << 4) & MASK6];
-            if (pad) {
-                cs[w++] = code[64];
-                cs[w++] = code[64];
-            }
-        } else if (rem == 2) {
-            int b1 = bs[r++] & MASK8, b2 = bs[r++] & MASK8;
-            cs[w++] = code[b1 >> 2];
-            cs[w++] = code[(b1 << 4) & MASK6 | (b2 >> 4)];
-            cs[w++] = code[(b2 << 2) & MASK6];
-            if (pad)
-                cs[w++] = code[64];
-        }
-        return new String(cs);
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str base64 string.
-     * @return byte array.
-     */
-    public static byte[] base642bytes(String str) {
-        return base642bytes(str, 0, str.length());
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str    base64 string.
-     * @param offset offset.
-     * @param length length.
-     * @return byte array.
-     */
-    public static byte[] base642bytes(String str, int offset, int length) {
-        return base642bytes(str, offset, length, C64);
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str  base64 string.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return byte array.
-     */
-    public static byte[] base642bytes(String str, String code) {
-        return base642bytes(str, 0, str.length(), code);
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str  base64 string.
-     * @param off  offset.
-     * @param len  length.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return byte array.
-     */
-    public static byte[] base642bytes(final String str, final int off, final int len, final String code) {
-        if (off < 0)
-            throw new IndexOutOfBoundsException("base642bytes: offset < 0, offset is " + off);
-        if (len < 0)
-            throw new IndexOutOfBoundsException("base642bytes: length < 0, length is " + len);
-        if (off + len > str.length())
-            throw new IndexOutOfBoundsException("base642bytes: offset + length > string length.");
-
-        if (code.length() < 64)
-            throw new IllegalArgumentException("Base64 code length < 64.");
-
-        int rem = len % 4;
-        if (rem == 1)
-            throw new IllegalArgumentException("base642bytes: base64 string length % 4 == 1.");
-
-        int num = len / 4, size = num * 3;
-        if (code.length() > 64) {
-            if (rem != 0)
-                throw new IllegalArgumentException("base642bytes: base64 string length error.");
-
-            char pc = code.charAt(64);
-            if (str.charAt(off + len - 2) == pc) {
-                size -= 2;
-                --num;
-                rem = 2;
-            } else if (str.charAt(off + len - 1) == pc) {
-                size--;
-                --num;
-                rem = 3;
-            }
-        } else {
-            if (rem == 2)
-                size++;
-            else if (rem == 3)
-                size += 2;
-        }
-
-        int r = off, w = 0;
-        byte[] b = new byte[size], t = decodeTable(code);
-        for (int i = 0; i < num; i++) {
-            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)];
-            int c3 = t[str.charAt(r++)], c4 = t[str.charAt(r++)];
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
-            b[w++] = (byte) ((c3 << 6) | c4);
-        }
-
-        if (rem == 2) {
-            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)];
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-        } else if (rem == 3) {
-            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)], c3 = t[str.charAt(r++)];
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
-        }
-        return b;
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str  base64 string.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return byte array.
-     */
-    public static byte[] base642bytes(String str, char[] code) {
-        return base642bytes(str, 0, str.length(), code);
-    }
-
-    /**
-     * from base64 string.
-     *
-     * @param str  base64 string.
-     * @param off  offset.
-     * @param len  length.
-     * @param code base64 code(0-63 is base64 char,64 is pad char).
-     * @return byte array.
-     */
-    public static byte[] base642bytes(final String str, final int off, final int len, final char[] code) {
-        if (off < 0)
-            throw new IndexOutOfBoundsException("base642bytes: offset < 0, offset is " + off);
-        if (len < 0)
-            throw new IndexOutOfBoundsException("base642bytes: length < 0, length is " + len);
-        if (off + len > str.length())
-            throw new IndexOutOfBoundsException("base642bytes: offset + length > string length.");
-
-        if (code.length < 64)
-            throw new IllegalArgumentException("Base64 code length < 64.");
-
-        int rem = len % 4;
-        if (rem == 1)
-            throw new IllegalArgumentException("base642bytes: base64 string length % 4 == 1.");
-
-        int num = len / 4, size = num * 3;
-        if (code.length > 64) {
-            if (rem != 0)
-                throw new IllegalArgumentException("base642bytes: base64 string length error.");
-
-            char pc = code[64];
-            if (str.charAt(off + len - 2) == pc)
-                size -= 2;
-            else if (str.charAt(off + len - 1) == pc)
-                size--;
-        } else {
-            if (rem == 2)
-                size++;
-            else if (rem == 3)
-                size += 2;
-        }
-
-        int r = off, w = 0;
-        byte[] b = new byte[size];
-        for (int i = 0; i < num; i++) {
-            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++));
-            int c3 = indexOf(code, str.charAt(r++)), c4 = indexOf(code, str.charAt(r++));
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
-            b[w++] = (byte) ((c3 << 6) | c4);
-        }
-
-        if (rem == 2) {
-            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++));
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-        } else if (rem == 3) {
-            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++)), c3 = indexOf(code, str.charAt(r++));
-
-            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
-            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
-        }
-        return b;
-    }
-
-    /**
-     * zip.
-     *
-     * @param bytes source.
-     * @return compressed byte array.
-     * @throws IOException
-     */
-    public static byte[] zip(byte[] bytes) throws IOException {
-        UnsafeByteArrayOutputStream bos = new UnsafeByteArrayOutputStream();
-        OutputStream os = new DeflaterOutputStream(bos);
-        try {
-            os.write(bytes);
-        } finally {
-            os.close();
-            bos.close();
-        }
-        return bos.toByteArray();
-    }
-
-    /**
-     * unzip.
-     *
-     * @param bytes compressed byte array.
-     * @return byte uncompressed array.
-     * @throws IOException
-     */
-    public static byte[] unzip(byte[] bytes) throws IOException {
-        UnsafeByteArrayInputStream bis = new UnsafeByteArrayInputStream(bytes);
-        UnsafeByteArrayOutputStream bos = new UnsafeByteArrayOutputStream();
-        InputStream is = new InflaterInputStream(bis);
-        try {
-            IOUtils.write(is, bos);
-            return bos.toByteArray();
-        } finally {
-            is.close();
-            bis.close();
-            bos.close();
-        }
-    }
-
-    /**
-     * get md5.
-     *
-     * @param str input string.
-     * @return MD5 byte array.
-     */
-    public static byte[] getMD5(String str) {
-        return getMD5(str.getBytes());
-    }
-
-    /**
-     * get md5.
-     *
-     * @param source byte array source.
-     * @return MD5 byte array.
-     */
-    public static byte[] getMD5(byte[] source) {
-        MessageDigest md = getMessageDigest();
-        return md.digest(source);
-    }
-
-    /**
-     * get md5.
-     *
-     * @param file file source.
-     * @return MD5 byte array.
-     */
-    public static byte[] getMD5(File file) throws IOException {
-        InputStream is = new FileInputStream(file);
-        try {
-            return getMD5(is);
-        } finally {
-            is.close();
-        }
-    }
-
-    /**
-     * get md5.
-     *
-     * @param is input stream.
-     * @return MD5 byte array.
-     */
-    public static byte[] getMD5(InputStream is) throws IOException {
-        return getMD5(is, 1024 * 8);
-    }
-
-    private static byte hex(char c) {
-        if (c <= '9') return (byte) (c - '0');
-        if (c >= 'a' && c <= 'f') return (byte) (c - 'a' + 10);
-        if (c >= 'A' && c <= 'F') return (byte) (c - 'A' + 10);
-        throw new IllegalArgumentException("hex string format error [" + c + "].");
-    }
-
-    private static int indexOf(char[] cs, char c) {
-        for (int i = 0, len = cs.length; i < len; i++)
-            if (cs[i] == c) return i;
-        return -1;
-    }
-
-    private static byte[] decodeTable(String code) {
-        int hash = code.hashCode();
-        byte[] ret = DECODE_TABLE_MAP.get(hash);
-        if (ret == null) {
-            if (code.length() < 64)
-                throw new IllegalArgumentException("Base64 code length < 64.");
-            // create new decode table.
-            ret = new byte[128];
-            for (int i = 0; i < 128; i++) // init table.
-                ret[i] = -1;
-            for (int i = 0; i < 64; i++)
-                ret[code.charAt(i)] = (byte) i;
-            DECODE_TABLE_MAP.put(hash, ret);
-        }
-        return ret;
-    }
-
-    private static byte[] getMD5(InputStream is, int bs) throws IOException {
-        MessageDigest md = getMessageDigest();
-        byte[] buf = new byte[bs];
-        while (is.available() > 0) {
-            int read, total = 0;
-            do {
-                if ((read = is.read(buf, total, bs - total)) <= 0)
-                    break;
-                total += read;
-            }
-            while (total < bs);
-            md.update(buf);
-        }
-        return md.digest();
-    }
-
-    private static MessageDigest getMessageDigest() {
-        MessageDigest ret = MD.get();
-        if (ret == null) {
-            try {
-                ret = MessageDigest.getInstance("MD5");
-                MD.set(ret);
-            } catch (NoSuchAlgorithmException e) {
-                throw new RuntimeException(e);
-            }
-        }
-        return ret;
-    }
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import org.apache.dubbo.common.utils.IOUtils;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.zip.DeflaterOutputStream;
+import java.util.zip.InflaterInputStream;
+
+/**
+ * CodecUtils.
+ */
+
+public class Bytes {
+    private static final String C64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/="; //default base64.
+
+    private static final char[] BASE16 = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}, BASE64 = C64.toCharArray();
+
+    private static final int MASK4 = 0x0f, MASK6 = 0x3f, MASK8 = 0xff;
+
+    private static final Map<Integer, byte[]> DECODE_TABLE_MAP = new ConcurrentHashMap<Integer, byte[]>();
+
+    private static ThreadLocal<MessageDigest> MD = new ThreadLocal<MessageDigest>();
+
+    private Bytes() {
+    }
+
+    /**
+     * byte array copy.
+     *
+     * @param src    src.
+     * @param length new length.
+     * @return new byte array.
+     */
+    public static byte[] copyOf(byte[] src, int length) {
+        byte[] dest = new byte[length];
+        System.arraycopy(src, 0, dest, 0, Math.min(src.length, length));
+        return dest;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @return byte[].
+     */
+    public static byte[] short2bytes(short v) {
+        byte[] ret = {0, 0};
+        short2bytes(v, ret);
+        return ret;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void short2bytes(short v, byte[] b) {
+        short2bytes(v, b, 0);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void short2bytes(short v, byte[] b, int off) {
+        b[off + 1] = (byte) v;
+        b[off + 0] = (byte) (v >>> 8);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @return byte[].
+     */
+    public static byte[] int2bytes(int v) {
+        byte[] ret = {0, 0, 0, 0};
+        int2bytes(v, ret);
+        return ret;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void int2bytes(int v, byte[] b) {
+        int2bytes(v, b, 0);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v   value.
+     * @param b   byte array.
+     * @param off array offset.
+     */
+    public static void int2bytes(int v, byte[] b, int off) {
+        b[off + 3] = (byte) v;
+        b[off + 2] = (byte) (v >>> 8);
+        b[off + 1] = (byte) (v >>> 16);
+        b[off + 0] = (byte) (v >>> 24);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @return byte[].
+     */
+    public static byte[] float2bytes(float v) {
+        byte[] ret = {0, 0, 0, 0};
+        float2bytes(v, ret);
+        return ret;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void float2bytes(float v, byte[] b) {
+        float2bytes(v, b, 0);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v   value.
+     * @param b   byte array.
+     * @param off array offset.
+     */
+    public static void float2bytes(float v, byte[] b, int off) {
+        int i = Float.floatToIntBits(v);
+        b[off + 3] = (byte) i;
+        b[off + 2] = (byte) (i >>> 8);
+        b[off + 1] = (byte) (i >>> 16);
+        b[off + 0] = (byte) (i >>> 24);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @return byte[].
+     */
+    public static byte[] long2bytes(long v) {
+        byte[] ret = {0, 0, 0, 0, 0, 0, 0, 0};
+        long2bytes(v, ret);
+        return ret;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void long2bytes(long v, byte[] b) {
+        long2bytes(v, b, 0);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v   value.
+     * @param b   byte array.
+     * @param off array offset.
+     */
+    public static void long2bytes(long v, byte[] b, int off) {
+        b[off + 7] = (byte) v;
+        b[off + 6] = (byte) (v >>> 8);
+        b[off + 5] = (byte) (v >>> 16);
+        b[off + 4] = (byte) (v >>> 24);
+        b[off + 3] = (byte) (v >>> 32);
+        b[off + 2] = (byte) (v >>> 40);
+        b[off + 1] = (byte) (v >>> 48);
+        b[off + 0] = (byte) (v >>> 56);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @return byte[].
+     */
+    public static byte[] double2bytes(double v) {
+        byte[] ret = {0, 0, 0, 0, 0, 0, 0, 0};
+        double2bytes(v, ret);
+        return ret;
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v value.
+     * @param b byte array.
+     */
+    public static void double2bytes(double v, byte[] b) {
+        double2bytes(v, b, 0);
+    }
+
+    /**
+     * to byte array.
+     *
+     * @param v   value.
+     * @param b   byte array.
+     * @param off array offset.
+     */
+    public static void double2bytes(double v, byte[] b, int off) {
+        long j = Double.doubleToLongBits(v);
+        b[off + 7] = (byte) j;
+        b[off + 6] = (byte) (j >>> 8);
+        b[off + 5] = (byte) (j >>> 16);
+        b[off + 4] = (byte) (j >>> 24);
+        b[off + 3] = (byte) (j >>> 32);
+        b[off + 2] = (byte) (j >>> 40);
+        b[off + 1] = (byte) (j >>> 48);
+        b[off + 0] = (byte) (j >>> 56);
+    }
+
+    /**
+     * to short.
+     *
+     * @param b byte array.
+     * @return short.
+     */
+    public static short bytes2short(byte[] b) {
+        return bytes2short(b, 0);
+    }
+
+    /**
+     * to short.
+     *
+     * @param b   byte array.
+     * @param off offset.
+     * @return short.
+     */
+    public static short bytes2short(byte[] b, int off) {
+        return (short) (((b[off + 1] & 0xFF) << 0) +
+                ((b[off + 0]) << 8));
+    }
+
+    /**
+     * to int.
+     *
+     * @param b byte array.
+     * @return int.
+     */
+    public static int bytes2int(byte[] b) {
+        return bytes2int(b, 0);
+    }
+
+    /**
+     * to int.
+     *
+     * @param b   byte array.
+     * @param off offset.
+     * @return int.
+     */
+    public static int bytes2int(byte[] b, int off) {
+        return ((b[off + 3] & 0xFF) << 0) +
+                ((b[off + 2] & 0xFF) << 8) +
+                ((b[off + 1] & 0xFF) << 16) +
+                ((b[off + 0]) << 24);
+    }
+
+    /**
+     * to int.
+     *
+     * @param b byte array.
+     * @return int.
+     */
+    public static float bytes2float(byte[] b) {
+        return bytes2float(b, 0);
+    }
+
+    /**
+     * to int.
+     *
+     * @param b   byte array.
+     * @param off offset.
+     * @return int.
+     */
+    public static float bytes2float(byte[] b, int off) {
+        int i = ((b[off + 3] & 0xFF) << 0) +
+                ((b[off + 2] & 0xFF) << 8) +
+                ((b[off + 1] & 0xFF) << 16) +
+                ((b[off + 0]) << 24);
+        return Float.intBitsToFloat(i);
+    }
+
+    /**
+     * to long.
+     *
+     * @param b byte array.
+     * @return long.
+     */
+    public static long bytes2long(byte[] b) {
+        return bytes2long(b, 0);
+    }
+
+    /**
+     * to long.
+     *
+     * @param b   byte array.
+     * @param off offset.
+     * @return long.
+     */
+    public static long bytes2long(byte[] b, int off) {
+        return ((b[off + 7] & 0xFFL) << 0) +
+                ((b[off + 6] & 0xFFL) << 8) +
+                ((b[off + 5] & 0xFFL) << 16) +
+                ((b[off + 4] & 0xFFL) << 24) +
+                ((b[off + 3] & 0xFFL) << 32) +
+                ((b[off + 2] & 0xFFL) << 40) +
+                ((b[off + 1] & 0xFFL) << 48) +
+                (((long) b[off + 0]) << 56);
+    }
+
+    /**
+     * to long.
+     *
+     * @param b byte array.
+     * @return double.
+     */
+    public static double bytes2double(byte[] b) {
+        return bytes2double(b, 0);
+    }
+
+    /**
+     * to long.
+     *
+     * @param b   byte array.
+     * @param off offset.
+     * @return double.
+     */
+    public static double bytes2double(byte[] b, int off) {
+        long j = ((b[off + 7] & 0xFFL) << 0) +
+                ((b[off + 6] & 0xFFL) << 8) +
+                ((b[off + 5] & 0xFFL) << 16) +
+                ((b[off + 4] & 0xFFL) << 24) +
+                ((b[off + 3] & 0xFFL) << 32) +
+                ((b[off + 2] & 0xFFL) << 40) +
+                ((b[off + 1] & 0xFFL) << 48) +
+                (((long) b[off + 0]) << 56);
+        return Double.longBitsToDouble(j);
+    }
+
+    /**
+     * to hex string.
+     *
+     * @param bs byte array.
+     * @return hex string.
+     */
+    public static String bytes2hex(byte[] bs) {
+        return bytes2hex(bs, 0, bs.length);
+    }
+
+    /**
+     * to hex string.
+     *
+     * @param bs  byte array.
+     * @param off offset.
+     * @param len length.
+     * @return hex string.
+     */
+    public static String bytes2hex(byte[] bs, int off, int len) {
+        if (off < 0)
+            throw new IndexOutOfBoundsException("bytes2hex: offset < 0, offset is " + off);
+        if (len < 0)
+            throw new IndexOutOfBoundsException("bytes2hex: length < 0, length is " + len);
+        if (off + len > bs.length)
+            throw new IndexOutOfBoundsException("bytes2hex: offset + length > array length.");
+
+        byte b;
+        int r = off, w = 0;
+        char[] cs = new char[len * 2];
+        for (int i = 0; i < len; i++) {
+            b = bs[r++];
+            cs[w++] = BASE16[b >> 4 & MASK4];
+            cs[w++] = BASE16[b & MASK4];
+        }
+        return new String(cs);
+    }
+
+    /**
+     * from hex string.
+     *
+     * @param str hex string.
+     * @return byte array.
+     */
+    public static byte[] hex2bytes(String str) {
+        return hex2bytes(str, 0, str.length());
+    }
+
+    /**
+     * from hex string.
+     *
+     * @param str hex string.
+     * @param off offset.
+     * @param len length.
+     * @return byte array.
+     */
+    public static byte[] hex2bytes(final String str, final int off, int len) {
+        if ((len & 1) == 1)
+            throw new IllegalArgumentException("hex2bytes: ( len & 1 ) == 1.");
+
+        if (off < 0)
+            throw new IndexOutOfBoundsException("hex2bytes: offset < 0, offset is " + off);
+        if (len < 0)
+            throw new IndexOutOfBoundsException("hex2bytes: length < 0, length is " + len);
+        if (off + len > str.length())
+            throw new IndexOutOfBoundsException("hex2bytes: offset + length > array length.");
+
+        int num = len / 2, r = off, w = 0;
+        byte[] b = new byte[num];
+        for (int i = 0; i < num; i++)
+            b[w++] = (byte) (hex(str.charAt(r++)) << 4 | hex(str.charAt(r++)));
+        return b;
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param b byte array.
+     * @return base64 string.
+     */
+    public static String bytes2base64(byte[] b) {
+        return bytes2base64(b, 0, b.length, BASE64);
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param b byte array.
+     * @return base64 string.
+     */
+    public static String bytes2base64(byte[] b, int offset, int length) {
+        return bytes2base64(b, offset, length, BASE64);
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param b    byte array.
+     * @param code base64 code string(0-63 is base64 char,64 is pad char).
+     * @return base64 string.
+     */
+    public static String bytes2base64(byte[] b, String code) {
+        return bytes2base64(b, 0, b.length, code);
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param b    byte array.
+     * @param code base64 code string(0-63 is base64 char,64 is pad char).
+     * @return base64 string.
+     */
+    public static String bytes2base64(byte[] b, int offset, int length, String code) {
+        if (code.length() < 64)
+            throw new IllegalArgumentException("Base64 code length < 64.");
+
+        return bytes2base64(b, offset, length, code.toCharArray());
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param b    byte array.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return base64 string.
+     */
+    public static String bytes2base64(byte[] b, char[] code) {
+        return bytes2base64(b, 0, b.length, code);
+    }
+
+    /**
+     * to base64 string.
+     *
+     * @param bs   byte array.
+     * @param off  offset.
+     * @param len  length.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return base64 string.
+     */
+    public static String bytes2base64(final byte[] bs, final int off, final int len, final char[] code) {
+        if (off < 0)
+            throw new IndexOutOfBoundsException("bytes2base64: offset < 0, offset is " + off);
+        if (len < 0)
+            throw new IndexOutOfBoundsException("bytes2base64: length < 0, length is " + len);
+        if (off + len > bs.length)
+            throw new IndexOutOfBoundsException("bytes2base64: offset + length > array length.");
+
+        if (code.length < 64)
+            throw new IllegalArgumentException("Base64 code length < 64.");
+
+        boolean pad = code.length > 64; // has pad char.
+        int num = len / 3, rem = len % 3, r = off, w = 0;
+        char[] cs = new char[num * 4 + (rem == 0 ? 0 : pad ? 4 : rem + 1)];
+
+        for (int i = 0; i < num; i++) {
+            int b1 = bs[r++] & MASK8, b2 = bs[r++] & MASK8, b3 = bs[r++] & MASK8;
+
+            cs[w++] = code[b1 >> 2];
+            cs[w++] = code[(b1 << 4) & MASK6 | (b2 >> 4)];
+            cs[w++] = code[(b2 << 2) & MASK6 | (b3 >> 6)];
+            cs[w++] = code[b3 & MASK6];
+        }
+
+        if (rem == 1) {
+            int b1 = bs[r++] & MASK8;
+            cs[w++] = code[b1 >> 2];
+            cs[w++] = code[(b1 << 4) & MASK6];
+            if (pad) {
+                cs[w++] = code[64];
+                cs[w++] = code[64];
+            }
+        } else if (rem == 2) {
+            int b1 = bs[r++] & MASK8, b2 = bs[r++] & MASK8;
+            cs[w++] = code[b1 >> 2];
+            cs[w++] = code[(b1 << 4) & MASK6 | (b2 >> 4)];
+            cs[w++] = code[(b2 << 2) & MASK6];
+            if (pad)
+                cs[w++] = code[64];
+        }
+        return new String(cs);
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str base64 string.
+     * @return byte array.
+     */
+    public static byte[] base642bytes(String str) {
+        return base642bytes(str, 0, str.length());
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str    base64 string.
+     * @param offset offset.
+     * @param length length.
+     * @return byte array.
+     */
+    public static byte[] base642bytes(String str, int offset, int length) {
+        return base642bytes(str, offset, length, C64);
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str  base64 string.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return byte array.
+     */
+    public static byte[] base642bytes(String str, String code) {
+        return base642bytes(str, 0, str.length(), code);
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str  base64 string.
+     * @param off  offset.
+     * @param len  length.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return byte array.
+     */
+    public static byte[] base642bytes(final String str, final int off, final int len, final String code) {
+        if (off < 0)
+            throw new IndexOutOfBoundsException("base642bytes: offset < 0, offset is " + off);
+        if (len < 0)
+            throw new IndexOutOfBoundsException("base642bytes: length < 0, length is " + len);
+        if (off + len > str.length())
+            throw new IndexOutOfBoundsException("base642bytes: offset + length > string length.");
+
+        if (code.length() < 64)
+            throw new IllegalArgumentException("Base64 code length < 64.");
+
+        int rem = len % 4;
+        if (rem == 1)
+            throw new IllegalArgumentException("base642bytes: base64 string length % 4 == 1.");
+
+        int num = len / 4, size = num * 3;
+        if (code.length() > 64) {
+            if (rem != 0)
+                throw new IllegalArgumentException("base642bytes: base64 string length error.");
+
+            char pc = code.charAt(64);
+            if (str.charAt(off + len - 2) == pc) {
+                size -= 2;
+                --num;
+                rem = 2;
+            } else if (str.charAt(off + len - 1) == pc) {
+                size--;
+                --num;
+                rem = 3;
+            }
+        } else {
+            if (rem == 2)
+                size++;
+            else if (rem == 3)
+                size += 2;
+        }
+
+        int r = off, w = 0;
+        byte[] b = new byte[size], t = decodeTable(code);
+        for (int i = 0; i < num; i++) {
+            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)];
+            int c3 = t[str.charAt(r++)], c4 = t[str.charAt(r++)];
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
+            b[w++] = (byte) ((c3 << 6) | c4);
+        }
+
+        if (rem == 2) {
+            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)];
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+        } else if (rem == 3) {
+            int c1 = t[str.charAt(r++)], c2 = t[str.charAt(r++)], c3 = t[str.charAt(r++)];
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
+        }
+        return b;
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str  base64 string.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return byte array.
+     */
+    public static byte[] base642bytes(String str, char[] code) {
+        return base642bytes(str, 0, str.length(), code);
+    }
+
+    /**
+     * from base64 string.
+     *
+     * @param str  base64 string.
+     * @param off  offset.
+     * @param len  length.
+     * @param code base64 code(0-63 is base64 char,64 is pad char).
+     * @return byte array.
+     */
+    public static byte[] base642bytes(final String str, final int off, final int len, final char[] code) {
+        if (off < 0)
+            throw new IndexOutOfBoundsException("base642bytes: offset < 0, offset is " + off);
+        if (len < 0)
+            throw new IndexOutOfBoundsException("base642bytes: length < 0, length is " + len);
+        if (off + len > str.length())
+            throw new IndexOutOfBoundsException("base642bytes: offset + length > string length.");
+
+        if (code.length < 64)
+            throw new IllegalArgumentException("Base64 code length < 64.");
+
+        int rem = len % 4;
+        if (rem == 1)
+            throw new IllegalArgumentException("base642bytes: base64 string length % 4 == 1.");
+
+        int num = len / 4, size = num * 3;
+        if (code.length > 64) {
+            if (rem != 0)
+                throw new IllegalArgumentException("base642bytes: base64 string length error.");
+
+            char pc = code[64];
+            if (str.charAt(off + len - 2) == pc)
+                size -= 2;
+            else if (str.charAt(off + len - 1) == pc)
+                size--;
+        } else {
+            if (rem == 2)
+                size++;
+            else if (rem == 3)
+                size += 2;
+        }
+
+        int r = off, w = 0;
+        byte[] b = new byte[size];
+        for (int i = 0; i < num; i++) {
+            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++));
+            int c3 = indexOf(code, str.charAt(r++)), c4 = indexOf(code, str.charAt(r++));
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
+            b[w++] = (byte) ((c3 << 6) | c4);
+        }
+
+        if (rem == 2) {
+            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++));
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+        } else if (rem == 3) {
+            int c1 = indexOf(code, str.charAt(r++)), c2 = indexOf(code, str.charAt(r++)), c3 = indexOf(code, str.charAt(r++));
+
+            b[w++] = (byte) ((c1 << 2) | (c2 >> 4));
+            b[w++] = (byte) ((c2 << 4) | (c3 >> 2));
+        }
+        return b;
+    }
+
+    /**
+     * zip.
+     *
+     * @param bytes source.
+     * @return compressed byte array.
+     * @throws IOException
+     */
+    public static byte[] zip(byte[] bytes) throws IOException {
+        UnsafeByteArrayOutputStream bos = new UnsafeByteArrayOutputStream();
+        OutputStream os = new DeflaterOutputStream(bos);
+        try {
+            os.write(bytes);
+        } finally {
+            os.close();
+            bos.close();
+        }
+        return bos.toByteArray();
+    }
+
+    /**
+     * unzip.
+     *
+     * @param bytes compressed byte array.
+     * @return byte uncompressed array.
+     * @throws IOException
+     */
+    public static byte[] unzip(byte[] bytes) throws IOException {
+        UnsafeByteArrayInputStream bis = new UnsafeByteArrayInputStream(bytes);
+        UnsafeByteArrayOutputStream bos = new UnsafeByteArrayOutputStream();
+        InputStream is = new InflaterInputStream(bis);
+        try {
+            IOUtils.write(is, bos);
+            return bos.toByteArray();
+        } finally {
+            is.close();
+            bis.close();
+            bos.close();
+        }
+    }
+
+    /**
+     * get md5.
+     *
+     * @param str input string.
+     * @return MD5 byte array.
+     */
+    public static byte[] getMD5(String str) {
+        return getMD5(str.getBytes());
+    }
+
+    /**
+     * get md5.
+     *
+     * @param source byte array source.
+     * @return MD5 byte array.
+     */
+    public static byte[] getMD5(byte[] source) {
+        MessageDigest md = getMessageDigest();
+        return md.digest(source);
+    }
+
+    /**
+     * get md5.
+     *
+     * @param file file source.
+     * @return MD5 byte array.
+     */
+    public static byte[] getMD5(File file) throws IOException {
+        InputStream is = new FileInputStream(file);
+        try {
+            return getMD5(is);
+        } finally {
+            is.close();
+        }
+    }
+
+    /**
+     * get md5.
+     *
+     * @param is input stream.
+     * @return MD5 byte array.
+     */
+    public static byte[] getMD5(InputStream is) throws IOException {
+        return getMD5(is, 1024 * 8);
+    }
+
+    private static byte hex(char c) {
+        if (c <= '9') return (byte) (c - '0');
+        if (c >= 'a' && c <= 'f') return (byte) (c - 'a' + 10);
+        if (c >= 'A' && c <= 'F') return (byte) (c - 'A' + 10);
+        throw new IllegalArgumentException("hex string format error [" + c + "].");
+    }
+
+    private static int indexOf(char[] cs, char c) {
+        for (int i = 0, len = cs.length; i < len; i++)
+            if (cs[i] == c) return i;
+        return -1;
+    }
+
+    private static byte[] decodeTable(String code) {
+        int hash = code.hashCode();
+        byte[] ret = DECODE_TABLE_MAP.get(hash);
+        if (ret == null) {
+            if (code.length() < 64)
+                throw new IllegalArgumentException("Base64 code length < 64.");
+            // create new decode table.
+            ret = new byte[128];
+            for (int i = 0; i < 128; i++) // init table.
+                ret[i] = -1;
+            for (int i = 0; i < 64; i++)
+                ret[code.charAt(i)] = (byte) i;
+            DECODE_TABLE_MAP.put(hash, ret);
+        }
+        return ret;
+    }
+
+    private static byte[] getMD5(InputStream is, int bs) throws IOException {
+        MessageDigest md = getMessageDigest();
+        byte[] buf = new byte[bs];
+        while (is.available() > 0) {
+            int read, total = 0;
+            do {
+                if ((read = is.read(buf, total, bs - total)) <= 0)
+                    break;
+                total += read;
+            }
+            while (total < bs);
+            md.update(buf);
+        }
+        return md.digest();
+    }
+
+    private static MessageDigest getMessageDigest() {
+        MessageDigest ret = MD.get();
+        if (ret == null) {
+            try {
+                ret = MessageDigest.getInstance("MD5");
+                MD.set(ret);
+            } catch (NoSuchAlgorithmException e) {
+                throw new RuntimeException(e);
+            }
+        }
+        return ret;
+    }
 }
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/StreamUtils.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/StreamUtils.java
index 9b52286769..cce92dfc57 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/StreamUtils.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/StreamUtils.java
@@ -1,214 +1,214 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import java.io.IOException;
-import java.io.InputStream;
-
-/**
- * Stream utils.
- */
-public class StreamUtils {
-    private StreamUtils() {
-    }
-
-    public static InputStream limitedInputStream(final InputStream is, final int limit) throws IOException {
-        return new InputStream() {
-            private int mPosition = 0, mMark = 0, mLimit = Math.min(limit, is.available());
-
-            @Override
-            public int read() throws IOException {
-                if (mPosition < mLimit) {
-                    mPosition++;
-                    return is.read();
-                }
-                return -1;
-            }
-
-            @Override
-            public int read(byte b[], int off, int len) throws IOException {
-                if (b == null)
-                    throw new NullPointerException();
-
-                if (off < 0 || len < 0 || len > b.length - off)
-                    throw new IndexOutOfBoundsException();
-
-                if (mPosition >= mLimit)
-                    return -1;
-
-                if (mPosition + len > mLimit)
-                    len = mLimit - mPosition;
-
-                if (len <= 0)
-                    return 0;
-
-                is.read(b, off, len);
-                mPosition += len;
-                return len;
-            }
-
-            @Override
-            public long skip(long len) throws IOException {
-                if (mPosition + len > mLimit)
-                    len = mLimit - mPosition;
-
-                if (len <= 0)
-                    return 0;
-
-                is.skip(len);
-                mPosition += len;
-                return len;
-            }
-
-            @Override
-            public int available() {
-                return mLimit - mPosition;
-            }
-
-            @Override
-            public boolean markSupported() {
-                return is.markSupported();
-            }
-
-            @Override
-            public void mark(int readlimit) {
-                is.mark(readlimit);
-                mMark = mPosition;
-            }
-
-            @Override
-            public void reset() throws IOException {
-                is.reset();
-                mPosition = mMark;
-            }
-
-            @Override
-            public void close() throws IOException {
-            }
-        };
-    }
-
-    public static InputStream markSupportedInputStream(final InputStream is, final int markBufferSize) {
-        if (is.markSupported()) {
-            return is;
-        }
-
-        return new InputStream() {
-            byte[] mMarkBuffer;
-
-            boolean mInMarked = false;
-            boolean mInReset = false;
-            boolean mDry = false;
-            private int mPosition = 0;
-            private int mCount = 0;
-
-            @Override
-            public int read() throws IOException {
-                if (!mInMarked) {
-                    return is.read();
-                } else {
-                    if (mPosition < mCount) {
-                        byte b = mMarkBuffer[mPosition++];
-                        return b & 0xFF;
-                    }
-
-                    if (!mInReset) {
-                        if (mDry) return -1;
-
-                        if (null == mMarkBuffer) {
-                            mMarkBuffer = new byte[markBufferSize];
-                        }
-                        if (mPosition >= markBufferSize) {
-                            throw new IOException("Mark buffer is full!");
-                        }
-
-                        int read = is.read();
-                        if (-1 == read) {
-                            mDry = true;
-                            return -1;
-                        }
-
-                        mMarkBuffer[mPosition++] = (byte) read;
-                        mCount++;
-
-                        return read;
-                    } else {
-                        // mark buffer is used, exit mark status!
-                        mInMarked = false;
-                        mInReset = false;
-                        mPosition = 0;
-                        mCount = 0;
-
-                        return is.read();
-                    }
-                }
-            }
-
-            /**
-             * NOTE: the <code>readlimit</code> argument for this class
-             *  has no meaning.
-             */
-            @Override
-            public synchronized void mark(int readlimit) {
-                mInMarked = true;
-                mInReset = false;
-
-                // mark buffer is not empty
-                int count = mCount - mPosition;
-                if (count > 0) {
-                    System.arraycopy(mMarkBuffer, mPosition, mMarkBuffer, 0, count);
-                    mCount = count;
-                    mPosition = 0;
-                }
-            }
-
-            @Override
-            public synchronized void reset() throws IOException {
-                if (!mInMarked) {
-                    throw new IOException("should mark befor reset!");
-                }
-
-                mInReset = true;
-                mPosition = 0;
-            }
-
-            @Override
-            public boolean markSupported() {
-                return true;
-            }
-
-            @Override
-            public int available() throws IOException {
-                int available = is.available();
-
-                if (mInMarked && mInReset) available += mCount - mPosition;
-
-                return available;
-            }
-        };
-    }
-
-    public static InputStream markSupportedInputStream(final InputStream is) {
-        return markSupportedInputStream(is, 1024);
-    }
-
-    public static void skipUnusedStream(InputStream is) throws IOException {
-        if (is.available() > 0) {
-            is.skip(is.available());
-        }
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * Stream utils.
+ */
+public class StreamUtils {
+    private StreamUtils() {
+    }
+
+    public static InputStream limitedInputStream(final InputStream is, final int limit) throws IOException {
+        return new InputStream() {
+            private int mPosition = 0, mMark = 0, mLimit = Math.min(limit, is.available());
+
+            @Override
+            public int read() throws IOException {
+                if (mPosition < mLimit) {
+                    mPosition++;
+                    return is.read();
+                }
+                return -1;
+            }
+
+            @Override
+            public int read(byte b[], int off, int len) throws IOException {
+                if (b == null)
+                    throw new NullPointerException();
+
+                if (off < 0 || len < 0 || len > b.length - off)
+                    throw new IndexOutOfBoundsException();
+
+                if (mPosition >= mLimit)
+                    return -1;
+
+                if (mPosition + len > mLimit)
+                    len = mLimit - mPosition;
+
+                if (len <= 0)
+                    return 0;
+
+                is.read(b, off, len);
+                mPosition += len;
+                return len;
+            }
+
+            @Override
+            public long skip(long len) throws IOException {
+                if (mPosition + len > mLimit)
+                    len = mLimit - mPosition;
+
+                if (len <= 0)
+                    return 0;
+
+                is.skip(len);
+                mPosition += len;
+                return len;
+            }
+
+            @Override
+            public int available() {
+                return mLimit - mPosition;
+            }
+
+            @Override
+            public boolean markSupported() {
+                return is.markSupported();
+            }
+
+            @Override
+            public void mark(int readlimit) {
+                is.mark(readlimit);
+                mMark = mPosition;
+            }
+
+            @Override
+            public void reset() throws IOException {
+                is.reset();
+                mPosition = mMark;
+            }
+
+            @Override
+            public void close() throws IOException {
+            }
+        };
+    }
+
+    public static InputStream markSupportedInputStream(final InputStream is, final int markBufferSize) {
+        if (is.markSupported()) {
+            return is;
+        }
+
+        return new InputStream() {
+            byte[] mMarkBuffer;
+
+            boolean mInMarked = false;
+            boolean mInReset = false;
+            boolean mDry = false;
+            private int mPosition = 0;
+            private int mCount = 0;
+
+            @Override
+            public int read() throws IOException {
+                if (!mInMarked) {
+                    return is.read();
+                } else {
+                    if (mPosition < mCount) {
+                        byte b = mMarkBuffer[mPosition++];
+                        return b & 0xFF;
+                    }
+
+                    if (!mInReset) {
+                        if (mDry) return -1;
+
+                        if (null == mMarkBuffer) {
+                            mMarkBuffer = new byte[markBufferSize];
+                        }
+                        if (mPosition >= markBufferSize) {
+                            throw new IOException("Mark buffer is full!");
+                        }
+
+                        int read = is.read();
+                        if (-1 == read) {
+                            mDry = true;
+                            return -1;
+                        }
+
+                        mMarkBuffer[mPosition++] = (byte) read;
+                        mCount++;
+
+                        return read;
+                    } else {
+                        // mark buffer is used, exit mark status!
+                        mInMarked = false;
+                        mInReset = false;
+                        mPosition = 0;
+                        mCount = 0;
+
+                        return is.read();
+                    }
+                }
+            }
+
+            /**
+             * NOTE: the <code>readlimit</code> argument for this class
+             *  has no meaning.
+             */
+            @Override
+            public synchronized void mark(int readlimit) {
+                mInMarked = true;
+                mInReset = false;
+
+                // mark buffer is not empty
+                int count = mCount - mPosition;
+                if (count > 0) {
+                    System.arraycopy(mMarkBuffer, mPosition, mMarkBuffer, 0, count);
+                    mCount = count;
+                    mPosition = 0;
+                }
+            }
+
+            @Override
+            public synchronized void reset() throws IOException {
+                if (!mInMarked) {
+                    throw new IOException("should mark befor reset!");
+                }
+
+                mInReset = true;
+                mPosition = 0;
+            }
+
+            @Override
+            public boolean markSupported() {
+                return true;
+            }
+
+            @Override
+            public int available() throws IOException {
+                int available = is.available();
+
+                if (mInMarked && mInReset) available += mCount - mPosition;
+
+                return available;
+            }
+        };
+    }
+
+    public static InputStream markSupportedInputStream(final InputStream is) {
+        return markSupportedInputStream(is, 1024);
+    }
+
+    public static void skipUnusedStream(InputStream is) throws IOException {
+        if (is.available() > 0) {
+            is.skip(is.available());
+        }
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayInputStream.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayInputStream.java
index b221da99f2..6c1de50765 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayInputStream.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayInputStream.java
@@ -1,111 +1,111 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import java.io.IOException;
-import java.io.InputStream;
-
-/**
- * UnsafeByteArrayInputStrem.
- */
-public class UnsafeByteArrayInputStream extends InputStream {
-    protected byte mData[];
-
-    protected int mPosition, mLimit, mMark = 0;
-
-    public UnsafeByteArrayInputStream(byte buf[]) {
-        this(buf, 0, buf.length);
-    }
-
-    public UnsafeByteArrayInputStream(byte buf[], int offset) {
-        this(buf, offset, buf.length - offset);
-    }
-
-    public UnsafeByteArrayInputStream(byte buf[], int offset, int length) {
-        mData = buf;
-        mPosition = mMark = offset;
-        mLimit = Math.min(offset + length, buf.length);
-    }
-
-    @Override
-    public int read() {
-        return (mPosition < mLimit) ? (mData[mPosition++] & 0xff) : -1;
-    }
-
-    @Override
-    public int read(byte b[], int off, int len) {
-        if (b == null)
-            throw new NullPointerException();
-        if (off < 0 || len < 0 || len > b.length - off)
-            throw new IndexOutOfBoundsException();
-        if (mPosition >= mLimit)
-            return -1;
-        if (mPosition + len > mLimit)
-            len = mLimit - mPosition;
-        if (len <= 0)
-            return 0;
-        System.arraycopy(mData, mPosition, b, off, len);
-        mPosition += len;
-        return len;
-    }
-
-    @Override
-    public long skip(long len) {
-        if (mPosition + len > mLimit)
-            len = mLimit - mPosition;
-        if (len <= 0)
-            return 0;
-        mPosition += len;
-        return len;
-    }
-
-    @Override
-    public int available() {
-        return mLimit - mPosition;
-    }
-
-    @Override
-    public boolean markSupported() {
-        return true;
-    }
-
-    @Override
-    public void mark(int readAheadLimit) {
-        mMark = mPosition;
-    }
-
-    @Override
-    public void reset() {
-        mPosition = mMark;
-    }
-
-    @Override
-    public void close() throws IOException {
-    }
-
-    public int position() {
-        return mPosition;
-    }
-
-    public void position(int newPosition) {
-        mPosition = newPosition;
-    }
-
-    public int size() {
-        return mData == null ? 0 : mData.length;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * UnsafeByteArrayInputStrem.
+ */
+public class UnsafeByteArrayInputStream extends InputStream {
+    protected byte mData[];
+
+    protected int mPosition, mLimit, mMark = 0;
+
+    public UnsafeByteArrayInputStream(byte buf[]) {
+        this(buf, 0, buf.length);
+    }
+
+    public UnsafeByteArrayInputStream(byte buf[], int offset) {
+        this(buf, offset, buf.length - offset);
+    }
+
+    public UnsafeByteArrayInputStream(byte buf[], int offset, int length) {
+        mData = buf;
+        mPosition = mMark = offset;
+        mLimit = Math.min(offset + length, buf.length);
+    }
+
+    @Override
+    public int read() {
+        return (mPosition < mLimit) ? (mData[mPosition++] & 0xff) : -1;
+    }
+
+    @Override
+    public int read(byte b[], int off, int len) {
+        if (b == null)
+            throw new NullPointerException();
+        if (off < 0 || len < 0 || len > b.length - off)
+            throw new IndexOutOfBoundsException();
+        if (mPosition >= mLimit)
+            return -1;
+        if (mPosition + len > mLimit)
+            len = mLimit - mPosition;
+        if (len <= 0)
+            return 0;
+        System.arraycopy(mData, mPosition, b, off, len);
+        mPosition += len;
+        return len;
+    }
+
+    @Override
+    public long skip(long len) {
+        if (mPosition + len > mLimit)
+            len = mLimit - mPosition;
+        if (len <= 0)
+            return 0;
+        mPosition += len;
+        return len;
+    }
+
+    @Override
+    public int available() {
+        return mLimit - mPosition;
+    }
+
+    @Override
+    public boolean markSupported() {
+        return true;
+    }
+
+    @Override
+    public void mark(int readAheadLimit) {
+        mMark = mPosition;
+    }
+
+    @Override
+    public void reset() {
+        mPosition = mMark;
+    }
+
+    @Override
+    public void close() throws IOException {
+    }
+
+    public int position() {
+        return mPosition;
+    }
+
+    public void position(int newPosition) {
+        mPosition = newPosition;
+    }
+
+    public int size() {
+        return mData == null ? 0 : mData.length;
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayOutputStream.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayOutputStream.java
index a5227c3faf..c01d1f216e 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayOutputStream.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeByteArrayOutputStream.java
@@ -1,96 +1,96 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import java.io.IOException;
-import java.io.OutputStream;
-import java.io.UnsupportedEncodingException;
-import java.nio.ByteBuffer;
-
-/**
- * UnsafeByteArrayOutputStream.
- */
-public class UnsafeByteArrayOutputStream extends OutputStream {
-    protected byte mBuffer[];
-
-    protected int mCount;
-
-    public UnsafeByteArrayOutputStream() {
-        this(32);
-    }
-
-    public UnsafeByteArrayOutputStream(int size) {
-        if (size < 0)
-            throw new IllegalArgumentException("Negative initial size: " + size);
-        mBuffer = new byte[size];
-    }
-
-    @Override
-    public void write(int b) {
-        int newcount = mCount + 1;
-        if (newcount > mBuffer.length)
-            mBuffer = Bytes.copyOf(mBuffer, Math.max(mBuffer.length << 1, newcount));
-        mBuffer[mCount] = (byte) b;
-        mCount = newcount;
-    }
-
-    @Override
-    public void write(byte b[], int off, int len) {
-        if ((off < 0) || (off > b.length) || (len < 0) || ((off + len) > b.length) || ((off + len) < 0))
-            throw new IndexOutOfBoundsException();
-        if (len == 0)
-            return;
-        int newcount = mCount + len;
-        if (newcount > mBuffer.length)
-            mBuffer = Bytes.copyOf(mBuffer, Math.max(mBuffer.length << 1, newcount));
-        System.arraycopy(b, off, mBuffer, mCount, len);
-        mCount = newcount;
-    }
-
-    public int size() {
-        return mCount;
-    }
-
-    public void reset() {
-        mCount = 0;
-    }
-
-    public byte[] toByteArray() {
-        return Bytes.copyOf(mBuffer, mCount);
-    }
-
-    public ByteBuffer toByteBuffer() {
-        return ByteBuffer.wrap(mBuffer, 0, mCount);
-    }
-
-    public void writeTo(OutputStream out) throws IOException {
-        out.write(mBuffer, 0, mCount);
-    }
-
-    @Override
-    public String toString() {
-        return new String(mBuffer, 0, mCount);
-    }
-
-    public String toString(String charset) throws UnsupportedEncodingException {
-        return new String(mBuffer, 0, mCount, charset);
-    }
-
-    @Override
-    public void close() throws IOException {
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import java.io.UnsupportedEncodingException;
+import java.nio.ByteBuffer;
+
+/**
+ * UnsafeByteArrayOutputStream.
+ */
+public class UnsafeByteArrayOutputStream extends OutputStream {
+    protected byte mBuffer[];
+
+    protected int mCount;
+
+    public UnsafeByteArrayOutputStream() {
+        this(32);
+    }
+
+    public UnsafeByteArrayOutputStream(int size) {
+        if (size < 0)
+            throw new IllegalArgumentException("Negative initial size: " + size);
+        mBuffer = new byte[size];
+    }
+
+    @Override
+    public void write(int b) {
+        int newcount = mCount + 1;
+        if (newcount > mBuffer.length)
+            mBuffer = Bytes.copyOf(mBuffer, Math.max(mBuffer.length << 1, newcount));
+        mBuffer[mCount] = (byte) b;
+        mCount = newcount;
+    }
+
+    @Override
+    public void write(byte b[], int off, int len) {
+        if ((off < 0) || (off > b.length) || (len < 0) || ((off + len) > b.length) || ((off + len) < 0))
+            throw new IndexOutOfBoundsException();
+        if (len == 0)
+            return;
+        int newcount = mCount + len;
+        if (newcount > mBuffer.length)
+            mBuffer = Bytes.copyOf(mBuffer, Math.max(mBuffer.length << 1, newcount));
+        System.arraycopy(b, off, mBuffer, mCount, len);
+        mCount = newcount;
+    }
+
+    public int size() {
+        return mCount;
+    }
+
+    public void reset() {
+        mCount = 0;
+    }
+
+    public byte[] toByteArray() {
+        return Bytes.copyOf(mBuffer, mCount);
+    }
+
+    public ByteBuffer toByteBuffer() {
+        return ByteBuffer.wrap(mBuffer, 0, mCount);
+    }
+
+    public void writeTo(OutputStream out) throws IOException {
+        out.write(mBuffer, 0, mCount);
+    }
+
+    @Override
+    public String toString() {
+        return new String(mBuffer, 0, mCount);
+    }
+
+    public String toString(String charset) throws UnsupportedEncodingException {
+        return new String(mBuffer, 0, mCount, charset);
+    }
+
+    @Override
+    public void close() throws IOException {
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringReader.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringReader.java
index dd8334ebb4..0579d6df78 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringReader.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringReader.java
@@ -1,111 +1,111 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import java.io.IOException;
-import java.io.Reader;
-
-/**
- * Thread-unsafe StringReader.
- */
-public class UnsafeStringReader extends Reader {
-    private String mString;
-
-    private int mPosition, mLimit, mMark;
-
-    public UnsafeStringReader(String str) {
-        mString = str;
-        mLimit = str.length();
-        mPosition = mMark = 0;
-    }
-
-    @Override
-    public int read() throws IOException {
-        ensureOpen();
-        if (mPosition >= mLimit)
-            return -1;
-
-        return mString.charAt(mPosition++);
-    }
-
-    @Override
-    public int read(char[] cs, int off, int len) throws IOException {
-        ensureOpen();
-        if ((off < 0) || (off > cs.length) || (len < 0) ||
-                ((off + len) > cs.length) || ((off + len) < 0))
-            throw new IndexOutOfBoundsException();
-
-        if (len == 0)
-            return 0;
-
-        if (mPosition >= mLimit)
-            return -1;
-
-        int n = Math.min(mLimit - mPosition, len);
-        mString.getChars(mPosition, mPosition + n, cs, off);
-        mPosition += n;
-        return n;
-    }
-
-    @Override
-    public long skip(long ns) throws IOException {
-        ensureOpen();
-        if (mPosition >= mLimit)
-            return 0;
-
-        long n = Math.min(mLimit - mPosition, ns);
-        n = Math.max(-mPosition, n);
-        mPosition += n;
-        return n;
-    }
-
-    @Override
-    public boolean ready() throws IOException {
-        ensureOpen();
-        return true;
-    }
-
-    @Override
-    public boolean markSupported() {
-        return true;
-    }
-
-    @Override
-    public void mark(int readAheadLimit) throws IOException {
-        if (readAheadLimit < 0)
-            throw new IllegalArgumentException("Read-ahead limit < 0");
-
-        ensureOpen();
-        mMark = mPosition;
-    }
-
-    @Override
-    public void reset() throws IOException {
-        ensureOpen();
-        mPosition = mMark;
-    }
-
-    @Override
-    public void close() throws IOException {
-        mString = null;
-    }
-
-    private void ensureOpen() throws IOException {
-        if (mString == null)
-            throw new IOException("Stream closed");
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import java.io.IOException;
+import java.io.Reader;
+
+/**
+ * Thread-unsafe StringReader.
+ */
+public class UnsafeStringReader extends Reader {
+    private String mString;
+
+    private int mPosition, mLimit, mMark;
+
+    public UnsafeStringReader(String str) {
+        mString = str;
+        mLimit = str.length();
+        mPosition = mMark = 0;
+    }
+
+    @Override
+    public int read() throws IOException {
+        ensureOpen();
+        if (mPosition >= mLimit)
+            return -1;
+
+        return mString.charAt(mPosition++);
+    }
+
+    @Override
+    public int read(char[] cs, int off, int len) throws IOException {
+        ensureOpen();
+        if ((off < 0) || (off > cs.length) || (len < 0) ||
+                ((off + len) > cs.length) || ((off + len) < 0))
+            throw new IndexOutOfBoundsException();
+
+        if (len == 0)
+            return 0;
+
+        if (mPosition >= mLimit)
+            return -1;
+
+        int n = Math.min(mLimit - mPosition, len);
+        mString.getChars(mPosition, mPosition + n, cs, off);
+        mPosition += n;
+        return n;
+    }
+
+    @Override
+    public long skip(long ns) throws IOException {
+        ensureOpen();
+        if (mPosition >= mLimit)
+            return 0;
+
+        long n = Math.min(mLimit - mPosition, ns);
+        n = Math.max(-mPosition, n);
+        mPosition += n;
+        return n;
+    }
+
+    @Override
+    public boolean ready() throws IOException {
+        ensureOpen();
+        return true;
+    }
+
+    @Override
+    public boolean markSupported() {
+        return true;
+    }
+
+    @Override
+    public void mark(int readAheadLimit) throws IOException {
+        if (readAheadLimit < 0)
+            throw new IllegalArgumentException("Read-ahead limit < 0");
+
+        ensureOpen();
+        mMark = mPosition;
+    }
+
+    @Override
+    public void reset() throws IOException {
+        ensureOpen();
+        mPosition = mMark;
+    }
+
+    @Override
+    public void close() throws IOException {
+        mString = null;
+    }
+
+    private void ensureOpen() throws IOException {
+        if (mString == null)
+            throw new IOException("Stream closed");
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringWriter.java b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringWriter.java
index ec99514e58..8f7ca7e714 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringWriter.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/io/UnsafeStringWriter.java
@@ -1,103 +1,103 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.io;
-
-import java.io.IOException;
-import java.io.Writer;
-
-/**
- * Thread-unsafe StringWriter.
- */
-public class UnsafeStringWriter extends Writer {
-    private StringBuilder mBuffer;
-
-    public UnsafeStringWriter() {
-        lock = mBuffer = new StringBuilder();
-    }
-
-    public UnsafeStringWriter(int size) {
-        if (size < 0)
-            throw new IllegalArgumentException("Negative buffer size");
-
-        lock = mBuffer = new StringBuilder();
-    }
-
-    @Override
-    public void write(int c) {
-        mBuffer.append((char) c);
-    }
-
-    @Override
-    public void write(char[] cs) throws IOException {
-        mBuffer.append(cs, 0, cs.length);
-    }
-
-    @Override
-    public void write(char[] cs, int off, int len) throws IOException {
-        if ((off < 0) || (off > cs.length) || (len < 0) ||
-                ((off + len) > cs.length) || ((off + len) < 0))
-            throw new IndexOutOfBoundsException();
-
-        if (len > 0)
-            mBuffer.append(cs, off, len);
-    }
-
-    @Override
-    public void write(String str) {
-        mBuffer.append(str);
-    }
-
-    @Override
-    public void write(String str, int off, int len) {
-        mBuffer.append(str.substring(off, off + len));
-    }
-
-    @Override
-    public Writer append(CharSequence csq) {
-        if (csq == null)
-            write("null");
-        else
-            write(csq.toString());
-        return this;
-    }
-
-    @Override
-    public Writer append(CharSequence csq, int start, int end) {
-        CharSequence cs = (csq == null ? "null" : csq);
-        write(cs.subSequence(start, end).toString());
-        return this;
-    }
-
-    @Override
-    public Writer append(char c) {
-        mBuffer.append(c);
-        return this;
-    }
-
-    @Override
-    public void close() {
-    }
-
-    @Override
-    public void flush() {
-    }
-
-    @Override
-    public String toString() {
-        return mBuffer.toString();
-    }
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.io;
+
+import java.io.IOException;
+import java.io.Writer;
+
+/**
+ * Thread-unsafe StringWriter.
+ */
+public class UnsafeStringWriter extends Writer {
+    private StringBuilder mBuffer;
+
+    public UnsafeStringWriter() {
+        lock = mBuffer = new StringBuilder();
+    }
+
+    public UnsafeStringWriter(int size) {
+        if (size < 0)
+            throw new IllegalArgumentException("Negative buffer size");
+
+        lock = mBuffer = new StringBuilder();
+    }
+
+    @Override
+    public void write(int c) {
+        mBuffer.append((char) c);
+    }
+
+    @Override
+    public void write(char[] cs) throws IOException {
+        mBuffer.append(cs, 0, cs.length);
+    }
+
+    @Override
+    public void write(char[] cs, int off, int len) throws IOException {
+        if ((off < 0) || (off > cs.length) || (len < 0) ||
+                ((off + len) > cs.length) || ((off + len) < 0))
+            throw new IndexOutOfBoundsException();
+
+        if (len > 0)
+            mBuffer.append(cs, off, len);
+    }
+
+    @Override
+    public void write(String str) {
+        mBuffer.append(str);
+    }
+
+    @Override
+    public void write(String str, int off, int len) {
+        mBuffer.append(str.substring(off, off + len));
+    }
+
+    @Override
+    public Writer append(CharSequence csq) {
+        if (csq == null)
+            write("null");
+        else
+            write(csq.toString());
+        return this;
+    }
+
+    @Override
+    public Writer append(CharSequence csq, int start, int end) {
+        CharSequence cs = (csq == null ? "null" : csq);
+        write(cs.subSequence(start, end).toString());
+        return this;
+    }
+
+    @Override
+    public Writer append(char c) {
+        mBuffer.append(c);
+        return this;
+    }
+
+    @Override
+    public void close() {
+    }
+
+    @Override
+    public void flush() {
+    }
+
+    @Override
+    public String toString() {
+        return mBuffer.toString();
+    }
 }
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/json/GenericJSONConverter.java b/dubbo-common/src/main/java/org/apache/dubbo/common/json/GenericJSONConverter.java
index f06089f035..b05ed20ff9 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/json/GenericJSONConverter.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/json/GenericJSONConverter.java
@@ -1,485 +1,485 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.json;
-
-import org.apache.dubbo.common.bytecode.Wrapper;
-import org.apache.dubbo.common.io.Bytes;
-
-import java.io.IOException;
-import java.lang.reflect.Array;
-import java.math.BigDecimal;
-import java.math.BigInteger;
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.Collection;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Locale;
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicInteger;
-import java.util.concurrent.atomic.AtomicLong;
-
-@Deprecated
-public class GenericJSONConverter implements JSONConverter {
-    private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss";
-    private static final Map<Class<?>, Encoder> GlobalEncoderMap = new HashMap<Class<?>, Encoder>();
-    private static final Map<Class<?>, Decoder> GlobalDecoderMap = new HashMap<Class<?>, Decoder>();
-
-    static {
-        // init encoder map.
-        Encoder e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueBoolean((Boolean) obj);
-            }
-        };
-        GlobalEncoderMap.put(boolean.class, e);
-        GlobalEncoderMap.put(Boolean.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueInt(((Number) obj).intValue());
-            }
-        };
-        GlobalEncoderMap.put(int.class, e);
-        GlobalEncoderMap.put(Integer.class, e);
-        GlobalEncoderMap.put(short.class, e);
-        GlobalEncoderMap.put(Short.class, e);
-        GlobalEncoderMap.put(byte.class, e);
-        GlobalEncoderMap.put(Byte.class, e);
-        GlobalEncoderMap.put(AtomicInteger.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueString(Character.toString((Character) obj));
-            }
-        };
-        GlobalEncoderMap.put(char.class, e);
-        GlobalEncoderMap.put(Character.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueLong(((Number) obj).longValue());
-            }
-        };
-        GlobalEncoderMap.put(long.class, e);
-        GlobalEncoderMap.put(Long.class, e);
-        GlobalEncoderMap.put(AtomicLong.class, e);
-        GlobalEncoderMap.put(BigInteger.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueFloat(((Number) obj).floatValue());
-            }
-        };
-        GlobalEncoderMap.put(float.class, e);
-        GlobalEncoderMap.put(Float.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueDouble(((Number) obj).doubleValue());
-            }
-        };
-        GlobalEncoderMap.put(double.class, e);
-        GlobalEncoderMap.put(Double.class, e);
-        GlobalEncoderMap.put(BigDecimal.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueString(obj.toString());
-            }
-        };
-        GlobalEncoderMap.put(String.class, e);
-        GlobalEncoderMap.put(StringBuilder.class, e);
-        GlobalEncoderMap.put(StringBuffer.class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueString(Bytes.bytes2base64((byte[]) obj));
-            }
-        };
-        GlobalEncoderMap.put(byte[].class, e);
-
-        e = new Encoder() {
-            @Override
-            public void encode(Object obj, JSONWriter jb) throws IOException {
-                jb.valueString(new SimpleDateFormat(DATE_FORMAT).format((Date) obj));
-            }
-        };
-        GlobalEncoderMap.put(Date.class, e);
-
-        // init decoder map.
-        Decoder d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                return jv.toString();
-            }
-        };
-        GlobalDecoderMap.put(String.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Boolean) return ((Boolean) jv).booleanValue();
-                return false;
-            }
-        };
-        GlobalDecoderMap.put(boolean.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Boolean) return (Boolean) jv;
-                return (Boolean) null;
-            }
-        };
-        GlobalDecoderMap.put(Boolean.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof String && ((String) jv).length() > 0) return ((String) jv).charAt(0);
-                return (char) 0;
-            }
-        };
-        GlobalDecoderMap.put(char.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof String && ((String) jv).length() > 0) return ((String) jv).charAt(0);
-                return (Character) null;
-            }
-        };
-        GlobalDecoderMap.put(Character.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).intValue();
-                return 0;
-            }
-        };
-        GlobalDecoderMap.put(int.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return Integer.valueOf(((Number) jv).intValue());
-                return (Integer) null;
-            }
-        };
-        GlobalDecoderMap.put(Integer.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).shortValue();
-                return (short) 0;
-            }
-        };
-        GlobalDecoderMap.put(short.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return Short.valueOf(((Number) jv).shortValue());
-                return (Short) null;
-            }
-        };
-        GlobalDecoderMap.put(Short.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).longValue();
-                return (long) 0;
-            }
-        };
-        GlobalDecoderMap.put(long.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return Long.valueOf(((Number) jv).longValue());
-                return (Long) null;
-            }
-        };
-        GlobalDecoderMap.put(Long.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).floatValue();
-                return (float) 0;
-            }
-        };
-        GlobalDecoderMap.put(float.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return new Float(((Number) jv).floatValue());
-                return (Float) null;
-            }
-        };
-        GlobalDecoderMap.put(Float.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).doubleValue();
-                return (double) 0;
-            }
-        };
-        GlobalDecoderMap.put(double.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return new Double(((Number) jv).doubleValue());
-                return (Double) null;
-            }
-        };
-        GlobalDecoderMap.put(Double.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return ((Number) jv).byteValue();
-                return (byte) 0;
-            }
-        };
-        GlobalDecoderMap.put(byte.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) {
-                if (jv instanceof Number) return Byte.valueOf(((Number) jv).byteValue());
-                return (Byte) null;
-            }
-        };
-        GlobalDecoderMap.put(Byte.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof String) return Bytes.base642bytes((String) jv);
-                return (byte[]) null;
-            }
-        };
-        GlobalDecoderMap.put(byte[].class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                return new StringBuilder(jv.toString());
-            }
-        };
-        GlobalDecoderMap.put(StringBuilder.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                return new StringBuffer(jv.toString());
-            }
-        };
-        GlobalDecoderMap.put(StringBuffer.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof Number) return BigInteger.valueOf(((Number) jv).longValue());
-                return (BigInteger) null;
-            }
-        };
-        GlobalDecoderMap.put(BigInteger.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof Number) return BigDecimal.valueOf(((Number) jv).doubleValue());
-                return (BigDecimal) null;
-            }
-        };
-        GlobalDecoderMap.put(BigDecimal.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof Number) return new AtomicInteger(((Number) jv).intValue());
-                return (AtomicInteger) null;
-            }
-        };
-        GlobalDecoderMap.put(AtomicInteger.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof Number) return new AtomicLong(((Number) jv).longValue());
-                return (AtomicLong) null;
-            }
-        };
-        GlobalDecoderMap.put(AtomicLong.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof String) {
-                    try {
-                        return new SimpleDateFormat(DATE_FORMAT).parse((String) jv);
-                    } catch (ParseException e) {
-                        throw new IllegalArgumentException(e.getMessage(), e);
-                    }
-                }
-                if (jv instanceof Number)
-                    return new Date(((Number) jv).longValue());
-                return (Date) null;
-            }
-        };
-        GlobalDecoderMap.put(Date.class, d);
-
-        d = new Decoder() {
-            @Override
-            public Object decode(Object jv) throws IOException {
-                if (jv instanceof String) {
-                    String[] items = ((String)jv).split("_");
-                    if(items.length == 1){
-                        return new Locale(items[0]);
-                    }
-                    if(items.length == 2){
-                        return new Locale(items[0], items[1]);
-                    }
-                    return new Locale(items[0], items[1], items[2]);
-                }
-                return (Locale)null;
-            }
-        };
-        GlobalDecoderMap.put(Locale.class, d);
-    }
-
-    @Override
-    @SuppressWarnings("unchecked")
-    public void writeValue(Object obj, JSONWriter jb, boolean writeClass) throws IOException {
-        if (obj == null) {
-            jb.valueNull();
-            return;
-        }
-        Class<?> c = obj.getClass();
-        Encoder encoder = GlobalEncoderMap.get(c);
-
-        if (encoder != null) {
-            encoder.encode(obj, jb);
-        } else if (obj instanceof JSONNode) {
-            ((JSONNode) obj).writeJSON(this, jb, writeClass);
-        } else if (c.isEnum()) {
-            jb.valueString(((Enum<?>) obj).name());
-        } else if (c.isArray()) {
-            int len = Array.getLength(obj);
-            jb.arrayBegin();
-            for (int i = 0; i < len; i++)
-                writeValue(Array.get(obj, i), jb, writeClass);
-            jb.arrayEnd();
-        } else if (Map.class.isAssignableFrom(c)) {
-            Object key, value;
-            jb.objectBegin();
-            for (Map.Entry<Object, Object> entry : ((Map<Object, Object>) obj).entrySet()) {
-                key = entry.getKey();
-                if (key == null)
-                    continue;
-                jb.objectItem(key.toString());
-
-                value = entry.getValue();
-                if (value == null)
-                    jb.valueNull();
-                else
-                    writeValue(value, jb, writeClass);
-            }
-            jb.objectEnd();
-        } else if (Collection.class.isAssignableFrom(c)) {
-            jb.arrayBegin();
-            for (Object item : (Collection<Object>) obj) {
-                if (item == null)
-                    jb.valueNull();
-                else
-                    writeValue(item, jb, writeClass);
-            }
-            jb.arrayEnd();
-        } else if(obj instanceof Locale) {
-            jb.valueString(obj.toString());
-        } else {
-            jb.objectBegin();
-
-            Wrapper w = Wrapper.getWrapper(c);
-            String pns[] = w.getPropertyNames();
-
-            for (String pn : pns) {
-                if ((obj instanceof Throwable) && (
-                        "localizedMessage".equals(pn)
-                                || "cause".equals(pn)
-                                || "suppressed".equals(pn)
-                                || "stackTrace".equals(pn))) {
-                    continue;
-                }
-
-                jb.objectItem(pn);
-
-                Object value = w.getPropertyValue(obj, pn);
-                if (value == null || value == obj)
-                    jb.valueNull();
-                else
-                    writeValue(value, jb, writeClass);
-            }
-            if (writeClass) {
-                jb.objectItem(JSONVisitor.CLASS_PROPERTY);
-                writeValue(obj.getClass().getName(), jb, writeClass);
-            }
-            jb.objectEnd();
-        }
-    }
-
-    @Override
-    @SuppressWarnings({"unchecked", "rawtypes"})
-    public Object readValue(Class<?> c, Object jv) throws IOException {
-        if (jv == null) {
-            return null;
-        }
-        Decoder decoder = GlobalDecoderMap.get(c);
-        if (decoder != null) {
-            return decoder.decode(jv);
-        }
-        if (c.isEnum()) {
-            return Enum.valueOf((Class<Enum>) c, String.valueOf(jv));
-        }
-        return jv;
-    }
-
-    protected interface Encoder {
-        void encode(Object obj, JSONWriter jb) throws IOException;
-    }
-
-    protected interface Decoder {
-        Object decode(Object jv) throws IOException;
-    }
-}
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.json;
+
+import org.apache.dubbo.common.bytecode.Wrapper;
+import org.apache.dubbo.common.io.Bytes;
+
+import java.io.IOException;
+import java.lang.reflect.Array;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Collection;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicInteger;
+import java.util.concurrent.atomic.AtomicLong;
+
+@Deprecated
+public class GenericJSONConverter implements JSONConverter {
+    private static final String DATE_FORMAT = "yyyy-MM-dd HH:mm:ss";
+    private static final Map<Class<?>, Encoder> GlobalEncoderMap = new HashMap<Class<?>, Encoder>();
+    private static final Map<Class<?>, Decoder> GlobalDecoderMap = new HashMap<Class<?>, Decoder>();
+
+    static {
+        // init encoder map.
+        Encoder e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueBoolean((Boolean) obj);
+            }
+        };
+        GlobalEncoderMap.put(boolean.class, e);
+        GlobalEncoderMap.put(Boolean.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueInt(((Number) obj).intValue());
+            }
+        };
+        GlobalEncoderMap.put(int.class, e);
+        GlobalEncoderMap.put(Integer.class, e);
+        GlobalEncoderMap.put(short.class, e);
+        GlobalEncoderMap.put(Short.class, e);
+        GlobalEncoderMap.put(byte.class, e);
+        GlobalEncoderMap.put(Byte.class, e);
+        GlobalEncoderMap.put(AtomicInteger.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueString(Character.toString((Character) obj));
+            }
+        };
+        GlobalEncoderMap.put(char.class, e);
+        GlobalEncoderMap.put(Character.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueLong(((Number) obj).longValue());
+            }
+        };
+        GlobalEncoderMap.put(long.class, e);
+        GlobalEncoderMap.put(Long.class, e);
+        GlobalEncoderMap.put(AtomicLong.class, e);
+        GlobalEncoderMap.put(BigInteger.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueFloat(((Number) obj).floatValue());
+            }
+        };
+        GlobalEncoderMap.put(float.class, e);
+        GlobalEncoderMap.put(Float.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueDouble(((Number) obj).doubleValue());
+            }
+        };
+        GlobalEncoderMap.put(double.class, e);
+        GlobalEncoderMap.put(Double.class, e);
+        GlobalEncoderMap.put(BigDecimal.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueString(obj.toString());
+            }
+        };
+        GlobalEncoderMap.put(String.class, e);
+        GlobalEncoderMap.put(StringBuilder.class, e);
+        GlobalEncoderMap.put(StringBuffer.class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueString(Bytes.bytes2base64((byte[]) obj));
+            }
+        };
+        GlobalEncoderMap.put(byte[].class, e);
+
+        e = new Encoder() {
+            @Override
+            public void encode(Object obj, JSONWriter jb) throws IOException {
+                jb.valueString(new SimpleDateFormat(DATE_FORMAT).format((Date) obj));
+            }
+        };
+        GlobalEncoderMap.put(Date.class, e);
+
+        // init decoder map.
+        Decoder d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                return jv.toString();
+            }
+        };
+        GlobalDecoderMap.put(String.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Boolean) return ((Boolean) jv).booleanValue();
+                return false;
+            }
+        };
+        GlobalDecoderMap.put(boolean.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Boolean) return (Boolean) jv;
+                return (Boolean) null;
+            }
+        };
+        GlobalDecoderMap.put(Boolean.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof String && ((String) jv).length() > 0) return ((String) jv).charAt(0);
+                return (char) 0;
+            }
+        };
+        GlobalDecoderMap.put(char.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof String && ((String) jv).length() > 0) return ((String) jv).charAt(0);
+                return (Character) null;
+            }
+        };
+        GlobalDecoderMap.put(Character.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).intValue();
+                return 0;
+            }
+        };
+        GlobalDecoderMap.put(int.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return Integer.valueOf(((Number) jv).intValue());
+                return (Integer) null;
+            }
+        };
+        GlobalDecoderMap.put(Integer.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).shortValue();
+                return (short) 0;
+            }
+        };
+        GlobalDecoderMap.put(short.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return Short.valueOf(((Number) jv).shortValue());
+                return (Short) null;
+            }
+        };
+        GlobalDecoderMap.put(Short.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).longValue();
+                return (long) 0;
+            }
+        };
+        GlobalDecoderMap.put(long.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return Long.valueOf(((Number) jv).longValue());
+                return (Long) null;
+            }
+        };
+        GlobalDecoderMap.put(Long.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).floatValue();
+                return (float) 0;
+            }
+        };
+        GlobalDecoderMap.put(float.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return new Float(((Number) jv).floatValue());
+                return (Float) null;
+            }
+        };
+        GlobalDecoderMap.put(Float.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).doubleValue();
+                return (double) 0;
+            }
+        };
+        GlobalDecoderMap.put(double.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return new Double(((Number) jv).doubleValue());
+                return (Double) null;
+            }
+        };
+        GlobalDecoderMap.put(Double.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return ((Number) jv).byteValue();
+                return (byte) 0;
+            }
+        };
+        GlobalDecoderMap.put(byte.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) {
+                if (jv instanceof Number) return Byte.valueOf(((Number) jv).byteValue());
+                return (Byte) null;
+            }
+        };
+        GlobalDecoderMap.put(Byte.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof String) return Bytes.base642bytes((String) jv);
+                return (byte[]) null;
+            }
+        };
+        GlobalDecoderMap.put(byte[].class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                return new StringBuilder(jv.toString());
+            }
+        };
+        GlobalDecoderMap.put(StringBuilder.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                return new StringBuffer(jv.toString());
+            }
+        };
+        GlobalDecoderMap.put(StringBuffer.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof Number) return BigInteger.valueOf(((Number) jv).longValue());
+                return (BigInteger) null;
+            }
+        };
+        GlobalDecoderMap.put(BigInteger.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof Number) return BigDecimal.valueOf(((Number) jv).doubleValue());
+                return (BigDecimal) null;
+            }
+        };
+        GlobalDecoderMap.put(BigDecimal.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof Number) return new AtomicInteger(((Number) jv).intValue());
+                return (AtomicInteger) null;
+            }
+        };
+        GlobalDecoderMap.put(AtomicInteger.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof Number) return new AtomicLong(((Number) jv).longValue());
+                return (AtomicLong) null;
+            }
+        };
+        GlobalDecoderMap.put(AtomicLong.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof String) {
+                    try {
+                        return new SimpleDateFormat(DATE_FORMAT).parse((String) jv);
+                    } catch (ParseException e) {
+                        throw new IllegalArgumentException(e.getMessage(), e);
+                    }
+                }
+                if (jv instanceof Number)
+                    return new Date(((Number) jv).longValue());
+                return (Date) null;
+            }
+        };
+        GlobalDecoderMap.put(Date.class, d);
+
+        d = new Decoder() {
+            @Override
+            public Object decode(Object jv) throws IOException {
+                if (jv instanceof String) {
+                    String[] items = ((String)jv).split("_");
+                    if(items.length == 1){
+                        return new Locale(items[0]);
+                    }
+                    if(items.length == 2){
+                        return new Locale(items[0], items[1]);
+                    }
+                    return new Locale(items[0], items[1], items[2]);
+                }
+                return (Locale)null;
+            }
+        };
+        GlobalDecoderMap.put(Locale.class, d);
+    }
+
+    @Override
+    @SuppressWarnings("unchecked")
+    public void writeValue(Object obj, JSONWriter jb, boolean writeClass) throws IOException {
+        if (obj == null) {
+            jb.valueNull();
+            return;
+        }
+        Class<?> c = obj.getClass();
+        Encoder encoder = GlobalEncoderMap.get(c);
+
+        if (encoder != null) {
+            encoder.encode(obj, jb);
+        } else if (obj instanceof JSONNode) {
+            ((JSONNode) obj).writeJSON(this, jb, writeClass);
+        } else if (c.isEnum()) {
+            jb.valueString(((Enum<?>) obj).name());
+        } else if (c.isArray()) {
+            int len = Array.getLength(obj);
+            jb.arrayBegin();
+            for (int i = 0; i < len; i++)
+                writeValue(Array.get(obj, i), jb, writeClass);
+            jb.arrayEnd();
+        } else if (Map.class.isAssignableFrom(c)) {
+            Object key, value;
+            jb.objectBegin();
+            for (Map.Entry<Object, Object> entry : ((Map<Object, Object>) obj).entrySet()) {
+                key = entry.getKey();
+                if (key == null)
+                    continue;
+                jb.objectItem(key.toString());
+
+                value = entry.getValue();
+                if (value == null)
+                    jb.valueNull();
+                else
+                    writeValue(value, jb, writeClass);
+            }
+            jb.objectEnd();
+        } else if (Collection.class.isAssignableFrom(c)) {
+            jb.arrayBegin();
+            for (Object item : (Collection<Object>) obj) {
+                if (item == null)
+                    jb.valueNull();
+                else
+                    writeValue(item, jb, writeClass);
+            }
+            jb.arrayEnd();
+        } else if(obj instanceof Locale) {
+            jb.valueString(obj.toString());
+        } else {
+            jb.objectBegin();
+
+            Wrapper w = Wrapper.getWrapper(c);
+            String pns[] = w.getPropertyNames();
+
+            for (String pn : pns) {
+                if ((obj instanceof Throwable) && (
+                        "localizedMessage".equals(pn)
+                                || "cause".equals(pn)
+                                || "suppressed".equals(pn)
+                                || "stackTrace".equals(pn))) {
+                    continue;
+                }
+
+                jb.objectItem(pn);
+
+                Object value = w.getPropertyValue(obj, pn);
+                if (value == null || value == obj)
+                    jb.valueNull();
+                else
+                    writeValue(value, jb, writeClass);
+            }
+            if (writeClass) {
+                jb.objectItem(JSONVisitor.CLASS_PROPERTY);
+                writeValue(obj.getClass().getName(), jb, writeClass);
+            }
+            jb.objectEnd();
+        }
+    }
+
+    @Override
+    @SuppressWarnings({"unchecked", "rawtypes"})
+    public Object readValue(Class<?> c, Object jv) throws IOException {
+        if (jv == null) {
+            return null;
+        }
+        Decoder decoder = GlobalDecoderMap.get(c);
+        if (decoder != null) {
+            return decoder.decode(jv);
+        }
+        if (c.isEnum()) {
+            return Enum.valueOf((Class<Enum>) c, String.valueOf(jv));
+        }
+        return jv;
+    }
+
+    protected interface Encoder {
+        void encode(Object obj, JSONWriter jb) throws IOException;
+    }
+
+    protected interface Decoder {
+        Object decode(Object jv) throws IOException;
+    }
+}
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONConverter.java b/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONConverter.java
index e9fe94c03e..9d45114332 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONConverter.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONConverter.java
@@ -1,44 +1,44 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.json;
-
-import java.io.IOException;
-
-/**
- * JSON converter.
- */
-@Deprecated
-public interface JSONConverter {
-    /**
-     * write object.
-     *
-     * @param obj     obj.
-     * @param builder builder.
-     * @throws IOException
-     */
-    void writeValue(Object obj, JSONWriter builder, boolean writeClass) throws IOException;
-
-    /**
-     * convert json value to target class.
-     *
-     * @param type target type.
-     * @param jv   json value.
-     * @return target object.
-     * @throws IOException
-     */
-    Object readValue(Class<?> type, Object jv) throws IOException;
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.json;
+
+import java.io.IOException;
+
+/**
+ * JSON converter.
+ */
+@Deprecated
+public interface JSONConverter {
+    /**
+     * write object.
+     *
+     * @param obj     obj.
+     * @param builder builder.
+     * @throws IOException
+     */
+    void writeValue(Object obj, JSONWriter builder, boolean writeClass) throws IOException;
+
+    /**
+     * convert json value to target class.
+     *
+     * @param type target type.
+     * @param jv   json value.
+     * @return target object.
+     * @throws IOException
+     */
+    Object readValue(Class<?> type, Object jv) throws IOException;
 }
\ No newline at end of file
diff --git a/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONReader.java b/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONReader.java
index 2fbf4f6df2..85a85c32b7 100644
--- a/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONReader.java
+++ b/dubbo-common/src/main/java/org/apache/dubbo/common/json/JSONReader.java
@@ -1,66 +1,66 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements.  See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.dubbo.common.json;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.Reader;
-import java.io.UnsupportedEncodingException;
-
-/**
- * JSON reader.
- */
-@Deprecated
-public class JSONReader {
-    private static ThreadLocal<Yylex> LOCAL_LEXER = new ThreadLocal<Yylex>() {
-    };
-
-    private Yylex mLex;
-
-    public JSONReader(InputStream is, String charset) throws UnsupportedEncodingException {
-        this(new InputStreamReader(is, charset));
-    }
-
-    public JSONReader(Reader reader) {
-        mLex = getLexer(reader);
-    }
-
-    private static Yylex getLexer(Reader reader) {
-        Yylex ret = LOCAL_LEXER.get();
-        if (ret == null) {
-            ret = new Yylex(reader);
-            LOCAL_LEXER.set(ret);
-        } else {
-            ret.yyreset(reader);
-        }
-        return ret;
-    }
-
-    public JSONToken nextToken() throws IOException, ParseException {
-        return mLex.yylex();
-    }
-
-    public JSONToken nextToken(int expect) throws IOException, ParseException {
-        JSONToken ret = mLex.yylex();
-        if (ret == null)
-            throw new ParseException("EOF error.");
-        if (expect != JSONToken.ANY && expect != ret.type)
-            throw new ParseException("Unexpected token.");
-        return ret;
-    }
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.dubbo.common.json;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.io.UnsupportedEncodingException;
+
+/**
+ * JSON reader.
+ */
+@Deprecated
+public class JSONReader {
+    private static ThreadLocal<Yylex> LOCAL_LEXER = new ThreadLocal<Yylex>() {
+    };
+
+    private Yylex mLex;
+
+    public JSONReader(InputStream is, String charset) throws UnsupportedEncodingException {
+        this(new InputStreamReader(is, charset));
+    }
+
+    public JSONReader(Reader reader) {
+        mLex = getLexer(reader);
+    }
+
+    private static Yylex getLexer(Reader reader) {
+        Yylex ret = LOCAL_LEXER.get();
+        if (ret == null) {
+            ret = new Yylex(reader);
+            LOCAL_LEXER.set(ret);
+        } else {

  (This diff was longer than 20,000 lines, and has been truncated...)


 

----------------------------------------------------------------
This is an automated message from the Apache Git Service.
To respond to the message, please log on GitHub and use the
URL above to go to the specific comment.
 
For queries about this service, please contact Infrastructure at:
users@infra.apache.org


With regards,
Apache Git Services

---------------------------------------------------------------------
To unsubscribe, e-mail: notifications-unsubscribe@dubbo.apache.org
For additional commands, e-mail: notifications-help@dubbo.apache.org